#define MAX_FILE_SIZE (10 * 1024 * 1024) // 10MB
void exif_edit_file (const char *path)
{
FILE *f = fopen(path, "rb");
if (!f) {
TL_LOG_DEBUG("%s,错误:无法打开文件 %s", __func__, path);
return;
}
fseek(f, 0, SEEK_END);
long file_size = ftell(f);
fseek(f, 0, SEEK_SET);
if (file_size <= 0 || file_size > MAX_FILE_SIZE) {
TL_LOG_DEBUG("%s,错误:文件大小无效 %ld", __func__, file_size);
fclose(f);
return;
}
unsigned char *file_data = (unsigned char *)tl_hal_mem_psram_malloc(file_size);
if (!file_data) {
TL_LOG_DEBUG("%s,错误:内存分配失败", __func__);
fclose(f);
return;
}
if (fread(file_data, 1, file_size, f) != (size_t)file_size) {
TL_LOG_DEBUG("%s,错误:读取文件失败", __func__);
free(file_data);
fclose(f);
return;
}
fclose(f);
ExifData *exif = exif_data_new_from_file(path);
if (!exif)
{
TL_LOG_DEBUG("%s,错误:无法读取EXIF数据 %s",__func__,path);
}
ExifEntry *date_entry = exif_content_get_entry(
exif->ifd[EXIF_IFD_EXIF],
EXIF_TAG_DATE_TIME_ORIGINAL
);
if (!date_entry) {
date_entry = exif_entry_new();
exif_content_add_entry(exif->ifd[EXIF_IFD_EXIF], date_entry);
exif_entry_initialize(date_entry, EXIF_TAG_DATE_TIME_ORIGINAL);
}
char datetime[20] = "2024:01:01 12:00:00";
size_t len = strlen(datetime) + 1;
date_entry->format = EXIF_FORMAT_ASCII;
date_entry->components = len;
date_entry->data = (unsigned char*) malloc(date_entry->size);
if (date_entry->data) {
strcpy((char*)date_entry->data, datetime);
} else {
}
unsigned char *exif_buffer;
unsigned int exif_size;
exif_data_save_data(exif, &exif_buffer, &exif_size);
DUMP8("%02X ", exif_buffer, exif_size);
// 4. 查找并替换原始文件中的EXIF段
unsigned char *new_file_data = NULL;
long new_file_size = 0;
// JPEG文件以FF D8开头,查找第一个FF E1 (APP1段,即EXIF段)
if (file_size >= 4 && file_data[0] == 0xFF && file_data[1] == 0xD8) {
int found_exif = 0;
long offset = 2; // 从SOI标记后开始
while (offset < file_size - 3) {
// 查找下一个标记
if (file_data[offset] == 0xFF && file_data[offset + 1] >= 0xE0 && file_data[offset + 1] <= 0xEF) {
// 找到APP段
unsigned short segment_size = (file_data[offset + 2] << 8) | file_data[offset + 3];
if (file_data[offset + 1] == 0xE1) {
// 找到EXIF段
found_exif = 1;
// 计算新文件大小:原始大小 - 旧EXIF段大小 + 新EXIF段大小
new_file_size = file_size - (segment_size + 2) + (exif_size + 2);
new_file_data = (unsigned char *)tl_hal_mem_psram_malloc(new_file_size);
if (!new_file_data) {
TL_LOG_DEBUG("%s,错误:内存分配失败", __func__);
break;
}
// 复制文件头(SOI标记)
memcpy(new_file_data, file_data, offset);
// 写入新的EXIF段
// 标记 (FF E1)
new_file_data[offset] = 0xFF;
new_file_data[offset + 1] = 0xE1;
// 段大小 (包含大小字段本身的两个字节)
unsigned short new_exif_size = exif_size + 2;
new_file_data[offset + 2] = (new_exif_size >> 8) & 0xFF;
new_file_data[offset + 3] = new_exif_size & 0xFF;
// 写入EXIF数据
memcpy(new_file_data + offset + 4, exif_buffer, exif_size);
// 复制剩余数据(跳过旧的EXIF段)
memcpy(new_file_data + offset + 4 + exif_size,
file_data + offset + 2 + segment_size,
file_size - (offset + 2 + segment_size));
break;
} else {
// 不是EXIF段,跳过
offset += 2 + segment_size;
}
} else {
// 不是标记,继续查找
offset++;
}
}
if (!found_exif) {
// 如果没有找到EXIF段,在文件头后插入新的EXIF段
new_file_size = file_size + exif_size + 4; // +4 是标记和大小字段
new_file_data = (unsigned char *)tl_hal_mem_psram_malloc(new_file_size);
if (!new_file_data) {
TL_LOG_DEBUG("%s,错误:内存分配失败", __func__);
} else {
// 复制SOI标记
memcpy(new_file_data, file_data, 2);
// 写入新的EXIF段
new_file_data[2] = 0xFF;
new_file_data[3] = 0xE1;
unsigned short new_exif_size = exif_size + 2;
new_file_data[4] = (new_exif_size >> 8) & 0xFF;
new_file_data[5] = new_exif_size & 0xFF;
memcpy(new_file_data + 6, exif_buffer, exif_size);
// 复制剩余数据
memcpy(new_file_data + 6 + exif_size, file_data + 2, file_size - 2);
}
}
}
// 5. 保存新文件
if (new_file_data && new_file_size > 0) {
f = fopen("/data/emmc2/media/photo_9999999_0.jpeg", "wb");
if (f) {
if (fwrite(new_file_data, 1, new_file_size, f) == (size_t)new_file_size) {
printf("EXIF数据编辑成功!保存至:/data/emmc2/media/photo_88888888_0.jpeg\n");
} else {
TL_LOG_DEBUG("%s,错误:写入文件失败", __func__);
}
fclose(f);
} else {
TL_LOG_DEBUG("%s,错误:无法创建输出文件", __func__);
}
tl_hal_mem_psram_free(new_file_data);
} else {
TL_LOG_DEBUG("%s,错误:无法生成新文件", __func__);
}
// 6. 清理资源
free(exif_buffer);
exif_data_unref(exif);
tl_hal_mem_psram_free(file_data);
printf("EXIF数据编辑成功!保存至:/data/emmc2/media/photo_88888888_0.jpeg\n");
}分析这段代码可能有什么问题
最新发布