Cleanup: add missing macros to clang-format
[blender.git] / source / blender / imbuf / intern / jp2.c
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  */
16
17 /** \file
18  * \ingroup imbuf
19  */
20
21 #include "MEM_guardedalloc.h"
22
23 #include "BLI_math.h"
24 #include "BLI_fileops.h"
25
26 #include "IMB_imbuf_types.h"
27 #include "IMB_imbuf.h"
28 #include "IMB_filetype.h"
29
30 #include "IMB_colormanagement.h"
31 #include "IMB_colormanagement_intern.h"
32
33 #include "openjpeg.h"
34
35 #define JP2_FILEHEADER_SIZE 12
36
37 static const char JP2_HEAD[] = {
38     0x0, 0x0, 0x0, 0x0C, 0x6A, 0x50, 0x20, 0x20, 0x0D, 0x0A, 0x87, 0x0A};
39 static const char J2K_HEAD[] = {0xFF, 0x4F, 0xFF, 0x51, 0x00};
40
41 /* We only need this because of how the presets are set */
42 /* this typedef is copied from 'openjpeg-1.5.0/applications/codec/image_to_j2k.c' */
43 typedef struct img_folder {
44   /** The directory path of the folder containing input images*/
45   char *imgdirpath;
46   /** Output format*/
47   char *out_format;
48   /** Enable option*/
49   char set_imgdir;
50   /** Enable Cod Format for output*/
51   char set_out_format;
52   /** User specified rate stored in case of cinema option*/
53   float *rates;
54 } img_fol_t;
55
56 enum {
57   DCP_CINEMA2K = 3,
58   DCP_CINEMA4K = 4,
59 };
60
61 static bool check_jp2(const unsigned char *mem) /* J2K_CFMT */
62 {
63   return memcmp(JP2_HEAD, mem, sizeof(JP2_HEAD)) ? 0 : 1;
64 }
65
66 static bool check_j2k(const unsigned char *mem) /* J2K_CFMT */
67 {
68   return memcmp(J2K_HEAD, mem, sizeof(J2K_HEAD)) ? 0 : 1;
69 }
70
71 static OPJ_CODEC_FORMAT format_from_header(const unsigned char mem[JP2_FILEHEADER_SIZE])
72 {
73   if (check_jp2(mem)) {
74     return OPJ_CODEC_JP2;
75   }
76   else if (check_j2k(mem)) {
77     return OPJ_CODEC_J2K;
78   }
79   else {
80     return OPJ_CODEC_UNKNOWN;
81   }
82 }
83
84 int imb_is_a_jp2(const unsigned char *buf)
85 {
86   return check_jp2(buf);
87 }
88
89 /**
90  * sample error callback expecting a FILE* client object
91  */
92 static void error_callback(const char *msg, void *client_data)
93 {
94   FILE *stream = (FILE *)client_data;
95   fprintf(stream, "[ERROR] %s", msg);
96 }
97 /**
98  * sample warning callback expecting a FILE* client object
99  */
100 static void warning_callback(const char *msg, void *client_data)
101 {
102   FILE *stream = (FILE *)client_data;
103   fprintf(stream, "[WARNING] %s", msg);
104 }
105
106 #ifdef DEBUG
107 /**
108  * sample debug callback expecting no client object
109  */
110 static void info_callback(const char *msg, void *client_data)
111 {
112   FILE *stream = (FILE *)client_data;
113   fprintf(stream, "[INFO] %s", msg);
114 }
115 #endif
116
117 #define PIXEL_LOOPER_BEGIN(_rect) \
118   for (y = h - 1; y != (unsigned int)(-1); y--) { \
119     for (i = y * w, i_next = (y + 1) * w; i < i_next; i++, _rect += 4) {
120
121 #define PIXEL_LOOPER_BEGIN_CHANNELS(_rect, _channels) \
122   for (y = h - 1; y != (unsigned int)(-1); y--) { \
123     for (i = y * w, i_next = (y + 1) * w; i < i_next; i++, _rect += _channels) {
124
125 #define PIXEL_LOOPER_END \
126   } \
127   } \
128   (void)0
129
130 /** \name Buffer Stream
131  * \{ */
132
133 struct BufInfo {
134   const unsigned char *buf;
135   const unsigned char *cur;
136   OPJ_OFF_T len;
137 };
138
139 static void opj_read_from_buffer_free(void *UNUSED(p_user_data))
140 {
141   /* nop */
142 }
143
144 static OPJ_SIZE_T opj_read_from_buffer(void *p_buffer, OPJ_SIZE_T p_nb_bytes, void *p_user_data)
145 {
146   struct BufInfo *p_file = p_user_data;
147   OPJ_UINT32 l_nb_read;
148
149   if (p_file->cur + p_nb_bytes < p_file->buf + p_file->len) {
150     l_nb_read = p_nb_bytes;
151   }
152   else {
153     l_nb_read = (OPJ_UINT32)(p_file->buf + p_file->len - p_file->cur);
154   }
155   memcpy(p_buffer, p_file->cur, l_nb_read);
156   p_file->cur += l_nb_read;
157
158   return l_nb_read ? l_nb_read : ((OPJ_SIZE_T)-1);
159 }
160
161 #if 0
162 static OPJ_SIZE_T opj_write_from_buffer(void *p_buffer, OPJ_SIZE_T p_nb_bytes, void *p_user_data)
163 {
164   struct BufInfo *p_file = p_user_data;
165   memcpy(p_file->cur, p_buffer, p_nb_bytes);
166   p_file->cur += p_nb_bytes;
167   p_file->len += p_nb_bytes;
168   return p_nb_bytes;
169 }
170 #endif
171
172 static OPJ_OFF_T opj_skip_from_buffer(OPJ_OFF_T p_nb_bytes, void *p_user_data)
173 {
174   struct BufInfo *p_file = p_user_data;
175   if (p_file->cur + p_nb_bytes < p_file->buf + p_file->len) {
176     p_file->cur += p_nb_bytes;
177     return p_nb_bytes;
178   }
179   p_file->cur = p_file->buf + p_file->len;
180   return (OPJ_OFF_T)-1;
181 }
182
183 static OPJ_BOOL opj_seek_from_buffer(OPJ_OFF_T p_nb_bytes, void *p_user_data)
184 {
185   struct BufInfo *p_file = p_user_data;
186   if (p_nb_bytes < p_file->len) {
187     p_file->cur = p_file->buf + p_nb_bytes;
188     return OPJ_TRUE;
189   }
190   p_file->cur = p_file->buf + p_file->len;
191   return OPJ_FALSE;
192 }
193
194 /**
195  * Stream wrapper for memory buffer
196  * (would be nice if this was supported by the API).
197  */
198
199 static opj_stream_t *opj_stream_create_from_buffer(struct BufInfo *p_file,
200                                                    OPJ_UINT32 p_size,
201                                                    OPJ_BOOL p_is_read_stream)
202 {
203   opj_stream_t *l_stream = opj_stream_create(p_size, p_is_read_stream);
204   if (l_stream == NULL) {
205     return NULL;
206   }
207   opj_stream_set_user_data(l_stream, p_file, opj_read_from_buffer_free);
208   opj_stream_set_user_data_length(l_stream, p_file->len);
209   opj_stream_set_read_function(l_stream, opj_read_from_buffer);
210 #if 0 /* UNUSED */
211   opj_stream_set_write_function(l_stream, opj_write_from_buffer);
212 #endif
213   opj_stream_set_skip_function(l_stream, opj_skip_from_buffer);
214   opj_stream_set_seek_function(l_stream, opj_seek_from_buffer);
215
216   return l_stream;
217 }
218
219 /** \} */
220
221 /** \name File Stream
222  * \{ */
223
224 static void opj_free_from_file(void *p_user_data)
225 {
226   FILE *f = p_user_data;
227   fclose(f);
228 }
229
230 static OPJ_UINT64 opj_get_data_length_from_file(void *p_user_data)
231 {
232   FILE *p_file = p_user_data;
233   OPJ_OFF_T file_length = 0;
234
235   fseek(p_file, 0, SEEK_END);
236   file_length = ftell(p_file);
237   fseek(p_file, 0, SEEK_SET);
238
239   return (OPJ_UINT64)file_length;
240 }
241
242 static OPJ_SIZE_T opj_read_from_file(void *p_buffer, OPJ_SIZE_T p_nb_bytes, void *p_user_data)
243 {
244   FILE *p_file = p_user_data;
245   OPJ_SIZE_T l_nb_read = fread(p_buffer, 1, p_nb_bytes, p_file);
246   return l_nb_read ? l_nb_read : (OPJ_SIZE_T)-1;
247 }
248
249 static OPJ_SIZE_T opj_write_from_file(void *p_buffer, OPJ_SIZE_T p_nb_bytes, void *p_user_data)
250 {
251   FILE *p_file = p_user_data;
252   return fwrite(p_buffer, 1, p_nb_bytes, p_file);
253 }
254
255 static OPJ_OFF_T opj_skip_from_file(OPJ_OFF_T p_nb_bytes, void *p_user_data)
256 {
257   FILE *p_file = p_user_data;
258   if (fseek(p_file, p_nb_bytes, SEEK_CUR)) {
259     return -1;
260   }
261   return p_nb_bytes;
262 }
263
264 static OPJ_BOOL opj_seek_from_file(OPJ_OFF_T p_nb_bytes, void *p_user_data)
265 {
266   FILE *p_file = p_user_data;
267   if (fseek(p_file, p_nb_bytes, SEEK_SET)) {
268     return OPJ_FALSE;
269   }
270   return OPJ_TRUE;
271 }
272
273 /**
274  * Stream wrapper for memory file
275  * (would be nice if this was supported by the API).
276  */
277
278 static opj_stream_t *opj_stream_create_from_file(const char *filepath,
279                                                  OPJ_UINT32 p_size,
280                                                  OPJ_BOOL p_is_read_stream,
281                                                  FILE **r_file)
282 {
283   FILE *p_file = BLI_fopen(filepath, p_is_read_stream ? "rb" : "wb");
284   if (p_file == NULL) {
285     return NULL;
286   }
287
288   opj_stream_t *l_stream = opj_stream_create(p_size, p_is_read_stream);
289   if (l_stream == NULL) {
290     fclose(p_file);
291     return NULL;
292   }
293
294   opj_stream_set_user_data(l_stream, p_file, opj_free_from_file);
295   opj_stream_set_user_data_length(l_stream, opj_get_data_length_from_file(p_file));
296   opj_stream_set_write_function(l_stream, opj_write_from_file);
297   opj_stream_set_read_function(l_stream, opj_read_from_file);
298   opj_stream_set_skip_function(l_stream, opj_skip_from_file);
299   opj_stream_set_seek_function(l_stream, opj_seek_from_file);
300
301   if (r_file) {
302     *r_file = p_file;
303   }
304   return l_stream;
305 }
306
307 /** \} */
308
309 static ImBuf *imb_load_jp2_stream(opj_stream_t *stream,
310                                   OPJ_CODEC_FORMAT p_format,
311                                   int flags,
312                                   char colorspace[IM_MAX_SPACE]);
313
314 ImBuf *imb_load_jp2(const unsigned char *mem,
315                     size_t size,
316                     int flags,
317                     char colorspace[IM_MAX_SPACE])
318 {
319   const OPJ_CODEC_FORMAT format = (size > JP2_FILEHEADER_SIZE) ? format_from_header(mem) :
320                                                                  OPJ_CODEC_UNKNOWN;
321   struct BufInfo buf_wrapper = {
322       .buf = mem,
323       .cur = mem,
324       .len = size,
325   };
326   opj_stream_t *stream = opj_stream_create_from_buffer(
327       &buf_wrapper, OPJ_J2K_STREAM_CHUNK_SIZE, true);
328   ImBuf *ibuf = imb_load_jp2_stream(stream, format, flags, colorspace);
329   opj_stream_destroy(stream);
330   return ibuf;
331 }
332
333 ImBuf *imb_load_jp2_filepath(const char *filepath, int flags, char colorspace[IM_MAX_SPACE])
334 {
335   FILE *p_file = NULL;
336   unsigned char mem[JP2_FILEHEADER_SIZE];
337   opj_stream_t *stream = opj_stream_create_from_file(
338       filepath, OPJ_J2K_STREAM_CHUNK_SIZE, true, &p_file);
339   if (stream) {
340     return NULL;
341   }
342   else {
343     if (fread(mem, sizeof(mem), 1, p_file) != sizeof(mem)) {
344       opj_stream_destroy(stream);
345       return NULL;
346     }
347     else {
348       fseek(p_file, 0, SEEK_SET);
349     }
350   }
351
352   const OPJ_CODEC_FORMAT format = format_from_header(mem);
353   ImBuf *ibuf = imb_load_jp2_stream(stream, format, flags, colorspace);
354   opj_stream_destroy(stream);
355   return ibuf;
356 }
357
358 static ImBuf *imb_load_jp2_stream(opj_stream_t *stream,
359                                   const OPJ_CODEC_FORMAT format,
360                                   int flags,
361                                   char colorspace[IM_MAX_SPACE])
362 {
363   if (format == OPJ_CODEC_UNKNOWN) {
364     return NULL;
365   }
366
367   struct ImBuf *ibuf = NULL;
368   bool use_float = false; /* for precision higher then 8 use float */
369   bool use_alpha = false;
370
371   long signed_offsets[4] = {0, 0, 0, 0};
372   int float_divs[4] = {1, 1, 1, 1};
373
374   unsigned int i, i_next, w, h, planes;
375   unsigned int y;
376   int *r, *g, *b, *a; /* matching 'opj_image_comp.data' type */
377
378   opj_dparameters_t parameters; /* decompression parameters */
379
380   opj_image_t *image = NULL;
381   opj_codec_t *codec = NULL; /* handle to a decompressor */
382
383   /* both 8, 12 and 16 bit JP2Ks are default to standard byte colorspace */
384   colorspace_set_default_role(colorspace, IM_MAX_SPACE, COLOR_ROLE_DEFAULT_BYTE);
385
386   /* set decoding parameters to default values */
387   opj_set_default_decoder_parameters(&parameters);
388
389   /* JPEG 2000 compressed image data */
390
391   /* get a decoder handle */
392   codec = opj_create_decompress(format);
393
394   /* configure the event callbacks (not required) */
395   opj_set_error_handler(codec, error_callback, stderr);
396   opj_set_warning_handler(codec, warning_callback, stderr);
397 #ifdef DEBUG /* too noisy */
398   opj_set_info_handler(codec, info_callback, stderr);
399 #endif
400
401   /* setup the decoder decoding parameters using the current image and user parameters */
402   if (opj_setup_decoder(codec, &parameters) == false) {
403     goto finally;
404   }
405
406   if (opj_read_header(stream, codec, &image) == false) {
407     printf("OpenJPEG error: failed to read the header\n");
408     goto finally;
409   }
410
411   /* decode the stream and fill the image structure */
412   if (opj_decode(codec, stream, image) == false) {
413     fprintf(stderr, "ERROR -> j2k_to_image: failed to decode image!\n");
414     goto finally;
415   }
416
417   if ((image->numcomps * image->x1 * image->y1) == 0) {
418     fprintf(stderr, "\nError: invalid raw image parameters\n");
419     goto finally;
420   }
421
422   w = image->comps[0].w;
423   h = image->comps[0].h;
424
425   switch (image->numcomps) {
426     case 1: /* Grayscale */
427     case 3: /* Color */
428       planes = 24;
429       use_alpha = false;
430       break;
431     default:       /* 2 or 4 - Grayscale or Color + alpha */
432       planes = 32; /* grayscale + alpha */
433       use_alpha = true;
434       break;
435   }
436
437   i = image->numcomps;
438   if (i > 4)
439     i = 4;
440
441   while (i) {
442     i--;
443
444     if (image->comps[i].prec > 8)
445       use_float = true;
446
447     if (image->comps[i].sgnd)
448       signed_offsets[i] = 1 << (image->comps[i].prec - 1);
449
450     /* only needed for float images but dosnt hurt to calc this */
451     float_divs[i] = (1 << image->comps[i].prec) - 1;
452   }
453
454   ibuf = IMB_allocImBuf(w, h, planes, use_float ? IB_rectfloat : IB_rect);
455
456   if (ibuf == NULL) {
457     goto finally;
458   }
459
460   ibuf->ftype = IMB_FTYPE_JP2;
461   if (1 /* is_jp2 */) {
462     ibuf->foptions.flag |= JP2_JP2;
463   }
464   else {
465     ibuf->foptions.flag |= JP2_J2K;
466   }
467
468   if (use_float) {
469     float *rect_float = ibuf->rect_float;
470
471     if (image->numcomps < 3) {
472       r = image->comps[0].data;
473       a = (use_alpha) ? image->comps[1].data : NULL;
474
475       /* grayscale 12bits+ */
476       if (use_alpha) {
477         a = image->comps[1].data;
478         PIXEL_LOOPER_BEGIN (rect_float) {
479           rect_float[0] = rect_float[1] = rect_float[2] = (float)(r[i] + signed_offsets[0]) /
480                                                           float_divs[0];
481           rect_float[3] = (a[i] + signed_offsets[1]) / float_divs[1];
482         }
483         PIXEL_LOOPER_END;
484       }
485       else {
486         PIXEL_LOOPER_BEGIN (rect_float) {
487           rect_float[0] = rect_float[1] = rect_float[2] = (float)(r[i] + signed_offsets[0]) /
488                                                           float_divs[0];
489           rect_float[3] = 1.0f;
490         }
491         PIXEL_LOOPER_END;
492       }
493     }
494     else {
495       r = image->comps[0].data;
496       g = image->comps[1].data;
497       b = image->comps[2].data;
498
499       /* rgb or rgba 12bits+ */
500       if (use_alpha) {
501         a = image->comps[3].data;
502         PIXEL_LOOPER_BEGIN (rect_float) {
503           rect_float[0] = (float)(r[i] + signed_offsets[0]) / float_divs[0];
504           rect_float[1] = (float)(g[i] + signed_offsets[1]) / float_divs[1];
505           rect_float[2] = (float)(b[i] + signed_offsets[2]) / float_divs[2];
506           rect_float[3] = (float)(a[i] + signed_offsets[3]) / float_divs[3];
507         }
508         PIXEL_LOOPER_END;
509       }
510       else {
511         PIXEL_LOOPER_BEGIN (rect_float) {
512           rect_float[0] = (float)(r[i] + signed_offsets[0]) / float_divs[0];
513           rect_float[1] = (float)(g[i] + signed_offsets[1]) / float_divs[1];
514           rect_float[2] = (float)(b[i] + signed_offsets[2]) / float_divs[2];
515           rect_float[3] = 1.0f;
516         }
517         PIXEL_LOOPER_END;
518       }
519     }
520   }
521   else {
522     unsigned char *rect_uchar = (unsigned char *)ibuf->rect;
523
524     if (image->numcomps < 3) {
525       r = image->comps[0].data;
526       a = (use_alpha) ? image->comps[1].data : NULL;
527
528       /* grayscale */
529       if (use_alpha) {
530         a = image->comps[3].data;
531         PIXEL_LOOPER_BEGIN (rect_uchar) {
532           rect_uchar[0] = rect_uchar[1] = rect_uchar[2] = (r[i] + signed_offsets[0]);
533           rect_uchar[3] = a[i] + signed_offsets[1];
534         }
535         PIXEL_LOOPER_END;
536       }
537       else {
538         PIXEL_LOOPER_BEGIN (rect_uchar) {
539           rect_uchar[0] = rect_uchar[1] = rect_uchar[2] = (r[i] + signed_offsets[0]);
540           rect_uchar[3] = 255;
541         }
542         PIXEL_LOOPER_END;
543       }
544     }
545     else {
546       r = image->comps[0].data;
547       g = image->comps[1].data;
548       b = image->comps[2].data;
549
550       /* 8bit rgb or rgba */
551       if (use_alpha) {
552         a = image->comps[3].data;
553         PIXEL_LOOPER_BEGIN (rect_uchar) {
554           rect_uchar[0] = r[i] + signed_offsets[0];
555           rect_uchar[1] = g[i] + signed_offsets[1];
556           rect_uchar[2] = b[i] + signed_offsets[2];
557           rect_uchar[3] = a[i] + signed_offsets[3];
558         }
559         PIXEL_LOOPER_END;
560       }
561       else {
562         PIXEL_LOOPER_BEGIN (rect_uchar) {
563           rect_uchar[0] = r[i] + signed_offsets[0];
564           rect_uchar[1] = g[i] + signed_offsets[1];
565           rect_uchar[2] = b[i] + signed_offsets[2];
566           rect_uchar[3] = 255;
567         }
568         PIXEL_LOOPER_END;
569       }
570     }
571   }
572
573   if (flags & IB_rect) {
574     IMB_rect_from_float(ibuf);
575   }
576
577 finally:
578
579   /* free remaining structures */
580   if (codec) {
581     opj_destroy_codec(codec);
582   }
583
584   if (image) {
585     opj_image_destroy(image);
586   }
587
588   return ibuf;
589 }
590
591 //static opj_image_t* rawtoimage(const char *filename, opj_cparameters_t *parameters, raw_cparameters_t *raw_cp)
592 /* prec can be 8, 12, 16 */
593
594 /* use inline because the float passed can be a function call that would end up being called many times */
595 #if 0
596 #  define UPSAMPLE_8_TO_12(_val) ((_val << 4) | (_val & ((1 << 4) - 1)))
597 #  define UPSAMPLE_8_TO_16(_val) ((_val << 8) + _val)
598
599 #  define DOWNSAMPLE_FLOAT_TO_8BIT(_val) \
600     (_val) <= 0.0f ? 0 : ((_val) >= 1.0f ? 255 : (int)(255.0f * (_val)))
601 #  define DOWNSAMPLE_FLOAT_TO_12BIT(_val) \
602     (_val) <= 0.0f ? 0 : ((_val) >= 1.0f ? 4095 : (int)(4095.0f * (_val)))
603 #  define DOWNSAMPLE_FLOAT_TO_16BIT(_val) \
604     (_val) <= 0.0f ? 0 : ((_val) >= 1.0f ? 65535 : (int)(65535.0f * (_val)))
605 #else
606
607 BLI_INLINE int UPSAMPLE_8_TO_12(const unsigned char _val)
608 {
609   return (_val << 4) | (_val & ((1 << 4) - 1));
610 }
611 BLI_INLINE int UPSAMPLE_8_TO_16(const unsigned char _val)
612 {
613   return (_val << 8) + _val;
614 }
615
616 BLI_INLINE int DOWNSAMPLE_FLOAT_TO_8BIT(const float _val)
617 {
618   return (_val) <= 0.0f ? 0 : ((_val) >= 1.0f ? 255 : (int)(255.0f * (_val)));
619 }
620 BLI_INLINE int DOWNSAMPLE_FLOAT_TO_12BIT(const float _val)
621 {
622   return (_val) <= 0.0f ? 0 : ((_val) >= 1.0f ? 4095 : (int)(4095.0f * (_val)));
623 }
624 BLI_INLINE int DOWNSAMPLE_FLOAT_TO_16BIT(const float _val)
625 {
626   return (_val) <= 0.0f ? 0 : ((_val) >= 1.0f ? 65535 : (int)(65535.0f * (_val)));
627 }
628 #endif
629
630 /*
631  * 2048x1080 (2K) at 24 fps or 48 fps, or 4096x2160 (4K) at 24 fps; 3x12 bits per pixel, XYZ color space
632  *
633  * - In 2K, for Scope (2.39:1) presentation 2048x858  pixels of the image is used
634  * - In 2K, for Flat  (1.85:1) presentation 1998x1080 pixels of the image is used
635  */
636
637 /* ****************************** COPIED FROM image_to_j2k.c */
638
639 /* ----------------------------------------------------------------------- */
640 #define CINEMA_24_CS 1302083 /*Codestream length for 24fps*/
641 #define CINEMA_48_CS 651041  /*Codestream length for 48fps*/
642 #define COMP_24_CS 1041666   /*Maximum size per color component for 2K & 4K @ 24fps*/
643 #define COMP_48_CS 520833    /*Maximum size per color component for 2K @ 48fps*/
644
645 static int initialise_4K_poc(opj_poc_t *POC, int numres)
646 {
647   POC[0].tile = 1;
648   POC[0].resno0 = 0;
649   POC[0].compno0 = 0;
650   POC[0].layno1 = 1;
651   POC[0].resno1 = numres - 1;
652   POC[0].compno1 = 3;
653   POC[0].prg1 = OPJ_CPRL;
654   POC[1].tile = 1;
655   POC[1].resno0 = numres - 1;
656   POC[1].compno0 = 0;
657   POC[1].layno1 = 1;
658   POC[1].resno1 = numres;
659   POC[1].compno1 = 3;
660   POC[1].prg1 = OPJ_CPRL;
661   return 2;
662 }
663
664 static void cinema_parameters(opj_cparameters_t *parameters)
665 {
666   parameters->tile_size_on = 0; /* false */
667   parameters->cp_tdx = 1;
668   parameters->cp_tdy = 1;
669
670   /*Tile part*/
671   parameters->tp_flag = 'C';
672   parameters->tp_on = 1;
673
674   /*Tile and Image shall be at (0, 0)*/
675   parameters->cp_tx0 = 0;
676   parameters->cp_ty0 = 0;
677   parameters->image_offset_x0 = 0;
678   parameters->image_offset_y0 = 0;
679
680   /*Codeblock size = 32 * 32*/
681   parameters->cblockw_init = 32;
682   parameters->cblockh_init = 32;
683   parameters->csty |= 0x01;
684
685   /*The progression order shall be CPRL*/
686   parameters->prog_order = OPJ_CPRL;
687
688   /* No ROI */
689   parameters->roi_compno = -1;
690
691   parameters->subsampling_dx = 1;
692   parameters->subsampling_dy = 1;
693
694   /* 9-7 transform */
695   parameters->irreversible = 1;
696 }
697
698 static void cinema_setup_encoder(opj_cparameters_t *parameters,
699                                  opj_image_t *image,
700                                  img_fol_t *img_fol)
701 {
702   int i;
703   float temp_rate;
704
705   switch (parameters->cp_cinema) {
706     case OPJ_CINEMA2K_24:
707     case OPJ_CINEMA2K_48:
708       if (parameters->numresolution > 6) {
709         parameters->numresolution = 6;
710       }
711       if (!((image->comps[0].w == 2048) || (image->comps[0].h == 1080))) {
712         fprintf(stdout,
713                 "Image coordinates %u x %u is not 2K compliant.\nJPEG Digital Cinema Profile-3 "
714                 "(2K profile) compliance requires that at least one of coordinates match 2048 x "
715                 "1080\n",
716                 image->comps[0].w,
717                 image->comps[0].h);
718         parameters->cp_rsiz = OPJ_STD_RSIZ;
719       }
720       else {
721         parameters->cp_rsiz = DCP_CINEMA2K;
722       }
723       break;
724
725     case OPJ_CINEMA4K_24:
726       if (parameters->numresolution < 1) {
727         parameters->numresolution = 1;
728       }
729       else if (parameters->numresolution > 7) {
730         parameters->numresolution = 7;
731       }
732       if (!((image->comps[0].w == 4096) || (image->comps[0].h == 2160))) {
733         fprintf(stdout,
734                 "Image coordinates %u x %u is not 4K compliant.\nJPEG Digital Cinema Profile-4"
735                 "(4K profile) compliance requires that at least one of coordinates match 4096 x "
736                 "2160\n",
737                 image->comps[0].w,
738                 image->comps[0].h);
739         parameters->cp_rsiz = OPJ_STD_RSIZ;
740       }
741       else {
742         parameters->cp_rsiz = DCP_CINEMA2K;
743       }
744       parameters->numpocs = initialise_4K_poc(parameters->POC, parameters->numresolution);
745       break;
746     case OPJ_OFF:
747       /* do nothing */
748       break;
749   }
750
751   switch (parameters->cp_cinema) {
752     case OPJ_CINEMA2K_24:
753     case OPJ_CINEMA4K_24:
754       for (i = 0; i < parameters->tcp_numlayers; i++) {
755         temp_rate = 0;
756         if (img_fol->rates[i] == 0) {
757           parameters->tcp_rates[0] = ((float)(image->numcomps * image->comps[0].w *
758                                               image->comps[0].h * image->comps[0].prec)) /
759                                      (CINEMA_24_CS * 8 * image->comps[0].dx * image->comps[0].dy);
760         }
761         else {
762           temp_rate = ((float)(image->numcomps * image->comps[0].w * image->comps[0].h *
763                                image->comps[0].prec)) /
764                       (img_fol->rates[i] * 8 * image->comps[0].dx * image->comps[0].dy);
765           if (temp_rate > CINEMA_24_CS) {
766             parameters->tcp_rates[i] = ((float)(image->numcomps * image->comps[0].w *
767                                                 image->comps[0].h * image->comps[0].prec)) /
768                                        (CINEMA_24_CS * 8 * image->comps[0].dx *
769                                         image->comps[0].dy);
770           }
771           else {
772             parameters->tcp_rates[i] = img_fol->rates[i];
773           }
774         }
775       }
776       parameters->max_comp_size = COMP_24_CS;
777       break;
778
779     case OPJ_CINEMA2K_48:
780       for (i = 0; i < parameters->tcp_numlayers; i++) {
781         temp_rate = 0;
782         if (img_fol->rates[i] == 0) {
783           parameters->tcp_rates[0] = ((float)(image->numcomps * image->comps[0].w *
784                                               image->comps[0].h * image->comps[0].prec)) /
785                                      (CINEMA_48_CS * 8 * image->comps[0].dx * image->comps[0].dy);
786         }
787         else {
788           temp_rate = ((float)(image->numcomps * image->comps[0].w * image->comps[0].h *
789                                image->comps[0].prec)) /
790                       (img_fol->rates[i] * 8 * image->comps[0].dx * image->comps[0].dy);
791           if (temp_rate > CINEMA_48_CS) {
792             parameters->tcp_rates[0] = ((float)(image->numcomps * image->comps[0].w *
793                                                 image->comps[0].h * image->comps[0].prec)) /
794                                        (CINEMA_48_CS * 8 * image->comps[0].dx *
795                                         image->comps[0].dy);
796           }
797           else {
798             parameters->tcp_rates[i] = img_fol->rates[i];
799           }
800         }
801       }
802       parameters->max_comp_size = COMP_48_CS;
803       break;
804     case OPJ_OFF:
805       /* do nothing */
806       break;
807   }
808   parameters->cp_disto_alloc = 1;
809 }
810
811 static float channel_colormanage_noop(float value)
812 {
813   return value;
814 }
815
816 static opj_image_t *ibuftoimage(ImBuf *ibuf, opj_cparameters_t *parameters)
817 {
818   unsigned char *rect_uchar;
819   float *rect_float, from_straight[4];
820
821   unsigned int subsampling_dx = parameters->subsampling_dx;
822   unsigned int subsampling_dy = parameters->subsampling_dy;
823
824   unsigned int i, i_next, numcomps, w, h, prec;
825   unsigned int y;
826   int *r, *g, *b, *a; /* matching 'opj_image_comp.data' type */
827   OPJ_COLOR_SPACE color_space;
828   opj_image_cmptparm_t cmptparm[4]; /* maximum of 4 components */
829   opj_image_t *image = NULL;
830
831   float (*chanel_colormanage_cb)(float);
832
833   img_fol_t img_fol; /* only needed for cinema presets */
834   memset(&img_fol, 0, sizeof(img_fol_t));
835
836   if (ibuf->float_colorspace || (ibuf->colormanage_flag & IMB_COLORMANAGE_IS_DATA)) {
837     /* float buffer was managed already, no need in color space conversion */
838     chanel_colormanage_cb = channel_colormanage_noop;
839   }
840   else {
841     /* standard linear-to-srgb conversion if float buffer wasn't managed */
842     chanel_colormanage_cb = linearrgb_to_srgb;
843   }
844
845   if (ibuf->foptions.flag & JP2_CINE) {
846
847     if (ibuf->x == 4096 || ibuf->y == 2160)
848       parameters->cp_cinema = OPJ_CINEMA4K_24;
849     else {
850       if (ibuf->foptions.flag & JP2_CINE_48FPS) {
851         parameters->cp_cinema = OPJ_CINEMA2K_48;
852       }
853       else {
854         parameters->cp_cinema = OPJ_CINEMA2K_24;
855       }
856     }
857     if (parameters->cp_cinema) {
858       img_fol.rates = (float *)MEM_mallocN(parameters->tcp_numlayers * sizeof(float), "jp2_rates");
859       for (i = 0; i < parameters->tcp_numlayers; i++) {
860         img_fol.rates[i] = parameters->tcp_rates[i];
861       }
862       cinema_parameters(parameters);
863     }
864
865     color_space = (ibuf->foptions.flag & JP2_YCC) ? OPJ_CLRSPC_SYCC : OPJ_CLRSPC_SRGB;
866     prec = 12;
867     numcomps = 3;
868   }
869   else {
870     /* Get settings from the imbuf */
871     color_space = (ibuf->foptions.flag & JP2_YCC) ? OPJ_CLRSPC_SYCC : OPJ_CLRSPC_SRGB;
872
873     if (ibuf->foptions.flag & JP2_16BIT)
874       prec = 16;
875     else if (ibuf->foptions.flag & JP2_12BIT)
876       prec = 12;
877     else
878       prec = 8;
879
880     /* 32bit images == alpha channel */
881     /* grayscale not supported yet */
882     numcomps = (ibuf->planes == 32) ? 4 : 3;
883   }
884
885   w = ibuf->x;
886   h = ibuf->y;
887
888   /* initialize image components */
889   memset(&cmptparm, 0, 4 * sizeof(opj_image_cmptparm_t));
890   for (i = 0; i < numcomps; i++) {
891     cmptparm[i].prec = prec;
892     cmptparm[i].bpp = prec;
893     cmptparm[i].sgnd = 0;
894     cmptparm[i].dx = subsampling_dx;
895     cmptparm[i].dy = subsampling_dy;
896     cmptparm[i].w = w;
897     cmptparm[i].h = h;
898   }
899   /* create the image */
900   image = opj_image_create(numcomps, &cmptparm[0], color_space);
901   if (!image) {
902     printf("Error: opj_image_create() failed\n");
903     return NULL;
904   }
905
906   /* set image offset and reference grid */
907   image->x0 = parameters->image_offset_x0;
908   image->y0 = parameters->image_offset_y0;
909   image->x1 = image->x0 + (w - 1) * subsampling_dx + 1 + image->x0;
910   image->y1 = image->y0 + (h - 1) * subsampling_dy + 1 + image->y0;
911
912   /* set image data */
913   rect_uchar = (unsigned char *)ibuf->rect;
914   rect_float = ibuf->rect_float;
915
916   /* set the destination channels */
917   r = image->comps[0].data;
918   g = image->comps[1].data;
919   b = image->comps[2].data;
920   a = (numcomps == 4) ? image->comps[3].data : NULL;
921
922   if (rect_float && rect_uchar && prec == 8) {
923     /* No need to use the floating point buffer, just write the 8 bits from the char buffer */
924     rect_float = NULL;
925   }
926
927   if (rect_float) {
928     int channels_in_float = ibuf->channels ? ibuf->channels : 4;
929
930     switch (prec) {
931       case 8: /* Convert blenders float color channels to 8, 12 or 16bit ints */
932         if (numcomps == 4) {
933           if (channels_in_float == 4) {
934             PIXEL_LOOPER_BEGIN (rect_float) {
935               premul_to_straight_v4_v4(from_straight, rect_float);
936               r[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(from_straight[0]));
937               g[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(from_straight[1]));
938               b[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(from_straight[2]));
939               a[i] = DOWNSAMPLE_FLOAT_TO_8BIT(from_straight[3]);
940             }
941             PIXEL_LOOPER_END;
942           }
943           else if (channels_in_float == 3) {
944             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 3) {
945               r[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(rect_float[0]));
946               g[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(rect_float[1]));
947               b[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(rect_float[2]));
948               a[i] = 255;
949             }
950             PIXEL_LOOPER_END;
951           }
952           else {
953             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 1) {
954               r[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(rect_float[0]));
955               g[i] = b[i] = r[i];
956               a[i] = 255;
957             }
958             PIXEL_LOOPER_END;
959           }
960         }
961         else {
962           if (channels_in_float == 4) {
963             PIXEL_LOOPER_BEGIN (rect_float) {
964               premul_to_straight_v4_v4(from_straight, rect_float);
965               r[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(from_straight[0]));
966               g[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(from_straight[1]));
967               b[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(from_straight[2]));
968             }
969             PIXEL_LOOPER_END;
970           }
971           else if (channels_in_float == 3) {
972             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 3) {
973               r[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(rect_float[0]));
974               g[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(rect_float[1]));
975               b[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(rect_float[2]));
976             }
977             PIXEL_LOOPER_END;
978           }
979           else {
980             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 1) {
981               r[i] = DOWNSAMPLE_FLOAT_TO_8BIT(chanel_colormanage_cb(rect_float[0]));
982               g[i] = b[i] = r[i];
983             }
984             PIXEL_LOOPER_END;
985           }
986         }
987         break;
988
989       case 12:
990         if (numcomps == 4) {
991           if (channels_in_float == 4) {
992             PIXEL_LOOPER_BEGIN (rect_float) {
993               premul_to_straight_v4_v4(from_straight, rect_float);
994               r[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(from_straight[0]));
995               g[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(from_straight[1]));
996               b[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(from_straight[2]));
997               a[i] = DOWNSAMPLE_FLOAT_TO_12BIT(from_straight[3]);
998             }
999             PIXEL_LOOPER_END;
1000           }
1001           else if (channels_in_float == 3) {
1002             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 3) {
1003               r[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(rect_float[0]));
1004               g[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(rect_float[1]));
1005               b[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(rect_float[2]));
1006               a[i] = 4095;
1007             }
1008             PIXEL_LOOPER_END;
1009           }
1010           else {
1011             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 1) {
1012               r[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(rect_float[0]));
1013               g[i] = b[i] = r[i];
1014               a[i] = 4095;
1015             }
1016             PIXEL_LOOPER_END;
1017           }
1018         }
1019         else {
1020           if (channels_in_float == 4) {
1021             PIXEL_LOOPER_BEGIN (rect_float) {
1022               premul_to_straight_v4_v4(from_straight, rect_float);
1023               r[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(from_straight[0]));
1024               g[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(from_straight[1]));
1025               b[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(from_straight[2]));
1026             }
1027             PIXEL_LOOPER_END;
1028           }
1029           else if (channels_in_float == 3) {
1030             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 3) {
1031               r[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(rect_float[0]));
1032               g[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(rect_float[1]));
1033               b[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(rect_float[2]));
1034             }
1035             PIXEL_LOOPER_END;
1036           }
1037           else {
1038             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 1) {
1039               r[i] = DOWNSAMPLE_FLOAT_TO_12BIT(chanel_colormanage_cb(rect_float[0]));
1040               g[i] = b[i] = r[i];
1041             }
1042             PIXEL_LOOPER_END;
1043           }
1044         }
1045         break;
1046
1047       case 16:
1048         if (numcomps == 4) {
1049           if (channels_in_float == 4) {
1050             PIXEL_LOOPER_BEGIN (rect_float) {
1051               premul_to_straight_v4_v4(from_straight, rect_float);
1052               r[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(from_straight[0]));
1053               g[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(from_straight[1]));
1054               b[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(from_straight[2]));
1055               a[i] = DOWNSAMPLE_FLOAT_TO_16BIT(from_straight[3]);
1056             }
1057             PIXEL_LOOPER_END;
1058           }
1059           else if (channels_in_float == 3) {
1060             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 3) {
1061               r[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(rect_float[0]));
1062               g[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(rect_float[1]));
1063               b[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(rect_float[2]));
1064               a[i] = 65535;
1065             }
1066             PIXEL_LOOPER_END;
1067           }
1068           else {
1069             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 1) {
1070               r[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(rect_float[0]));
1071               g[i] = b[i] = r[i];
1072               a[i] = 65535;
1073             }
1074             PIXEL_LOOPER_END;
1075           }
1076         }
1077         else {
1078           if (channels_in_float == 4) {
1079             PIXEL_LOOPER_BEGIN (rect_float) {
1080               premul_to_straight_v4_v4(from_straight, rect_float);
1081               r[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(from_straight[0]));
1082               g[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(from_straight[1]));
1083               b[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(from_straight[2]));
1084             }
1085             PIXEL_LOOPER_END;
1086           }
1087           else if (channels_in_float == 3) {
1088             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 3) {
1089               r[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(rect_float[0]));
1090               g[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(rect_float[1]));
1091               b[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(rect_float[2]));
1092             }
1093             PIXEL_LOOPER_END;
1094           }
1095           else {
1096             PIXEL_LOOPER_BEGIN_CHANNELS (rect_float, 1) {
1097               r[i] = DOWNSAMPLE_FLOAT_TO_16BIT(chanel_colormanage_cb(rect_float[0]));
1098               g[i] = b[i] = r[i];
1099             }
1100             PIXEL_LOOPER_END;
1101           }
1102         }
1103         break;
1104     }
1105   }
1106   else {
1107     /* just use rect*/
1108     switch (prec) {
1109       case 8:
1110         if (numcomps == 4) {
1111           PIXEL_LOOPER_BEGIN (rect_uchar) {
1112             r[i] = rect_uchar[0];
1113             g[i] = rect_uchar[1];
1114             b[i] = rect_uchar[2];
1115             a[i] = rect_uchar[3];
1116           }
1117           PIXEL_LOOPER_END;
1118         }
1119         else {
1120           PIXEL_LOOPER_BEGIN (rect_uchar) {
1121             r[i] = rect_uchar[0];
1122             g[i] = rect_uchar[1];
1123             b[i] = rect_uchar[2];
1124           }
1125           PIXEL_LOOPER_END;
1126         }
1127         break;
1128
1129       case 12: /* Up Sampling, a bit pointless but best write the bit depth requested */
1130         if (numcomps == 4) {
1131           PIXEL_LOOPER_BEGIN (rect_uchar) {
1132             r[i] = UPSAMPLE_8_TO_12(rect_uchar[0]);
1133             g[i] = UPSAMPLE_8_TO_12(rect_uchar[1]);
1134             b[i] = UPSAMPLE_8_TO_12(rect_uchar[2]);
1135             a[i] = UPSAMPLE_8_TO_12(rect_uchar[3]);
1136           }
1137           PIXEL_LOOPER_END;
1138         }
1139         else {
1140           PIXEL_LOOPER_BEGIN (rect_uchar) {
1141             r[i] = UPSAMPLE_8_TO_12(rect_uchar[0]);
1142             g[i] = UPSAMPLE_8_TO_12(rect_uchar[1]);
1143             b[i] = UPSAMPLE_8_TO_12(rect_uchar[2]);
1144           }
1145           PIXEL_LOOPER_END;
1146         }
1147         break;
1148
1149       case 16:
1150         if (numcomps == 4) {
1151           PIXEL_LOOPER_BEGIN (rect_uchar) {
1152             r[i] = UPSAMPLE_8_TO_16(rect_uchar[0]);
1153             g[i] = UPSAMPLE_8_TO_16(rect_uchar[1]);
1154             b[i] = UPSAMPLE_8_TO_16(rect_uchar[2]);
1155             a[i] = UPSAMPLE_8_TO_16(rect_uchar[3]);
1156           }
1157           PIXEL_LOOPER_END;
1158         }
1159         else {
1160           PIXEL_LOOPER_BEGIN (rect_uchar) {
1161             r[i] = UPSAMPLE_8_TO_16(rect_uchar[0]);
1162             g[i] = UPSAMPLE_8_TO_16(rect_uchar[1]);
1163             b[i] = UPSAMPLE_8_TO_16(rect_uchar[2]);
1164           }
1165           PIXEL_LOOPER_END;
1166         }
1167         break;
1168     }
1169   }
1170
1171   /* Decide if MCT should be used */
1172   parameters->tcp_mct = image->numcomps == 3 ? 1 : 0;
1173
1174   if (parameters->cp_cinema) {
1175     cinema_setup_encoder(parameters, image, &img_fol);
1176   }
1177
1178   if (img_fol.rates)
1179     MEM_freeN(img_fol.rates);
1180
1181   return image;
1182 }
1183
1184 int imb_save_jp2_stream(struct ImBuf *ibuf, opj_stream_t *stream, int flags);
1185
1186 int imb_save_jp2(struct ImBuf *ibuf, const char *filepath, int flags)
1187 {
1188   opj_stream_t *stream = opj_stream_create_from_file(
1189       filepath, OPJ_J2K_STREAM_CHUNK_SIZE, false, NULL);
1190   if (stream == NULL) {
1191     return 0;
1192   }
1193   int ret = imb_save_jp2_stream(ibuf, stream, flags);
1194   opj_stream_destroy(stream);
1195   return ret;
1196 }
1197
1198 /* Found write info at http://users.ece.gatech.edu/~slabaugh/personal/c/bitmapUnix.c */
1199 int imb_save_jp2_stream(struct ImBuf *ibuf, opj_stream_t *stream, int UNUSED(flags))
1200 {
1201   int quality = ibuf->foptions.quality;
1202
1203   opj_cparameters_t parameters; /* compression parameters */
1204   opj_image_t *image = NULL;
1205
1206   /* set encoding parameters to default values */
1207   opj_set_default_encoder_parameters(&parameters);
1208
1209   /* compression ratio */
1210   /* invert range, from 10-100, 100-1
1211    * where jpeg see's 1 and highest quality (lossless) and 100 is very low quality*/
1212   parameters.tcp_rates[0] = ((100 - quality) / 90.0f * 99.0f) + 1;
1213
1214   parameters.tcp_numlayers = 1; /* only one resolution */
1215   parameters.cp_disto_alloc = 1;
1216
1217   image = ibuftoimage(ibuf, &parameters);
1218
1219   opj_codec_t *codec = NULL;
1220   int ok = false;
1221   /* JP2 format output */
1222   {
1223     /* get a JP2 compressor handle */
1224     OPJ_CODEC_FORMAT format = OPJ_CODEC_JP2;
1225     if (ibuf->foptions.flag & JP2_J2K) {
1226       format = OPJ_CODEC_J2K;
1227     }
1228     else if (ibuf->foptions.flag & JP2_JP2) {
1229       format = OPJ_CODEC_JP2;
1230     }
1231
1232     codec = opj_create_compress(format);
1233
1234     /* configure the event callbacks (not required) */
1235     opj_set_error_handler(codec, error_callback, stderr);
1236     opj_set_warning_handler(codec, warning_callback, stderr);
1237 #ifdef DEBUG /* too noisy */
1238     opj_set_info_handler(codec, info_callback, stderr);
1239 #endif
1240
1241     /* setup the encoder parameters using the current image and using user parameters */
1242     if (opj_setup_encoder(codec, &parameters, image) == false) {
1243       goto finally;
1244     }
1245
1246     if (opj_start_compress(codec, image, stream) == false) {
1247       goto finally;
1248     }
1249     if (opj_encode(codec, stream) == false) {
1250       goto finally;
1251     }
1252     if (opj_end_compress(codec, stream) == false) {
1253       goto finally;
1254     }
1255   }
1256
1257   ok = true;
1258
1259 finally:
1260   /* free remaining compression structures */
1261   if (codec) {
1262     opj_destroy_codec(codec);
1263   }
1264
1265   /* free image data */
1266   if (image) {
1267     opj_image_destroy(image);
1268   }
1269
1270   if (ok == false) {
1271     fprintf(stderr, "failed to encode image\n");
1272   }
1273
1274   return ok;
1275 }