postprocess.c 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483
  1. #include <assert.h>
  2. #include <string.h>
  3. #include <dirent.h>
  4. #include <libraw/libraw.h>
  5. #include <tiffio.h>
  6. #include <jpeglib.h>
  7. #include <libexif/exif-data.h>
  8. #include <time.h>
  9. #include <unistd.h>
  10. #include "postprocess.h"
  11. #include "stacker.h"
  12. static void
  13. register_custom_tiff_tags(TIFF *tif)
  14. {
  15. static const TIFFFieldInfo custom_fields[] = {
  16. {TIFFTAG_FORWARDMATRIX1, -1, -1, TIFF_SRATIONAL, FIELD_CUSTOM, 1, 1,
  17. "ForwardMatrix1"},
  18. };
  19. // Add missing dng fields
  20. TIFFMergeFieldInfo(tif, custom_fields,
  21. sizeof(custom_fields) / sizeof(custom_fields[0]));
  22. }
  23. libraw_processed_image_t *
  24. debayer_file(char *filename)
  25. {
  26. libraw_data_t *raw;
  27. int ret;
  28. raw = libraw_init(0);
  29. if (libraw_open_file(raw, filename) != LIBRAW_SUCCESS) {
  30. err("could not open file");
  31. libraw_close(raw);
  32. }
  33. if (libraw_unpack(raw) != LIBRAW_SUCCESS) {
  34. err("could not unpack file");
  35. libraw_close(raw);
  36. }
  37. raw->params.no_auto_bright = 1;
  38. if (libraw_dcraw_process(raw) != LIBRAW_SUCCESS) {
  39. err("could not process file");
  40. libraw_free_image(raw);
  41. libraw_close(raw);
  42. }
  43. libraw_processed_image_t *proc_img = libraw_dcraw_make_mem_image(raw, &ret);
  44. libraw_free_image(raw);
  45. if (!proc_img) {
  46. err("could not export image");
  47. libraw_close(raw);
  48. }
  49. libraw_recycle(raw);
  50. libraw_close(raw);
  51. return proc_img;
  52. }
  53. void
  54. save_jpeg(char *path, libraw_processed_image_t *data, int quality, ExifData *exif)
  55. {
  56. unsigned char *exif_data;
  57. unsigned int exif_len;
  58. FILE *out = fopen(path, "wb");
  59. if (!out) {
  60. err("could not open target file");
  61. exit(1);
  62. }
  63. struct jpeg_compress_struct jpeg;
  64. struct jpeg_error_mgr error_mgr;
  65. jpeg.err = jpeg_std_error(&error_mgr);
  66. jpeg_create_compress(&jpeg);
  67. jpeg_stdio_dest(&jpeg, out);
  68. jpeg.image_width = data->width;
  69. jpeg.image_height = data->height;
  70. jpeg.input_components = 3;
  71. jpeg.in_color_space = JCS_RGB;
  72. jpeg_set_defaults(&jpeg);
  73. jpeg_set_quality(&jpeg, quality, 1);
  74. jpeg_start_compress(&jpeg, 1);
  75. // Write exif
  76. exif_data_save_data(exif, &exif_data, &exif_len);
  77. jpeg_write_marker(&jpeg, JPEG_APP1, exif_data, exif_len);
  78. // Write image data
  79. JSAMPROW row_pointer;
  80. int row_stride = jpeg.image_width * jpeg.input_components;
  81. while (jpeg.next_scanline < jpeg.image_height) {
  82. row_pointer = (JSAMPROW) &data->data[jpeg.next_scanline * row_stride];
  83. jpeg_write_scanlines(&jpeg, &row_pointer, 1);
  84. }
  85. jpeg_finish_compress(&jpeg);
  86. jpeg_destroy_compress(&jpeg);
  87. fclose(out);
  88. }
  89. static ExifEntry *
  90. init_tag(ExifData *exif, ExifIfd ifd, ExifTag tag)
  91. {
  92. ExifEntry *entry;
  93. /* Return an existing tag if one exists */
  94. if (!((entry = exif_content_get_entry(exif->ifd[ifd], tag)))) {
  95. /* Allocate a new entry */
  96. entry = exif_entry_new();
  97. assert(entry != NULL); /* catch an out of memory condition */
  98. entry->tag = tag; /* tag must be set before calling
  99. exif_content_add_entry */
  100. /* Attach the ExifEntry to an IFD */
  101. exif_content_add_entry(exif->ifd[ifd], entry);
  102. /* Allocate memory for the entry and fill with default data */
  103. exif_entry_initialize(entry, tag);
  104. /* Ownership of the ExifEntry has now been passed to the IFD.
  105. * One must be very careful in accessing a structure after
  106. * unref'ing it; in this case, we know "entry" won't be freed
  107. * because the reference count was bumped when it was added to
  108. * the IFD.
  109. */
  110. exif_entry_unref(entry);
  111. }
  112. return entry;
  113. }
  114. void
  115. exif_set_string(ExifEntry *ed, const char *s, size_t size)
  116. {
  117. if (ed->data) {
  118. free(ed->data);
  119. }
  120. ed->components = size + 1;
  121. ed->size = sizeof(char) * ed->components;
  122. ed->data = (unsigned char *) malloc(ed->size);
  123. if (!ed->data) {
  124. err("Could not allocate exif string");
  125. exit(1);
  126. }
  127. strncpy((char *) ed->data, (char *) s, size);
  128. exif_entry_fix(ed);
  129. }
  130. ExifData *
  131. create_exif(struct Imagedata data)
  132. {
  133. ExifEntry *entry;
  134. ExifRational rational;
  135. long denominator = 100000;
  136. ExifData *exif = exif_data_new();
  137. if (!exif) {
  138. err("Could not initialize libexif");
  139. }
  140. exif_data_set_option(exif, EXIF_DATA_OPTION_FOLLOW_SPECIFICATION);
  141. exif_data_set_data_type(exif, EXIF_DATA_TYPE_COMPRESSED);
  142. exif_data_set_byte_order(exif, EXIF_BYTE_ORDER_INTEL);
  143. exif_data_fix(exif);
  144. // Width
  145. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_PIXEL_X_DIMENSION);
  146. exif_set_long(entry->data, EXIF_BYTE_ORDER_INTEL, data.width);
  147. // Height
  148. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_PIXEL_Y_DIMENSION);
  149. exif_set_long(entry->data, EXIF_BYTE_ORDER_INTEL, data.height);
  150. // Colorspace, 1=sRGB
  151. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_COLOR_SPACE);
  152. exif_set_long(entry->data, EXIF_BYTE_ORDER_INTEL, 1);
  153. // Exposure program, enum
  154. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_EXPOSURE_PROGRAM);
  155. exif_set_long(entry->data, EXIF_BYTE_ORDER_INTEL, data.exposure_program);
  156. // Camera make
  157. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_MAKE);
  158. exif_set_string(entry, data.make, strlen(data.make));
  159. // Camera model
  160. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_MODEL);
  161. exif_set_string(entry, data.model, strlen(data.model));
  162. // Processing software
  163. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_SOFTWARE);
  164. exif_set_string(entry, data.software, strlen(data.software));
  165. // Various datetime fields
  166. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_DATE_TIME);
  167. exif_set_string(entry, data.datetime, strlen(data.datetime));
  168. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_DATE_TIME_DIGITIZED);
  169. exif_set_string(entry, data.datetime, strlen(data.datetime));
  170. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_DATE_TIME_ORIGINAL);
  171. exif_set_string(entry, data.datetime, strlen(data.datetime));
  172. // Exposure time
  173. rational.numerator = (long) ((double) data.exposure_time * denominator);
  174. rational.denominator = denominator;
  175. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_EXPOSURE_TIME);
  176. exif_set_rational(entry->data, EXIF_BYTE_ORDER_INTEL, rational);
  177. // fnumber
  178. rational.numerator = (long) ((double) data.fnumber * denominator);
  179. rational.denominator = denominator;
  180. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_FNUMBER);
  181. exif_set_rational(entry->data, EXIF_BYTE_ORDER_INTEL, rational);
  182. // focal length
  183. rational.numerator = (long) ((double) data.focal_length * denominator);
  184. rational.denominator = denominator;
  185. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_FOCAL_LENGTH);
  186. exif_set_rational(entry->data, EXIF_BYTE_ORDER_INTEL, rational);
  187. // focal length, 35mm equiv
  188. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_FOCAL_LENGTH_IN_35MM_FILM);
  189. exif_set_short(entry->data, EXIF_BYTE_ORDER_INTEL, data.focal_length_35mm);
  190. // ISO
  191. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_ISO_SPEED_RATINGS);
  192. exif_set_long(entry->data, EXIF_BYTE_ORDER_INTEL, data.isospeed);
  193. // Flash
  194. entry = init_tag(exif, EXIF_IFD_EXIF, EXIF_TAG_FLASH);
  195. exif_set_short(entry->data, EXIF_BYTE_ORDER_INTEL, data.flash);
  196. return exif;
  197. }
  198. struct Imagedata
  199. read_exif(char *filename)
  200. {
  201. struct Imagedata imagedata;
  202. uint16_t subifd_count;
  203. uint32_t *subifd_offsets;
  204. uint32_t exif_offset;
  205. uint32_t value_count;
  206. uint16_t *short_array;
  207. char *temp;
  208. TIFF *im = TIFFOpen(filename, "r");
  209. if (im == NULL) {
  210. fprintf(stderr, "Could not open tiff");
  211. exit(1);
  212. }
  213. if (TIFFGetField(im, TIFFTAG_MAKE, &temp) != 1) {
  214. err("failed to read TIFFTAG_MAKE");
  215. }
  216. imagedata.make = strdup(temp);
  217. if (TIFFGetField(im, TIFFTAG_MODEL, &temp) != 1) {
  218. err("failed to read TIFFTAG_MODEL");
  219. }
  220. imagedata.model = strdup(temp);
  221. if (TIFFGetField(im, TIFFTAG_SOFTWARE, &temp) != 1) {
  222. err("failed to read TIFFTAG_SOFTWARE");
  223. }
  224. imagedata.software = strdup(temp);
  225. if (TIFFGetField(im, TIFFTAG_DATETIME, &temp) != 1) {
  226. err("failed to read TIFFTAG_DATETIME");
  227. }
  228. imagedata.datetime = strdup(temp);
  229. if (TIFFGetField(im, TIFFTAG_ORIENTATION, &imagedata.orientation) != 1) {
  230. err("failed to read TIFFTAG_ORIENTATION");
  231. }
  232. // Get the EXIF directory for the rest of the metadata
  233. if (TIFFGetField(im, TIFFTAG_EXIFIFD, &exif_offset) != 1) {
  234. err("failed to read TIFFTAG_EXIFIFD");
  235. }
  236. // Read the actual picture instead of the embedded thumbnail
  237. if (TIFFGetField(im, TIFFTAG_SUBIFD, &subifd_count, &subifd_offsets)) {
  238. if (subifd_count > 0) {
  239. TIFFSetSubDirectory(im, subifd_offsets[0]);
  240. }
  241. }
  242. if (TIFFGetField(im, TIFFTAG_IMAGELENGTH, &imagedata.height) != 1) {
  243. err("failed to read TIFFTAG_IMAGELENGTH");
  244. }
  245. if (TIFFGetField(im, TIFFTAG_IMAGEWIDTH, &imagedata.width) != 1) {
  246. err("failed to read TIFFTAG_IMAGEWIDTH");
  247. }
  248. if (TIFFGetField(im, TIFFTAG_BITSPERSAMPLE, &imagedata.bitspersample) != 1) {
  249. err("failed to read TIFFTAG_BITSPERSAMPLE");
  250. }
  251. // Read the exif directory
  252. TIFFReadEXIFDirectory(im, exif_offset);
  253. if (TIFFGetField(im, EXIFTAG_EXPOSUREPROGRAM, &imagedata.exposure_program) != 1) {
  254. err("failed to read EXIFTAG_EXPOSUREPROGRAM");
  255. }
  256. if (TIFFGetField(im, EXIFTAG_EXPOSURETIME, &imagedata.exposure_time) != 1) {
  257. err("failed to read EXIFTAG_EXPOSURETIME");
  258. }
  259. if (TIFFGetField(im, EXIFTAG_PHOTOGRAPHICSENSITIVITY, &value_count, &short_array) != 1) {
  260. err("failed to read EXIFTAG_PHOTOGRAPHICSENSITIVITY");
  261. }else {
  262. imagedata.isospeed = short_array[0];
  263. }
  264. if (TIFFGetField(im, EXIFTAG_FNUMBER, &imagedata.fnumber) != 1) {
  265. err("failed to read EXIFTAG_FNUMBER");
  266. }
  267. if (TIFFGetField(im, EXIFTAG_FOCALLENGTH, &imagedata.focal_length) != 1) {
  268. err("failed to read EXIFTAG_FOCALLENGTH");
  269. }
  270. if (TIFFGetField(im, EXIFTAG_FOCALLENGTHIN35MMFILM, &imagedata.focal_length_35mm) != 1) {
  271. err("failed to read EXIFTAG_FOCALLENGTHIN35MMFILM");
  272. }
  273. if (TIFFGetField(im, EXIFTAG_FLASH, &imagedata.flash) != 1) {
  274. err("failed to read EXIFTAG_FLASH");
  275. }
  276. TIFFClose(im);
  277. return imagedata;
  278. }
  279. static int
  280. filter_dng(const struct dirent *dir)
  281. {
  282. if (!dir)
  283. return 0;
  284. if (dir->d_type == DT_REG) {
  285. const char *ext = strrchr(dir->d_name, '.');
  286. if ((!ext) || (ext == dir->d_name))
  287. return 0;
  288. else {
  289. if (strcmp(ext, ".dng") == 0)
  290. return 1;
  291. }
  292. }
  293. return 0;
  294. }
  295. void
  296. postprocess_setup()
  297. {
  298. TIFFSetTagExtender(register_custom_tiff_tags);
  299. }
  300. void
  301. postprocess_internal(char *burst_dir, char *target_dir, int keep)
  302. {
  303. struct dirent **namelist;
  304. int burst_size;
  305. int first = 1;
  306. struct Imagedata imagedata;
  307. libraw_processed_image_t *decoded;
  308. ExifData *exif;
  309. char path[512];
  310. char outpath[512];
  311. char stackpath[512];
  312. nice(19);
  313. burst_size = scandir(burst_dir, &namelist, filter_dng, alphasort);
  314. if (burst_size < 0) {
  315. printf("oop\n");
  316. exit(1);
  317. }
  318. if (burst_size == 0) {
  319. printf("No DNG files found\n");
  320. exit(1);
  321. }
  322. stacker_t *stacker = stacker_create(1);
  323. while (burst_size--) {
  324. fprintf(stderr, "DEBAYER %s\n", namelist[burst_size]->d_name);
  325. snprintf(path, sizeof(path), "%s/%s", burst_dir, namelist[burst_size]->d_name);
  326. if(keep)
  327. snprintf(outpath, sizeof(outpath), "%s.%d.jpg", target_dir, burst_size);
  328. else
  329. snprintf(outpath, sizeof(outpath), "%s.jpg", target_dir);
  330. if (first) {
  331. imagedata = read_exif(path);
  332. exif = create_exif(imagedata);
  333. }
  334. decoded = debayer_file(path);
  335. if(keep || first) {
  336. fprintf(stderr, "JPEG %s\n", namelist[burst_size]->d_name);
  337. save_jpeg(outpath, decoded, 90, exif);
  338. }
  339. fprintf(stderr, "CONVERG %s\n", namelist[burst_size]->d_name);
  340. stacker_add_image(stacker, decoded->data, decoded->width, decoded->height);
  341. free(namelist[burst_size]);
  342. if (first) {
  343. first = 0;
  344. }
  345. }
  346. free(namelist);
  347. fprintf(stderr, "STACK stacked.jpg\n");
  348. // Convert opencv result to a libraw struct and feed it in the jpeg encoder with the original exif data
  349. char *stacked = stacker_get_result(stacker);
  350. decoded->width = stacker_get_width(stacker);
  351. decoded->height = stacker_get_height(stacker);
  352. int result_size = decoded->width * decoded->height * 3;
  353. libraw_processed_image_t *stacked_data = (libraw_processed_image_t *) malloc(
  354. sizeof(libraw_processed_image_t) + result_size);
  355. memset(stacked_data, 0, sizeof(libraw_processed_image_t));
  356. stacked_data->colors = 3;
  357. stacked_data->width = decoded->width;
  358. stacked_data->height = decoded->height;
  359. memmove(stacked_data->data, stacked, result_size);
  360. // Save the final file
  361. fprintf(stderr, "JPEG stacked.jpg\n");
  362. if(keep)
  363. snprintf(stackpath, sizeof(stackpath), "%s.stacked.jpg", target_dir);
  364. else
  365. snprintf(stackpath, sizeof(stackpath), "%s.jpg", target_dir);
  366. save_jpeg(stackpath, stacked_data, 90, exif);
  367. }
  368. void
  369. postprocess_single(char *in_path, char *out_path, int quality, int verbose)
  370. {
  371. libraw_processed_image_t *decoded;
  372. libraw_processed_image_t *processed_data;
  373. struct Imagedata imagedata;
  374. ExifData *exif;
  375. int width, height, result_size;
  376. char *result;
  377. clock_t timer;
  378. stacker_t *stacker = stacker_create(verbose);
  379. // Give the operating system more cpu time
  380. nice(19);
  381. // Parse exif data from original file
  382. timer = clock();
  383. imagedata = read_exif(in_path);
  384. exif = create_exif(imagedata);
  385. if (verbose) {
  386. printf("[%.1fms] %s\n", (float) (clock() - timer) / CLOCKS_PER_SEC * 1000, "exif read");
  387. }
  388. // Convert the sensor data to rgb
  389. timer = clock();
  390. decoded = debayer_file(in_path);
  391. if (verbose) {
  392. printf("[%.1fms] %s\n", (float) (clock() - timer) / CLOCKS_PER_SEC * 1000, "debayer");
  393. }
  394. // Run the opencv postprocessing on the single frame
  395. result = stacker_postprocess(stacker, decoded->data, decoded->width, decoded->height);
  396. width = stacker_get_width(stacker);
  397. height = stacker_get_height(stacker);
  398. // Export the final jpeg with the original exif data
  399. timer = clock();
  400. result_size = width * height * 3;
  401. processed_data = (libraw_processed_image_t *) malloc(sizeof(libraw_processed_image_t) + result_size);
  402. memset(processed_data, 0, sizeof(libraw_processed_image_t));
  403. processed_data->colors = 3;
  404. processed_data->width = decoded->width;
  405. processed_data->height = decoded->height;
  406. memmove(processed_data->data, result, result_size);
  407. save_jpeg(out_path, processed_data, quality, exif);
  408. if (verbose) {
  409. printf("[%.1fms] %s\n", (float) (clock() - timer) / CLOCKS_PER_SEC * 1000, "export");
  410. }
  411. }