c71edf569f2624b82941399a54b0d17e1e482b0b
[openjpeg.git] / libopenjpeg / j2k.c
1 /*
2  * Copyright (c) 2002-2007, Communications and Remote Sensing Laboratory, Universite catholique de Louvain (UCL), Belgium
3  * Copyright (c) 2002-2007, Professor Benoit Macq
4  * Copyright (c) 2001-2003, David Janssens
5  * Copyright (c) 2002-2003, Yannick Verschueren
6  * Copyright (c) 2003-2007, Francois-Olivier Devaux and Antonin Descampe
7  * Copyright (c) 2005, Herve Drolon, FreeImage Team
8  * Copyright (c) 2008, Jerome Fimes, Communications & Systemes <jerome.fimes@c-s.fr>
9  * Copyright (c) 2006-2007, Parvatha Elangovan
10  * Copyright (c) 2010-2011, Kaori Hagihara
11  * Copyright (c) 2011-2012, Mickael Savinaud, Communications & Systemes <mickael.savinaud@c-s.fr>
12  * All rights reserved.
13  *
14  * Redistribution and use in source and binary forms, with or without
15  * modification, are permitted provided that the following conditions
16  * are met:
17  * 1. Redistributions of source code must retain the above copyright
18  *    notice, this list of conditions and the following disclaimer.
19  * 2. Redistributions in binary form must reproduce the above copyright
20  *    notice, this list of conditions and the following disclaimer in the
21  *    documentation and/or other materials provided with the distribution.
22  *
23  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS `AS IS'
24  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26  * ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
27  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
28  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
29  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
30  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
31  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
32  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
33  * POSSIBILITY OF SUCH DAMAGE.
34  */
35
36 #include "opj_includes.h"
37
38 /** @defgroup J2K J2K - JPEG-2000 codestream reader/writer */
39 /*@{*/
40
41 /** @name Local static functions */
42 /*@{*/
43
44 /**
45  * Sets up the procedures to do on reading header. Developpers wanting to extend the library can add their own reading procedures.
46  */
47 void j2k_setup_header_reading (opj_j2k_v2_t *p_j2k);
48
49 /**
50  * The read header procedure.
51  */
52 static opj_bool j2k_read_header_procedure(  opj_j2k_v2_t *p_j2k,
53                                             opj_stream_private_t *p_stream,
54                                             opj_event_mgr_t * p_manager);
55
56 /**
57  * The default encoding validation procedure without any extension.
58  *
59  * @param       p_j2k                   the jpeg2000 codec to validate.
60  * @param       p_stream                the input stream to validate.
61  * @param       p_manager               the user event manager.
62  *
63  * @return true if the parameters are correct.
64  */
65 static opj_bool j2k_encoding_validation (   opj_j2k_v2_t * p_j2k,
66                                             opj_stream_private_t *p_stream,
67                                             opj_event_mgr_t * p_manager );
68
69 /**
70  * The default decoding validation procedure without any extension.
71  *
72  * @param       p_j2k                   the jpeg2000 codec to validate.
73  * @param       p_stream                                the input stream to validate.
74  * @param       p_manager               the user event manager.
75  *
76  * @return true if the parameters are correct.
77  */
78 static opj_bool j2k_decoding_validation (   opj_j2k_v2_t * p_j2k,
79                                             opj_stream_private_t *p_stream,
80                                             opj_event_mgr_t * p_manager );
81
82 /**
83  * Sets up the validation ,i.e. adds the procedures to lauch to make sure the codec parameters
84  * are valid. Developpers wanting to extend the library can add their own validation procedures.
85  */
86 static void j2k_setup_encoding_validation (opj_j2k_v2_t *p_j2k);
87
88 /**
89  * Sets up the validation ,i.e. adds the procedures to lauch to make sure the codec parameters
90  * are valid. Developpers wanting to extend the library can add their own validation procedures.
91  */
92 static void j2k_setup_decoding_validation (opj_j2k_v2_t *p_j2k);
93
94 /**
95  * Sets up the validation ,i.e. adds the procedures to lauch to make sure the codec parameters
96  * are valid. Developpers wanting to extend the library can add their own validation procedures.
97  */
98 static void j2k_setup_end_compress (opj_j2k_v2_t *p_j2k);
99
100 /**
101  * The mct encoding validation procedure.
102  *
103  * @param       p_j2k                   the jpeg2000 codec to validate.
104  * @param       p_stream                                the input stream to validate.
105  * @param       p_manager               the user event manager.
106  *
107  * @return true if the parameters are correct.
108  */
109 static opj_bool j2k_mct_validation (opj_j2k_v2_t * p_j2k,
110                                     opj_stream_private_t *p_stream,
111                                     opj_event_mgr_t * p_manager );
112
113 /**
114  * Builds the tcd decoder to use to decode tile.
115  */
116 static opj_bool j2k_build_decoder ( opj_j2k_v2_t * p_j2k,
117                                     opj_stream_private_t *p_stream,
118                                     opj_event_mgr_t * p_manager );
119 /**
120  * Builds the tcd encoder to use to encode tile.
121  */
122 static opj_bool j2k_build_encoder ( opj_j2k_v2_t * p_j2k,
123                                     opj_stream_private_t *p_stream,
124                                     opj_event_mgr_t * p_manager );
125
126 /**
127  * Creates a tile-coder decoder.
128  *
129  * @param       p_stream                        the stream to write data to.
130  * @param       p_j2k                           J2K codec.
131  * @param       p_manager                   the user event manager.
132 */
133 static opj_bool j2k_create_tcd( opj_j2k_v2_t *p_j2k,
134                                                                 struct opj_stream_private *p_stream,
135                                                                 struct opj_event_mgr * p_manager );
136
137 /**
138  * Excutes the given procedures on the given codec.
139  *
140  * @param       p_procedure_list        the list of procedures to execute
141  * @param       p_j2k                           the jpeg2000 codec to execute the procedures on.
142  * @param       p_stream                        the stream to execute the procedures on.
143  * @param       p_manager                       the user manager.
144  *
145  * @return      true                            if all the procedures were successfully executed.
146  */
147 static opj_bool j2k_exec (  opj_j2k_v2_t * p_j2k,
148                             opj_procedure_list_t * p_procedure_list,
149                             opj_stream_private_t *p_stream,
150                             opj_event_mgr_t * p_manager);
151
152 /**
153  * Updates the rates of the tcp.
154  *
155  * @param       p_stream                                the stream to write data to.
156  * @param       p_j2k                           J2K codec.
157  * @param       p_manager               the user event manager.
158 */
159 static opj_bool j2k_update_rates(       opj_j2k_v2_t *p_j2k,
160                                                                         opj_stream_private_t *p_stream,
161                                                                         opj_event_mgr_t * p_manager );
162
163 /**
164  * Copies the decoding tile parameters onto all the tile parameters.
165  * Creates also the tile decoder.
166  */
167 static opj_bool j2k_copy_default_tcp_and_create_tcd (   opj_j2k_v2_t * p_j2k,
168                                                         opj_stream_private_t *p_stream,
169                                                         opj_event_mgr_t * p_manager );
170
171 /**
172  * Destroys the memory associated with the decoding of headers.
173  */
174 static opj_bool j2k_destroy_header_memory ( opj_j2k_v2_t * p_j2k,
175                                             opj_stream_private_t *p_stream,
176                                             opj_event_mgr_t * p_manager );
177
178 /**
179  * Reads the lookup table containing all the marker, status and action, and returns the handler associated
180  * with the marker value.
181  * @param       p_id            Marker value to look up
182  *
183  * @return      the handler associated with the id.
184 */
185 static const struct opj_dec_memory_marker_handler * j2k_get_marker_handler (OPJ_UINT32 p_id);
186
187 /**
188  * Destroys a tile coding parameter structure.
189  *
190  * @param       p_tcp           the tile coding parameter to destroy.
191  */
192 static void j2k_tcp_destroy (opj_tcp_v2_t *p_tcp);
193
194 /**
195  * Destroys the data inside a tile coding parameter structure.
196  *
197  * @param       p_tcp           the tile coding parameter which contain data to destroy.
198  */
199 static void j2k_tcp_data_destroy (opj_tcp_v2_t *p_tcp);
200
201 /**
202  * Destroys a coding parameter structure.
203  *
204  * @param       p_cp            the coding parameter to destroy.
205  */
206 static void j2k_cp_destroy (opj_cp_v2_t *p_cp);
207
208
209 /**
210  * Writes a SPCod or SPCoc element, i.e. the coding style of a given component of a tile.
211  *
212  * @param       p_comp_no       the component number to output.
213  * @param       p_stream                        the stream to write data to.
214  * @param       p_j2k                   J2K codec.
215  * @param       p_manager       the user event manager.
216  *
217 */
218 static opj_bool j2k_write_SPCod_SPCoc(  opj_j2k_v2_t *p_j2k,
219                                                                                 OPJ_UINT32 p_tile_no,
220                                                                                 OPJ_UINT32 p_comp_no,
221                                                                                 OPJ_BYTE * p_data,
222                                                                                 OPJ_UINT32 * p_header_size,
223                                                                                 struct opj_event_mgr * p_manager );
224
225 /**
226  * Gets the size taken by writing a SPCod or SPCoc for the given tile and component.
227  *
228  * @param       p_tile_no               the tile index.
229  * @param       p_comp_no               the component being outputted.
230  * @param       p_j2k                   the J2K codec.
231  *
232  * @return      the number of bytes taken by the SPCod element.
233  */
234 static OPJ_UINT32 j2k_get_SPCod_SPCoc_size (opj_j2k_v2_t *p_j2k,
235                                                                                         OPJ_UINT32 p_tile_no,
236                                                                                         OPJ_UINT32 p_comp_no );
237
238 /**
239  * Reads a SPCod or SPCoc element, i.e. the coding style of a given component of a tile.
240  * @param       p_header_data   the data contained in the COM box.
241  * @param       p_j2k                   the jpeg2000 codec.
242  * @param       p_header_size   the size of the data contained in the COM marker.
243  * @param       p_manager               the user event manager.
244 */
245 static opj_bool j2k_read_SPCod_SPCoc(   opj_j2k_v2_t *p_j2k,
246                                         OPJ_UINT32 compno,
247                                         OPJ_BYTE * p_header_data,
248                                         OPJ_UINT32 * p_header_size,
249                                         opj_event_mgr_t * p_manager );
250
251 /**
252  * Gets the size taken by writing SQcd or SQcc element, i.e. the quantization values of a band in the QCD or QCC.
253  *
254  * @param       p_tile_no               the tile index.
255  * @param       p_comp_no               the component being outputted.
256  * @param       p_j2k                   the J2K codec.
257  *
258  * @return      the number of bytes taken by the SPCod element.
259  */
260 static OPJ_UINT32 j2k_get_SQcd_SQcc_size (      opj_j2k_v2_t *p_j2k,
261                                                                                 OPJ_UINT32 p_tile_no,
262                                                                                 OPJ_UINT32 p_comp_no );
263
264 /**
265  * Writes a SQcd or SQcc element, i.e. the quantization values of a band in the QCD or QCC.
266  *
267  * @param       p_tile_no               the tile to output.
268  * @param       p_comp_no               the component number to output.
269  * @param       p_data                  the data buffer.
270  * @param       p_header_size   pointer to the size of the data buffer, it is changed by the function.
271  * @param       p_j2k                   J2K codec.
272  * @param       p_manager               the user event manager.
273  *
274 */
275 static opj_bool j2k_write_SQcd_SQcc(opj_j2k_v2_t *p_j2k,
276                                                                         OPJ_UINT32 p_tile_no,
277                                                                         OPJ_UINT32 p_comp_no,
278                                                                         OPJ_BYTE * p_data,
279                                                                         OPJ_UINT32 * p_header_size,
280                                                                         opj_event_mgr_t * p_manager);
281
282 /**
283  * Updates the Tile Length Marker.
284  */
285 static void j2k_update_tlm ( opj_j2k_v2_t * p_j2k, OPJ_UINT32 p_tile_part_size);
286
287 /**
288  * Reads a SQcd or SQcc element, i.e. the quantization values of a band in the QCD or QCC.
289  *
290  * @param       p_tile_no               the tile to output.
291  * @param       p_comp_no               the component number to output.
292  * @param       p_data                  the data buffer.
293  * @param       p_header_size   pointer to the size of the data buffer, it is changed by the function.
294  * @param       p_j2k                           J2K codec.
295  * @param       p_manager               the user event manager.
296  *
297 */
298 static opj_bool j2k_read_SQcd_SQcc( opj_j2k_v2_t *p_j2k,
299                                     OPJ_UINT32 compno,
300                                     OPJ_BYTE * p_header_data,
301                                     OPJ_UINT32 * p_header_size,
302                                     opj_event_mgr_t * p_manager );
303
304 /**
305  * Copies the tile component parameters of all the component from the first tile component.
306  *
307  * @param               p_j2k           the J2k codec.
308  */
309 static void j2k_copy_tile_component_parameters( opj_j2k_v2_t *p_j2k );
310
311 /**
312  * Copies the tile quantization parameters of all the component from the first tile component.
313  *
314  * @param               p_j2k           the J2k codec.
315  */
316 static void j2k_copy_tile_quantization_parameters( opj_j2k_v2_t *p_j2k );
317
318 /**
319  * Reads the tiles.
320  */
321 static opj_bool j2k_decode_tiles (      opj_j2k_v2_t *p_j2k,
322                                     opj_stream_private_t *p_stream,
323                                     opj_event_mgr_t * p_manager);
324
325
326 static opj_bool j2k_pre_write_tile ( opj_j2k_v2_t * p_j2k,
327                                                                          OPJ_UINT32 p_tile_index,
328                                                                          opj_stream_private_t *p_stream,
329                                                                          opj_event_mgr_t * p_manager );
330
331 static opj_bool j2k_update_image_data (opj_tcd_v2_t * p_tcd, OPJ_BYTE * p_data, opj_image_t* p_output_image);
332
333 static void j2k_get_tile_data (opj_tcd_v2_t * p_tcd, OPJ_BYTE * p_data);
334
335 static opj_bool j2k_post_write_tile (opj_j2k_v2_t * p_j2k,
336                                                                          OPJ_BYTE * p_data,
337                                                                          OPJ_UINT32 p_data_size,
338                                                                          opj_stream_private_t *p_stream,
339                                                                          opj_event_mgr_t * p_manager );
340
341 /**
342  * Sets up the procedures to do on writing header.
343  * Developers wanting to extend the library can add their own writing procedures.
344  */
345 static void j2k_setup_header_writting (opj_j2k_v2_t *p_j2k);
346
347 static opj_bool j2k_write_first_tile_part(      opj_j2k_v2_t *p_j2k,
348                                                                                         OPJ_BYTE * p_data,
349                                                                                         OPJ_UINT32 * p_data_written,
350                                                                                         OPJ_UINT32 p_total_data_size,
351                                                                                         opj_stream_private_t *p_stream,
352                                                                                         struct opj_event_mgr * p_manager );
353
354 static opj_bool j2k_write_all_tile_parts(       opj_j2k_v2_t *p_j2k,
355                                                                                         OPJ_BYTE * p_data,
356                                                                                         OPJ_UINT32 * p_data_written,
357                                                                                         OPJ_UINT32 p_total_data_size,
358                                                                                         opj_stream_private_t *p_stream,
359                                                                                         struct opj_event_mgr * p_manager );
360
361 /**
362  * Gets the offset of the header.
363  *
364  * @param       p_stream                the stream to write data to.
365  * @param       p_j2k                   J2K codec.
366  * @param       p_manager               the user event manager.
367 */
368 static opj_bool j2k_get_end_header(     opj_j2k_v2_t *p_j2k,
369                                                                         struct opj_stream_private *p_stream,
370                                                                         struct opj_event_mgr * p_manager );
371
372 static opj_bool j2k_allocate_tile_element_cstr_index(opj_j2k_v2_t *p_j2k);
373
374 /*
375  * -----------------------------------------------------------------------
376  * -----------------------------------------------------------------------
377  * -----------------------------------------------------------------------
378  */
379
380 /**
381 Write the SOC marker (Start Of Codestream)
382 @param j2k J2K handle
383 */
384 static void j2k_write_soc(opj_j2k_t *j2k);
385
386 /**
387  * Writes the SOC marker (Start Of Codestream)
388  *
389  * @param       p_stream                        the stream to write data to.
390  * @param       p_j2k                   J2K codec.
391  * @param       p_manager       the user event manager.
392 */
393 static opj_bool j2k_write_soc_v2(       opj_j2k_v2_t *p_j2k,
394                                                                         struct opj_stream_private *p_stream,
395                                                                         struct opj_event_mgr * p_manager );
396
397 /**
398  * Reads a SOC marker (Start of Codestream)
399  * @param       p_header_data   the data contained in the SOC box.
400  * @param       jp2                             the jpeg2000 file codec.
401  * @param       p_header_size   the size of the data contained in the SOC marker.
402  * @param       p_manager               the user event manager.
403 */
404 static opj_bool opj_j2k_read_soc(
405                                         opj_j2k_v2_t *p_j2k,
406                                         struct opj_stream_private *p_stream,
407                                         struct opj_event_mgr * p_manager
408                                  );
409
410 /**
411 Write the SIZ marker (image and tile size)
412 @param j2k J2K handle
413 */
414 static void j2k_write_siz(opj_j2k_t *j2k);
415
416 /**
417  * Writes the SIZ marker (image and tile size)
418  *
419  * @param       p_stream                        the stream to write data to.
420  * @param       p_j2k                   J2K codec.
421  * @param       p_manager       the user event manager.
422 */
423 static opj_bool j2k_write_siz_v2(       opj_j2k_v2_t *p_j2k,
424                                                                         struct opj_stream_private *p_stream,
425                                                                         struct opj_event_mgr * p_manager );
426
427 /**
428  * Reads a SIZ marker (image and tile size)
429  * @param       p_header_data   the data contained in the SIZ box.
430  * @param       jp2                             the jpeg2000 file codec.
431  * @param       p_header_size   the size of the data contained in the SIZ marker.
432  * @param       p_manager               the user event manager.
433 */
434 static opj_bool opj_j2k_read_siz(opj_j2k_v2_t *p_j2k,
435                                  OPJ_BYTE * p_header_data,
436                                  OPJ_UINT32 p_header_size,
437                                  opj_event_mgr_t * p_manager);
438
439 /**
440 Write the COM marker (comment)
441 @param j2k J2K handle
442 */
443 static void j2k_write_com(opj_j2k_t *j2k);
444
445 /**
446  * Writes the COM marker (comment)
447  * 
448  * @param       p_stream                        the stream to write data to.
449  * @param       p_j2k                   J2K codec.
450  * @param       p_manager       the user event manager.
451 */
452 static opj_bool j2k_write_com_v2(       opj_j2k_v2_t *p_j2k,
453                                                                         struct opj_stream_private *p_stream,
454                                                                         struct opj_event_mgr * p_manager );
455
456 /**
457  * Reads a COM marker (comments)
458  * @param       p_header_data   the data contained in the COM box.
459  * @param       jp2                             the jpeg2000 file codec.
460  * @param       p_header_size   the size of the data contained in the COM marker.
461  * @param       p_manager               the user event manager.
462 */
463 static opj_bool j2k_read_com_v2 (
464                                         opj_j2k_v2_t *p_j2k,
465                                         OPJ_BYTE * p_header_data,
466                                         OPJ_UINT32 p_header_size,
467                                         struct opj_event_mgr * p_manager
468                                         );
469 /**
470 Write the value concerning the specified component in the marker COD and COC
471 @param j2k J2K handle
472 @param compno Number of the component concerned by the information written
473 */
474 static void j2k_write_cox(opj_j2k_t *j2k, int compno);
475
476 /**
477 Write the COD marker (coding style default)
478 @param j2k J2K handle
479 */
480 static void j2k_write_cod(opj_j2k_t *j2k);
481
482 /**
483  * Writes the COD marker (Coding style default)
484  *
485  * @param       p_stream                        the stream to write data to.
486  * @param       p_j2k                   J2K codec.
487  * @param       p_manager       the user event manager.
488 */
489 static opj_bool j2k_write_cod_v2(       opj_j2k_v2_t *p_j2k,
490                                                                         struct opj_stream_private *p_stream,
491                                                                         struct opj_event_mgr * p_manager );
492
493 /**
494  * Reads a COD marker (Coding Styke defaults)
495  * @param       p_header_data   the data contained in the COD box.
496  * @param       p_j2k                   the jpeg2000 codec.
497  * @param       p_header_size   the size of the data contained in the COD marker.
498  * @param       p_manager               the user event manager.
499 */
500 static opj_bool opj_j2k_read_cod (  opj_j2k_v2_t *p_j2k,
501                                     OPJ_BYTE * p_header_data,
502                                     OPJ_UINT32 p_header_size,
503                                     opj_event_mgr_t * p_manager);
504
505 /**
506 Write the COC marker (coding style component)
507 @param j2k J2K handle
508 @param compno Number of the component concerned by the information written
509 */
510 static void j2k_write_coc(opj_j2k_t *j2k, int compno);
511
512 /**
513  * Writes the COC marker (Coding style component)
514  *
515  * @param       p_comp_number   the index of the component to output.
516  * @param       p_stream                                the stream to write data to.
517  * @param       p_j2k                           J2K codec.
518  * @param       p_manager               the user event manager.
519 */
520 static opj_bool j2k_write_coc_v2( opj_j2k_v2_t *p_j2k,
521                                                         OPJ_UINT32 p_comp_number,
522                                                         struct opj_stream_private *p_stream,
523                                                         struct opj_event_mgr * p_manager
524                                                   );
525 /**
526  * Writes the COC marker (Coding style component)
527  *
528  * @param       p_comp_no               the index of the component to output.
529  * @param       p_stream                the stream to write data to.
530  * @param       p_j2k                   J2K codec.
531  * @param       p_manager               the user event manager.
532 */
533 static void j2k_write_coc_in_memory(opj_j2k_v2_t *p_j2k,
534                                                                         OPJ_UINT32 p_comp_no,
535                                                                         OPJ_BYTE * p_data,
536                                                                         OPJ_UINT32 * p_data_written,
537                                                                         struct opj_event_mgr * p_manager );
538
539 /**
540  * Gets the maximum size taken by a coc.
541  *
542  * @param       p_j2k   the jpeg2000 codec to use.
543  */
544 static OPJ_UINT32 j2k_get_max_coc_size(opj_j2k_v2_t *p_j2k);
545
546
547 /**
548  * Reads a COC marker (Coding Style Component)
549  * @param       p_header_data   the data contained in the COC box.
550  * @param       p_j2k                   the jpeg2000 codec.
551  * @param       p_header_size   the size of the data contained in the COC marker.
552  * @param       p_manager               the user event manager.
553 */
554 static opj_bool opj_j2k_read_coc (  opj_j2k_v2_t *p_j2k,
555                                     OPJ_BYTE * p_header_data,
556                                     OPJ_UINT32 p_header_size,
557                                     opj_event_mgr_t * p_manager );
558
559 /**
560 Write the value concerning the specified component in the marker QCD and QCC
561 @param j2k J2K handle
562 @param compno Number of the component concerned by the information written
563 */
564 static void j2k_write_qcx(opj_j2k_t *j2k, int compno);
565
566 /**
567 Write the QCD marker (quantization default)
568 @param j2k J2K handle
569 */
570 static void j2k_write_qcd(opj_j2k_t *j2k);
571
572 /**
573  * Writes the QCD marker (quantization default)
574  *
575  * @param       p_comp_number   the index of the component to output.
576  * @param       p_stream                the stream to write data to.
577  * @param       p_j2k                   J2K codec.
578  * @param       p_manager               the user event manager.
579 */
580 static opj_bool j2k_write_qcd_v2(       opj_j2k_v2_t *p_j2k,
581                                                                         struct opj_stream_private *p_stream,
582                                                                         struct opj_event_mgr * p_manager );
583
584 /**
585  * Reads a QCD marker (Quantization defaults)
586  * @param       p_header_data   the data contained in the QCD box.
587  * @param       p_j2k                   the jpeg2000 codec.
588  * @param       p_header_size   the size of the data contained in the QCD marker.
589  * @param       p_manager               the user event manager.
590 */
591 static opj_bool opj_j2k_read_qcd (  opj_j2k_v2_t *p_j2k,
592                                     OPJ_BYTE * p_header_data,
593                                     OPJ_UINT32 p_header_size,
594                                     opj_event_mgr_t * p_manager );
595
596 /**
597 Write the QCC marker (quantization component)
598 @param j2k J2K handle
599 @param compno Number of the component concerned by the information written
600 */
601 static void j2k_write_qcc(opj_j2k_t *j2k, int compno);
602
603 /**
604  * Writes the QCC marker (quantization component)
605  *
606  * @param       p_comp_no       the index of the component to output.
607  * @param       p_stream                the stream to write data to.
608  * @param       p_j2k                   J2K codec.
609  * @param       p_manager               the user event manager.
610 */
611 static opj_bool j2k_write_qcc_v2(       opj_j2k_v2_t *p_j2k,
612                                                                         OPJ_UINT32 p_comp_no,
613                                                                         struct opj_stream_private *p_stream,
614                                                                         struct opj_event_mgr * p_manager );
615
616 /**
617  * Writes the QCC marker (quantization component)
618  *
619  * @param       p_comp_no       the index of the component to output.
620  * @param       p_stream                the stream to write data to.
621  * @param       p_j2k                   J2K codec.
622  * @param       p_manager               the user event manager.
623 */
624 static void j2k_write_qcc_in_memory(opj_j2k_v2_t *p_j2k,
625                                                                         OPJ_UINT32 p_comp_no,
626                                                                         OPJ_BYTE * p_data,
627                                                                         OPJ_UINT32 * p_data_written,
628                                                                         struct opj_event_mgr * p_manager );
629
630 /**
631  * Gets the maximum size taken by a qcc.
632  */
633 static OPJ_UINT32 j2k_get_max_qcc_size (opj_j2k_v2_t *p_j2k);
634
635 /**
636  * Reads a QCC marker (Quantization component)
637  * @param       p_header_data   the data contained in the QCC box.
638  * @param       p_j2k                   the jpeg2000 codec.
639  * @param       p_header_size   the size of the data contained in the QCC marker.
640  * @param       p_manager               the user event manager.
641 */
642 static opj_bool opj_j2k_read_qcc(   opj_j2k_v2_t *p_j2k,
643                                     OPJ_BYTE * p_header_data,
644                                     OPJ_UINT32 p_header_size,
645                                     opj_event_mgr_t * p_manager);
646
647 /**
648 Write the POC marker (progression order change)
649 @param j2k J2K handle
650 */
651 static void j2k_write_poc(opj_j2k_t *j2k);
652
653 /**
654  * Writes the POC marker (Progression Order Change)
655  * 
656  * @param       p_stream                                the stream to write data to.
657  * @param       p_j2k                           J2K codec.
658  * @param       p_manager               the user event manager.
659 */
660 static opj_bool j2k_write_poc_v2(       opj_j2k_v2_t *p_j2k,
661                                                                         struct opj_stream_private *p_stream,
662                                                                         struct opj_event_mgr * p_manager );
663
664 /**
665  * Writes the POC marker (Progression Order Change)
666  *
667  * @param       p_stream                the stream to write data to.
668  * @param       p_j2k                   J2K codec.
669  * @param       p_manager               the user event manager.
670  */
671 static void j2k_write_poc_in_memory(opj_j2k_v2_t *p_j2k,
672                                                                         OPJ_BYTE * p_data,
673                                                                         OPJ_UINT32 * p_data_written,
674                                                                         struct opj_event_mgr * p_manager );
675
676 /**
677  * Gets the maximum size taken by the writting of a POC.
678  */
679 static OPJ_UINT32 j2k_get_max_poc_size(opj_j2k_v2_t *p_j2k);
680
681 /**
682  * Gets the maximum size taken by the toc headers of all the tile parts of any given tile.
683  */
684 static OPJ_UINT32 j2k_get_max_toc_size (opj_j2k_v2_t *p_j2k);
685
686 /**
687  * Gets the maximum size taken by the headers of the SOT.
688  *
689  * @param       p_j2k   the jpeg2000 codec to use.
690  */
691 static OPJ_UINT32 j2k_get_specific_header_sizes(opj_j2k_v2_t *p_j2k);
692
693 /**
694  * Reads a POC marker (Progression Order Change)
695  *
696  * @param       p_header_data   the data contained in the POC box.
697  * @param       p_j2k                   the jpeg2000 codec.
698  * @param       p_header_size   the size of the data contained in the POC marker.
699  * @param       p_manager               the user event manager.
700 */
701 static opj_bool opj_j2k_read_poc (  opj_j2k_v2_t *p_j2k,
702                                     OPJ_BYTE * p_header_data,
703                                     OPJ_UINT32 p_header_size,
704                                     opj_event_mgr_t * p_manager );
705
706 /**
707  * Reads a CRG marker (Component registration)
708  *
709  * @param       p_header_data   the data contained in the TLM box.
710  * @param       p_j2k                   the jpeg2000 codec.
711  * @param       p_header_size   the size of the data contained in the TLM marker.
712  * @param       p_manager               the user event manager.
713 */
714 static opj_bool opj_j2k_read_crg (  opj_j2k_v2_t *p_j2k,
715                                     OPJ_BYTE * p_header_data,
716                                     OPJ_UINT32 p_header_size,
717                                     opj_event_mgr_t * p_manager );
718 /**
719  * Reads a TLM marker (Tile Length Marker)
720  *
721  * @param       p_header_data   the data contained in the TLM box.
722  * @param       p_j2k                   the jpeg2000 codec.
723  * @param       p_header_size   the size of the data contained in the TLM marker.
724  * @param       p_manager               the user event manager.
725 */
726 static opj_bool opj_j2k_read_tlm (  opj_j2k_v2_t *p_j2k,
727                                     OPJ_BYTE * p_header_data,
728                                     OPJ_UINT32 p_header_size,
729                                     opj_event_mgr_t * p_manager);
730
731 /**
732  * Writes the updated tlm.
733  *
734  * @param       p_stream                the stream to write data to.
735  * @param       p_j2k                   J2K codec.
736  * @param       p_manager               the user event manager.
737 */
738 static opj_bool j2k_write_updated_tlm(  opj_j2k_v2_t *p_j2k,
739                                                                                 struct opj_stream_private *p_stream,
740                                                                                 struct opj_event_mgr * p_manager );
741
742 /**
743  * Reads a PLM marker (Packet length, main header marker)
744  *
745  * @param       p_header_data   the data contained in the TLM box.
746  * @param       p_j2k                   the jpeg2000 codec.
747  * @param       p_header_size   the size of the data contained in the TLM marker.
748  * @param       p_manager               the user event manager.
749 */
750 static opj_bool opj_j2k_read_plm (  opj_j2k_v2_t *p_j2k,
751                                     OPJ_BYTE * p_header_data,
752                                     OPJ_UINT32 p_header_size,
753                                     opj_event_mgr_t * p_manager);
754 /**
755  * Reads a PLT marker (Packet length, tile-part header)
756  *
757  * @param       p_header_data   the data contained in the PLT box.
758  * @param       p_j2k                   the jpeg2000 codec.
759  * @param       p_header_size   the size of the data contained in the PLT marker.
760  * @param       p_manager               the user event manager.
761 */
762 static opj_bool opj_j2k_read_plt (  opj_j2k_v2_t *p_j2k,
763                                     OPJ_BYTE * p_header_data,
764                                     OPJ_UINT32 p_header_size,
765                                     opj_event_mgr_t * p_manager );
766
767
768 /**
769  * Reads a PPM marker (Packed packet headers, main header)
770  *
771  * @param       p_header_data   the data contained in the POC box.
772  * @param       p_j2k                   the jpeg2000 codec.
773  * @param       p_header_size   the size of the data contained in the POC marker.
774  * @param       p_manager               the user event manager.
775 */
776 #if 0
777 static opj_bool j2k_read_ppm_v2 (
778                                                 opj_j2k_v2_t *p_j2k,
779                                                 OPJ_BYTE * p_header_data,
780                                                 OPJ_UINT32 p_header_size,
781                                                 struct opj_event_mgr * p_manager
782                                         );
783 #endif
784
785 static opj_bool j2k_read_ppm_v3 (
786                                                 opj_j2k_v2_t *p_j2k,
787                                                 OPJ_BYTE * p_header_data,
788                                                 OPJ_UINT32 p_header_size,
789                                                 struct opj_event_mgr * p_manager
790                                         );
791
792
793 /**
794  * Reads a PPT marker (Packed packet headers, tile-part header)
795  *
796  * @param       p_header_data   the data contained in the PPT box.
797  * @param       p_j2k                   the jpeg2000 codec.
798  * @param       p_header_size   the size of the data contained in the PPT marker.
799  * @param       p_manager               the user event manager.
800 */
801 static opj_bool opj_j2k_read_ppt (  opj_j2k_v2_t *p_j2k,
802                                     OPJ_BYTE * p_header_data,
803                                     OPJ_UINT32 p_header_size,
804                                     opj_event_mgr_t * p_manager );
805 /**
806 Write the TLM marker (Mainheader)
807 @param j2k J2K handle
808 */
809 static void j2k_write_tlm(opj_j2k_t *j2k);
810
811 /**
812  * Writes the TLM marker (Tile Length Marker)
813  * 
814  * @param       p_stream                                the stream to write data to.
815  * @param       p_j2k                           J2K codec.
816  * @param       p_manager               the user event manager.
817 */
818 static opj_bool j2k_write_tlm_v2(       opj_j2k_v2_t *p_j2k,
819                                                                         struct opj_stream_private *p_stream,
820                                                                         struct opj_event_mgr * p_manager );
821
822 /**
823 Write the SOT marker (start of tile-part)
824 @param j2k J2K handle
825 */
826 static void j2k_write_sot(opj_j2k_t *j2k);
827
828 /**
829  * Writes the SOT marker (Start of tile-part)
830  *
831  * @param       p_stream                the stream to write data to.
832  * @param       p_j2k                   J2K codec.
833  * @param       p_manager               the user event manager.
834 */
835 static opj_bool j2k_write_sot_v2(       opj_j2k_v2_t *p_j2k,
836                                                                         OPJ_BYTE * p_data,
837                                                                         OPJ_UINT32 * p_data_written,
838                                                                         const struct opj_stream_private *p_stream,
839                                                                         struct opj_event_mgr * p_manager );
840
841 /**
842  * Reads a PPT marker (Packed packet headers, tile-part header)
843  *
844  * @param       p_header_data   the data contained in the PPT box.
845  * @param       p_j2k                   the jpeg2000 codec.
846  * @param       p_header_size   the size of the data contained in the PPT marker.
847  * @param       p_manager               the user event manager.
848 */
849 static opj_bool opj_j2k_read_sot (  opj_j2k_v2_t *p_j2k,
850                                     OPJ_BYTE * p_header_data,
851                                     OPJ_UINT32 p_header_size,
852                                     opj_event_mgr_t * p_manager );
853
854 /**
855 Write the SOD marker (start of data)
856 @param j2k J2K handle
857 @param tile_coder Pointer to a TCD handle
858 */
859 static void j2k_write_sod(opj_j2k_t *j2k, void *tile_coder);
860
861 /**
862  * Writes the SOD marker (Start of data)
863  *
864  * @param       p_stream                                the stream to write data to.
865  * @param       p_j2k                           J2K codec.
866  * @param       p_manager               the user event manager.
867 */
868 static opj_bool j2k_write_sod_v2(       opj_j2k_v2_t *p_j2k,
869                                                                         struct opj_tcd_v2 * p_tile_coder,
870                                                                         OPJ_BYTE * p_data,
871                                                                         OPJ_UINT32 * p_data_written,
872                                                                         OPJ_UINT32 p_total_data_size,
873                                                                         const struct opj_stream_private *p_stream,
874                                                                         struct opj_event_mgr * p_manager );
875
876 /**
877  * Reads a SOD marker (Start Of Data)
878  *
879  * @param       p_header_data   the data contained in the SOD box.
880  * @param       p_j2k                   the jpeg2000 codec.
881  * @param       p_header_size   the size of the data contained in the SOD marker.
882  * @param       p_manager               the user event manager.
883 */
884 static opj_bool opj_j2k_read_sod(   opj_j2k_v2_t *p_j2k,
885                                     opj_stream_private_t *p_stream,
886                                     opj_event_mgr_t * p_manager );
887
888 /**
889  * Updates the Tile Length Marker.
890  */
891 void j2k_update_tlm (opj_j2k_v2_t * p_j2k, OPJ_UINT32 p_tile_part_size )
892 {
893         opj_write_bytes(p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_current,p_j2k->m_current_tile_number,1);                                    /* PSOT */
894         ++p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_current;
895
896         opj_write_bytes(p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_current,p_tile_part_size,4);                                        /* PSOT */
897         p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_current += 4;
898 }
899
900 /**
901 Write the RGN marker (region-of-interest)
902 @param j2k J2K handle
903 @param compno Number of the component concerned by the information written
904 @param tileno Number of the tile concerned by the information written
905 */
906 static void j2k_write_rgn(opj_j2k_t *j2k, int compno, int tileno);
907
908 /**
909  * Writes the RGN marker (Region Of Interest)
910  *
911  * @param       p_tile_no               the tile to output
912  * @param       p_comp_no               the component to output
913  * @param       p_stream                                the stream to write data to.
914  * @param       p_j2k                           J2K codec.
915  * @param       p_manager               the user event manager.
916 */
917 static opj_bool j2k_write_rgn_v2(       opj_j2k_v2_t *p_j2k,
918                                                                         OPJ_UINT32 p_tile_no,
919                                                                         OPJ_UINT32 p_comp_no,
920                                                                         struct opj_stream_private *p_stream,
921                                                                         struct opj_event_mgr * p_manager );
922
923 /**
924  * Reads a RGN marker (Region Of Interest)
925  *
926  * @param       p_header_data   the data contained in the POC box.
927  * @param       p_j2k                   the jpeg2000 codec.
928  * @param       p_header_size   the size of the data contained in the POC marker.
929  * @param       p_manager               the user event manager.
930 */
931 static opj_bool opj_j2k_read_rgn (opj_j2k_v2_t *p_j2k,
932                                   OPJ_BYTE * p_header_data,
933                                   OPJ_UINT32 p_header_size,
934                                   opj_event_mgr_t * p_manager );
935
936 /**
937  * Writes the EOC marker (End of Codestream)
938  * 
939  * @param       p_stream                the stream to write data to.
940  * @param       p_j2k                   J2K codec.
941  * @param       p_manager               the user event manager.
942 */
943 static opj_bool j2k_write_eoc_v2(       opj_j2k_v2_t *p_j2k,
944                                                                         struct opj_stream_private *p_stream,
945                                                                         struct opj_event_mgr * p_manager );
946
947 /**
948 Write the EOC marker (end of codestream)
949 @param j2k J2K handle
950 */
951 static void j2k_write_eoc(opj_j2k_t *j2k);
952 /**
953 Read the EOC marker (end of codestream)
954 @param j2k J2K handle
955 */
956 static void j2k_read_eoc(opj_j2k_t *j2k);
957
958 /**
959  * Reads a EOC marker (End Of Codestream)
960  *
961  * @param       p_header_data   the data contained in the SOD box.
962  * @param       p_j2k                   the jpeg2000 codec.
963  * @param       p_header_size   the size of the data contained in the SOD marker.
964  * @param       p_manager               the user event manager.
965 */
966 #if 0
967 static opj_bool j2k_read_eoc_v2 (
968                                             opj_j2k_v2_t *p_j2k,
969                                                 struct opj_stream_private *p_stream,
970                                                 struct opj_event_mgr * p_manager
971                                         ) ;
972 #endif
973
974
975
976 /**
977  * Writes the CBD-MCT-MCC-MCO markers (Multi components transform)
978  *
979  * @param       p_stream                        the stream to write data to.
980  * @param       p_j2k                   J2K codec.
981  * @param       p_manager       the user event manager.
982 */
983 static opj_bool j2k_write_mct_data_group(       opj_j2k_v2_t *p_j2k,
984                                                                                         struct opj_stream_private *p_stream,
985                                                                                         struct opj_event_mgr * p_manager );
986
987 /**
988  * Inits the Info
989  *
990  * @param       p_stream                the stream to write data to.
991  * @param       p_j2k                   J2K codec.
992  * @param       p_manager               the user event manager.
993 */
994 static opj_bool j2k_init_info(  opj_j2k_v2_t *p_j2k,
995                                                                 struct opj_stream_private *p_stream,
996                                                                 struct opj_event_mgr * p_manager );
997
998 /**
999 Read an unknown marker
1000 @param j2k J2K handle
1001 */
1002 static void j2k_read_unk(opj_j2k_t *j2k);
1003 /**
1004 Add main header marker information
1005 @param cstr_info Codestream information structure
1006 @param type marker type
1007 @param pos byte offset of marker segment
1008 @param len length of marker segment
1009  */
1010 static void j2k_add_mhmarker(opj_codestream_info_t *cstr_info, unsigned short int type, int pos, int len);
1011
1012 static void j2k_add_mhmarker_v2(opj_codestream_index_t *cstr_index, OPJ_UINT32 type, OPJ_OFF_T pos, OPJ_UINT32 len) ;
1013 /**
1014 Add tile header marker information
1015 @param tileno tile index number
1016 @param cstr_info Codestream information structure
1017 @param type marker type
1018 @param pos byte offset of marker segment
1019 @param len length of marker segment
1020  */
1021 static void j2k_add_tlmarker( int tileno, opj_codestream_info_t *cstr_info, unsigned short int type, int pos, int len);
1022
1023 static void j2k_add_tlmarker_v2(OPJ_UINT32 tileno, opj_codestream_index_t *cstr_index, OPJ_UINT32 type, OPJ_OFF_T pos, OPJ_UINT32 len);
1024
1025 /**
1026  * Reads an unknown marker
1027  *
1028  * @param       p_stream                the stream object to read from.
1029  * @param       p_j2k                   the jpeg2000 codec.
1030  * @param       p_manager               the user event manager.
1031  *
1032  * @return      true                    if the marker could be deduced.
1033 */
1034 static opj_bool j2k_read_unk_v2 (       opj_j2k_v2_t *p_j2k,
1035                                                                         struct opj_stream_private *p_stream,
1036                                                                         OPJ_UINT32 *output_marker,
1037                                                                         struct opj_event_mgr * p_manager );
1038
1039 /**
1040  * Writes the MCT marker (Multiple Component Transform)
1041  *
1042  * @param       p_stream                                the stream to write data to.
1043  * @param       p_j2k                           J2K codec.
1044  * @param       p_manager               the user event manager.
1045 */
1046 static opj_bool j2k_write_mct_record(   opj_j2k_v2_t *p_j2k,
1047                                                                                 opj_mct_data_t * p_mct_record,
1048                                                                                 struct opj_stream_private *p_stream,
1049                                                                                 struct opj_event_mgr * p_manager );
1050
1051 /**
1052  * Reads a MCT marker (Multiple Component Transform)
1053  *
1054  * @param       p_header_data   the data contained in the MCT box.
1055  * @param       p_j2k                   the jpeg2000 codec.
1056  * @param       p_header_size   the size of the data contained in the MCT marker.
1057  * @param       p_manager               the user event manager.
1058 */
1059 static opj_bool j2k_read_mct (  opj_j2k_v2_t *p_j2k,
1060                                                                 OPJ_BYTE * p_header_data,
1061                                                                 OPJ_UINT32 p_header_size,
1062                                                                 struct opj_event_mgr * p_manager );
1063
1064 /**
1065  * Writes the MCC marker (Multiple Component Collection)
1066  *
1067  * @param       p_stream                the stream to write data to.
1068  * @param       p_j2k                   J2K codec.
1069  * @param       p_manager               the user event manager.
1070 */
1071 static opj_bool j2k_write_mcc_record(   opj_j2k_v2_t *p_j2k,
1072                                                                                 struct opj_simple_mcc_decorrelation_data * p_mcc_record,
1073                                                                                 struct opj_stream_private *p_stream,
1074                                                                                 struct opj_event_mgr * p_manager );
1075
1076
1077 /**
1078  * Reads a MCC marker (Multiple Component Collection)
1079  *
1080  * @param       p_header_data   the data contained in the MCC box.
1081  * @param       p_j2k                   the jpeg2000 codec.
1082  * @param       p_header_size   the size of the data contained in the MCC marker.
1083  * @param       p_manager               the user event manager.
1084 */
1085 static opj_bool j2k_read_mcc (  opj_j2k_v2_t *p_j2k,
1086                                                                 OPJ_BYTE * p_header_data,
1087                                                                 OPJ_UINT32 p_header_size,
1088                                                                 struct opj_event_mgr * p_manager );
1089
1090 /**
1091  * Writes the MCO marker (Multiple component transformation ordering)
1092  *
1093  * @param       p_stream                                the stream to write data to.
1094  * @param       p_j2k                           J2K codec.
1095  * @param       p_manager               the user event manager.
1096 */
1097 static opj_bool j2k_write_mco(  opj_j2k_v2_t *p_j2k,
1098                                                                 struct opj_stream_private *p_stream,
1099                                                                 struct opj_event_mgr * p_manager );
1100
1101 /**
1102  * Reads a MCO marker (Multiple Component Transform Ordering)
1103  *
1104  * @param       p_header_data   the data contained in the MCO box.
1105  * @param       p_j2k                   the jpeg2000 codec.
1106  * @param       p_header_size   the size of the data contained in the MCO marker.
1107  * @param       p_manager               the user event manager.
1108 */
1109 static opj_bool j2k_read_mco (  opj_j2k_v2_t *p_j2k,
1110                                                                 OPJ_BYTE * p_header_data,
1111                                                                 OPJ_UINT32 p_header_size,
1112                                                                 struct opj_event_mgr * p_manager );
1113
1114 static opj_bool j2k_add_mct(opj_tcp_v2_t * p_tcp, opj_image_t * p_image, OPJ_UINT32 p_index);
1115
1116 static void  j2k_read_int16_to_float (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1117 static void  j2k_read_int32_to_float (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1118 static void  j2k_read_float32_to_float (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1119 static void  j2k_read_float64_to_float (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1120
1121 static void  j2k_read_int16_to_int32 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1122 static void  j2k_read_int32_to_int32 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1123 static void  j2k_read_float32_to_int32 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1124 static void  j2k_read_float64_to_int32 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1125
1126 static void  j2k_write_float_to_int16 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1127 static void  j2k_write_float_to_int32 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1128 static void  j2k_write_float_to_float (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1129 static void  j2k_write_float_to_float64 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1130
1131
1132 /**
1133  * Ends the encoding, i.e. frees memory.
1134  *
1135  * @param       p_stream                the stream to write data to.
1136  * @param       p_j2k                   J2K codec.
1137  * @param       p_manager               the user event manager.
1138 */
1139 static opj_bool j2k_end_encoding(       opj_j2k_v2_t *p_j2k,
1140                                                                         struct opj_stream_private *p_stream,
1141                                                                         struct opj_event_mgr * p_manager );
1142
1143 /**
1144  * Writes the CBD marker (Component bit depth definition)
1145  *
1146  * @param       p_stream                                the stream to write data to.
1147  * @param       p_j2k                           J2K codec.
1148  * @param       p_manager               the user event manager.
1149 */
1150 static opj_bool j2k_write_cbd(  opj_j2k_v2_t *p_j2k,
1151                                                                 struct opj_stream_private *p_stream,
1152                                                                 struct opj_event_mgr * p_manager );
1153
1154 /**
1155  * Reads a CBD marker (Component bit depth definition)
1156  * @param       p_header_data   the data contained in the CBD box.
1157  * @param       p_j2k                   the jpeg2000 codec.
1158  * @param       p_header_size   the size of the data contained in the CBD marker.
1159  * @param       p_manager               the user event manager.
1160 */
1161 static opj_bool j2k_read_cbd (  opj_j2k_v2_t *p_j2k,
1162                                                         OPJ_BYTE * p_header_data,
1163                                                         OPJ_UINT32 p_header_size,
1164                                                         struct opj_event_mgr * p_manager);
1165
1166 /**
1167  * Writes the image components.
1168  *
1169  * @param       p_stream                the stream to write data to.
1170  * @param       p_j2k                   J2K codec.
1171  * @param       p_manager               the user event manager.
1172 */
1173 static opj_bool j2k_write_image_components(     opj_j2k_v2_t *p_j2k,
1174                                                                                         struct opj_stream_private *p_stream,
1175                                                                                         struct opj_event_mgr * p_manager );
1176
1177 /**
1178  * Writes regions of interests.
1179  *
1180  * @param       p_stream                the stream to write data to.
1181  * @param       p_j2k                   J2K codec.
1182  * @param       p_manager               the user event manager.
1183 */
1184 static opj_bool j2k_write_regions(      opj_j2k_v2_t *p_j2k,
1185                                                                         struct opj_stream_private *p_stream,
1186                                                                         struct opj_event_mgr * p_manager );
1187
1188 /**
1189  * Writes EPC ????
1190  *
1191  * @param       p_stream                the stream to write data to.
1192  * @param       p_j2k                   J2K codec.
1193  * @param       p_manager               the user event manager.
1194 */
1195 static opj_bool j2k_write_epc(  opj_j2k_v2_t *p_j2k,
1196                                                                 struct opj_stream_private *p_stream,
1197                                                                 struct opj_event_mgr * p_manager );
1198
1199 /**
1200  * Checks the progression order changes values. Tells of the poc given as input are valid.
1201  * A nice message is outputted at errors.
1202  *
1203  * @param       p_pocs                          the progression order changes.
1204  * @param       p_nb_pocs                       the number of progression order changes.
1205  * @param       p_nb_resolutions        the number of resolutions.
1206  * @param       numcomps                        the number of components
1207  * @param       numlayers                       the number of layers.
1208  *
1209  * @return      true if the pocs are valid.
1210  */
1211 static opj_bool j2k_check_poc_val(      const opj_poc_t *p_pocs,
1212                                                                         OPJ_UINT32 p_nb_pocs,
1213                                                                         OPJ_UINT32 p_nb_resolutions,
1214                                                                         OPJ_UINT32 numcomps,
1215                                                                         OPJ_UINT32 numlayers,
1216                                                                         opj_event_mgr_t * p_manager);
1217
1218 /**
1219  * Gets the number of tile parts used for the given change of progression (if any) and the given tile.
1220  *
1221  * @param               cp                      the coding parameters.
1222  * @param               pino            the offset of the given poc (i.e. its position in the coding parameter).
1223  * @param               tileno          the given tile.
1224  *
1225  * @return              the number of tile parts.
1226  */
1227 static OPJ_UINT32 j2k_get_num_tp_v2( opj_cp_v2_t *cp, OPJ_UINT32 pino, OPJ_UINT32 tileno);
1228
1229 /**     mem allocation for TLM marker*/
1230 static int j2k_calculate_tp(opj_cp_t *cp,int img_numcomp,opj_image_t *image,opj_j2k_t *j2k );
1231
1232 /**
1233  * Calculates the total number of tile parts needed by the encoder to
1234  * encode such an image. If not enough memory is available, then the function return false.
1235  *
1236  * @param       p_nb_tiles      pointer that will hold the number of tile parts.
1237  * @param       cp                      the coding parameters for the image.
1238  * @param       image           the image to encode.
1239  * @param       p_j2k                   the p_j2k encoder.
1240  * @param       p_manager       the user event manager.
1241  *
1242  * @return true if the function was successful, false else.
1243  */
1244 static opj_bool j2k_calculate_tp_v2(opj_j2k_v2_t *p_j2k,
1245                                                                         opj_cp_v2_t *cp,
1246                                                                         OPJ_UINT32 * p_nb_tiles,
1247                                                                         opj_image_t *image,
1248                                                                         opj_event_mgr_t * p_manager);
1249
1250 static void j2k_dump_MH_info(opj_j2k_v2_t* p_j2k, FILE* out_stream);
1251
1252 static void j2k_dump_MH_index(opj_j2k_v2_t* p_j2k, FILE* out_stream);
1253
1254 static opj_codestream_index_t* j2k_create_cstr_index(void);
1255
1256 /*@}*/
1257
1258 /*@}*/
1259
1260 /* ----------------------------------------------------------------------- */
1261 typedef struct j2k_prog_order{
1262         OPJ_PROG_ORDER enum_prog;
1263         char str_prog[5];
1264 }j2k_prog_order_t;
1265
1266 j2k_prog_order_t j2k_prog_order_list[] = {
1267         {CPRL, "CPRL"},
1268         {LRCP, "LRCP"},
1269         {PCRL, "PCRL"},
1270         {RLCP, "RLCP"},
1271         {RPCL, "RPCL"},
1272         {(OPJ_PROG_ORDER)-1, ""}
1273 };
1274
1275
1276
1277 /**
1278  * FIXME DOC
1279  */
1280 const OPJ_UINT32 MCT_ELEMENT_SIZE [] =
1281 {
1282         2,
1283         4,
1284         4,
1285         8
1286 };
1287
1288 typedef void (* j2k_mct_function) (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem);
1289
1290 const j2k_mct_function j2k_mct_read_functions_to_float [] =
1291 {
1292         j2k_read_int16_to_float,
1293         j2k_read_int32_to_float,
1294         j2k_read_float32_to_float,
1295         j2k_read_float64_to_float
1296 };
1297
1298 const j2k_mct_function j2k_mct_read_functions_to_int32 [] =
1299 {
1300         j2k_read_int16_to_int32,
1301         j2k_read_int32_to_int32,
1302         j2k_read_float32_to_int32,
1303         j2k_read_float64_to_int32
1304 };
1305
1306 const j2k_mct_function j2k_mct_write_functions_from_float [] =
1307 {
1308         j2k_write_float_to_int16,
1309         j2k_write_float_to_int32,
1310         j2k_write_float_to_float,
1311         j2k_write_float_to_float64
1312 };
1313
1314 typedef struct opj_dec_memory_marker_handler
1315 {
1316         /** marker value */
1317         OPJ_UINT32 id;
1318         /** value of the state when the marker can appear */
1319         OPJ_UINT32 states;
1320         /** action linked to the marker */
1321         opj_bool (*handler) (
1322                                         opj_j2k_v2_t *p_j2k,
1323                                         OPJ_BYTE * p_header_data,
1324                                         OPJ_UINT32 p_header_size,
1325                                         struct opj_event_mgr * p_manager
1326                                                 );
1327 }
1328 opj_dec_memory_marker_handler_t;
1329
1330 const opj_dec_memory_marker_handler_t j2k_memory_marker_handler_tab [] =
1331 {
1332 #ifdef TODO_MS
1333   {J2K_MS_SOT, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPHSOT, j2k_read_sot},
1334   {J2K_MS_COD, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPH, j2k_read_cod},
1335   {J2K_MS_COC, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPH, j2k_read_coc},
1336   {J2K_MS_RGN, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPH, j2k_read_rgn},
1337   {J2K_MS_QCD, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPH, j2k_read_qcd},
1338   {J2K_MS_QCC, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPH, j2k_read_qcc},
1339   {J2K_MS_POC, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPH, j2k_read_poc},
1340   {J2K_MS_SIZ, J2K_DEC_STATE_MHSIZ , j2k_read_siz},
1341   {J2K_MS_TLM, J2K_DEC_STATE_MH, j2k_read_tlm},
1342   {J2K_MS_PLM, J2K_DEC_STATE_MH, j2k_read_plm},
1343   {J2K_MS_PLT, J2K_DEC_STATE_TPH, j2k_read_plt},
1344   {J2K_MS_PPM, J2K_DEC_STATE_MH, j2k_read_ppm},
1345   {J2K_MS_PPT, J2K_DEC_STATE_TPH, j2k_read_ppt},
1346   {J2K_MS_SOP, 0, 0},
1347   {J2K_MS_CRG, J2K_DEC_STATE_MH, j2k_read_crg},
1348   {J2K_MS_COM, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPH, j2k_read_com},
1349   {J2K_MS_MCT, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPH, j2k_read_mct},
1350   {J2K_MS_CBD, J2K_DEC_STATE_MH , j2k_read_cbd},
1351   {J2K_MS_MCC, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPH, j2k_read_mcc},
1352   {J2K_MS_MCO, J2K_DEC_STATE_MH | J2K_DEC_STATE_TPH, j2k_read_mco},
1353 #endif
1354   {J2K_MS_SOT, J2K_STATE_MH | J2K_STATE_TPHSOT, opj_j2k_read_sot},
1355   {J2K_MS_COD, J2K_STATE_MH | J2K_STATE_TPH, opj_j2k_read_cod},
1356   {J2K_MS_COC, J2K_STATE_MH | J2K_STATE_TPH, opj_j2k_read_coc},
1357   {J2K_MS_RGN, J2K_STATE_MH | J2K_STATE_TPH, opj_j2k_read_rgn},
1358   {J2K_MS_QCD, J2K_STATE_MH | J2K_STATE_TPH, opj_j2k_read_qcd},
1359   {J2K_MS_QCC, J2K_STATE_MH | J2K_STATE_TPH, opj_j2k_read_qcc},
1360   {J2K_MS_POC, J2K_STATE_MH | J2K_STATE_TPH, opj_j2k_read_poc},
1361   {J2K_MS_SIZ, J2K_STATE_MHSIZ, opj_j2k_read_siz},
1362   {J2K_MS_TLM, J2K_STATE_MH, opj_j2k_read_tlm},
1363   {J2K_MS_PLM, J2K_STATE_MH, opj_j2k_read_plm},
1364   {J2K_MS_PLT, J2K_STATE_TPH, opj_j2k_read_plt},
1365   {J2K_MS_PPM, J2K_STATE_MH, j2k_read_ppm_v3},
1366   {J2K_MS_PPT, J2K_STATE_TPH, opj_j2k_read_ppt},
1367   {J2K_MS_SOP, 0, 0},
1368   {J2K_MS_CRG, J2K_STATE_MH, opj_j2k_read_crg},
1369   {J2K_MS_COM, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_com_v2},
1370   {J2K_MS_MCT, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_mct},
1371   {J2K_MS_CBD, J2K_STATE_MH , j2k_read_cbd},
1372   {J2K_MS_MCC, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_mcc},
1373   {J2K_MS_MCO, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_mco},
1374 #ifdef USE_JPWL
1375 #ifdef TODO_MS /* FIXME */
1376   {J2K_MS_EPC, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_epc},
1377   {J2K_MS_EPB, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_epb},
1378   {J2K_MS_ESD, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_esd},
1379   {J2K_MS_RED, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_red},
1380 #endif
1381 #endif /* USE_JPWL */
1382 #ifdef USE_JPSEC
1383   {J2K_MS_SEC, J2K_DEC_STATE_MH, j2k_read_sec},
1384   {J2K_MS_INSEC, 0, j2k_read_insec}
1385 #endif /* USE_JPSEC */
1386   {J2K_MS_UNK, J2K_STATE_MH | J2K_STATE_TPH, 0}/*j2k_read_unk_v2}*/
1387 };
1388
1389
1390
1391 void  j2k_read_int16_to_float (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1392 {
1393         OPJ_BYTE * l_src_data = (OPJ_BYTE *) p_src_data;
1394         OPJ_FLOAT32 * l_dest_data = (OPJ_FLOAT32 *) p_dest_data;
1395         OPJ_UINT32 i;
1396         OPJ_UINT32 l_temp;
1397
1398         for (i=0;i<p_nb_elem;++i) {
1399                 opj_read_bytes(l_src_data,&l_temp,2);
1400
1401                 l_src_data+=sizeof(OPJ_INT16);
1402
1403                 *(l_dest_data++) = (OPJ_FLOAT32) l_temp;
1404         }
1405 }
1406
1407 void  j2k_read_int32_to_float (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1408 {
1409         OPJ_BYTE * l_src_data = (OPJ_BYTE *) p_src_data;
1410         OPJ_FLOAT32 * l_dest_data = (OPJ_FLOAT32 *) p_dest_data;
1411         OPJ_UINT32 i;
1412         OPJ_UINT32 l_temp;
1413
1414         for (i=0;i<p_nb_elem;++i) {
1415                 opj_read_bytes(l_src_data,&l_temp,4);
1416
1417                 l_src_data+=sizeof(OPJ_INT32);
1418
1419                 *(l_dest_data++) = (OPJ_FLOAT32) l_temp;
1420         }
1421 }
1422
1423 void  j2k_read_float32_to_float (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1424 {
1425         OPJ_BYTE * l_src_data = (OPJ_BYTE *) p_src_data;
1426         OPJ_FLOAT32 * l_dest_data = (OPJ_FLOAT32 *) p_dest_data;
1427         OPJ_UINT32 i;
1428         OPJ_FLOAT32 l_temp;
1429
1430         for (i=0;i<p_nb_elem;++i) {
1431                 opj_read_float(l_src_data,&l_temp);
1432
1433                 l_src_data+=sizeof(OPJ_FLOAT32);
1434
1435                 *(l_dest_data++) = l_temp;
1436         }
1437 }
1438
1439 void  j2k_read_float64_to_float (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1440 {
1441         OPJ_BYTE * l_src_data = (OPJ_BYTE *) p_src_data;
1442         OPJ_FLOAT32 * l_dest_data = (OPJ_FLOAT32 *) p_dest_data;
1443         OPJ_UINT32 i;
1444         OPJ_FLOAT64 l_temp;
1445
1446         for (i=0;i<p_nb_elem;++i) {
1447                 opj_read_double(l_src_data,&l_temp);
1448
1449                 l_src_data+=sizeof(OPJ_FLOAT64);
1450
1451                 *(l_dest_data++) = (OPJ_FLOAT32) l_temp;
1452         }
1453 }
1454
1455 void  j2k_read_int16_to_int32 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1456 {
1457         OPJ_BYTE * l_src_data = (OPJ_BYTE *) p_src_data;
1458         OPJ_INT32 * l_dest_data = (OPJ_INT32 *) p_dest_data;
1459         OPJ_UINT32 i;
1460         OPJ_UINT32 l_temp;
1461
1462         for (i=0;i<p_nb_elem;++i) {
1463                 opj_read_bytes(l_src_data,&l_temp,2);
1464
1465                 l_src_data+=sizeof(OPJ_INT16);
1466
1467                 *(l_dest_data++) = (OPJ_INT32) l_temp;
1468         }
1469 }
1470
1471 void  j2k_read_int32_to_int32 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1472 {
1473         OPJ_BYTE * l_src_data = (OPJ_BYTE *) p_src_data;
1474         OPJ_INT32 * l_dest_data = (OPJ_INT32 *) p_dest_data;
1475         OPJ_UINT32 i;
1476         OPJ_UINT32 l_temp;
1477
1478         for (i=0;i<p_nb_elem;++i) {
1479                 opj_read_bytes(l_src_data,&l_temp,4);
1480
1481                 l_src_data+=sizeof(OPJ_INT32);
1482
1483                 *(l_dest_data++) = (OPJ_INT32) l_temp;
1484         }
1485 }
1486
1487 void  j2k_read_float32_to_int32 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1488 {
1489         OPJ_BYTE * l_src_data = (OPJ_BYTE *) p_src_data;
1490         OPJ_INT32 * l_dest_data = (OPJ_INT32 *) p_dest_data;
1491         OPJ_UINT32 i;
1492         OPJ_FLOAT32 l_temp;
1493
1494         for (i=0;i<p_nb_elem;++i) {
1495                 opj_read_float(l_src_data,&l_temp);
1496
1497                 l_src_data+=sizeof(OPJ_FLOAT32);
1498
1499                 *(l_dest_data++) = (OPJ_INT32) l_temp;
1500         }
1501 }
1502
1503 void  j2k_read_float64_to_int32 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1504 {
1505         OPJ_BYTE * l_src_data = (OPJ_BYTE *) p_src_data;
1506         OPJ_INT32 * l_dest_data = (OPJ_INT32 *) p_dest_data;
1507         OPJ_UINT32 i;
1508         OPJ_FLOAT64 l_temp;
1509
1510         for (i=0;i<p_nb_elem;++i) {
1511                 opj_read_double(l_src_data,&l_temp);
1512
1513                 l_src_data+=sizeof(OPJ_FLOAT64);
1514
1515                 *(l_dest_data++) = (OPJ_INT32) l_temp;
1516         }
1517 }
1518
1519 void  j2k_write_float_to_int16 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1520 {
1521         OPJ_BYTE * l_dest_data = (OPJ_BYTE *) p_dest_data;
1522         OPJ_FLOAT32 * l_src_data = (OPJ_FLOAT32 *) p_src_data;
1523         OPJ_UINT32 i;
1524         OPJ_UINT32 l_temp;
1525
1526         for (i=0;i<p_nb_elem;++i) {
1527                 l_temp = (OPJ_UINT32) *(l_src_data++);
1528
1529                 opj_write_bytes(l_dest_data,l_temp,sizeof(OPJ_INT16));
1530
1531                 l_dest_data+=sizeof(OPJ_INT16);
1532         }
1533 }
1534
1535 void  j2k_write_float_to_int32 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1536 {
1537         OPJ_BYTE * l_dest_data = (OPJ_BYTE *) p_dest_data;
1538         OPJ_FLOAT32 * l_src_data = (OPJ_FLOAT32 *) p_src_data;
1539         OPJ_UINT32 i;
1540         OPJ_UINT32 l_temp;
1541
1542         for (i=0;i<p_nb_elem;++i) {
1543                 l_temp = (OPJ_UINT32) *(l_src_data++);
1544
1545                 opj_write_bytes(l_dest_data,l_temp,sizeof(OPJ_INT32));
1546
1547                 l_dest_data+=sizeof(OPJ_INT32);
1548         }
1549 }
1550
1551 void  j2k_write_float_to_float (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1552 {
1553         OPJ_BYTE * l_dest_data = (OPJ_BYTE *) p_dest_data;
1554         OPJ_FLOAT32 * l_src_data = (OPJ_FLOAT32 *) p_src_data;
1555         OPJ_UINT32 i;
1556         OPJ_FLOAT32 l_temp;
1557
1558         for (i=0;i<p_nb_elem;++i) {
1559                 l_temp = (OPJ_FLOAT32) *(l_src_data++);
1560
1561                 opj_write_float(l_dest_data,l_temp);
1562
1563                 l_dest_data+=sizeof(OPJ_FLOAT32);
1564         }
1565 }
1566
1567 void  j2k_write_float_to_float64 (const void * p_src_data, void * p_dest_data, OPJ_UINT32 p_nb_elem)
1568 {
1569         OPJ_BYTE * l_dest_data = (OPJ_BYTE *) p_dest_data;
1570         OPJ_FLOAT32 * l_src_data = (OPJ_FLOAT32 *) p_src_data;
1571         OPJ_UINT32 i;
1572         OPJ_FLOAT64 l_temp;
1573
1574         for (i=0;i<p_nb_elem;++i) {
1575                 l_temp = (OPJ_FLOAT64) *(l_src_data++);
1576
1577                 opj_write_double(l_dest_data,l_temp);
1578
1579                 l_dest_data+=sizeof(OPJ_FLOAT64);
1580         }
1581 }
1582
1583
1584 /**
1585  * Converts an enum type progression order to string type.
1586  *
1587  * @param prg_order             the progression order to get.
1588  *
1589  * @return      the string representation of the given progression order.
1590  */
1591 char *j2k_convert_progression_order(OPJ_PROG_ORDER prg_order){
1592         j2k_prog_order_t *po;
1593         for(po = j2k_prog_order_list; po->enum_prog != -1; po++ ){
1594                 if(po->enum_prog == prg_order){
1595                         return po->str_prog;
1596                 }
1597         }
1598         return po->str_prog;
1599 }
1600
1601 /**
1602  * Checks the progression order changes values. Tells if the poc given as input are valid.
1603  *
1604  * @param       p_pocs                          the progression order changes.
1605  * @param       p_nb_pocs                       the number of progression order changes.
1606  * @param       p_nb_resolutions        the number of resolutions.
1607  * @param       numcomps                        the number of components
1608  * @param       numlayers                       the number of layers.
1609  * @param       p_manager                       the user event manager.
1610  *
1611  * @return      true if the pocs are valid.
1612  */
1613 opj_bool j2k_check_poc_val(     const opj_poc_t *p_pocs,
1614                                                         OPJ_UINT32 p_nb_pocs,
1615                                                         OPJ_UINT32 p_nb_resolutions,
1616                                                         OPJ_UINT32 p_num_comps,
1617                                                         OPJ_UINT32 p_num_layers,
1618                                                         opj_event_mgr_t * p_manager)
1619 {
1620         OPJ_UINT32* packet_array;
1621         OPJ_UINT32 index , resno, compno, layno;
1622         OPJ_UINT32 i;
1623         OPJ_UINT32 step_c = 1;
1624         OPJ_UINT32 step_r = p_num_comps * step_c;
1625         OPJ_UINT32 step_l = p_nb_resolutions * step_r;
1626         opj_bool loss = OPJ_FALSE;
1627         OPJ_UINT32 layno0 = 0;
1628
1629         packet_array = (OPJ_UINT32*) opj_calloc(step_l * p_num_layers, sizeof(OPJ_UINT32));
1630         if (packet_array == 00) {
1631                 opj_event_msg_v2(p_manager , EVT_ERROR, "Not enough memory for checking the poc values.\n");
1632                 return OPJ_FALSE;
1633         }
1634         memset(packet_array,0,step_l * p_num_layers* sizeof(OPJ_UINT32));
1635
1636         if (p_nb_pocs == 0) {
1637                 return OPJ_TRUE;
1638         }
1639
1640         index = step_r * p_pocs->resno0;
1641         // take each resolution for each poc
1642         for (resno = p_pocs->resno0 ; resno < p_pocs->resno1 ; ++resno)
1643         {
1644                 OPJ_UINT32 res_index = index + p_pocs->compno0 * step_c;
1645
1646                 // take each comp of each resolution for each poc
1647                 for (compno = p_pocs->compno0 ; compno < p_pocs->compno1 ; ++compno) {
1648                         OPJ_UINT32 comp_index = res_index + layno0 * step_l;
1649
1650                         // and finally take each layer of each res of ...
1651                         for (layno = layno0; layno < p_pocs->layno1 ; ++layno) {
1652                                 //index = step_r * resno + step_c * compno + step_l * layno;
1653                                 packet_array[comp_index] = 1;
1654                                 comp_index += step_l;
1655                         }
1656
1657                         res_index += step_c;
1658                 }
1659
1660                 index += step_r;
1661         }
1662         ++p_pocs;
1663
1664         // iterate through all the pocs
1665         for (i = 1; i < p_nb_pocs ; ++i) {
1666                 OPJ_UINT32 l_last_layno1 = (p_pocs-1)->layno1 ;
1667
1668                 layno0 = (p_pocs->layno1 > l_last_layno1)? l_last_layno1 : 0;
1669                 index = step_r * p_pocs->resno0;
1670
1671                 // take each resolution for each poc
1672                 for (resno = p_pocs->resno0 ; resno < p_pocs->resno1 ; ++resno) {
1673                         OPJ_UINT32 res_index = index + p_pocs->compno0 * step_c;
1674
1675                         // take each comp of each resolution for each poc
1676                         for (compno = p_pocs->compno0 ; compno < p_pocs->compno1 ; ++compno) {
1677                                 OPJ_UINT32 comp_index = res_index + layno0 * step_l;
1678
1679                                 // and finally take each layer of each res of ...
1680                                 for (layno = layno0; layno < p_pocs->layno1 ; ++layno) {
1681                                         //index = step_r * resno + step_c * compno + step_l * layno;
1682                                         packet_array[comp_index] = 1;
1683                                         comp_index += step_l;
1684                                 }
1685
1686                                 res_index += step_c;
1687                         }
1688
1689                         index += step_r;
1690                 }
1691
1692                 ++p_pocs;
1693         }
1694
1695         index = 0;
1696         for (layno = 0; layno < p_num_layers ; ++layno) {
1697                 for (resno = 0; resno < p_nb_resolutions; ++resno) {
1698                         for (compno = 0; compno < p_num_comps; ++compno) {
1699                                 loss |= (packet_array[index]!=1);
1700                                 //index = step_r * resno + step_c * compno + step_l * layno;
1701                                 index += step_c;
1702                         }
1703                 }
1704         }
1705
1706         if (loss) {
1707                 opj_event_msg_v2(p_manager , EVT_ERROR, "Missing packets possible loss of data\n");
1708         }
1709
1710         opj_free(packet_array);
1711
1712         return !loss;
1713 }
1714
1715 /* ----------------------------------------------------------------------- */
1716 static int j2k_get_num_tp(opj_cp_t *cp,int pino,int tileno){
1717         char *prog;
1718         int i;
1719         int tpnum=1,tpend=0;
1720         opj_tcp_t *tcp = &cp->tcps[tileno];
1721         prog = j2k_convert_progression_order(tcp->prg);
1722         
1723         if(cp->tp_on == 1){
1724                 for(i=0;i<4;i++){
1725                         if(tpend!=1){
1726                                 if( cp->tp_flag == prog[i] ){
1727                                         tpend=1;cp->tp_pos=i;
1728                                 }
1729                                 switch(prog[i]){
1730                                 case 'C':
1731                                         tpnum= tpnum * tcp->pocs[pino].compE;
1732                                         break;
1733                                 case 'R':
1734                                         tpnum= tpnum * tcp->pocs[pino].resE;
1735                                         break;
1736                                 case 'P':
1737                                         tpnum= tpnum * tcp->pocs[pino].prcE;
1738                                         break;
1739                                 case 'L':
1740                                         tpnum= tpnum * tcp->pocs[pino].layE;
1741                                         break;
1742                                 }
1743                         }
1744                 }
1745         }else{
1746                 tpnum=1;
1747         }
1748         return tpnum;
1749 }
1750
1751 /**
1752  * Gets the number of tile parts used for the given change of progression (if any) and the given tile.
1753  *
1754  * @param               cp                      the coding parameters.
1755  * @param               pino            the offset of the given poc (i.e. its position in the coding parameter).
1756  * @param               tileno          the given tile.
1757  *
1758  * @return              the number of tile parts.
1759  */
1760 OPJ_UINT32 j2k_get_num_tp_v2(opj_cp_v2_t *cp, OPJ_UINT32 pino, OPJ_UINT32 tileno)
1761 {
1762         const OPJ_CHAR *prog = 00;
1763         OPJ_UINT32 i;
1764         OPJ_UINT32 tpnum = 1;
1765         opj_tcp_v2_t *tcp = 00;
1766         opj_poc_t * l_current_poc = 00;
1767
1768         /*  preconditions */
1769         assert(tileno < (cp->tw * cp->th));
1770         assert(pino < (cp->tcps[tileno].numpocs + 1));
1771
1772         /* get the given tile coding parameter */
1773         tcp = &cp->tcps[tileno];
1774         assert(tcp != 00);
1775
1776         l_current_poc = &(tcp->pocs[pino]);
1777         assert(l_current_poc != 0);
1778
1779         /* get the progression order as a character string */
1780         prog = j2k_convert_progression_order(tcp->prg);
1781         assert(strlen(prog) > 0);
1782
1783         if (cp->m_specific_param.m_enc.m_tp_on == 1) {
1784                 for (i=0;i<4;++i) {
1785                         switch (prog[i])
1786                         {
1787                                 /* component wise */
1788                                 case 'C':
1789                                         tpnum *= l_current_poc->compE;
1790                                         break;
1791                                 /* resolution wise */
1792                                 case 'R':
1793                                         tpnum *= l_current_poc->resE;
1794                                         break;
1795                                 /* precinct wise */
1796                                 case 'P':
1797                                         tpnum *= l_current_poc->prcE;
1798                                         break;
1799                                 /* layer wise */
1800                                 case 'L':
1801                                         tpnum *= l_current_poc->layE;
1802                                         break;
1803                         }
1804                         /* whould we split here ? */
1805                         if ( cp->m_specific_param.m_enc.m_tp_flag == prog[i] ) {
1806                                 cp->m_specific_param.m_enc.m_tp_pos=i;
1807                                 break;
1808                         }
1809                 }
1810         }
1811         else {
1812                 tpnum=1;
1813         }
1814
1815         return tpnum;
1816 }
1817
1818 /**     mem allocation for TLM marker*/
1819 int j2k_calculate_tp(opj_cp_t *cp,int img_numcomp,opj_image_t *image,opj_j2k_t *j2k ){
1820         int pino,tileno,totnum_tp=0;
1821
1822         OPJ_ARG_NOT_USED(img_numcomp);
1823
1824         j2k->cur_totnum_tp = (int *) opj_malloc(cp->tw * cp->th * sizeof(int));
1825         for (tileno = 0; tileno < cp->tw * cp->th; tileno++) {
1826                 int cur_totnum_tp = 0;
1827                 opj_tcp_t *tcp = &cp->tcps[tileno];
1828                 for(pino = 0; pino <= tcp->numpocs; pino++) {
1829                         int tp_num=0;
1830                         opj_pi_iterator_t *pi = pi_initialise_encode(image, cp, tileno,FINAL_PASS);
1831                         if(!pi) { return -1;}
1832                         tp_num = j2k_get_num_tp(cp,pino,tileno);
1833                         totnum_tp = totnum_tp + tp_num;
1834                         cur_totnum_tp = cur_totnum_tp + tp_num;
1835                         pi_destroy(pi, cp, tileno);
1836                 }
1837                 j2k->cur_totnum_tp[tileno] = cur_totnum_tp;
1838                 /* INDEX >> */
1839                 if (j2k->cstr_info) {
1840                         j2k->cstr_info->tile[tileno].num_tps = cur_totnum_tp;
1841                         j2k->cstr_info->tile[tileno].tp = (opj_tp_info_t *) opj_malloc(cur_totnum_tp * sizeof(opj_tp_info_t));
1842                 }
1843                 /* << INDEX */
1844         }
1845         return totnum_tp;
1846 }
1847
1848 /**
1849  * Calculates the total number of tile parts needed by the encoder to
1850  * encode such an image. If not enough memory is available, then the function return false.
1851  *
1852  * @param       p_nb_tiles      pointer that will hold the number of tile parts.
1853  * @param       cp                      the coding parameters for the image.
1854  * @param       image           the image to encode.
1855  * @param       p_j2k                   the p_j2k encoder.
1856  * @param       p_manager       the user event manager.
1857  *
1858  * @return true if the function was successful, false else.
1859  */
1860 opj_bool j2k_calculate_tp_v2( opj_j2k_v2_t *p_j2k,
1861                                                           opj_cp_v2_t *cp,
1862                                                           OPJ_UINT32 * p_nb_tiles,
1863                                                           opj_image_t *image,
1864                                                           opj_event_mgr_t * p_manager)
1865 {
1866         OPJ_UINT32 pino,tileno;
1867         OPJ_UINT32 l_nb_tiles;
1868         opj_tcp_v2_t *tcp;
1869
1870         /* preconditions */
1871         assert(p_nb_tiles != 00);
1872         assert(cp != 00);
1873         assert(image != 00);
1874         assert(p_j2k != 00);
1875         assert(p_manager != 00);
1876
1877         l_nb_tiles = cp->tw * cp->th;
1878         * p_nb_tiles = 0;
1879         tcp = cp->tcps;
1880
1881         /* INDEX >> */
1882         /* TODO mergeV2: check this part which use cstr_info */
1883         /*if (p_j2k->cstr_info) {
1884                 opj_tile_info_t * l_info_tile_ptr = p_j2k->cstr_info->tile;
1885
1886                 for (tileno = 0; tileno < l_nb_tiles; ++tileno) {
1887                         OPJ_UINT32 cur_totnum_tp = 0;
1888
1889                         pi_update_encoding_parameters(image,cp,tileno);
1890
1891                         for (pino = 0; pino <= tcp->numpocs; ++pino)
1892                         {
1893                                 OPJ_UINT32 tp_num = j2k_get_num_tp_v2(cp,pino,tileno);
1894
1895                                 *p_nb_tiles = *p_nb_tiles + tp_num;
1896
1897                                 cur_totnum_tp += tp_num;
1898                         }
1899
1900                         tcp->m_nb_tile_parts = cur_totnum_tp;
1901
1902                         l_info_tile_ptr->tp = (opj_tp_info_t *) opj_malloc(cur_totnum_tp * sizeof(opj_tp_info_t));
1903                         if (l_info_tile_ptr->tp == 00) {
1904                                 return OPJ_FALSE;
1905                         }
1906
1907                         memset(l_info_tile_ptr->tp,0,cur_totnum_tp * sizeof(opj_tp_info_t));
1908
1909                         l_info_tile_ptr->num_tps = cur_totnum_tp;
1910
1911                         ++l_info_tile_ptr;
1912                         ++tcp;
1913                 }
1914         }
1915         else */{
1916                 for (tileno = 0; tileno < l_nb_tiles; ++tileno) {
1917                         OPJ_UINT32 cur_totnum_tp = 0;
1918
1919                         pi_update_encoding_parameters(image,cp,tileno);
1920
1921                         for (pino = 0; pino <= tcp->numpocs; ++pino) {
1922                                 OPJ_UINT32 tp_num = j2k_get_num_tp_v2(cp,pino,tileno);
1923
1924                                 *p_nb_tiles = *p_nb_tiles + tp_num;
1925
1926                                 cur_totnum_tp += tp_num;
1927                         }
1928                         tcp->m_nb_tile_parts = cur_totnum_tp;
1929
1930                         ++tcp;
1931                 }
1932         }
1933
1934         return OPJ_TRUE;
1935 }
1936
1937 static void j2k_write_soc(opj_j2k_t *j2k) {
1938         opj_cio_t *cio = j2k->cio;
1939         cio_write(cio, J2K_MS_SOC, 2);
1940
1941         if(j2k->cstr_info)
1942           j2k_add_mhmarker(j2k->cstr_info, J2K_MS_SOC, cio_tell(cio), 0);
1943
1944 /* UniPG>> */
1945 #ifdef USE_JPWL
1946
1947         /* update markers struct */
1948         j2k_add_marker(j2k->cstr_info, J2K_MS_SOC, cio_tell(cio) - 2, 2);
1949 #endif /* USE_JPWL */
1950 /* <<UniPG */
1951 }
1952
1953 /**
1954  * Writes the SOC marker (Start Of Codestream)
1955  *
1956  * @param       p_stream                        the stream to write data to.
1957  * @param       p_j2k                   J2K codec.
1958  * @param       p_manager       the user event manager.
1959 */
1960 opj_bool j2k_write_soc_v2(      opj_j2k_v2_t *p_j2k,
1961                                                         struct opj_stream_private *p_stream,
1962                                                         struct opj_event_mgr * p_manager )
1963 {
1964         /* 2 bytes will be written */
1965         OPJ_BYTE * l_start_stream = 00;
1966
1967         /* preconditions */
1968         assert(p_stream != 00);
1969         assert(p_j2k != 00);
1970         assert(p_manager != 00);
1971
1972         l_start_stream = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
1973
1974         /* write SOC identifier */
1975         opj_write_bytes(l_start_stream,J2K_MS_SOC,2);
1976
1977         if (opj_stream_write_data(p_stream,l_start_stream,2,p_manager) != 2) {
1978                 return OPJ_FALSE;
1979         }
1980
1981 /* UniPG>> */
1982 #ifdef USE_JPWL
1983         /* update markers struct */
1984 /*
1985         j2k_add_marker(p_j2k->cstr_info, J2K_MS_SOC, p_stream_tell(p_stream) - 2, 2);
1986 */
1987   assert( 0 && "TODO" );
1988 #endif /* USE_JPWL */
1989 /* <<UniPG */
1990
1991         return OPJ_TRUE;
1992 }
1993
1994
1995
1996 /**
1997  * Reads a SOC marker (Start of Codestream)
1998  * @param       p_header_data   the data contained in the SOC box.
1999  * @param       jp2                             the jpeg2000 file codec.
2000  * @param       p_header_size   the size of the data contained in the SOC marker.
2001  * @param       p_manager               the user event manager.
2002 */
2003 static opj_bool opj_j2k_read_soc(       opj_j2k_v2_t *p_j2k,
2004                                                                         struct opj_stream_private *p_stream,
2005                                                                         struct opj_event_mgr * p_manager )
2006 {
2007         OPJ_BYTE l_data [2];
2008         OPJ_UINT32 l_marker;
2009
2010         /* preconditions */
2011         assert(p_j2k != 00);
2012         assert(p_manager != 00);
2013         assert(p_stream != 00);
2014
2015         if (opj_stream_read_data(p_stream,l_data,2,p_manager) != 2) {
2016                 return OPJ_FALSE;
2017         }
2018
2019         opj_read_bytes(l_data,&l_marker,2);
2020         if (l_marker != J2K_MS_SOC) {
2021                 return OPJ_FALSE;
2022         }
2023
2024         /* Next marker should be a SIZ marker in the main header */
2025         p_j2k->m_specific_param.m_decoder.m_state = J2K_STATE_MHSIZ;
2026
2027         /* FIXME move it in a index structure included in p_j2k*/
2028         p_j2k->cstr_index->main_head_start = opj_stream_tell(p_stream) - 2;
2029
2030         opj_event_msg_v2(p_manager, EVT_INFO, "Start to read j2k main header (%d).\n", p_j2k->cstr_index->main_head_start);
2031
2032         /* Add the marker to the codestream index*/
2033         j2k_add_mhmarker_v2(p_j2k->cstr_index, J2K_MS_SOC, p_j2k->cstr_index->main_head_start, 2);
2034
2035         return OPJ_TRUE;
2036 }
2037
2038 static void j2k_write_siz(opj_j2k_t *j2k) {
2039         OPJ_UINT32 i;
2040         int lenp, len;
2041
2042         opj_cio_t *cio = j2k->cio;
2043         opj_image_t *image = j2k->image;
2044         opj_cp_t *cp = j2k->cp;
2045
2046         cio_write(cio, J2K_MS_SIZ, 2);  /* SIZ */
2047         lenp = cio_tell(cio);
2048         cio_skip(cio, 2);
2049         cio_write(cio, cp->rsiz, 2);                    /* Rsiz (capabilities) */
2050         cio_write(cio, image->x1, 4);   /* Xsiz */
2051         cio_write(cio, image->y1, 4);   /* Ysiz */
2052         cio_write(cio, image->x0, 4);   /* X0siz */
2053         cio_write(cio, image->y0, 4);   /* Y0siz */
2054         cio_write(cio, cp->tdx, 4);             /* XTsiz */
2055         cio_write(cio, cp->tdy, 4);             /* YTsiz */
2056         cio_write(cio, cp->tx0, 4);             /* XT0siz */
2057         cio_write(cio, cp->ty0, 4);             /* YT0siz */
2058         cio_write(cio, image->numcomps, 2);     /* Csiz */
2059         for (i = 0; i < image->numcomps; i++) {
2060                 cio_write(cio, image->comps[i].prec - 1 + (image->comps[i].sgnd << 7), 1);      /* Ssiz_i */
2061                 cio_write(cio, image->comps[i].dx, 1);  /* XRsiz_i */
2062                 cio_write(cio, image->comps[i].dy, 1);  /* YRsiz_i */
2063         }
2064         len = cio_tell(cio) - lenp;
2065         cio_seek(cio, lenp);
2066         cio_write(cio, len, 2);         /* Lsiz */
2067         cio_seek(cio, lenp + len);
2068         
2069         if(j2k->cstr_info)
2070           j2k_add_mhmarker(j2k->cstr_info, J2K_MS_SIZ, lenp, len);
2071 }
2072
2073 /**
2074  * Writes the SIZ marker (image and tile size)
2075  *
2076  * @param       p_stream                        the stream to write data to.
2077  * @param       p_j2k                   J2K codec.
2078  * @param       p_manager       the user event manager.
2079 */
2080 opj_bool j2k_write_siz_v2(      opj_j2k_v2_t *p_j2k,
2081                                                         struct opj_stream_private *p_stream,
2082                                                         struct opj_event_mgr * p_manager )
2083 {
2084         OPJ_UINT32 i;
2085         OPJ_UINT32 l_size_len;
2086         OPJ_BYTE * l_current_ptr;
2087         opj_image_t * l_image = 00;
2088         opj_cp_v2_t *cp = 00;
2089         opj_image_comp_t * l_img_comp = 00;
2090
2091         /* preconditions */
2092         assert(p_stream != 00);
2093         assert(p_j2k != 00);
2094         assert(p_manager != 00);
2095
2096         l_image = p_j2k->m_private_image;
2097         cp = &(p_j2k->m_cp);
2098         l_size_len = 40 + 3 * l_image->numcomps;
2099         l_img_comp = l_image->comps;
2100
2101         if (l_size_len > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
2102
2103                 p_j2k->m_specific_param.m_encoder.m_header_tile_data
2104                         = (OPJ_BYTE*)opj_realloc(
2105                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
2106                                 l_size_len);
2107                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
2108                         return OPJ_FALSE;
2109                 }
2110
2111                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_size_len;
2112         }
2113
2114         l_current_ptr = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
2115
2116         /* write SOC identifier */
2117         opj_write_bytes(l_current_ptr,J2K_MS_SIZ,2);    /* SIZ */
2118         l_current_ptr+=2;
2119
2120         opj_write_bytes(l_current_ptr,l_size_len-2,2); /* L_SIZ */
2121         l_current_ptr+=2;
2122
2123         opj_write_bytes(l_current_ptr, cp->rsiz, 2);    /* Rsiz (capabilities) */
2124         l_current_ptr+=2;
2125
2126         opj_write_bytes(l_current_ptr, l_image->x1, 4); /* Xsiz */
2127         l_current_ptr+=4;
2128
2129         opj_write_bytes(l_current_ptr, l_image->y1, 4); /* Ysiz */
2130         l_current_ptr+=4;
2131
2132         opj_write_bytes(l_current_ptr, l_image->x0, 4); /* X0siz */
2133         l_current_ptr+=4;
2134
2135         opj_write_bytes(l_current_ptr, l_image->y0, 4); /* Y0siz */
2136         l_current_ptr+=4;
2137
2138         opj_write_bytes(l_current_ptr, cp->tdx, 4);             /* XTsiz */
2139         l_current_ptr+=4;
2140
2141         opj_write_bytes(l_current_ptr, cp->tdy, 4);             /* YTsiz */
2142         l_current_ptr+=4;
2143
2144         opj_write_bytes(l_current_ptr, cp->tx0, 4);             /* XT0siz */
2145         l_current_ptr+=4;
2146
2147         opj_write_bytes(l_current_ptr, cp->ty0, 4);             /* YT0siz */
2148         l_current_ptr+=4;
2149
2150         opj_write_bytes(l_current_ptr, l_image->numcomps, 2);   /* Csiz */
2151         l_current_ptr+=2;
2152
2153         for (i = 0; i < l_image->numcomps; ++i) {
2154                 /* TODO here with MCT ? */
2155                 opj_write_bytes(l_current_ptr, l_img_comp->prec - 1 + (l_img_comp->sgnd << 7), 1);      /* Ssiz_i */
2156                 ++l_current_ptr;
2157
2158                 opj_write_bytes(l_current_ptr, l_img_comp->dx, 1);      /* XRsiz_i */
2159                 ++l_current_ptr;
2160
2161                 opj_write_bytes(l_current_ptr, l_img_comp->dy, 1);      /* YRsiz_i */
2162                 ++l_current_ptr;
2163
2164                 ++l_img_comp;
2165         }
2166
2167         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_size_len,p_manager) != l_size_len) {
2168                 return OPJ_FALSE;
2169         }
2170
2171         return OPJ_TRUE;
2172 }
2173
2174
2175
2176 /**
2177  * Reads a SIZ marker (image and tile size)
2178  * @param       p_header_data   the data contained in the SIZ box.
2179  * @param       jp2                             the jpeg2000 file codec.
2180  * @param       p_header_size   the size of the data contained in the SIZ marker.
2181  * @param       p_manager               the user event manager.
2182 */
2183 static opj_bool opj_j2k_read_siz(opj_j2k_v2_t *p_j2k,
2184                                  OPJ_BYTE * p_header_data,
2185                                  OPJ_UINT32 p_header_size,
2186                                  opj_event_mgr_t * p_manager
2187                                  )
2188 {
2189         OPJ_UINT32 l_size, i;
2190         OPJ_UINT32 l_nb_comp;
2191         OPJ_UINT32 l_nb_comp_remain;
2192         OPJ_UINT32 l_remaining_size;
2193         OPJ_UINT32 l_nb_tiles;
2194         OPJ_UINT32 l_tmp;
2195         opj_image_t *l_image = 00;
2196         opj_cp_v2_t *l_cp = 00;
2197         opj_image_comp_t * l_img_comp = 00;
2198         opj_tcp_v2_t * l_current_tile_param = 00;
2199
2200         /* preconditions */
2201         assert(p_j2k != 00);
2202         assert(p_manager != 00);
2203         assert(p_header_data != 00);
2204
2205         l_image = p_j2k->m_private_image;
2206         l_cp = &(p_j2k->m_cp);
2207
2208         /* minimum size == 39 - 3 (= minimum component parameter) */
2209         if (p_header_size < 36) {
2210                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error with SIZ marker size\n");
2211                 return OPJ_FALSE;
2212         }
2213
2214         l_remaining_size = p_header_size - 36;
2215         l_nb_comp = l_remaining_size / 3;
2216         l_nb_comp_remain = l_remaining_size % 3;
2217         if (l_nb_comp_remain != 0){
2218                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error with SIZ marker size\n");
2219                 return OPJ_FALSE;
2220         }
2221
2222         l_size = p_header_size + 2;                                                                             /* Lsiz */
2223
2224         opj_read_bytes(p_header_data,&l_tmp ,2);                                                /* Rsiz (capabilities) */
2225         p_header_data+=2;
2226         l_cp->rsiz = (OPJ_RSIZ_CAPABILITIES) l_tmp;
2227         opj_read_bytes(p_header_data, (OPJ_UINT32*) &l_image->x1, 4);   /* Xsiz */
2228         p_header_data+=4;
2229         opj_read_bytes(p_header_data, (OPJ_UINT32*) &l_image->y1, 4);   /* Ysiz */
2230         p_header_data+=4;
2231         opj_read_bytes(p_header_data, (OPJ_UINT32*) &l_image->x0, 4);   /* X0siz */
2232         p_header_data+=4;
2233         opj_read_bytes(p_header_data, (OPJ_UINT32*) &l_image->y0, 4);   /* Y0siz */
2234         p_header_data+=4;
2235         opj_read_bytes(p_header_data, (OPJ_UINT32*) &l_cp->tdx, 4);             /* XTsiz */
2236         p_header_data+=4;
2237         opj_read_bytes(p_header_data, (OPJ_UINT32*) &l_cp->tdy, 4);             /* YTsiz */
2238         p_header_data+=4;
2239         opj_read_bytes(p_header_data, (OPJ_UINT32*) &l_cp->tx0, 4);             /* XT0siz */
2240         p_header_data+=4;
2241         opj_read_bytes(p_header_data, (OPJ_UINT32*) &l_cp->ty0, 4);             /* YT0siz */
2242         p_header_data+=4;
2243         opj_read_bytes(p_header_data, (OPJ_UINT32*) &l_tmp, 2);                 /* Csiz */
2244         p_header_data+=2;
2245         if (l_tmp < 16385)
2246                 l_image->numcomps = (OPJ_UINT16) l_tmp;
2247         else {
2248                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error with SIZ marker: number of component is illegal -> %d\n", l_tmp);
2249                 return OPJ_FALSE;
2250         }
2251
2252         if (l_image->numcomps != l_nb_comp) {
2253                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error with SIZ marker: number of component is not compatible with the remaining number of parameters ( %d vs %d)\n", l_image->numcomps, l_nb_comp);
2254                 return OPJ_FALSE;
2255         }
2256
2257 #ifdef USE_JPWL
2258         if (l_cp->correct) {
2259                 /* if JPWL is on, we check whether TX errors have damaged
2260                   too much the SIZ parameters */
2261                 if (!(l_image->x1 * l_image->y1)) {
2262                         opj_event_msg_v2(p_manager, EVT_ERROR,
2263                                 "JPWL: bad image size (%d x %d)\n",
2264                                 l_image->x1, l_image->y1);
2265                         if (!JPWL_ASSUME || JPWL_ASSUME) {
2266                                 opj_event_msg_v2(p_manager, EVT_ERROR, "JPWL: giving up\n");
2267                                 return OPJ_FALSE;
2268                         }
2269                 }
2270
2271         /* FIXME check previously in the function so why keep this piece of code ? Need by the norm ?
2272                 if (l_image->numcomps != ((len - 38) / 3)) {
2273                         opj_event_msg_v2(p_manager, JPWL_ASSUME ? EVT_WARNING : EVT_ERROR,
2274                                 "JPWL: Csiz is %d => space in SIZ only for %d comps.!!!\n",
2275                                 l_image->numcomps, ((len - 38) / 3));
2276                         if (!JPWL_ASSUME) {
2277                                 opj_event_msg_v2(p_manager, EVT_ERROR, "JPWL: giving up\n");
2278                                 return OPJ_FALSE;
2279                         }
2280         */              /* we try to correct */
2281         /*              opj_event_msg_v2(p_manager, EVT_WARNING, "- trying to adjust this\n");
2282                         if (l_image->numcomps < ((len - 38) / 3)) {
2283                                 len = 38 + 3 * l_image->numcomps;
2284                                 opj_event_msg_v2(p_manager, EVT_WARNING, "- setting Lsiz to %d => HYPOTHESIS!!!\n",
2285                                         len);
2286                         } else {
2287                                 l_image->numcomps = ((len - 38) / 3);
2288                                 opj_event_msg_v2(p_manager, EVT_WARNING, "- setting Csiz to %d => HYPOTHESIS!!!\n",
2289                                         l_image->numcomps);
2290                         }
2291                 }
2292         */
2293
2294                 /* update components number in the jpwl_exp_comps filed */
2295                 l_cp->exp_comps = l_image->numcomps;
2296         }
2297 #endif /* USE_JPWL */
2298
2299         /* Allocate the resulting image components */
2300         l_image->comps = (opj_image_comp_t*) opj_calloc(l_image->numcomps, sizeof(opj_image_comp_t));
2301         if (l_image->comps == 00){
2302                 l_image->numcomps = 0;
2303                 opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory to take in charge SIZ marker\n");
2304                 return OPJ_FALSE;
2305         }
2306
2307         memset(l_image->comps,0,l_image->numcomps * sizeof(opj_image_comp_t));
2308         l_img_comp = l_image->comps;
2309
2310         /* Read the component information */
2311         for (i = 0; i < l_image->numcomps; ++i){
2312                 OPJ_UINT32 tmp;
2313                 opj_read_bytes(p_header_data,&tmp,1);   /* Ssiz_i */
2314                 ++p_header_data;
2315                 l_img_comp->prec = (tmp & 0x7f) + 1;
2316                 l_img_comp->sgnd = tmp >> 7;
2317                 opj_read_bytes(p_header_data,&tmp,1);   /* XRsiz_i */
2318                 ++p_header_data;
2319                 l_img_comp->dx = (OPJ_INT32)tmp; /* should be between 1 and 255 */
2320                 opj_read_bytes(p_header_data,&tmp,1);   /* YRsiz_i */
2321                 ++p_header_data;
2322                 l_img_comp->dy = (OPJ_INT32)tmp; /* should be between 1 and 255 */
2323
2324 #ifdef USE_JPWL
2325                 if (l_cp->correct) {
2326                 /* if JPWL is on, we check whether TX errors have damaged
2327                         too much the SIZ parameters, again */
2328                         if (!(l_image->comps[i].dx * l_image->comps[i].dy)) {
2329                                 opj_event_msg_v2(p_manager, JPWL_ASSUME ? EVT_WARNING : EVT_ERROR,
2330                                         "JPWL: bad XRsiz_%d/YRsiz_%d (%d x %d)\n",
2331                                         i, i, l_image->comps[i].dx, l_image->comps[i].dy);
2332                                 if (!JPWL_ASSUME) {
2333                                         opj_event_msg_v2(p_manager, EVT_ERROR, "JPWL: giving up\n");
2334                                         return OPJ_FALSE;
2335                                 }
2336                                 /* we try to correct */
2337                                 opj_event_msg_v2(p_manager, EVT_WARNING, "- trying to adjust them\n");
2338                                 if (!l_image->comps[i].dx) {
2339                                         l_image->comps[i].dx = 1;
2340                                         opj_event_msg_v2(p_manager, EVT_WARNING, "- setting XRsiz_%d to %d => HYPOTHESIS!!!\n",
2341                                                 i, l_image->comps[i].dx);
2342                                 }
2343                                 if (!l_image->comps[i].dy) {
2344                                         l_image->comps[i].dy = 1;
2345                                         opj_event_msg_v2(p_manager, EVT_WARNING, "- setting YRsiz_%d to %d => HYPOTHESIS!!!\n",
2346                                                 i, l_image->comps[i].dy);
2347                                 }
2348                         }
2349                 }
2350 #endif /* USE_JPWL */
2351                 l_img_comp->resno_decoded = 0;                                                          /* number of resolution decoded */
2352                 l_img_comp->factor = l_cp->m_specific_param.m_dec.m_reduce; /* reducing factor per component */
2353                 ++l_img_comp;
2354         }
2355
2356         /* Compute the number of tiles */
2357         l_cp->tw = int_ceildiv(l_image->x1 - l_cp->tx0, l_cp->tdx);
2358         l_cp->th = int_ceildiv(l_image->y1 - l_cp->ty0, l_cp->tdy);
2359         l_nb_tiles = l_cp->tw * l_cp->th;
2360
2361         /* Define the tiles which will be decoded */
2362         if (p_j2k->m_specific_param.m_decoder.m_discard_tiles) {
2363                 p_j2k->m_specific_param.m_decoder.m_start_tile_x = (p_j2k->m_specific_param.m_decoder.m_start_tile_x - l_cp->tx0) / l_cp->tdx;
2364                 p_j2k->m_specific_param.m_decoder.m_start_tile_y = (p_j2k->m_specific_param.m_decoder.m_start_tile_y - l_cp->ty0) / l_cp->tdy;
2365                 p_j2k->m_specific_param.m_decoder.m_end_tile_x = int_ceildiv((p_j2k->m_specific_param.m_decoder.m_end_tile_x - l_cp->tx0), l_cp->tdx);
2366                 p_j2k->m_specific_param.m_decoder.m_end_tile_y = int_ceildiv((p_j2k->m_specific_param.m_decoder.m_end_tile_y - l_cp->ty0), l_cp->tdy);
2367         }
2368         else {
2369                 p_j2k->m_specific_param.m_decoder.m_start_tile_x = 0;
2370                 p_j2k->m_specific_param.m_decoder.m_start_tile_y = 0;
2371                 p_j2k->m_specific_param.m_decoder.m_end_tile_x = l_cp->tw;
2372                 p_j2k->m_specific_param.m_decoder.m_end_tile_y = l_cp->th;
2373         }
2374
2375 #ifdef USE_JPWL
2376         if (l_cp->correct) {
2377                 /* if JPWL is on, we check whether TX errors have damaged
2378                   too much the SIZ parameters */
2379                 if ((l_cp->tw < 1) || (l_cp->th < 1) || (l_cp->tw > l_cp->max_tiles) || (l_cp->th > l_cp->max_tiles)) {
2380                         opj_event_msg_v2(p_manager, JPWL_ASSUME ? EVT_WARNING : EVT_ERROR,
2381                                 "JPWL: bad number of tiles (%d x %d)\n",
2382                                 l_cp->tw, l_cp->th);
2383                         if (!JPWL_ASSUME) {
2384                                 opj_event_msg_v2(p_manager, EVT_ERROR, "JPWL: giving up\n");
2385                                 return OPJ_FALSE;
2386                         }
2387                         /* we try to correct */
2388                         opj_event_msg_v2(p_manager, EVT_WARNING, "- trying to adjust them\n");
2389                         if (l_cp->tw < 1) {
2390                                 l_cp->tw= 1;
2391                                 opj_event_msg_v2(p_manager, EVT_WARNING, "- setting %d tiles in x => HYPOTHESIS!!!\n",
2392                                                 l_cp->tw);
2393                         }
2394                         if (l_cp->tw > l_cp->max_tiles) {
2395                                 l_cp->tw= 1;
2396                                 opj_event_msg_v2(p_manager, EVT_WARNING, "- too large x, increase expectance of %d\n"
2397                                         "- setting %d tiles in x => HYPOTHESIS!!!\n",
2398                                         l_cp->max_tiles, l_cp->tw);
2399                         }
2400                         if (l_cp->th < 1) {
2401                                 l_cp->th= 1;
2402                                 opj_event_msg_v2(p_manager, EVT_WARNING, "- setting %d tiles in y => HYPOTHESIS!!!\n",
2403                                                 l_cp->th);
2404                         }
2405                         if (l_cp->th > l_cp->max_tiles) {
2406                                 l_cp->th= 1;
2407                                 opj_event_msg_v2(p_manager, EVT_WARNING, "- too large y, increase expectance of %d to continue\n",
2408                                         "- setting %d tiles in y => HYPOTHESIS!!!\n",
2409                                         l_cp->max_tiles, l_cp->th);
2410                         }
2411                 }
2412         }
2413 #endif /* USE_JPWL */
2414
2415         /* memory allocations */
2416         l_cp->tcps = (opj_tcp_v2_t*) opj_calloc(l_nb_tiles, sizeof(opj_tcp_v2_t));
2417         if (l_cp->tcps == 00) {
2418                 opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory to take in charge SIZ marker\n");
2419                 return OPJ_FALSE;
2420         }
2421         memset(l_cp->tcps,0,l_nb_tiles*sizeof(opj_tcp_t));
2422
2423 #ifdef USE_JPWL
2424         if (l_cp->correct) {
2425                 if (!l_cp->tcps) {
2426                         opj_event_msg_v2(p_manager, JPWL_ASSUME ? EVT_WARNING : EVT_ERROR,
2427                                 "JPWL: could not alloc tcps field of cp\n");
2428                         if (!JPWL_ASSUME || JPWL_ASSUME) {
2429                                 opj_event_msg_v2(p_manager, EVT_ERROR, "JPWL: giving up\n");
2430                                 return OPJ_FALSE;
2431                         }
2432                 }
2433         }
2434 #endif /* USE_JPWL */
2435
2436         p_j2k->m_specific_param.m_decoder.m_default_tcp->tccps =
2437                         (opj_tccp_t*) opj_calloc(l_image->numcomps, sizeof(opj_tccp_t));
2438         if(p_j2k->m_specific_param.m_decoder.m_default_tcp->tccps  == 00) {
2439                 opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory to take in charge SIZ marker\n");
2440                 return OPJ_FALSE;
2441         }
2442         memset(p_j2k->m_specific_param.m_decoder.m_default_tcp->tccps ,0,l_image->numcomps*sizeof(opj_tccp_t));
2443
2444         p_j2k->m_specific_param.m_decoder.m_default_tcp->m_mct_records =
2445                         (opj_mct_data_t*)opj_malloc(J2K_MCT_DEFAULT_NB_RECORDS * sizeof(opj_mct_data_t));
2446
2447         if (! p_j2k->m_specific_param.m_decoder.m_default_tcp->m_mct_records) {
2448                 opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory to take in charge SIZ marker\n");
2449                 return OPJ_FALSE;
2450         }
2451         memset(p_j2k->m_specific_param.m_decoder.m_default_tcp->m_mct_records,0,J2K_MCT_DEFAULT_NB_RECORDS * sizeof(opj_mct_data_t));
2452         p_j2k->m_specific_param.m_decoder.m_default_tcp->m_nb_max_mct_records = J2K_MCT_DEFAULT_NB_RECORDS;
2453
2454         p_j2k->m_specific_param.m_decoder.m_default_tcp->m_mcc_records =
2455                         (opj_simple_mcc_decorrelation_data_t*)
2456                         opj_malloc(J2K_MCC_DEFAULT_NB_RECORDS * sizeof(opj_simple_mcc_decorrelation_data_t));
2457
2458         if (! p_j2k->m_specific_param.m_decoder.m_default_tcp->m_mcc_records) {
2459                 opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory to take in charge SIZ marker\n");
2460                 return OPJ_FALSE;
2461         }
2462         memset(p_j2k->m_specific_param.m_decoder.m_default_tcp->m_mcc_records,0,J2K_MCC_DEFAULT_NB_RECORDS * sizeof(opj_simple_mcc_decorrelation_data_t));
2463         p_j2k->m_specific_param.m_decoder.m_default_tcp->m_nb_max_mcc_records = J2K_MCC_DEFAULT_NB_RECORDS;
2464
2465         /* set up default dc level shift */
2466         for (i=0;i<l_image->numcomps;++i) {
2467                 if (! l_image->comps[i].sgnd) {
2468                         p_j2k->m_specific_param.m_decoder.m_default_tcp->tccps[i].m_dc_level_shift = 1 << (l_image->comps[i].prec - 1);
2469                 }
2470         }
2471
2472         l_current_tile_param = l_cp->tcps;
2473         for     (i = 0; i < l_nb_tiles; ++i) {
2474                 l_current_tile_param->tccps = (opj_tccp_t*) opj_malloc(l_image->numcomps * sizeof(opj_tccp_t));
2475                 if (l_current_tile_param->tccps == 00) {
2476                         opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory to take in charge SIZ marker\n");
2477                         return OPJ_FALSE;
2478                 }
2479                 memset(l_current_tile_param->tccps,0,l_image->numcomps * sizeof(opj_tccp_t));
2480
2481                 ++l_current_tile_param;
2482         }
2483
2484         p_j2k->m_specific_param.m_decoder.m_state =  J2K_STATE_MH; /* FIXME J2K_DEC_STATE_MH; */
2485         opj_image_comp_header_update(l_image,l_cp);
2486
2487         return OPJ_TRUE;
2488 }
2489
2490
2491
2492 static void j2k_write_com(opj_j2k_t *j2k) {
2493         unsigned int i;
2494         int lenp, len;
2495
2496         if(j2k->cp->comment) {
2497                 opj_cio_t *cio = j2k->cio;
2498                 char *comment = j2k->cp->comment;
2499
2500                 cio_write(cio, J2K_MS_COM, 2);
2501                 lenp = cio_tell(cio);
2502                 cio_skip(cio, 2);
2503                 cio_write(cio, 1, 2);           /* General use (IS 8859-15:1999 (Latin) values) */
2504                 for (i = 0; i < strlen(comment); i++) {
2505                         cio_write(cio, comment[i], 1);
2506                 }
2507                 len = cio_tell(cio) - lenp;
2508                 cio_seek(cio, lenp);
2509                 cio_write(cio, len, 2);
2510                 cio_seek(cio, lenp + len);
2511
2512                 
2513                 if(j2k->cstr_info)
2514                   j2k_add_mhmarker(j2k->cstr_info, J2K_MS_COM, lenp, len);
2515
2516         }
2517 }
2518
2519 /**
2520  * Writes the COM marker (comment)
2521  * 
2522  * @param       p_stream                        the stream to write data to.
2523  * @param       p_j2k                   J2K codec.
2524  * @param       p_manager       the user event manager.
2525 */
2526 opj_bool j2k_write_com_v2(      opj_j2k_v2_t *p_j2k,
2527                                                         struct opj_stream_private *p_stream,
2528                                                         struct opj_event_mgr * p_manager )
2529 {
2530         OPJ_UINT32 l_comment_size;
2531         OPJ_UINT32 l_total_com_size;
2532         const OPJ_CHAR *l_comment;
2533         OPJ_BYTE * l_current_ptr = 00;
2534
2535         // preconditions
2536         assert(p_j2k != 00);
2537         assert(p_stream != 00);
2538         assert(p_manager != 00);
2539         
2540         l_comment = p_j2k->m_cp.comment;
2541         l_comment_size = strlen(l_comment);
2542         l_total_com_size = l_comment_size + 6;
2543
2544         if (l_total_com_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
2545                 p_j2k->m_specific_param.m_encoder.m_header_tile_data 
2546                         = (OPJ_BYTE*)opj_realloc(       p_j2k->m_specific_param.m_encoder.m_header_tile_data,
2547                                                                                 l_total_com_size);
2548                 
2549                 if(! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
2550                         return OPJ_FALSE;
2551                 }
2552
2553                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_total_com_size;
2554         }
2555
2556         l_current_ptr = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
2557         
2558         opj_write_bytes(l_current_ptr,J2K_MS_COM , 2);  /* COM */
2559         l_current_ptr+=2;
2560         
2561         opj_write_bytes(l_current_ptr,l_total_com_size - 2 , 2);        /* L_COM */
2562         l_current_ptr+=2;
2563         
2564         opj_write_bytes(l_current_ptr,1 , 2);   /* General use (IS 8859-15:1999 (Latin) values) */
2565         l_current_ptr+=2;
2566         
2567         memcpy( l_current_ptr,l_comment,l_comment_size);
2568         
2569         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_total_com_size,p_manager) != l_total_com_size) {
2570                 return OPJ_FALSE;
2571         }
2572
2573         return OPJ_TRUE;
2574 }
2575
2576 /**
2577  * Reads a COM marker (comments)
2578  * @param       p_header_data   the data contained in the COM box.
2579  * @param       jp2                             the jpeg2000 file codec.
2580  * @param       p_header_size   the size of the data contained in the COM marker.
2581  * @param       p_manager               the user event manager.
2582 */
2583 opj_bool j2k_read_com_v2 (
2584                                         opj_j2k_v2_t *p_j2k,
2585                                         OPJ_BYTE * p_header_data,
2586                                         OPJ_UINT32 p_header_size,
2587                                         struct opj_event_mgr * p_manager
2588                                         )
2589 {
2590         /* preconditions */
2591         assert(p_j2k != 00);
2592         assert(p_manager != 00);
2593         assert(p_header_data != 00);
2594   (void)p_header_size;
2595
2596         return OPJ_TRUE;
2597 }
2598
2599 static void j2k_write_cox(opj_j2k_t *j2k, int compno) {
2600         OPJ_UINT32 i;
2601
2602         opj_cp_t *cp = j2k->cp;
2603         opj_tcp_t *tcp = &cp->tcps[j2k->curtileno];
2604         opj_tccp_t *tccp = &tcp->tccps[compno];
2605         opj_cio_t *cio = j2k->cio;
2606         
2607         cio_write(cio, tccp->numresolutions - 1, 1);    /* SPcox (D) */
2608         cio_write(cio, tccp->cblkw - 2, 1);                             /* SPcox (E) */
2609         cio_write(cio, tccp->cblkh - 2, 1);                             /* SPcox (F) */
2610         cio_write(cio, tccp->cblksty, 1);                               /* SPcox (G) */
2611         cio_write(cio, tccp->qmfbid, 1);                                /* SPcox (H) */
2612         
2613         if (tccp->csty & J2K_CCP_CSTY_PRT) {
2614                 for (i = 0; i < tccp->numresolutions; i++) {
2615                         cio_write(cio, tccp->prcw[i] + (tccp->prch[i] << 4), 1);        /* SPcox (I_i) */
2616                 }
2617         }
2618 }
2619
2620
2621 static void j2k_write_cod(opj_j2k_t *j2k) {
2622         opj_cp_t *cp = NULL;
2623         opj_tcp_t *tcp = NULL;
2624         int lenp, len;
2625
2626         opj_cio_t *cio = j2k->cio;
2627         
2628         cio_write(cio, J2K_MS_COD, 2);  /* COD */
2629         
2630         lenp = cio_tell(cio);
2631         cio_skip(cio, 2);
2632         
2633         cp = j2k->cp;
2634         tcp = &cp->tcps[j2k->curtileno];
2635
2636         cio_write(cio, tcp->csty, 1);           /* Scod */
2637         cio_write(cio, tcp->prg, 1);            /* SGcod (A) */
2638         cio_write(cio, tcp->numlayers, 2);      /* SGcod (B) */
2639         cio_write(cio, tcp->mct, 1);            /* SGcod (C) */
2640         
2641         j2k_write_cox(j2k, 0);
2642         len = cio_tell(cio) - lenp;
2643         cio_seek(cio, lenp);
2644         cio_write(cio, len, 2);         /* Lcod */
2645         cio_seek(cio, lenp + len);
2646
2647         if(j2k->cstr_info)
2648           j2k_add_mhmarker(j2k->cstr_info, J2K_MS_COD, lenp, len);
2649
2650 }
2651
2652 /**
2653  * Writes the COD marker (Coding style default)
2654  *
2655  * @param       p_stream                        the stream to write data to.
2656  * @param       p_j2k                   J2K codec.
2657  * @param       p_manager       the user event manager.
2658 */
2659 opj_bool j2k_write_cod_v2(      opj_j2k_v2_t *p_j2k,
2660                                                         struct opj_stream_private *p_stream,
2661                                                         struct opj_event_mgr * p_manager )
2662 {
2663         opj_cp_v2_t *l_cp = 00;
2664         opj_tcp_v2_t *l_tcp = 00;
2665         OPJ_UINT32 l_code_size,l_remaining_size;
2666         OPJ_BYTE * l_current_data = 00;
2667
2668         /* preconditions */
2669         assert(p_j2k != 00);
2670         assert(p_manager != 00);
2671         assert(p_stream != 00);
2672
2673         l_cp = &(p_j2k->m_cp);
2674         l_tcp = &l_cp->tcps[p_j2k->m_current_tile_number];
2675         l_code_size = 9 + j2k_get_SPCod_SPCoc_size(p_j2k,p_j2k->m_current_tile_number,0);
2676         l_remaining_size = l_code_size;
2677
2678         if (l_code_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
2679                 p_j2k->m_specific_param.m_encoder.m_header_tile_data
2680                         = (OPJ_BYTE*)opj_realloc(
2681                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
2682                                 l_code_size);
2683
2684                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
2685                         return OPJ_FALSE;
2686                 }
2687
2688                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_code_size;
2689         }
2690
2691         l_current_data = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
2692
2693         opj_write_bytes(l_current_data,J2K_MS_COD,2);           /* COD */
2694         l_current_data += 2;
2695
2696         opj_write_bytes(l_current_data,l_code_size-2,2);        /* L_COD */
2697         l_current_data += 2;
2698
2699         opj_write_bytes(l_current_data,l_tcp->csty,1);          /* Scod */
2700         ++l_current_data;
2701
2702         opj_write_bytes(l_current_data,l_tcp->prg,1);           /* SGcod (A) */
2703         ++l_current_data;
2704
2705         opj_write_bytes(l_current_data,l_tcp->numlayers,2);     /* SGcod (B) */
2706         l_current_data+=2;
2707
2708         opj_write_bytes(l_current_data,l_tcp->mct,1);           /* SGcod (C) */
2709         ++l_current_data;
2710
2711         l_remaining_size -= 9;
2712
2713         if (! j2k_write_SPCod_SPCoc(p_j2k,p_j2k->m_current_tile_number,0,l_current_data,&l_remaining_size,p_manager)) {
2714                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error writting COD marker\n");
2715                 return OPJ_FALSE;
2716         }
2717
2718         if (l_remaining_size != 0) {
2719                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error writting COD marker\n");
2720                 return OPJ_FALSE;
2721         }
2722
2723         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_code_size,p_manager) != l_code_size) {
2724                 return OPJ_FALSE;
2725         }
2726
2727         return OPJ_TRUE;
2728 }
2729
2730
2731 /**
2732  * Reads a COD marker (Coding Styke defaults)
2733  * @param       p_header_data   the data contained in the COD box.
2734  * @param       p_j2k                   the jpeg2000 codec.
2735  * @param       p_header_size   the size of the data contained in the COD marker.
2736  * @param       p_manager               the user event manager.
2737 */
2738 static opj_bool opj_j2k_read_cod (  opj_j2k_v2_t *p_j2k,
2739                                     OPJ_BYTE * p_header_data,
2740                                     OPJ_UINT32 p_header_size,
2741                                     opj_event_mgr_t * p_manager
2742                                     )
2743 {
2744         /* loop */
2745         OPJ_UINT32 i;
2746         OPJ_UINT32 l_tmp;
2747         opj_cp_v2_t *l_cp = 00;
2748         opj_tcp_v2_t *l_tcp = 00;
2749         opj_image_t *l_image = 00;
2750
2751         /* preconditions */
2752         assert(p_header_data != 00);
2753         assert(p_j2k != 00);
2754         assert(p_manager != 00);
2755
2756         l_image = p_j2k->m_private_image;
2757         l_cp = &(p_j2k->m_cp);
2758
2759         /* If we are in the first tile-part header of the current tile */
2760         l_tcp = (p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH) ?
2761                                 &l_cp->tcps[p_j2k->m_current_tile_number] :
2762                                 p_j2k->m_specific_param.m_decoder.m_default_tcp;
2763
2764         /* Make sure room is sufficient */
2765         if (p_header_size < 5) {
2766                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading COD marker\n");
2767                 return OPJ_FALSE;
2768         }
2769
2770         opj_read_bytes(p_header_data,&l_tcp->csty,1);           /* Scod */
2771         ++p_header_data;
2772         opj_read_bytes(p_header_data,&l_tmp,1);                         /* SGcod (A) */
2773         ++p_header_data;
2774         l_tcp->prg = (OPJ_PROG_ORDER) l_tmp;
2775         opj_read_bytes(p_header_data,&l_tcp->numlayers,2);      /* SGcod (B) */
2776         p_header_data+=2;
2777
2778         /* If user didn't set a number layer to decode take the max specify in the codestream. */
2779         if      (l_cp->m_specific_param.m_dec.m_layer) {
2780                 l_tcp->num_layers_to_decode = l_cp->m_specific_param.m_dec.m_layer;
2781         }
2782         else {
2783                 l_tcp->num_layers_to_decode = l_tcp->numlayers;
2784         }
2785
2786         opj_read_bytes(p_header_data,&l_tcp->mct,1);            /* SGcod (C) */
2787         ++p_header_data;
2788
2789         p_header_size -= 5;
2790         for     (i = 0; i < l_image->numcomps; ++i) {
2791                 l_tcp->tccps[i].csty = l_tcp->csty & J2K_CCP_CSTY_PRT;
2792         }
2793
2794         if (! j2k_read_SPCod_SPCoc(p_j2k,0,p_header_data,&p_header_size,p_manager)) {
2795                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading COD marker\n");
2796                 return OPJ_FALSE;
2797         }
2798
2799         if (p_header_size != 0) {
2800                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading COD marker\n");
2801                 return OPJ_FALSE;
2802         }
2803
2804         /* Apply the coding style to other components of the current tile or the m_default_tcp*/
2805         j2k_copy_tile_component_parameters(p_j2k);
2806
2807         /* Index */
2808 #ifdef WIP_REMOVE_MSD
2809         if (p_j2k->cstr_info) {
2810                 /*opj_codestream_info_t *l_cstr_info = p_j2k->cstr_info;*/
2811                 p_j2k->cstr_info->prog = l_tcp->prg;
2812                 p_j2k->cstr_info->numlayers = l_tcp->numlayers;
2813                 p_j2k->cstr_info->numdecompos = (OPJ_INT32*) opj_malloc(l_image->numcomps * sizeof(OPJ_UINT32));
2814                 for     (i = 0; i < l_image->numcomps; ++i) {
2815                         p_j2k->cstr_info->numdecompos[i] = l_tcp->tccps[i].numresolutions - 1;
2816                 }
2817         }
2818 #endif
2819
2820         return OPJ_TRUE;
2821 }
2822
2823 static void j2k_write_coc(opj_j2k_t *j2k, int compno) {
2824         int lenp, len;
2825
2826         opj_cp_t *cp = j2k->cp;
2827         opj_tcp_t *tcp = &cp->tcps[j2k->curtileno];
2828         opj_image_t *image = j2k->image;
2829         opj_cio_t *cio = j2k->cio;
2830         
2831         cio_write(cio, J2K_MS_COC, 2);  /* COC */
2832         lenp = cio_tell(cio);
2833         cio_skip(cio, 2);
2834         cio_write(cio, compno, image->numcomps <= 256 ? 1 : 2); /* Ccoc */
2835         cio_write(cio, tcp->tccps[compno].csty, 1);     /* Scoc */
2836         j2k_write_cox(j2k, compno);
2837         len = cio_tell(cio) - lenp;
2838         cio_seek(cio, lenp);
2839         cio_write(cio, len, 2);                 /* Lcoc */
2840         cio_seek(cio, lenp + len);
2841 }
2842
2843 /**
2844  * Writes the COC marker (Coding style component)
2845  *
2846  * @param       p_comp_no               the index of the component to output.
2847  * @param       p_stream                                the stream to write data to.
2848  * @param       p_j2k                           J2K codec.
2849  * @param       p_manager               the user event manager.
2850 */
2851 opj_bool j2k_write_coc_v2(      opj_j2k_v2_t *p_j2k,
2852                                                         OPJ_UINT32 p_comp_no,
2853                                                         struct opj_stream_private *p_stream,
2854                                                         struct opj_event_mgr * p_manager )
2855 {
2856         OPJ_UINT32 l_coc_size,l_remaining_size;
2857         OPJ_UINT32 l_comp_room;
2858
2859         /* preconditions */
2860         assert(p_j2k != 00);
2861         assert(p_manager != 00);
2862         assert(p_stream != 00);
2863
2864         l_comp_room = (p_j2k->m_private_image->numcomps <= 256) ? 1 : 2;
2865
2866         l_coc_size = 5 + l_comp_room + j2k_get_SPCod_SPCoc_size(p_j2k,p_j2k->m_current_tile_number,p_comp_no);
2867
2868         if (l_coc_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
2869                 p_j2k->m_specific_param.m_encoder.m_header_tile_data
2870                         = (OPJ_BYTE*)opj_realloc(
2871                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
2872                                 l_coc_size);
2873                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
2874                         return OPJ_FALSE;
2875                 }
2876
2877                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_coc_size;
2878         }
2879
2880         j2k_write_coc_in_memory(p_j2k,p_comp_no,p_j2k->m_specific_param.m_encoder.m_header_tile_data,&l_remaining_size,p_manager);
2881
2882         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_coc_size,p_manager) != l_coc_size) {
2883                 return OPJ_FALSE;
2884         }
2885
2886         return OPJ_TRUE;
2887 }
2888
2889 /**
2890  * Writes the COC marker (Coding style component)
2891  *
2892  * @param       p_comp_no               the index of the component to output.
2893  * @param       p_stream                                the stream to write data to.
2894  * @param       p_j2k                           J2K codec.
2895  * @param       p_manager               the user event manager.
2896 */
2897 void j2k_write_coc_in_memory(   opj_j2k_v2_t *p_j2k,
2898                                                                 OPJ_UINT32 p_comp_no,
2899                                                                 OPJ_BYTE * p_data,
2900                                                                 OPJ_UINT32 * p_data_written,
2901                                                                 struct opj_event_mgr * p_manager )
2902 {
2903         opj_cp_v2_t *l_cp = 00;
2904         opj_tcp_v2_t *l_tcp = 00;
2905         OPJ_UINT32 l_coc_size,l_remaining_size;
2906         OPJ_BYTE * l_current_data = 00;
2907         opj_image_t *l_image = 00;
2908         OPJ_UINT32 l_comp_room;
2909
2910         /* preconditions */
2911         assert(p_j2k != 00);
2912         assert(p_manager != 00);
2913
2914         l_cp = &(p_j2k->m_cp);
2915         l_tcp = &l_cp->tcps[p_j2k->m_current_tile_number];
2916         l_image = p_j2k->m_private_image;
2917         l_comp_room = (l_image->numcomps <= 256) ? 1 : 2;
2918
2919         l_coc_size = 5 + l_comp_room + j2k_get_SPCod_SPCoc_size(p_j2k,p_j2k->m_current_tile_number,p_comp_no);
2920         l_remaining_size = l_coc_size;
2921
2922         l_current_data = p_data;
2923
2924         opj_write_bytes(l_current_data,J2K_MS_COC,2);                           /* COC */
2925         l_current_data += 2;
2926
2927         opj_write_bytes(l_current_data,l_coc_size-2,2);                         /* L_COC */
2928         l_current_data += 2;
2929
2930         opj_write_bytes(l_current_data,p_comp_no, l_comp_room);         /* Ccoc */
2931         l_current_data+=l_comp_room;
2932
2933         opj_write_bytes(l_current_data, l_tcp->tccps[p_comp_no].csty, 1);               /* Scoc */
2934         ++l_current_data;
2935
2936         l_remaining_size -= (5 + l_comp_room);
2937         j2k_write_SPCod_SPCoc(p_j2k,p_j2k->m_current_tile_number,0,l_current_data,&l_remaining_size,p_manager);
2938         * p_data_written = l_coc_size;
2939 }
2940
2941 /**
2942  * Gets the maximum size taken by a coc.
2943  *
2944  * @param       p_j2k   the jpeg2000 codec to use.
2945  */
2946 OPJ_UINT32 j2k_get_max_coc_size(opj_j2k_v2_t *p_j2k)
2947 {
2948         OPJ_UINT32 i,j;
2949         OPJ_UINT32 l_nb_comp;
2950         OPJ_UINT32 l_nb_tiles;
2951         OPJ_UINT32 l_max = 0;
2952
2953         /* preconditions */
2954
2955         l_nb_tiles = p_j2k->m_cp.tw * p_j2k->m_cp.th ;
2956         l_nb_comp = p_j2k->m_private_image->numcomps;
2957
2958         for (i=0;i<l_nb_tiles;++i) {
2959                 for (j=0;j<l_nb_comp;++j) {
2960                         l_max = uint_max(l_max,j2k_get_SPCod_SPCoc_size(p_j2k,i,j));
2961                 }
2962         }
2963
2964         return 6 + l_max;
2965 }
2966
2967
2968 /**
2969  * Reads a COC marker (Coding Style Component)
2970  * @param       p_header_data   the data contained in the COC box.
2971  * @param       p_j2k                   the jpeg2000 codec.
2972  * @param       p_header_size   the size of the data contained in the COC marker.
2973  * @param       p_manager               the user event manager.
2974 */
2975 static opj_bool opj_j2k_read_coc (  opj_j2k_v2_t *p_j2k,
2976                                     OPJ_BYTE * p_header_data,
2977                                     OPJ_UINT32 p_header_size,
2978                                     opj_event_mgr_t * p_manager 
2979                                     )
2980 {
2981         opj_cp_v2_t *l_cp = NULL;
2982         opj_tcp_v2_t *l_tcp = NULL;
2983         opj_image_t *l_image = NULL;
2984         OPJ_UINT32 l_comp_room;
2985         OPJ_UINT32 l_comp_no;
2986
2987         /* preconditions */
2988         assert(p_header_data != 00);
2989         assert(p_j2k != 00);
2990         assert(p_manager != 00);
2991
2992         l_cp = &(p_j2k->m_cp);
2993         l_tcp = (p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH ) ? /*FIXME J2K_DEC_STATE_TPH*/
2994                                 &l_cp->tcps[p_j2k->m_current_tile_number] :
2995                                 p_j2k->m_specific_param.m_decoder.m_default_tcp;
2996         l_image = p_j2k->m_private_image;
2997
2998         l_comp_room = l_image->numcomps <= 256 ? 1 : 2;
2999
3000         /* make sure room is sufficient*/
3001         if (p_header_size < l_comp_room + 1) {
3002                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading COC marker\n");
3003                 return OPJ_FALSE;
3004         }
3005         p_header_size -= l_comp_room + 1;
3006
3007         opj_read_bytes(p_header_data,&l_comp_no,l_comp_room);                   /* Ccoc */
3008         p_header_data += l_comp_room;
3009         if (l_comp_no >= l_image->numcomps) {
3010                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading COC marker (bad number of components)\n");
3011                 return OPJ_FALSE;
3012         }
3013
3014         opj_read_bytes(p_header_data,&l_tcp->tccps[l_comp_no].csty,1);                  /* Scoc */
3015         ++p_header_data ;
3016
3017         if (! j2k_read_SPCod_SPCoc(p_j2k,l_comp_no,p_header_data,&p_header_size,p_manager)) {
3018                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading COC marker\n");
3019                 return OPJ_FALSE;
3020         }
3021
3022         if (p_header_size != 0) {
3023                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading COC marker\n");
3024                 return OPJ_FALSE;
3025         }
3026         return OPJ_TRUE;
3027 }
3028
3029 static void j2k_write_qcx(opj_j2k_t *j2k, int compno) {
3030         int bandno, numbands;
3031         int expn, mant;
3032         
3033         opj_cp_t *cp = j2k->cp;
3034         opj_tcp_t *tcp = &cp->tcps[j2k->curtileno];
3035         opj_tccp_t *tccp = &tcp->tccps[compno];
3036         opj_cio_t *cio = j2k->cio;
3037         
3038         cio_write(cio, tccp->qntsty + (tccp->numgbits << 5), 1);        /* Sqcx */
3039         numbands = tccp->qntsty == J2K_CCP_QNTSTY_SIQNT ? 1 : tccp->numresolutions * 3 - 2;
3040         
3041         for (bandno = 0; bandno < numbands; bandno++) {
3042                 expn = tccp->stepsizes[bandno].expn;
3043                 mant = tccp->stepsizes[bandno].mant;
3044                 
3045                 if (tccp->qntsty == J2K_CCP_QNTSTY_NOQNT) {
3046                         cio_write(cio, expn << 3, 1);   /* SPqcx_i */
3047                 } else {
3048                         cio_write(cio, (expn << 11) + mant, 2); /* SPqcx_i */
3049                 }
3050         }
3051 }
3052
3053
3054 static void j2k_write_qcd(opj_j2k_t *j2k) {
3055         int lenp, len;
3056
3057         opj_cio_t *cio = j2k->cio;
3058         
3059         cio_write(cio, J2K_MS_QCD, 2);  /* QCD */
3060         lenp = cio_tell(cio);
3061         cio_skip(cio, 2);
3062         j2k_write_qcx(j2k, 0);
3063         len = cio_tell(cio) - lenp;
3064         cio_seek(cio, lenp);
3065         cio_write(cio, len, 2);                 /* Lqcd */
3066         cio_seek(cio, lenp + len);
3067
3068         if(j2k->cstr_info)
3069           j2k_add_mhmarker(j2k->cstr_info, J2K_MS_QCD, lenp, len);
3070 }
3071
3072 /**
3073  * Writes the QCD marker (quantization default)
3074  *
3075  * @param       p_comp_number   the index of the component to output.
3076  * @param       p_stream                                the stream to write data to.
3077  * @param       p_j2k                           J2K codec.
3078  * @param       p_manager               the user event manager.
3079 */
3080 opj_bool j2k_write_qcd_v2(      opj_j2k_v2_t *p_j2k,
3081                                                         struct opj_stream_private *p_stream,
3082                                                         struct opj_event_mgr * p_manager )
3083 {
3084         opj_cp_v2_t *l_cp = 00;
3085         opj_tcp_v2_t *l_tcp = 00;
3086         OPJ_UINT32 l_qcd_size,l_remaining_size;
3087         OPJ_BYTE * l_current_data = 00;
3088
3089         /* preconditions */
3090         assert(p_j2k != 00);
3091         assert(p_manager != 00);
3092         assert(p_stream != 00);
3093
3094         l_cp = &(p_j2k->m_cp);
3095         l_tcp = &l_cp->tcps[p_j2k->m_current_tile_number];
3096         l_qcd_size = 4 + j2k_get_SQcd_SQcc_size(p_j2k,p_j2k->m_current_tile_number,0);
3097         l_remaining_size = l_qcd_size;
3098
3099         if (l_qcd_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
3100                 p_j2k->m_specific_param.m_encoder.m_header_tile_data
3101                         = (OPJ_BYTE*)opj_realloc(
3102                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
3103                                 l_qcd_size);
3104
3105                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
3106                         return OPJ_FALSE;
3107                 }
3108
3109                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_qcd_size;
3110         }
3111
3112         l_current_data = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
3113
3114         opj_write_bytes(l_current_data,J2K_MS_QCD,2);           /* QCD */
3115         l_current_data += 2;
3116
3117         opj_write_bytes(l_current_data,l_qcd_size-2,2);         /* L_QCD */
3118         l_current_data += 2;
3119
3120         l_remaining_size -= 4;
3121
3122         if (! j2k_write_SQcd_SQcc(p_j2k,p_j2k->m_current_tile_number,0,l_current_data,&l_remaining_size,p_manager)) {
3123                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error writting QCD marker\n");
3124                 return OPJ_FALSE;
3125         }
3126
3127         if (l_remaining_size != 0) {
3128                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error writting QCD marker\n");
3129                 return OPJ_FALSE;
3130         }
3131
3132         if (opj_stream_write_data(p_stream, p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_qcd_size,p_manager) != l_qcd_size) {
3133                 return OPJ_FALSE;
3134         }
3135
3136         return OPJ_TRUE;
3137 }
3138
3139 /**
3140  * Reads a QCD marker (Quantization defaults)
3141  * @param       p_header_data   the data contained in the QCD box.
3142  * @param       p_j2k                   the jpeg2000 codec.
3143  * @param       p_header_size   the size of the data contained in the QCD marker.
3144  * @param       p_manager               the user event manager.
3145 */
3146 static opj_bool opj_j2k_read_qcd (  opj_j2k_v2_t *p_j2k,
3147                                     OPJ_BYTE * p_header_data,
3148                                     OPJ_UINT32 p_header_size,
3149                                     opj_event_mgr_t * p_manager 
3150                                     )
3151 {
3152         /* preconditions */
3153         assert(p_header_data != 00);
3154         assert(p_j2k != 00);
3155         assert(p_manager != 00);
3156
3157         if (! j2k_read_SQcd_SQcc(p_j2k,0,p_header_data,&p_header_size,p_manager)) {
3158                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading QCD marker\n");
3159                 return OPJ_FALSE;
3160         }
3161
3162         if (p_header_size != 0) {
3163                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading QCD marker\n");
3164                 return OPJ_FALSE;
3165         }
3166
3167         /* Apply the quantization parameters to other components of the current tile or the m_default_tcp */
3168         j2k_copy_tile_quantization_parameters(p_j2k);
3169
3170         return OPJ_TRUE;
3171 }
3172
3173 static void j2k_write_qcc(opj_j2k_t *j2k, int compno) {
3174         int lenp, len;
3175
3176         opj_cio_t *cio = j2k->cio;
3177         
3178         cio_write(cio, J2K_MS_QCC, 2);  /* QCC */
3179         lenp = cio_tell(cio);
3180         cio_skip(cio, 2);
3181         cio_write(cio, compno, j2k->image->numcomps <= 256 ? 1 : 2);    /* Cqcc */
3182         j2k_write_qcx(j2k, compno);
3183         len = cio_tell(cio) - lenp;
3184         cio_seek(cio, lenp);
3185         cio_write(cio, len, 2);                 /* Lqcc */
3186         cio_seek(cio, lenp + len);
3187 }
3188
3189 /**
3190  * Writes the QCC marker (quantization component)
3191  *
3192  * @param       p_comp_no       the index of the component to output.
3193  * @param       p_stream                                the stream to write data to.
3194  * @param       p_j2k                           J2K codec.
3195  * @param       p_manager               the user event manager.
3196 */
3197 opj_bool j2k_write_qcc_v2(      opj_j2k_v2_t *p_j2k,
3198                                                         OPJ_UINT32 p_comp_no,
3199                                                         struct opj_stream_private *p_stream,
3200                                                         struct opj_event_mgr * p_manager )
3201 {
3202         OPJ_UINT32 l_qcc_size,l_remaining_size;
3203
3204         /* preconditions */
3205         assert(p_j2k != 00);
3206         assert(p_manager != 00);
3207         assert(p_stream != 00);
3208
3209         l_qcc_size = 6 + j2k_get_SQcd_SQcc_size(p_j2k,p_j2k->m_current_tile_number,p_comp_no);
3210         l_remaining_size = l_qcc_size;
3211
3212         if (l_qcc_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
3213                 p_j2k->m_specific_param.m_encoder.m_header_tile_data
3214                         = (OPJ_BYTE*)opj_realloc(
3215                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
3216                                 l_qcc_size);
3217                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
3218                         return OPJ_FALSE;
3219                 }
3220
3221                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_qcc_size;
3222         }
3223
3224         j2k_write_qcc_in_memory(p_j2k,p_comp_no,p_j2k->m_specific_param.m_encoder.m_header_tile_data,&l_remaining_size,p_manager);
3225
3226         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_qcc_size,p_manager) != l_qcc_size) {
3227                 return OPJ_FALSE;
3228         }
3229
3230         return OPJ_TRUE;
3231 }
3232
3233 /**
3234  * Writes the QCC marker (quantization component)
3235  *
3236  * @param       p_comp_no       the index of the component to output.
3237  * @param       p_stream                                the stream to write data to.
3238  * @param       p_j2k                           J2K codec.
3239  * @param       p_manager               the user event manager.
3240 */
3241 void j2k_write_qcc_in_memory(   opj_j2k_v2_t *p_j2k,
3242                                                                 OPJ_UINT32 p_comp_no,
3243                                                                 OPJ_BYTE * p_data,
3244                                                                 OPJ_UINT32 * p_data_written,
3245                                                                 struct opj_event_mgr * p_manager )
3246 {
3247         OPJ_UINT32 l_qcc_size,l_remaining_size;
3248         OPJ_BYTE * l_current_data = 00;
3249
3250         /* preconditions */
3251         assert(p_j2k != 00);
3252         assert(p_manager != 00);
3253
3254         l_qcc_size = 6 + j2k_get_SQcd_SQcc_size(p_j2k,p_j2k->m_current_tile_number,p_comp_no);
3255         l_remaining_size = l_qcc_size;
3256
3257         l_current_data = p_data;
3258
3259         opj_write_bytes(l_current_data,J2K_MS_QCC,2);           /* QCC */
3260         l_current_data += 2;
3261
3262         if (p_j2k->m_private_image->numcomps <= 256) {
3263                 --l_qcc_size;
3264
3265                 opj_write_bytes(l_current_data,l_qcc_size-2,2);         /* L_QCC */
3266                 l_current_data += 2;
3267
3268                 opj_write_bytes(l_current_data, p_comp_no, 1);  /* Cqcc */
3269                 ++l_current_data;
3270
3271                 /* in the case only one byte is sufficient the last byte allocated is useless -> still do -6 for available */
3272                 l_remaining_size -= 6;
3273         }
3274         else {
3275                 opj_write_bytes(l_current_data,l_qcc_size-2,2);         /* L_QCC */
3276                 l_current_data += 2;
3277
3278                 opj_write_bytes(l_current_data, p_comp_no, 2);  /* Cqcc */
3279                 l_current_data+=2;
3280
3281                 l_remaining_size -= 6;
3282         }
3283
3284         j2k_write_SQcd_SQcc(p_j2k,p_j2k->m_current_tile_number,p_comp_no,l_current_data,&l_remaining_size,p_manager);
3285
3286         *p_data_written = l_qcc_size;
3287 }
3288
3289 /**
3290  * Gets the maximum size taken by a qcc.
3291  */
3292 OPJ_UINT32 j2k_get_max_qcc_size (opj_j2k_v2_t *p_j2k)
3293 {
3294         return j2k_get_max_coc_size(p_j2k);
3295 }
3296
3297 /**
3298  * Reads a QCC marker (Quantization component)
3299  * @param       p_header_data   the data contained in the QCC box.
3300  * @param       p_j2k                   the jpeg2000 codec.
3301  * @param       p_header_size   the size of the data contained in the QCC marker.
3302  * @param       p_manager               the user event manager.
3303 */
3304 static opj_bool opj_j2k_read_qcc(   opj_j2k_v2_t *p_j2k,
3305                                     OPJ_BYTE * p_header_data,
3306                                     OPJ_UINT32 p_header_size,
3307                                     opj_event_mgr_t * p_manager
3308                                     )
3309 {
3310         OPJ_UINT32 l_num_comp,l_comp_no;
3311
3312         /* preconditions */
3313         assert(p_header_data != 00);
3314         assert(p_j2k != 00);
3315         assert(p_manager != 00);
3316
3317         l_num_comp = p_j2k->m_private_image->numcomps;
3318
3319         if (l_num_comp <= 256) {
3320                 if (p_header_size < 1) {
3321                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading QCC marker\n");
3322                         return OPJ_FALSE;
3323                 }
3324                 opj_read_bytes(p_header_data,&l_comp_no,1);
3325                 ++p_header_data;
3326                 --p_header_size;
3327         }
3328         else {
3329                 if (p_header_size < 2) {
3330                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading QCC marker\n");
3331                         return OPJ_FALSE;
3332                 }
3333                 opj_read_bytes(p_header_data,&l_comp_no,2);
3334                 p_header_data+=2;
3335                 p_header_size-=2;
3336         }
3337
3338 #ifdef USE_JPWL
3339         if (p_j2k->m_cp.correct) {
3340
3341                 static OPJ_UINT32 backup_compno = 0;
3342
3343                 /* compno is negative or larger than the number of components!!! */
3344                 if (/*(l_comp_no < 0) ||*/ (l_comp_no >= l_num_comp)) {
3345                         opj_event_msg_v2(p_manager, EVT_ERROR,
3346                                 "JPWL: bad component number in QCC (%d out of a maximum of %d)\n",
3347                                 l_comp_no, l_num_comp);
3348                         if (!JPWL_ASSUME) {
3349                                 opj_event_msg_v2(p_manager, EVT_ERROR, "JPWL: giving up\n");
3350                                 return OPJ_FALSE;
3351                         }
3352                         /* we try to correct */
3353                         l_comp_no = backup_compno % l_num_comp;
3354                         opj_event_msg_v2(p_manager, EVT_WARNING, "- trying to adjust this\n"
3355                                 "- setting component number to %d\n",
3356                                 l_comp_no);
3357                 }
3358
3359                 /* keep your private count of tiles */
3360                 backup_compno++;
3361         };
3362 #endif /* USE_JPWL */
3363
3364         if (! j2k_read_SQcd_SQcc(p_j2k,l_comp_no,p_header_data,&p_header_size,p_manager)) {
3365                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading QCC marker\n");
3366                 return OPJ_FALSE;
3367         }
3368
3369         if (p_header_size != 0) {
3370                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading QCC marker\n");
3371                 return OPJ_FALSE;
3372         }
3373
3374         return OPJ_TRUE;
3375 }
3376
3377
3378 static void j2k_write_poc(opj_j2k_t *j2k) {
3379         int len, numpchgs, i;
3380
3381         int numcomps = j2k->image->numcomps;
3382         
3383         opj_cp_t *cp = j2k->cp;
3384         opj_tcp_t *tcp = &cp->tcps[j2k->curtileno];
3385         opj_tccp_t *tccp = &tcp->tccps[0];
3386         opj_cio_t *cio = j2k->cio;
3387
3388         numpchgs = 1 + tcp->numpocs;
3389         cio_write(cio, J2K_MS_POC, 2);  /* POC  */
3390         len = 2 + (5 + 2 * (numcomps <= 256 ? 1 : 2)) * numpchgs;
3391         cio_write(cio, len, 2);         /* Lpoc */
3392         for (i = 0; i < numpchgs; i++) {
3393                 opj_poc_t *poc = &tcp->pocs[i];
3394                 cio_write(cio, poc->resno0, 1); /* RSpoc_i */
3395                 cio_write(cio, poc->compno0, (numcomps <= 256 ? 1 : 2));        /* CSpoc_i */
3396                 cio_write(cio, poc->layno1, 2); /* LYEpoc_i */
3397                 poc->layno1 = int_min(poc->layno1, tcp->numlayers);
3398                 cio_write(cio, poc->resno1, 1); /* REpoc_i */
3399                 poc->resno1 = int_min(poc->resno1, tccp->numresolutions);
3400                 cio_write(cio, poc->compno1, (numcomps <= 256 ? 1 : 2));        /* CEpoc_i */
3401                 poc->compno1 = int_min(poc->compno1, numcomps);
3402                 cio_write(cio, poc->prg, 1);    /* Ppoc_i */
3403         }
3404 }
3405
3406 /**
3407  * Writes the POC marker (Progression Order Change)
3408  * 
3409  * @param       p_stream                                the stream to write data to.
3410  * @param       p_j2k                           J2K codec.
3411  * @param       p_manager               the user event manager.
3412 */
3413 opj_bool j2k_write_poc_v2(      opj_j2k_v2_t *p_j2k,
3414                                                         struct opj_stream_private *p_stream,
3415                                                         struct opj_event_mgr * p_manager )
3416 {
3417         OPJ_UINT32 l_nb_comp;
3418         OPJ_UINT32 l_nb_poc;
3419         OPJ_UINT32 l_poc_size;
3420         OPJ_UINT32 l_written_size = 0;
3421         opj_tcp_v2_t *l_tcp = 00;
3422         opj_tccp_t *l_tccp = 00;
3423         OPJ_UINT32 l_poc_room;
3424
3425         // preconditions
3426         assert(p_j2k != 00);
3427         assert(p_manager != 00);
3428         assert(p_stream != 00);
3429
3430         l_tcp = &p_j2k->m_cp.tcps[p_j2k->m_current_tile_number];
3431         l_tccp = &l_tcp->tccps[0];
3432         l_nb_comp = p_j2k->m_private_image->numcomps;
3433         l_nb_poc = 1 + l_tcp->numpocs;
3434         
3435         if (l_nb_comp <= 256) {
3436                 l_poc_room = 1;
3437         }
3438         else {
3439                 l_poc_room = 2;
3440         }
3441         l_poc_size = 4 + (5 + 2 * l_poc_room) * l_nb_poc;
3442         
3443         if (l_poc_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
3444                 p_j2k->m_specific_param.m_encoder.m_header_tile_data 
3445                         = (OPJ_BYTE*)opj_realloc(
3446                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
3447                                 l_poc_size);
3448                 
3449                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
3450                         return OPJ_FALSE;
3451                 }
3452
3453                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_poc_size;
3454         }
3455
3456         j2k_write_poc_in_memory(p_j2k,p_j2k->m_specific_param.m_encoder.m_header_tile_data,&l_written_size,p_manager);
3457
3458         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_poc_size,p_manager) != l_poc_size) {
3459                 return OPJ_FALSE;
3460         }
3461
3462         return OPJ_TRUE;
3463 }
3464
3465
3466 /**
3467  * Writes the POC marker (Progression Order Change)
3468  *
3469  * @param       p_stream                                the stream to write data to.
3470  * @param       p_j2k                           J2K codec.
3471  * @param       p_manager               the user event manager.
3472 */
3473 void j2k_write_poc_in_memory(   opj_j2k_v2_t *p_j2k,
3474                                                                 OPJ_BYTE * p_data,
3475                                                                 OPJ_UINT32 * p_data_written,
3476                                                                 struct opj_event_mgr * p_manager )
3477 {
3478         OPJ_UINT32 i;
3479         OPJ_BYTE * l_current_data = 00;
3480         OPJ_UINT32 l_nb_comp;
3481         OPJ_UINT32 l_nb_poc;
3482         OPJ_UINT32 l_poc_size;
3483         opj_image_t *l_image = 00;
3484         opj_tcp_v2_t *l_tcp = 00;
3485         opj_tccp_t *l_tccp = 00;
3486         opj_poc_t *l_current_poc = 00;
3487         OPJ_UINT32 l_poc_room;
3488
3489         /* preconditions */
3490         assert(p_j2k != 00);
3491         assert(p_manager != 00);
3492
3493         l_tcp = &p_j2k->m_cp.tcps[p_j2k->m_current_tile_number];
3494         l_tccp = &l_tcp->tccps[0];
3495         l_image = p_j2k->m_private_image;
3496         l_nb_comp = l_image->numcomps;
3497         l_nb_poc = 1 + l_tcp->numpocs;
3498
3499         if (l_nb_comp <= 256) {
3500                 l_poc_room = 1;
3501         }
3502         else {
3503                 l_poc_room = 2;
3504         }
3505
3506         l_poc_size = 4 + (5 + 2 * l_poc_room) * l_nb_poc;
3507
3508         l_current_data = p_data;
3509
3510         opj_write_bytes(l_current_data,J2K_MS_POC,2);                                   /* POC  */
3511         l_current_data += 2;
3512
3513         opj_write_bytes(l_current_data,l_poc_size-2,2);                                 /* Lpoc */
3514         l_current_data += 2;
3515
3516         l_current_poc =  l_tcp->pocs;
3517         for (i = 0; i < l_nb_poc; ++i) {
3518                 opj_write_bytes(l_current_data,l_current_poc->resno0,1);                                /* RSpoc_i */
3519                 ++l_current_data;
3520
3521                 opj_write_bytes(l_current_data,l_current_poc->compno0,l_poc_room);              /* CSpoc_i */
3522                 l_current_data+=l_poc_room;
3523
3524                 opj_write_bytes(l_current_data,l_current_poc->layno1,2);                                /* LYEpoc_i */
3525                 l_current_data+=2;
3526
3527                 opj_write_bytes(l_current_data,l_current_poc->resno1,1);                                /* REpoc_i */
3528                 ++l_current_data;
3529
3530                 opj_write_bytes(l_current_data,l_current_poc->compno1,l_poc_room);              /* CEpoc_i */
3531                 l_current_data+=l_poc_room;
3532
3533                 opj_write_bytes(l_current_data,l_current_poc->prg,1);                                   /* Ppoc_i */
3534                 ++l_current_data;
3535
3536                 /* change the value of the max layer according to the actual number of layers in the file, components and resolutions*/
3537                 l_current_poc->layno1 = int_min(l_current_poc->layno1, l_tcp->numlayers);
3538                 l_current_poc->resno1 = int_min(l_current_poc->resno1, l_tccp->numresolutions);
3539                 l_current_poc->compno1 = int_min(l_current_poc->compno1, l_nb_comp);
3540
3541                 ++l_current_poc;
3542         }
3543
3544         *p_data_written = l_poc_size;
3545 }
3546
3547 /**
3548  * Gets the maximum size taken by the writing of a POC.
3549  */
3550 OPJ_UINT32 j2k_get_max_poc_size(opj_j2k_v2_t *p_j2k)
3551 {
3552         opj_tcp_v2_t * l_tcp = 00;
3553         OPJ_UINT32 l_nb_tiles = 0;
3554         OPJ_UINT32 l_max_poc = 0;
3555         OPJ_UINT32 i;
3556
3557         l_tcp = p_j2k->m_cp.tcps;
3558         l_nb_tiles = p_j2k->m_cp.th * p_j2k->m_cp.tw;
3559
3560         for (i=0;i<l_nb_tiles;++i) {
3561                 l_max_poc = uint_max(l_max_poc,l_tcp->numpocs);
3562                 ++l_tcp;
3563         }
3564
3565         ++l_max_poc;
3566
3567         return 4 + 9 * l_max_poc;
3568 }
3569
3570 /**
3571  * Gets the maximum size taken by the toc headers of all the tile parts of any given tile.
3572  */
3573 OPJ_UINT32 j2k_get_max_toc_size (opj_j2k_v2_t *p_j2k)
3574 {
3575         OPJ_UINT32 i;
3576         OPJ_UINT32 l_nb_tiles;
3577         OPJ_UINT32 l_max = 0;
3578         opj_tcp_v2_t * l_tcp = 00;
3579
3580         l_tcp = p_j2k->m_cp.tcps;
3581         l_nb_tiles = p_j2k->m_cp.tw * p_j2k->m_cp.th ;
3582
3583         for (i=0;i<l_nb_tiles;++i) {
3584                 l_max = uint_max(l_max,l_tcp->m_nb_tile_parts);
3585
3586                 ++l_tcp;
3587         }
3588
3589         return 12 * l_max;
3590 }
3591
3592
3593 /**
3594  * Gets the maximum size taken by the headers of the SOT.
3595  *
3596  * @param       p_j2k   the jpeg2000 codec to use.
3597  */
3598 OPJ_UINT32 j2k_get_specific_header_sizes(opj_j2k_v2_t *p_j2k)
3599 {
3600         OPJ_UINT32 l_nb_bytes = 0;
3601         OPJ_UINT32 l_nb_comps;
3602         OPJ_UINT32 l_coc_bytes,l_qcc_bytes;
3603
3604         l_nb_comps = p_j2k->m_private_image->numcomps - 1;
3605         l_nb_bytes += j2k_get_max_toc_size(p_j2k);
3606
3607         if (p_j2k->m_cp.m_specific_param.m_enc.m_cinema == 0) {
3608                 l_coc_bytes = j2k_get_max_coc_size(p_j2k);
3609                 l_nb_bytes += l_nb_comps * l_coc_bytes;
3610
3611                 l_qcc_bytes = j2k_get_max_qcc_size(p_j2k);
3612                 l_nb_bytes += l_nb_comps * l_qcc_bytes;
3613         }
3614
3615         l_nb_bytes += j2k_get_max_poc_size(p_j2k);
3616
3617         /*** DEVELOPER CORNER, Add room for your headers ***/
3618
3619         return l_nb_bytes;
3620 }
3621
3622
3623 /**
3624  * Reads a POC marker (Progression Order Change)
3625  *
3626  * @param       p_header_data   the data contained in the POC box.
3627  * @param       p_j2k                   the jpeg2000 codec.
3628  * @param       p_header_size   the size of the data contained in the POC marker.
3629  * @param       p_manager               the user event manager.
3630 */
3631 static opj_bool opj_j2k_read_poc (  opj_j2k_v2_t *p_j2k,
3632                                     OPJ_BYTE * p_header_data,
3633                                     OPJ_UINT32 p_header_size,
3634                                     opj_event_mgr_t * p_manager 
3635                                     )
3636 {
3637         OPJ_UINT32 i, l_nb_comp, l_tmp;
3638         opj_image_t * l_image = 00;
3639         OPJ_UINT32 l_old_poc_nb, l_current_poc_nb, l_current_poc_remaining;
3640         OPJ_UINT32 l_chunk_size, l_comp_room;
3641
3642         opj_cp_v2_t *l_cp = 00;
3643         opj_tcp_v2_t *l_tcp = 00;
3644         opj_poc_t *l_current_poc = 00;
3645
3646         /* preconditions */
3647         assert(p_header_data != 00);
3648         assert(p_j2k != 00);
3649         assert(p_manager != 00);
3650
3651         l_image = p_j2k->m_private_image;
3652         l_nb_comp = l_image->numcomps;
3653         if (l_nb_comp <= 256) {
3654                 l_comp_room = 1;
3655         }
3656         else {
3657                 l_comp_room = 2;
3658         }
3659         l_chunk_size = 5 + 2 * l_comp_room;
3660         l_current_poc_nb = p_header_size / l_chunk_size;
3661         l_current_poc_remaining = p_header_size % l_chunk_size;
3662
3663         if ((l_current_poc_nb <= 0) || (l_current_poc_remaining != 0)) {
3664                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading POC marker\n");
3665                 return OPJ_FALSE;
3666         }
3667
3668         l_cp = &(p_j2k->m_cp);
3669         l_tcp = (p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH) ?
3670                                 &l_cp->tcps[p_j2k->m_current_tile_number] :
3671                                 p_j2k->m_specific_param.m_decoder.m_default_tcp;
3672         l_old_poc_nb = l_tcp->POC ? l_tcp->numpocs + 1 : 0;
3673         l_current_poc_nb += l_old_poc_nb;
3674
3675         assert(l_current_poc_nb < 32);
3676
3677         /* now poc is in use.*/
3678         l_tcp->POC = 1;
3679
3680         l_current_poc = &l_tcp->pocs[l_old_poc_nb];
3681         for     (i = l_old_poc_nb; i < l_current_poc_nb; ++i) {
3682                 opj_read_bytes(p_header_data,&(l_current_poc->resno0),1);                               /* RSpoc_i */
3683                 ++p_header_data;
3684                 opj_read_bytes(p_header_data,&(l_current_poc->compno0),l_comp_room);    /* CSpoc_i */
3685                 p_header_data+=l_comp_room;
3686                 opj_read_bytes(p_header_data,&(l_current_poc->layno1),2);                               /* LYEpoc_i */
3687                 p_header_data+=2;
3688                 opj_read_bytes(p_header_data,&(l_current_poc->resno1),1);                               /* REpoc_i */
3689                 ++p_header_data;
3690                 opj_read_bytes(p_header_data,&(l_current_poc->compno1),l_comp_room);    /* CEpoc_i */
3691                 p_header_data+=l_comp_room;
3692                 opj_read_bytes(p_header_data,&l_tmp,1);                                                                 /* Ppoc_i */
3693                 ++p_header_data;
3694                 l_current_poc->prg = (OPJ_PROG_ORDER) l_tmp;
3695                 /* make sure comp is in acceptable bounds */
3696                 l_current_poc->compno1 = uint_min(l_current_poc->compno1, l_nb_comp);
3697                 ++l_current_poc;
3698         }
3699
3700         l_tcp->numpocs = l_current_poc_nb - 1;
3701         return OPJ_TRUE;
3702 }
3703
3704 /**
3705  * Reads a CRG marker (Component registration)
3706  *
3707  * @param       p_header_data   the data contained in the TLM box.
3708  * @param       p_j2k                   the jpeg2000 codec.
3709  * @param       p_header_size   the size of the data contained in the TLM marker.
3710  * @param       p_manager               the user event manager.
3711 */
3712 static opj_bool opj_j2k_read_crg (  opj_j2k_v2_t *p_j2k,
3713                                     OPJ_BYTE * p_header_data,
3714                                     OPJ_UINT32 p_header_size,
3715                                     opj_event_mgr_t * p_manager 
3716                                     )
3717 {
3718         OPJ_UINT32 l_nb_comp;
3719         /* preconditions */
3720         assert(p_header_data != 00);
3721         assert(p_j2k != 00);
3722         assert(p_manager != 00);
3723
3724         l_nb_comp = p_j2k->m_private_image->numcomps;
3725
3726         if (p_header_size != l_nb_comp *4) {
3727                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading CRG marker\n");
3728                 return OPJ_FALSE;
3729         }
3730         /* Do not care of this at the moment since only local variables are set here */
3731         /*
3732         for
3733                 (i = 0; i < l_nb_comp; ++i)
3734         {
3735                 opj_read_bytes(p_header_data,&l_Xcrg_i,2);                              // Xcrg_i
3736                 p_header_data+=2;
3737                 opj_read_bytes(p_header_data,&l_Ycrg_i,2);                              // Xcrg_i
3738                 p_header_data+=2;
3739         }
3740         */
3741         return OPJ_TRUE;
3742 }
3743
3744 /**
3745  * Reads a TLM marker (Tile Length Marker)
3746  *
3747  * @param       p_header_data   the data contained in the TLM box.
3748  * @param       p_j2k                   the jpeg2000 codec.
3749  * @param       p_header_size   the size of the data contained in the TLM marker.
3750  * @param       p_manager               the user event manager.
3751 */
3752 static opj_bool opj_j2k_read_tlm (  opj_j2k_v2_t *p_j2k,
3753                                     OPJ_BYTE * p_header_data,
3754                                     OPJ_UINT32 p_header_size,
3755                                     opj_event_mgr_t * p_manager
3756                                     )
3757 {
3758         OPJ_UINT32 l_Ztlm, l_Stlm, l_ST, l_SP, l_tot_num_tp, l_tot_num_tp_remaining, l_quotient, l_Ptlm_size;
3759         /* preconditions */
3760         assert(p_header_data != 00);
3761         assert(p_j2k != 00);
3762         assert(p_manager != 00);
3763
3764         if (p_header_size < 2) {
3765                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading TLM marker\n");
3766                 return OPJ_FALSE;
3767         }
3768         p_header_size -= 2;
3769
3770         opj_read_bytes(p_header_data,&l_Ztlm,1);                                /* Ztlm */
3771         ++p_header_data;
3772         opj_read_bytes(p_header_data,&l_Stlm,1);                                /* Stlm */
3773         ++p_header_data;
3774
3775         l_ST = ((l_Stlm >> 4) & 0x3);
3776         l_SP = (l_Stlm >> 6) & 0x1;
3777
3778         l_Ptlm_size = (l_SP + 1) * 2;
3779         l_quotient = l_Ptlm_size + l_ST;
3780
3781         l_tot_num_tp = p_header_size / l_quotient;
3782         l_tot_num_tp_remaining = p_header_size % l_quotient;
3783
3784         if (l_tot_num_tp_remaining != 0) {
3785                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading TLM marker\n");
3786                 return OPJ_FALSE;
3787         }
3788         /* FIXME Do not care of this at the moment since only local variables are set here */
3789         /*
3790         for
3791                 (i = 0; i < l_tot_num_tp; ++i)
3792         {
3793                 opj_read_bytes(p_header_data,&l_Ttlm_i,l_ST);                           // Ttlm_i
3794                 p_header_data += l_ST;
3795                 opj_read_bytes(p_header_data,&l_Ptlm_i,l_Ptlm_size);            // Ptlm_i
3796                 p_header_data += l_Ptlm_size;
3797         }*/
3798         return OPJ_TRUE;
3799 }
3800
3801
3802 /**
3803  * Reads a PLM marker (Packet length, main header marker)
3804  *
3805  * @param       p_header_data   the data contained in the TLM box.
3806  * @param       p_j2k                   the jpeg2000 codec.
3807  * @param       p_header_size   the size of the data contained in the TLM marker.
3808  * @param       p_manager               the user event manager.
3809 */
3810 static opj_bool opj_j2k_read_plm (  opj_j2k_v2_t *p_j2k,
3811                                     OPJ_BYTE * p_header_data,
3812                                     OPJ_UINT32 p_header_size,
3813                                     opj_event_mgr_t * p_manager
3814                                     )
3815 {
3816         /* preconditions */
3817         assert(p_header_data != 00);
3818         assert(p_j2k != 00);
3819         assert(p_manager != 00);
3820
3821         if (p_header_size < 1) {
3822                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading PLM marker\n");
3823                 return OPJ_FALSE;
3824         }
3825         /* Do not care of this at the moment since only local variables are set here */
3826         /*
3827         opj_read_bytes(p_header_data,&l_Zplm,1);                                        // Zplm
3828         ++p_header_data;
3829         --p_header_size;
3830
3831         while
3832                 (p_header_size > 0)
3833         {
3834                 opj_read_bytes(p_header_data,&l_Nplm,1);                                // Nplm
3835                 ++p_header_data;
3836                 p_header_size -= (1+l_Nplm);
3837                 if
3838                         (p_header_size < 0)
3839                 {
3840                         opj_event_msg(p_manager, EVT_ERROR, "Error reading PLM marker\n");
3841                         return false;
3842                 }
3843                 for
3844                         (i = 0; i < l_Nplm; ++i)
3845                 {
3846                         opj_read_bytes(p_header_data,&l_tmp,1);                         // Iplm_ij
3847                         ++p_header_data;
3848                         // take only the last seven bytes
3849                         l_packet_len |= (l_tmp & 0x7f);
3850                         if
3851                                 (l_tmp & 0x80)
3852                         {
3853                                 l_packet_len <<= 7;
3854                         }
3855                         else
3856                         {
3857                 // store packet length and proceed to next packet
3858                                 l_packet_len = 0;
3859                         }
3860                 }
3861                 if
3862                         (l_packet_len != 0)
3863                 {
3864                         opj_event_msg(p_manager, EVT_ERROR, "Error reading PLM marker\n");
3865                         return false;
3866                 }
3867         }
3868         */
3869         return OPJ_TRUE;
3870 }
3871
3872 /**
3873  * Reads a PLT marker (Packet length, tile-part header)
3874  *
3875  * @param       p_header_data   the data contained in the PLT box.
3876  * @param       p_j2k                   the jpeg2000 codec.
3877  * @param       p_header_size   the size of the data contained in the PLT marker.
3878  * @param       p_manager               the user event manager.
3879 */
3880 static opj_bool opj_j2k_read_plt (  opj_j2k_v2_t *p_j2k,
3881                                     OPJ_BYTE * p_header_data,
3882                                     OPJ_UINT32 p_header_size,
3883                                     opj_event_mgr_t * p_manager
3884                                     )
3885 {
3886         OPJ_UINT32 l_Zplt, l_tmp, l_packet_len = 0, i;
3887
3888         /* preconditions */
3889         assert(p_header_data != 00);
3890         assert(p_j2k != 00);
3891         assert(p_manager != 00);
3892
3893         if (p_header_size < 1) {
3894                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading PLT marker\n");
3895                 return OPJ_FALSE;
3896         }
3897
3898         opj_read_bytes(p_header_data,&l_Zplt,1);                /* Zplt */
3899         ++p_header_data;
3900         --p_header_size;
3901
3902         for (i = 0; i < p_header_size; ++i) {
3903                 opj_read_bytes(p_header_data,&l_tmp,1);         /* Iplt_ij */
3904                 ++p_header_data;
3905                 /* take only the last seven bytes */
3906                 l_packet_len |= (l_tmp & 0x7f);
3907                 if (l_tmp & 0x80) {
3908                         l_packet_len <<= 7;
3909                 }
3910                 else {
3911             /* store packet length and proceed to next packet */
3912                         l_packet_len = 0;
3913                 }
3914         }
3915
3916         if (l_packet_len != 0) {
3917                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading PLT marker\n");
3918                 return OPJ_FALSE;
3919         }
3920
3921         return OPJ_TRUE;
3922 }
3923
3924
3925 /**
3926  * Reads a PPM marker (Packed packet headers, main header)
3927  *
3928  * @param       p_header_data   the data contained in the POC box.
3929  * @param       p_j2k                   the jpeg2000 codec.
3930  * @param       p_header_size   the size of the data contained in the POC marker.
3931  * @param       p_manager               the user event manager.
3932 */
3933 #if 0
3934 opj_bool j2k_read_ppm_v2 (
3935                                                 opj_j2k_v2_t *p_j2k,
3936                                                 OPJ_BYTE * p_header_data,
3937                                                 OPJ_UINT32 p_header_size,
3938                                                 struct opj_event_mgr * p_manager
3939                                         )
3940 {
3941
3942         opj_cp_v2_t *l_cp = 00;
3943         OPJ_UINT32 l_remaining_data, l_Z_ppm, l_N_ppm;
3944
3945         /* preconditions */
3946         assert(p_header_data != 00);
3947         assert(p_j2k != 00);
3948         assert(p_manager != 00);
3949
3950         if (p_header_size < 1) {
3951                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading PPM marker\n");
3952                 return OPJ_FALSE;
3953         }
3954
3955         l_cp = &(p_j2k->m_cp);
3956         l_cp->ppm = 1;
3957
3958         opj_read_bytes(p_header_data,&l_Z_ppm,1);               /* Z_ppm */
3959         ++p_header_data;
3960         --p_header_size;
3961
3962         /* First PPM marker */
3963         if (l_Z_ppm == 0) {
3964                 if (p_header_size < 4) {
3965                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading PPM marker\n");
3966                         return OPJ_FALSE;
3967                 }
3968
3969                 opj_read_bytes(p_header_data,&l_N_ppm,4);               /* N_ppm */
3970                 p_header_data+=4;
3971                 p_header_size-=4;
3972
3973                 /* First PPM marker: Initialization */
3974                 l_cp->ppm_len = l_N_ppm;
3975                 l_cp->ppm_data_size = 0;
3976
3977                 l_cp->ppm_buffer = (OPJ_BYTE *) opj_malloc(l_cp->ppm_len);
3978                 if (l_cp->ppm_buffer == 00) {
3979                         opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory reading ppm marker\n");
3980                         return OPJ_FALSE;
3981                 }
3982                 memset(l_cp->ppm_buffer,0,l_cp->ppm_len);
3983
3984                 l_cp->ppm_data = l_cp->ppm_buffer;
3985         }
3986
3987         while (1) {
3988                 if (l_cp->ppm_data_size == l_cp->ppm_len) {
3989                         if (p_header_size >= 4) {
3990                                 /* read a N_ppm */
3991                                 opj_read_bytes(p_header_data,&l_N_ppm,4);               /* N_ppm */
3992                                 p_header_data+=4;
3993                                 p_header_size-=4;
3994                                 l_cp->ppm_len += l_N_ppm ;
3995
3996                                 l_cp->ppm_buffer = (OPJ_BYTE *) opj_realloc(l_cp->ppm_buffer, l_cp->ppm_len);
3997                                 if (l_cp->ppm_buffer == 00) {
3998                                         opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory reading ppm marker\n");
3999                                         return OPJ_FALSE;
4000                                 }
4001                                 memset(l_cp->ppm_buffer+l_cp->ppm_data_size,0,l_N_ppm);
4002
4003                                 l_cp->ppm_data = l_cp->ppm_buffer;
4004                         }
4005                         else {
4006                                 return OPJ_FALSE;
4007                         }
4008                 }
4009
4010                 l_remaining_data = l_cp->ppm_len - l_cp->ppm_data_size;
4011
4012                 if (l_remaining_data <= p_header_size) {
4013                         /* we must store less information than available in the packet */
4014                         memcpy(l_cp->ppm_buffer + l_cp->ppm_data_size , p_header_data , l_remaining_data);
4015                         l_cp->ppm_data_size = l_cp->ppm_len;
4016                         p_header_size -= l_remaining_data;
4017                         p_header_data += l_remaining_data;
4018                 }
4019                 else {
4020                         memcpy(l_cp->ppm_buffer + l_cp->ppm_data_size , p_header_data , p_header_size);
4021                         l_cp->ppm_data_size += p_header_size;
4022                         p_header_data += p_header_size;
4023                         p_header_size = 0;
4024                         break;
4025                 }
4026         }
4027
4028         return OPJ_TRUE;
4029 }
4030 #endif
4031
4032
4033
4034 /**
4035  * Reads a PPM marker (Packed packet headers, main header)
4036  *
4037  * @param       p_header_data   the data contained in the POC box.
4038  * @param       p_j2k                   the jpeg2000 codec.
4039  * @param       p_header_size   the size of the data contained in the POC marker.
4040  * @param       p_manager               the user event manager.
4041 */
4042 opj_bool j2k_read_ppm_v3 (
4043                                                 opj_j2k_v2_t *p_j2k,
4044                                                 OPJ_BYTE * p_header_data,
4045                                                 OPJ_UINT32 p_header_size,
4046                                                 struct opj_event_mgr * p_manager
4047                                         )
4048 {
4049         opj_cp_v2_t *l_cp = 00;
4050         OPJ_UINT32 l_remaining_data, l_Z_ppm, l_N_ppm;
4051
4052         /* preconditions */
4053         assert(p_header_data != 00);
4054         assert(p_j2k != 00);
4055         assert(p_manager != 00);
4056
4057         /* Minimum size of PPM marker is equal to the size of Zppm element */
4058         if (p_header_size < 1) {
4059                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading PPM marker\n");
4060                 return OPJ_FALSE;
4061         }
4062
4063         l_cp = &(p_j2k->m_cp);
4064         l_cp->ppm = 1;
4065
4066         opj_read_bytes(p_header_data,&l_Z_ppm,1);               /* Z_ppm */
4067         ++p_header_data;
4068         --p_header_size;
4069
4070         /* First PPM marker */
4071         if (l_Z_ppm == 0) {
4072                 /* We need now at least the Nppm^0 element */
4073                 if (p_header_size < 4) {
4074                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading PPM marker\n");
4075                         return OPJ_FALSE;
4076                 }
4077
4078                 opj_read_bytes(p_header_data,&l_N_ppm,4);               /* First N_ppm */
4079                 p_header_data+=4;
4080                 p_header_size-=4;
4081
4082                 /* First PPM marker: Initialization */
4083                 l_cp->ppm_len = l_N_ppm;
4084                 l_cp->ppm_data_read = 0;
4085
4086                 l_cp->ppm_data = (OPJ_BYTE *) opj_malloc(l_cp->ppm_len);
4087                 if (l_cp->ppm_data == 00) {
4088                         opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory reading ppm marker\n");
4089                         return OPJ_FALSE;
4090                 }
4091                 memset(l_cp->ppm_data,0,l_cp->ppm_len);
4092
4093                 l_cp->ppm_data_current = l_cp->ppm_data;
4094
4095                 /*l_cp->ppm_data = l_cp->ppm_buffer;*/
4096         }
4097         else {
4098                 if (p_header_size < 4) {
4099                         opj_event_msg_v2(p_manager, EVT_WARNING, "Empty PPM marker\n");
4100                         return OPJ_TRUE;
4101                 }
4102                 else {
4103                         /* Uncompleted Ippm series in the previous PPM marker?*/
4104                         if (l_cp->ppm_data_read < l_cp->ppm_len) {
4105                                 /* Get the place where add the remaining Ippm series*/
4106                                 l_cp->ppm_data_current = &(l_cp->ppm_data[l_cp->ppm_data_read]);
4107                                 l_N_ppm = l_cp->ppm_len - l_cp->ppm_data_read;
4108                         }
4109                         else {
4110                                 opj_read_bytes(p_header_data,&l_N_ppm,4);               /* First N_ppm */
4111                                 p_header_data+=4;
4112                                 p_header_size-=4;
4113
4114                                 /* Increase the size of ppm_data to add the new Ippm series*/
4115                                 l_cp->ppm_data = (OPJ_BYTE *) opj_realloc(l_cp->ppm_data, l_cp->ppm_len + l_N_ppm);
4116
4117                                 /* Keep the position of the place where concatenate the new series*/
4118                                 l_cp->ppm_data_current = &(l_cp->ppm_data[l_cp->ppm_len]);
4119                                 l_cp->ppm_len += l_N_ppm;
4120                         }
4121                 }
4122         }
4123
4124         l_remaining_data = p_header_size;
4125
4126         while (l_remaining_data >= l_N_ppm) {
4127                 /* read a complete Ippm series*/
4128                 memcpy(l_cp->ppm_data_current, p_header_data, l_N_ppm);
4129                 p_header_size -= l_N_ppm;
4130                 p_header_data += l_N_ppm;
4131
4132                 l_cp->ppm_data_read += l_N_ppm; /* Increase the number of data read*/
4133
4134                 if (p_header_size)
4135                 {
4136                         opj_read_bytes(p_header_data,&l_N_ppm,4);               /* N_ppm^i */
4137                         p_header_data+=4;
4138                         p_header_size-=4;
4139                 }
4140                 else {
4141                         l_remaining_data = p_header_size;
4142                         break;
4143                 }
4144
4145                 l_remaining_data = p_header_size;
4146
4147                 /* Next Ippm series is a complete series ?*/
4148                 if (l_remaining_data > l_N_ppm) {
4149                         /* Increase the size of ppm_data to add the new Ippm series*/
4150                         l_cp->ppm_data = (OPJ_BYTE *) opj_realloc(l_cp->ppm_data, l_cp->ppm_len + l_N_ppm);
4151
4152                         /* Keep the position of the place where concatenate the new series */
4153                         l_cp->ppm_data_current = &(l_cp->ppm_data[l_cp->ppm_len]);
4154                         l_cp->ppm_len += l_N_ppm;
4155                 }
4156
4157         }
4158
4159         /* Need to read an incomplete Ippm series*/
4160         if (l_remaining_data) {
4161                 l_cp->ppm_data = (OPJ_BYTE *) opj_realloc(l_cp->ppm_data, l_cp->ppm_len + l_N_ppm);
4162
4163                 /* Keep the position of the place where concatenate the new series*/
4164                 l_cp->ppm_data_current = &(l_cp->ppm_data[l_cp->ppm_len]);
4165                 l_cp->ppm_len += l_N_ppm;
4166
4167                 /* Read incomplete Ippm series*/
4168                 memcpy(l_cp->ppm_data_current, p_header_data, l_remaining_data);
4169                 p_header_size -= l_remaining_data;
4170                 p_header_data += l_remaining_data;
4171
4172                 l_cp->ppm_data_read += l_remaining_data; /* Increase the number of data read*/
4173         }
4174
4175 #ifdef CLEAN_MSD
4176
4177                 if (l_cp->ppm_data_size == l_cp->ppm_len) {
4178                         if (p_header_size >= 4) {
4179                                 /* read a N_ppm*/
4180                                 opj_read_bytes(p_header_data,&l_N_ppm,4);               /* N_ppm */
4181                                 p_header_data+=4;
4182                                 p_header_size-=4;
4183                                 l_cp->ppm_len += l_N_ppm ;
4184
4185                                 l_cp->ppm_buffer = (OPJ_BYTE *) opj_realloc(l_cp->ppm_buffer, l_cp->ppm_len);
4186                                 if (l_cp->ppm_buffer == 00) {
4187                                         opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory reading ppm marker\n");
4188                                         return OPJ_FALSE;
4189                                 }
4190                                 memset(l_cp->ppm_buffer+l_cp->ppm_data_size,0,l_N_ppm);
4191
4192                                 l_cp->ppm_data = l_cp->ppm_buffer;
4193                         }
4194                         else {
4195                                 return OPJ_FALSE;
4196                         }
4197                 }
4198
4199                 l_remaining_data = l_cp->ppm_len - l_cp->ppm_data_size;
4200
4201                 if (l_remaining_data <= p_header_size) {
4202                         /* we must store less information than available in the packet */
4203                         memcpy(l_cp->ppm_buffer + l_cp->ppm_data_size , p_header_data , l_remaining_data);
4204                         l_cp->ppm_data_size = l_cp->ppm_len;
4205                         p_header_size -= l_remaining_data;
4206                         p_header_data += l_remaining_data;
4207                 }
4208                 else {
4209                         memcpy(l_cp->ppm_buffer + l_cp->ppm_data_size , p_header_data , p_header_size);
4210                         l_cp->ppm_data_size += p_header_size;
4211                         p_header_data += p_header_size;
4212                         p_header_size = 0;
4213                         break;
4214                 }
4215         }
4216 #endif
4217         return OPJ_TRUE;
4218 }
4219
4220 /**
4221  * Reads a PPT marker (Packed packet headers, tile-part header)
4222  *
4223  * @param       p_header_data   the data contained in the PPT box.
4224  * @param       p_j2k                   the jpeg2000 codec.
4225  * @param       p_header_size   the size of the data contained in the PPT marker.
4226  * @param       p_manager               the user event manager.
4227 */
4228 static opj_bool opj_j2k_read_ppt (  opj_j2k_v2_t *p_j2k,
4229                                     OPJ_BYTE * p_header_data,
4230                                     OPJ_UINT32 p_header_size,
4231                                     opj_event_mgr_t * p_manager 
4232                                     )
4233 {
4234         opj_cp_v2_t *l_cp = 00;
4235         opj_tcp_v2_t *l_tcp = 00;
4236         OPJ_UINT32 l_Z_ppt;
4237
4238         /* preconditions */
4239         assert(p_header_data != 00);
4240         assert(p_j2k != 00);
4241         assert(p_manager != 00);
4242
4243         /* We need to have the Z_ppt element at minimum */
4244         if (p_header_size < 1) {
4245                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading PPT marker\n");
4246                 return OPJ_FALSE;
4247         }
4248
4249         l_cp = &(p_j2k->m_cp);
4250         if (l_cp->ppm){
4251                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading PPT marker: packet header have been previously found in the main header (PPM marker).\n");
4252                 return OPJ_FALSE;
4253         }
4254
4255         l_tcp = &(l_cp->tcps[p_j2k->m_current_tile_number]);
4256         l_tcp->ppt = 1;
4257
4258         opj_read_bytes(p_header_data,&l_Z_ppt,1);               /* Z_ppt */
4259         ++p_header_data;
4260         --p_header_size;
4261
4262         /* Allocate buffer to read the packet header */
4263         if (l_Z_ppt == 0) {
4264                 /* First PPT marker */
4265                 l_tcp->ppt_data_size = 0;
4266                 l_tcp->ppt_len = p_header_size;
4267
4268                 l_tcp->ppt_buffer = (OPJ_BYTE *) opj_calloc(l_tcp->ppt_len, sizeof(OPJ_BYTE) );
4269                 if (l_tcp->ppt_buffer == 00) {
4270                         opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory reading PPT marker\n");
4271                         return OPJ_FALSE;
4272                 }
4273                 l_tcp->ppt_data = l_tcp->ppt_buffer;
4274
4275                 /* memset(l_tcp->ppt_buffer,0,l_tcp->ppt_len); */
4276         }
4277         else {
4278                 l_tcp->ppt_len += p_header_size;
4279
4280                 l_tcp->ppt_buffer = (OPJ_BYTE *) opj_realloc(l_tcp->ppt_buffer,l_tcp->ppt_len);
4281                 if (l_tcp->ppt_buffer == 00) {
4282                         opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory reading PPT marker\n");
4283                         return OPJ_FALSE;
4284                 }
4285                 l_tcp->ppt_data = l_tcp->ppt_buffer;
4286
4287                 memset(l_tcp->ppt_buffer+l_tcp->ppt_data_size,0,p_header_size);
4288         }
4289
4290         /* Read packet header from buffer */
4291         memcpy(l_tcp->ppt_buffer+l_tcp->ppt_data_size,p_header_data,p_header_size);
4292
4293         l_tcp->ppt_data_size += p_header_size;
4294
4295         return OPJ_TRUE;
4296 }
4297
4298 /**
4299  * Writes the TLM marker (Tile Length Marker)
4300  * 
4301  * @param       p_stream                                the stream to write data to.
4302  * @param       p_j2k                           J2K codec.
4303  * @param       p_manager               the user event manager.
4304 */
4305 opj_bool j2k_write_tlm_v2(      opj_j2k_v2_t *p_j2k,
4306                                                         struct opj_stream_private *p_stream,
4307                                                         struct opj_event_mgr * p_manager )
4308 {
4309         OPJ_BYTE * l_current_data = 00;
4310         OPJ_UINT32 l_tlm_size;
4311
4312         // preconditions
4313         assert(p_j2k != 00);
4314         assert(p_manager != 00);
4315         assert(p_stream != 00);
4316
4317         l_tlm_size = 6 + (5*p_j2k->m_specific_param.m_encoder.m_total_tile_parts);
4318         
4319         if (l_tlm_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
4320                 p_j2k->m_specific_param.m_encoder.m_header_tile_data 
4321                         = (OPJ_BYTE*)opj_realloc(
4322                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
4323                                 l_tlm_size);
4324                 
4325                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
4326                         return OPJ_FALSE;
4327                 }
4328
4329                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_tlm_size;
4330         }
4331
4332         l_current_data = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
4333
4334         /* change the way data is written to avoid seeking if possible */
4335         // TODO
4336         p_j2k->m_specific_param.m_encoder.m_tlm_start = opj_stream_tell(p_stream);
4337         
4338         opj_write_bytes(l_current_data,J2K_MS_TLM,2);                                   /* TLM */
4339         l_current_data += 2;
4340         
4341         opj_write_bytes(l_current_data,l_tlm_size-2,2);                                 /* Lpoc */
4342         l_current_data += 2;
4343         
4344         opj_write_bytes(l_current_data,0,1);                                                    /* Ztlm=0*/
4345         ++l_current_data;
4346         
4347         opj_write_bytes(l_current_data,0x50,1);                                                 /* Stlm ST=1(8bits-255 tiles max),SP=1(Ptlm=32bits) */
4348         ++l_current_data;
4349         
4350         /* do nothing on the 5 * l_j2k->m_specific_param.m_encoder.m_total_tile_parts remaining data */
4351         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_tlm_size,p_manager) != l_tlm_size) {
4352                 return OPJ_FALSE;
4353         }
4354
4355         return OPJ_TRUE;
4356 }
4357
4358 static void j2k_write_tlm(opj_j2k_t *j2k){
4359         int lenp;
4360         opj_cio_t *cio = j2k->cio;
4361         j2k->tlm_start = cio_tell(cio);
4362         cio_write(cio, J2K_MS_TLM, 2);/* TLM */
4363         lenp = 4 + (5*j2k->totnum_tp);
4364         cio_write(cio,lenp,2);                          /* Ltlm */
4365         cio_write(cio, 0,1);                                    /* Ztlm=0*/
4366         cio_write(cio,80,1);                                    /* Stlm ST=1(8bits-255 tiles max),SP=1(Ptlm=32bits) */
4367         cio_skip(cio,5*j2k->totnum_tp);
4368 }
4369
4370 static void j2k_write_sot(opj_j2k_t *j2k) {
4371         int lenp, len;
4372
4373         opj_cio_t *cio = j2k->cio;
4374
4375         j2k->sot_start = cio_tell(cio);
4376         cio_write(cio, J2K_MS_SOT, 2);          /* SOT */
4377         lenp = cio_tell(cio);
4378         cio_skip(cio, 2);                                       /* Lsot (further) */
4379         cio_write(cio, j2k->curtileno, 2);      /* Isot */
4380         cio_skip(cio, 4);                                       /* Psot (further in j2k_write_sod) */
4381         cio_write(cio, j2k->cur_tp_num , 1);    /* TPsot */
4382         cio_write(cio, j2k->cur_totnum_tp[j2k->curtileno], 1);          /* TNsot */
4383         len = cio_tell(cio) - lenp;
4384         cio_seek(cio, lenp);
4385         cio_write(cio, len, 2);                         /* Lsot */
4386         cio_seek(cio, lenp + len);
4387
4388         /* UniPG>> */
4389 #ifdef USE_JPWL
4390         /* update markers struct */
4391         j2k_add_marker(j2k->cstr_info, J2K_MS_SOT, j2k->sot_start, len + 2);
4392 #endif /* USE_JPWL */
4393         /* <<UniPG */
4394
4395         if( j2k->cstr_info && j2k->cur_tp_num==0){
4396           j2k_add_tlmarker( j2k->curtileno, j2k->cstr_info, J2K_MS_SOT, lenp, len);
4397         }
4398 }
4399
4400 /**
4401  * Writes the SOT marker (Start of tile-part)
4402  *
4403  * @param       p_stream                                the stream to write data to.
4404  * @param       p_j2k                           J2K codec.
4405  * @param       p_manager               the user event manager.
4406 */
4407 opj_bool j2k_write_sot_v2(      opj_j2k_v2_t *p_j2k,
4408                                                         OPJ_BYTE * p_data,
4409                                                         OPJ_UINT32 * p_data_written,
4410                                                         const struct opj_stream_private *p_stream,
4411                                                         struct opj_event_mgr * p_manager )
4412 {
4413         /* preconditions */
4414         assert(p_j2k != 00);
4415         assert(p_manager != 00);
4416         assert(p_stream != 00);
4417
4418         opj_write_bytes(p_data,J2K_MS_SOT,2);                                   /* SOT */
4419         p_data += 2;
4420
4421         opj_write_bytes(p_data,10,2);                                                   /* Lsot */
4422         p_data += 2;
4423
4424         opj_write_bytes(p_data, p_j2k->m_current_tile_number,2);                        /* Isot */
4425         p_data += 2;
4426
4427         /* Psot  */
4428         p_data += 4;
4429
4430         opj_write_bytes(p_data, p_j2k->m_specific_param.m_encoder.m_current_tile_part_number,1);                        /* TPsot */
4431         ++p_data;
4432
4433         opj_write_bytes(p_data, p_j2k->m_cp.tcps[p_j2k->m_current_tile_number].m_nb_tile_parts,1);                      /* TNsot */
4434         ++p_data;
4435
4436         /* UniPG>> */
4437 #ifdef USE_JPWL
4438         /* update markers struct */
4439 /*
4440         j2k_add_marker(p_j2k->cstr_info, J2K_MS_SOT, p_j2k->sot_start, len + 2);
4441 */
4442   assert( 0 && "TODO" );
4443 #endif /* USE_JPWL */
4444
4445         * p_data_written = 12;
4446
4447         return OPJ_TRUE;
4448 }
4449
4450
4451
4452
4453 /**
4454  * Reads a PPT marker (Packed packet headers, tile-part header)
4455  *
4456  * @param       p_header_data   the data contained in the PPT box.
4457  * @param       p_j2k                   the jpeg2000 codec.
4458  * @param       p_header_size   the size of the data contained in the PPT marker.
4459  * @param       p_manager               the user event manager.
4460 */
4461 opj_bool opj_j2k_read_sot ( opj_j2k_v2_t *p_j2k,
4462                             OPJ_BYTE * p_header_data,
4463                             OPJ_UINT32 p_header_size,
4464                             opj_event_mgr_t * p_manager )
4465 {
4466         opj_cp_v2_t *l_cp = 00;
4467         opj_tcp_v2_t *l_tcp = 00;
4468         OPJ_UINT32 l_tot_len, l_num_parts = 0;
4469         OPJ_UINT32 l_current_part;
4470         OPJ_UINT32 l_tile_x,l_tile_y;
4471
4472         /* preconditions */
4473         assert(p_header_data != 00);
4474         assert(p_j2k != 00);
4475         assert(p_manager != 00);
4476
4477         /* Size of this marker is fixed = 12 (we have already read marker and its size)*/
4478         if (p_header_size != 8) {
4479                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading SOT marker\n");
4480                 return OPJ_FALSE;
4481         }
4482
4483         l_cp = &(p_j2k->m_cp);
4484         opj_read_bytes(p_header_data,&(p_j2k->m_current_tile_number),2);                /* Isot */
4485         p_header_data+=2;
4486
4487         l_tcp = &l_cp->tcps[p_j2k->m_current_tile_number];
4488         l_tile_x = p_j2k->m_current_tile_number % l_cp->tw;
4489         l_tile_y = p_j2k->m_current_tile_number / l_cp->tw;
4490
4491 #ifdef USE_JPWL
4492         if (l_cp->correct) {
4493
4494                 int tileno = p_j2k->m_current_tile_number;
4495                 static int backup_tileno = 0;
4496
4497                 /* tileno is negative or larger than the number of tiles!!! */
4498                 if ((tileno < 0) || (tileno > (l_cp->tw * l_cp->th))) {
4499                         opj_event_msg_v2(p_manager, EVT_ERROR,
4500                                 "JPWL: bad tile number (%d out of a maximum of %d)\n",
4501                                 tileno, (l_cp->tw * l_cp->th));
4502                         if (!JPWL_ASSUME) {
4503                                 opj_event_msg_v2(p_manager, EVT_ERROR, "JPWL: giving up\n");
4504                                 return OPJ_FALSE;
4505                         }
4506                         /* we try to correct */
4507                         tileno = backup_tileno;
4508                         opj_event_msg_v2(p_manager, EVT_WARNING, "- trying to adjust this\n"
4509                                 "- setting tile number to %d\n",
4510                                 tileno);
4511                 }
4512
4513                 /* keep your private count of tiles */
4514                 backup_tileno++;
4515         };
4516 #endif /* USE_JPWL */
4517
4518         /* look for the tile in the list of already processed tile (in parts). */
4519         /* Optimization possible here with a more complex data structure and with the removing of tiles */
4520         /* since the time taken by this function can only grow at the time */
4521
4522         opj_read_bytes(p_header_data,&l_tot_len,4);             /* Psot */
4523         p_header_data+=4;
4524
4525         /* PSot should be equal to zero or >=14 or <= 2^32-1 */
4526         if ((l_tot_len !=0 ) && (l_tot_len < 14) )
4527         {
4528                 opj_event_msg_v2(p_manager, EVT_ERROR, "Psot value (%d) is not correct regards to the JPEG2000 norm!\n", l_tot_len);
4529                 return OPJ_FALSE;
4530         }
4531
4532
4533 #ifdef USE_JPWL
4534         if (l_cp->correct) {
4535
4536                 /* totlen is negative or larger than the bytes left!!! */
4537                 if (/*(l_tot_len < 0) ||*/ (l_tot_len > p_header_size ) ) { /* FIXME it seems correct; for info in V1 -> (p_stream_numbytesleft(p_stream) + 8))) { */
4538                         opj_event_msg_v2(p_manager, EVT_ERROR,
4539                                 "JPWL: bad tile byte size (%d bytes against %d bytes left)\n",
4540                                 l_tot_len, p_header_size ); /* FIXME it seems correct; for info in V1 -> p_stream_numbytesleft(p_stream) + 8); */
4541                         if (!JPWL_ASSUME) {
4542                                 opj_event_msg_v2(p_manager, EVT_ERROR, "JPWL: giving up\n");
4543                                 return OPJ_FALSE;
4544                         }
4545                         /* we try to correct */
4546                         l_tot_len = 0;
4547                         opj_event_msg_v2(p_manager, EVT_WARNING, "- trying to adjust this\n"
4548                                 "- setting Psot to %d => assuming it is the last tile\n",
4549                                 l_tot_len);
4550                 }
4551         };
4552 #endif /* USE_JPWL */
4553
4554         /* Ref A.4.2: Psot could be equal zero if it is the last tile-part of the codestream.*/
4555         if (!l_tot_len) {
4556                 opj_event_msg_v2(p_manager, EVT_INFO, "Psot value of the current tile-part is equal to zero, "
4557                                 "we assuming it is the last tile-part of the codestream.\n");
4558                 p_j2k->m_specific_param.m_decoder.m_last_tile_part = 1;
4559         }
4560
4561         opj_read_bytes(p_header_data,&l_current_part ,1);       /* TPsot */
4562         ++p_header_data;
4563
4564         opj_read_bytes(p_header_data,&l_num_parts ,1);          /* TNsot */
4565         ++p_header_data;
4566
4567         if (l_num_parts != 0) { /* Number of tile-part header is provided by this tile-part header */
4568                 /* Useful to manage the case of textGBR.jp2 file because two values of TNSot are allowed: the correct numbers of
4569                  * tile-parts for that tile and zero (A.4.2 of 15444-1 : 2002). */
4570                 if (l_tcp->m_nb_tile_parts) {
4571                         if (l_current_part >= l_tcp->m_nb_tile_parts){
4572                                 opj_event_msg_v2(p_manager, EVT_ERROR, "In SOT marker, TPSot (%d) is not valid regards to the current "
4573                                                 "number of tile-part (%d), giving up\n", l_current_part, l_tcp->m_nb_tile_parts );
4574                                 p_j2k->m_specific_param.m_decoder.m_last_tile_part = 1;
4575                                 return OPJ_FALSE;
4576                         }
4577                 }
4578                 l_tcp->m_nb_tile_parts = l_num_parts;
4579         }
4580
4581         /* If know the number of tile part header we will check if we didn't read the last*/
4582         if (l_tcp->m_nb_tile_parts) {
4583                 if (l_tcp->m_nb_tile_parts == (l_current_part + 1)) {
4584                         p_j2k->m_specific_param.m_decoder.m_can_decode = 1; /* Process the last tile-part header*/
4585                 }
4586         }
4587
4588         if (!p_j2k->m_specific_param.m_decoder.m_last_tile_part){
4589                 /* Keep the size of data to skip after this marker */
4590                 p_j2k->m_specific_param.m_decoder.m_sot_length = l_tot_len - 12; /* SOT_marker_size = 12 */
4591         }
4592         else {
4593                 /* FIXME: need to be computed from the number of bytes remaining in the codestream */
4594                 p_j2k->m_specific_param.m_decoder.m_sot_length = 0;
4595         }
4596
4597         p_j2k->m_specific_param.m_decoder.m_state = J2K_STATE_TPH;
4598
4599         /* Check if the current tile is outside the area we want decode or not corresponding to the tile index*/
4600         if (p_j2k->m_specific_param.m_decoder.m_tile_ind_to_dec == -1) {
4601                 p_j2k->m_specific_param.m_decoder.m_skip_data =
4602                                 (l_tile_x < p_j2k->m_specific_param.m_decoder.m_start_tile_x)
4603                         ||      (l_tile_x >= p_j2k->m_specific_param.m_decoder.m_end_tile_x)
4604                         ||  (l_tile_y < p_j2k->m_specific_param.m_decoder.m_start_tile_y)
4605                         ||      (l_tile_y >= p_j2k->m_specific_param.m_decoder.m_end_tile_y);
4606         }
4607   else {
4608       assert( p_j2k->m_specific_param.m_decoder.m_tile_ind_to_dec >= 0 );
4609     p_j2k->m_specific_param.m_decoder.m_skip_data =
4610       (p_j2k->m_current_tile_number != (OPJ_UINT32)p_j2k->m_specific_param.m_decoder.m_tile_ind_to_dec);
4611     }
4612
4613         /* Index */
4614         if (p_j2k->cstr_index)
4615         {
4616     assert(p_j2k->cstr_index->tile_index != 00);
4617                 p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].tileno = p_j2k->m_current_tile_number;
4618                 p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].current_tpsno = l_current_part;
4619
4620                 if (l_num_parts != 0){
4621                         p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].nb_tps = l_num_parts;
4622                         p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].current_nb_tps = l_num_parts;
4623
4624
4625                         if (!p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index)
4626                                 p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index =
4627                                         (opj_tp_index_t*)opj_calloc(l_num_parts, sizeof(opj_tp_index_t));
4628                         else
4629                                 p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index =
4630                                         (opj_tp_index_t*)opj_realloc(
4631                                                         p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index,
4632                                                         l_num_parts* sizeof(opj_tp_index_t));
4633                 }
4634                 else{
4635                         /*if (!p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index)*/ {
4636
4637                                 if (!p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index) {
4638                                         p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].current_nb_tps = 10;
4639                                         p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index =
4640                                                 (opj_tp_index_t*)opj_calloc( p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].current_nb_tps,
4641                                                                                                          sizeof(opj_tp_index_t));
4642                                 }
4643
4644                                 if ( l_current_part >= p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].current_nb_tps ){
4645                                         p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].current_nb_tps += 10;
4646                                         p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index =
4647                                                 (opj_tp_index_t*)opj_realloc( p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index,
4648                                                                                                           p_j2k->cstr_index->tile_index[p_j2k->m_current_tile_number].current_nb_tps
4649                                                                                                           * sizeof(opj_tp_index_t));
4650                                 }
4651                         }
4652
4653                 }
4654
4655         }
4656
4657
4658         /* FIXME move this onto a separate method to call before reading any SOT, remove part about main_end header, use a index struct inside p_j2k */
4659         /* if (p_j2k->cstr_info) {
4660                 if (l_tcp->first) {
4661                         if (tileno == 0) {
4662                                 p_j2k->cstr_info->main_head_end = p_stream_tell(p_stream) - 13;
4663                         }
4664
4665                         p_j2k->cstr_info->tile[tileno].tileno = tileno;
4666                         p_j2k->cstr_info->tile[tileno].start_pos = p_stream_tell(p_stream) - 12;
4667                         p_j2k->cstr_info->tile[tileno].end_pos = p_j2k->cstr_info->tile[tileno].start_pos + totlen - 1;
4668                         p_j2k->cstr_info->tile[tileno].num_tps = numparts;
4669
4670                         if (numparts) {
4671                                 p_j2k->cstr_info->tile[tileno].tp = (opj_tp_info_t *) opj_malloc(numparts * sizeof(opj_tp_info_t));
4672                         }
4673                         else {
4674                                 p_j2k->cstr_info->tile[tileno].tp = (opj_tp_info_t *) opj_malloc(10 * sizeof(opj_tp_info_t)); // Fixme (10)
4675                         }
4676                 }
4677                 else {
4678                         p_j2k->cstr_info->tile[tileno].end_pos += totlen;
4679                 }
4680
4681                 p_j2k->cstr_info->tile[tileno].tp[partno].tp_start_pos = p_stream_tell(p_stream) - 12;
4682                 p_j2k->cstr_info->tile[tileno].tp[partno].tp_end_pos =
4683                 p_j2k->cstr_info->tile[tileno].tp[partno].tp_start_pos + totlen - 1;
4684         }*/
4685         return OPJ_TRUE;
4686 }
4687
4688 static void j2k_write_sod(opj_j2k_t *j2k, void *tile_coder) {
4689         int l, layno;
4690         int totlen;
4691         opj_tcp_t *tcp = NULL;
4692         opj_codestream_info_t *cstr_info = NULL;
4693         
4694         opj_tcd_t *tcd = (opj_tcd_t*)tile_coder;        /* cast is needed because of conflicts in header inclusions */
4695         opj_cp_t *cp = j2k->cp;
4696         opj_cio_t *cio = j2k->cio;
4697
4698         tcd->tp_num = j2k->tp_num ;
4699         tcd->cur_tp_num = j2k->cur_tp_num;
4700         
4701         cio_write(cio, J2K_MS_SOD, 2);
4702
4703         if( j2k->cstr_info && j2k->cur_tp_num==0){
4704           j2k_add_tlmarker( j2k->curtileno, j2k->cstr_info, J2K_MS_SOD, cio_tell(cio), 0);
4705         }
4706
4707         if (j2k->curtileno == 0) {
4708                 j2k->sod_start = cio_tell(cio) + j2k->pos_correction;
4709         }
4710
4711         /* INDEX >> */
4712         cstr_info = j2k->cstr_info;
4713         if (cstr_info) {
4714                 if (!j2k->cur_tp_num ) {
4715                         cstr_info->tile[j2k->curtileno].end_header = cio_tell(cio) + j2k->pos_correction - 1;
4716                         j2k->cstr_info->tile[j2k->curtileno].tileno = j2k->curtileno;
4717                 }
4718                 else{
4719                         if(cstr_info->tile[j2k->curtileno].packet[cstr_info->packno - 1].end_pos < cio_tell(cio))
4720                                 cstr_info->tile[j2k->curtileno].packet[cstr_info->packno].start_pos = cio_tell(cio);
4721                 }
4722                 /* UniPG>> */
4723 #ifdef USE_JPWL
4724                 /* update markers struct */
4725                 j2k_add_marker(j2k->cstr_info, J2K_MS_SOD, j2k->sod_start, 2);
4726 #endif /* USE_JPWL */
4727                 /* <<UniPG */
4728         }
4729         /* << INDEX */
4730         
4731         tcp = &cp->tcps[j2k->curtileno];
4732         for (layno = 0; layno < tcp->numlayers; layno++) {
4733                 if (tcp->rates[layno]>(j2k->sod_start / (cp->th * cp->tw))) {
4734                         tcp->rates[layno]-=(j2k->sod_start / (cp->th * cp->tw));
4735                 } else if (tcp->rates[layno]) {
4736                         tcp->rates[layno]=1;
4737                 }
4738         }
4739         if(j2k->cur_tp_num == 0){
4740                 tcd->tcd_image->tiles->packno = 0;
4741                 if(cstr_info)
4742                         cstr_info->packno = 0;
4743         }
4744         
4745         l = tcd_encode_tile(tcd, j2k->curtileno, cio_getbp(cio), cio_numbytesleft(cio) - 2, cstr_info);
4746         
4747         /* Writing Psot in SOT marker */
4748         totlen = cio_tell(cio) + l - j2k->sot_start;
4749         cio_seek(cio, j2k->sot_start + 6);
4750         cio_write(cio, totlen, 4);
4751         cio_seek(cio, j2k->sot_start + totlen);
4752         /* Writing Ttlm and Ptlm in TLM marker */
4753         if(cp->cinema){
4754                 cio_seek(cio, j2k->tlm_start + 6 + (5*j2k->cur_tp_num));
4755                 cio_write(cio, j2k->curtileno, 1);
4756                 cio_write(cio, totlen, 4);
4757         }
4758         cio_seek(cio, j2k->sot_start + totlen);
4759 }
4760
4761 /**
4762  * Writes the SOD marker (Start of data)
4763  *
4764  * @param       p_stream                                the stream to write data to.
4765  * @param       p_j2k                           J2K codec.
4766  * @param       p_manager               the user event manager.
4767 */
4768 opj_bool j2k_write_sod_v2(      opj_j2k_v2_t *p_j2k,
4769                                                         struct opj_tcd_v2 * p_tile_coder,
4770                                                         OPJ_BYTE * p_data,
4771                                                         OPJ_UINT32 * p_data_written,
4772                                                         OPJ_UINT32 p_total_data_size,
4773                                                         const struct opj_stream_private *p_stream,
4774                                                         struct opj_event_mgr * p_manager )
4775 {
4776         opj_tcp_v2_t *l_tcp = 00;
4777         opj_codestream_info_t *l_cstr_info = 00;
4778         opj_cp_v2_t *l_cp = 00;
4779
4780         OPJ_UINT32 l_size_tile;
4781         OPJ_UINT32 l_remaining_data;
4782
4783         /* preconditions */
4784         assert(p_j2k != 00);
4785         assert(p_manager != 00);
4786         assert(p_stream != 00);
4787
4788         opj_write_bytes(p_data,J2K_MS_SOD,2);                                   /* SOD */
4789         p_data += 2;
4790
4791         /* make room for the EOF marker */
4792         l_remaining_data =  p_total_data_size - 4;
4793
4794         l_cp = &(p_j2k->m_cp);
4795         l_tcp = &l_cp->tcps[p_j2k->m_current_tile_number];
4796
4797
4798         /* update tile coder */
4799         p_tile_coder->tp_num = p_j2k->m_specific_param.m_encoder.m_current_poc_tile_part_number ;
4800         p_tile_coder->cur_tp_num = p_j2k->m_specific_param.m_encoder.m_current_tile_part_number;
4801
4802         l_size_tile = l_cp->th * l_cp->tw;
4803
4804         /* INDEX >> */
4805         /* TODO mergeV2: check this part which use cstr_info */
4806         /*l_cstr_info = p_j2k->cstr_info;
4807         if (l_cstr_info) {
4808                 if (!p_j2k->m_specific_param.m_encoder.m_current_tile_part_number ) {
4809                         //TODO cstr_info->tile[p_j2k->m_current_tile_number].end_header = p_stream_tell(p_stream) + p_j2k->pos_correction - 1;
4810                         l_cstr_info->tile[p_j2k->m_current_tile_number].tileno = p_j2k->m_current_tile_number;
4811                 }
4812                 else {*/
4813                         /*
4814                         TODO
4815                         if
4816                                 (cstr_info->tile[p_j2k->m_current_tile_number].packet[cstr_info->packno - 1].end_pos < p_stream_tell(p_stream))
4817                         {
4818                                 cstr_info->tile[p_j2k->m_current_tile_number].packet[cstr_info->packno].start_pos = p_stream_tell(p_stream);
4819                         }*/
4820                 /*}*/
4821                 /* UniPG>> */
4822 #ifdef USE_JPWL
4823                 /* update markers struct */
4824                 /*j2k_add_marker(p_j2k->cstr_info, J2K_MS_SOD, p_j2k->sod_start, 2);
4825 */
4826   assert( 0 && "TODO" );
4827 #endif /* USE_JPWL */
4828                 /* <<UniPG */
4829         /*}*/
4830         /* << INDEX */
4831
4832         if (p_j2k->m_specific_param.m_encoder.m_current_tile_part_number == 0) {
4833                 p_tile_coder->tcd_image->tiles->packno = 0;
4834                 if (l_cstr_info) {
4835                         l_cstr_info->packno = 0;
4836                 }
4837         }
4838
4839         *p_data_written = 0;
4840
4841         if (! tcd_encode_tile_v2(p_tile_coder, p_j2k->m_current_tile_number, p_data, p_data_written, l_remaining_data , l_cstr_info)) {
4842                 opj_event_msg_v2(p_manager, EVT_ERROR, "Cannot encode tile\n");
4843                 return OPJ_FALSE;
4844         }
4845
4846         *p_data_written += 2;
4847
4848         return OPJ_TRUE;
4849 }
4850
4851
4852
4853
4854 /**
4855  * Reads a SOD marker (Start Of Data)
4856  *
4857  * @param       p_header_data   the data contained in the SOD box.
4858  * @param       p_j2k                   the jpeg2000 codec.
4859  * @param       p_header_size   the size of the data contained in the SOD marker.
4860  * @param       p_manager               the user event manager.
4861 */
4862 opj_bool opj_j2k_read_sod (opj_j2k_v2_t *p_j2k,
4863                            opj_stream_private_t *p_stream,
4864                                                    opj_event_mgr_t * p_manager
4865                            )
4866 {
4867         OPJ_UINT32 l_current_read_size;
4868         opj_codestream_index_t * l_cstr_index = 00;
4869         OPJ_BYTE ** l_current_data = 00;
4870         opj_tcp_v2_t * l_tcp = 00;
4871         OPJ_UINT32 * l_tile_len = 00;
4872
4873         /* preconditions */
4874         assert(p_j2k != 00);
4875         assert(p_manager != 00);
4876         assert(p_stream != 00);
4877
4878         l_tcp = &(p_j2k->m_cp.tcps[p_j2k->m_current_tile_number]);
4879
4880         if (p_j2k->m_specific_param.m_decoder.m_last_tile_part) {
4881                 /* opj_stream_get_number_byte_left returns OPJ_OFF_T
4882                 // but we are in the last tile part,
4883                 // so its result will fit on OPJ_UINT32 unless we find
4884                 // a file with a single tile part of more than 4 GB...*/
4885                 p_j2k->m_specific_param.m_decoder.m_sot_length = (OPJ_UINT32)(opj_stream_get_number_byte_left(p_stream) - 2);
4886         }
4887         else
4888                 p_j2k->m_specific_param.m_decoder.m_sot_length -= 2;
4889
4890         l_current_data = &(l_tcp->m_data);
4891         l_tile_len = &l_tcp->m_data_size;
4892
4893         if (! *l_current_data) {
4894                 *l_current_data = (OPJ_BYTE*) opj_malloc(p_j2k->m_specific_param.m_decoder.m_sot_length);
4895         }
4896         else {
4897                 *l_current_data = (OPJ_BYTE*) opj_realloc(*l_current_data, *l_tile_len + p_j2k->m_specific_param.m_decoder.m_sot_length);
4898         }
4899
4900         if (*l_current_data == 00) {
4901                 opj_event_msg_v2(p_manager, EVT_ERROR, "Cannot decode tile\n");
4902                 return OPJ_FALSE;
4903         }
4904
4905
4906         /* Index */
4907         l_cstr_index = p_j2k->cstr_index;
4908         if (l_cstr_index) {
4909                 OPJ_OFF_T l_current_pos = opj_stream_tell(p_stream) - 2;
4910
4911                 OPJ_UINT32 l_current_tile_part = l_cstr_index->tile_index[p_j2k->m_current_tile_number].current_tpsno;
4912                 l_cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index[l_current_tile_part].end_header =
4913                                 l_current_pos;
4914                 l_cstr_index->tile_index[p_j2k->m_current_tile_number].tp_index[l_current_tile_part].end_pos =
4915                                 l_current_pos + p_j2k->m_specific_param.m_decoder.m_sot_length + 2;
4916
4917                 j2k_add_tlmarker_v2(p_j2k->m_current_tile_number,
4918                                                         l_cstr_index,
4919                                                         J2K_MS_SOD,
4920                                                         l_current_pos,
4921                                                         p_j2k->m_specific_param.m_decoder.m_sot_length + 2);
4922
4923                 /*l_cstr_index->packno = 0;*/
4924         }
4925
4926         l_current_read_size = opj_stream_read_data(     p_stream,
4927                                                                                                 *l_current_data + *l_tile_len,
4928                                                                                                 p_j2k->m_specific_param.m_decoder.m_sot_length,
4929                                                                                                 p_manager);
4930
4931         if (l_current_read_size != p_j2k->m_specific_param.m_decoder.m_sot_length) {
4932                 p_j2k->m_specific_param.m_decoder.m_state = J2K_STATE_NEOC;
4933         }
4934         else {
4935                 p_j2k->m_specific_param.m_decoder.m_state = J2K_STATE_TPHSOT;
4936         }
4937
4938         *l_tile_len +=  l_current_read_size;
4939
4940         return OPJ_TRUE;
4941 }
4942
4943
4944 static void j2k_write_rgn(opj_j2k_t *j2k, int compno, int tileno) {
4945         opj_cp_t *cp = j2k->cp;
4946         opj_tcp_t *tcp = &cp->tcps[tileno];
4947         opj_cio_t *cio = j2k->cio;
4948         int numcomps = j2k->image->numcomps;
4949         
4950         cio_write(cio, J2K_MS_RGN, 2);                                          /* RGN  */
4951         cio_write(cio, numcomps <= 256 ? 5 : 6, 2);                     /* Lrgn */
4952         cio_write(cio, compno, numcomps <= 256 ? 1 : 2);        /* Crgn */
4953         cio_write(cio, 0, 1);                                                           /* Srgn */
4954         cio_write(cio, tcp->tccps[compno].roishift, 1);         /* SPrgn */
4955 }
4956
4957 /**
4958  * Writes the RGN marker (Region Of Interest)
4959  *
4960  * @param       p_tile_no               the tile to output
4961  * @param       p_comp_no               the component to output
4962  * @param       p_stream                                the stream to write data to.
4963  * @param       p_j2k                           J2K codec.
4964  * @param       p_manager               the user event manager.
4965 */
4966 opj_bool j2k_write_rgn_v2(      opj_j2k_v2_t *p_j2k,
4967                                                         OPJ_UINT32 p_tile_no,
4968                                                         OPJ_UINT32 p_comp_no,
4969                                                         struct opj_stream_private *p_stream,
4970                                                         struct opj_event_mgr * p_manager )
4971 {
4972         OPJ_BYTE * l_current_data = 00;
4973         OPJ_UINT32 l_nb_comp;
4974         OPJ_UINT32 l_rgn_size;
4975         opj_image_t *l_image = 00;
4976         opj_cp_v2_t *l_cp = 00;
4977         opj_tcp_v2_t *l_tcp = 00;
4978         opj_tccp_t *l_tccp = 00;
4979         OPJ_UINT32 l_comp_room;
4980
4981         /* preconditions */
4982         assert(p_j2k != 00);
4983         assert(p_manager != 00);
4984         assert(p_stream != 00);
4985
4986         l_cp = &(p_j2k->m_cp);
4987         l_tcp = &l_cp->tcps[p_tile_no];
4988         l_tccp = &l_tcp->tccps[p_comp_no];
4989
4990         l_nb_comp = l_image->numcomps;
4991
4992         if (l_nb_comp <= 256) {
4993                 l_comp_room = 1;
4994         }
4995         else {
4996                 l_comp_room = 2;
4997         }
4998
4999         l_rgn_size = 6 + l_comp_room;
5000
5001         l_current_data = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
5002
5003         opj_write_bytes(l_current_data,J2K_MS_RGN,2);                                   /* RGN  */
5004         l_current_data += 2;
5005
5006         opj_write_bytes(l_current_data,l_rgn_size-2,2);                                 /* Lrgn */
5007         l_current_data += 2;
5008
5009         opj_write_bytes(l_current_data,p_comp_no,l_comp_room);                  /* Crgn */
5010         l_current_data+=l_comp_room;
5011
5012         opj_write_bytes(l_current_data, 0,1);                                                   /* Srgn */
5013         ++l_current_data;
5014
5015         opj_write_bytes(l_current_data, l_tccp->roishift,1);                    /* SPrgn */
5016         ++l_current_data;
5017
5018         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_rgn_size,p_manager) != l_rgn_size) {
5019                 return OPJ_FALSE;
5020         }
5021
5022         return OPJ_TRUE;
5023 }
5024
5025
5026 static void j2k_write_eoc(opj_j2k_t *j2k) {
5027         opj_cio_t *cio = j2k->cio;
5028         /* opj_event_msg(j2k->cinfo, "%.8x: EOC\n", cio_tell(cio) + j2k->pos_correction); */
5029         cio_write(cio, J2K_MS_EOC, 2);
5030
5031 /* UniPG>> */
5032 #ifdef USE_JPWL
5033         /* update markers struct */
5034         j2k_add_marker(j2k->cstr_info, J2K_MS_EOC, cio_tell(cio) - 2, 2);
5035 #endif /* USE_JPWL */
5036 /* <<UniPG */
5037 }
5038
5039 /**
5040  * Writes the EOC marker (End of Codestream)
5041  * 
5042  * @param       p_stream                the stream to write data to.
5043  * @param       p_j2k                   J2K codec.
5044  * @param       p_manager               the user event manager.
5045 */
5046 opj_bool j2k_write_eoc_v2(      opj_j2k_v2_t *p_j2k,
5047                                                         struct opj_stream_private *p_stream,
5048                                                         struct opj_event_mgr * p_manager )
5049 {
5050         /* preconditions */
5051         assert(p_j2k != 00);
5052         assert(p_manager != 00);
5053         assert(p_stream != 00);
5054         
5055         opj_write_bytes(p_j2k->m_specific_param.m_encoder.m_header_tile_data,J2K_MS_EOC,2);                                     /* EOC */
5056         
5057
5058 /* UniPG>> */
5059 #ifdef USE_JPWL
5060         /* update markers struct */
5061         /*
5062         j2k_add_marker(p_j2k->cstr_info, J2K_MS_EOC, p_stream_tell(p_stream) - 2, 2);
5063 */
5064 #endif /* USE_JPWL */
5065
5066         if ( opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,2,p_manager) != 2) {
5067                 return OPJ_FALSE;
5068         }
5069
5070         if ( ! opj_stream_flush(p_stream,p_manager) ) {
5071                 return OPJ_FALSE;
5072         }
5073
5074         return OPJ_TRUE;
5075 }
5076
5077
5078 /**
5079  * Reads a RGN marker (Region Of Interest)
5080  *
5081  * @param       p_header_data   the data contained in the POC box.
5082  * @param       p_j2k                   the jpeg2000 codec.
5083  * @param       p_header_size   the size of the data contained in the POC marker.
5084  * @param       p_manager               the user event manager.
5085 */
5086 static opj_bool opj_j2k_read_rgn (opj_j2k_v2_t *p_j2k,
5087                                   OPJ_BYTE * p_header_data,
5088                                   OPJ_UINT32 p_header_size,
5089                                   opj_event_mgr_t * p_manager 
5090                                   )
5091 {
5092         OPJ_UINT32 l_nb_comp;
5093         opj_image_t * l_image = 00;
5094
5095         opj_cp_v2_t *l_cp = 00;
5096         opj_tcp_v2_t *l_tcp = 00;
5097         OPJ_UINT32 l_comp_room, l_comp_no, l_roi_sty;
5098
5099         /* preconditions*/
5100         assert(p_header_data != 00);
5101         assert(p_j2k != 00);
5102         assert(p_manager != 00);
5103
5104         l_image = p_j2k->m_private_image;
5105         l_nb_comp = l_image->numcomps;
5106
5107         if (l_nb_comp <= 256) {
5108                 l_comp_room = 1; }
5109         else {
5110                 l_comp_room = 2; }
5111
5112         if (p_header_size != 2 + l_comp_room) {
5113                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading RGN marker\n");
5114                 return OPJ_FALSE;
5115         }
5116
5117         l_cp = &(p_j2k->m_cp);
5118         l_tcp = (p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH) ?
5119                                 &l_cp->tcps[p_j2k->m_current_tile_number] :
5120                                 p_j2k->m_specific_param.m_decoder.m_default_tcp;
5121
5122         opj_read_bytes(p_header_data,&l_comp_no,l_comp_room);           /* Crgn */
5123         p_header_data+=l_comp_room;
5124         opj_read_bytes(p_header_data,&l_roi_sty,1);                                     /* Srgn */
5125         ++p_header_data;
5126
5127 #ifdef USE_JPWL
5128         if (l_cp->correct) {
5129                 /* totlen is negative or larger than the bytes left!!! */
5130                 if (l_comp_room >= l_nb_comp) {
5131                         opj_event_msg_v2(p_manager, EVT_ERROR,
5132                                 "JPWL: bad component number in RGN (%d when there are only %d)\n",
5133                                 l_comp_room, l_nb_comp);
5134                         if (!JPWL_ASSUME || JPWL_ASSUME) {
5135                                 opj_event_msg_v2(p_manager, EVT_ERROR, "JPWL: giving up\n");
5136                                 return OPJ_FALSE;
5137                         }
5138                 }
5139         };
5140 #endif /* USE_JPWL */
5141
5142         opj_read_bytes(p_header_data,(OPJ_UINT32 *) (&(l_tcp->tccps[l_comp_no].roishift)),1);   /* SPrgn */
5143         ++p_header_data;
5144
5145         return OPJ_TRUE;
5146
5147 }
5148
5149 static OPJ_FLOAT32 get_tp_stride (opj_tcp_v2_t * p_tcp)
5150 {
5151         return (OPJ_FLOAT32) ((p_tcp->m_nb_tile_parts - 1) * 14);
5152 }
5153
5154 static OPJ_FLOAT32 get_default_stride (opj_tcp_v2_t * p_tcp)
5155 {
5156   (void)p_tcp;
5157         return 0;
5158 }
5159
5160 /**
5161  * Updates the rates of the tcp.
5162  *
5163  * @param       p_stream                the stream to write data to.
5164  * @param       p_j2k                   J2K codec.
5165  * @param       p_manager               the user event manager.
5166 */
5167 opj_bool j2k_update_rates(      opj_j2k_v2_t *p_j2k,
5168                                                         struct opj_stream_private *p_stream,
5169                                                         struct opj_event_mgr * p_manager )
5170 {
5171         opj_cp_v2_t * l_cp = 00;
5172         opj_image_t * l_image = 00;
5173         opj_tcp_v2_t * l_tcp = 00;
5174         opj_image_comp_t * l_img_comp = 00;
5175
5176         OPJ_UINT32 i,j,k;
5177         OPJ_INT32 l_x0,l_y0,l_x1,l_y1;
5178         OPJ_FLOAT32 * l_rates = 0;
5179         OPJ_FLOAT32 l_sot_remove;
5180         OPJ_UINT32 l_bits_empty, l_size_pixel;
5181         OPJ_UINT32 l_tile_size = 0;
5182         OPJ_UINT32 l_last_res;
5183         OPJ_FLOAT32 (* l_tp_stride_func)(opj_tcp_v2_t *) = 00;
5184
5185         /* preconditions */
5186         assert(p_j2k != 00);
5187         assert(p_manager != 00);
5188         assert(p_stream != 00);
5189
5190
5191         l_cp = &(p_j2k->m_cp);
5192         l_image = p_j2k->m_private_image;
5193         l_tcp = l_cp->tcps;
5194
5195         l_bits_empty = 8 * l_image->comps->dx * l_image->comps->dy;
5196         l_size_pixel = l_image->numcomps * l_image->comps->prec;
5197         l_sot_remove = ((OPJ_FLOAT32) opj_stream_tell(p_stream)) / (l_cp->th * l_cp->tw);
5198
5199         if (l_cp->m_specific_param.m_enc.m_tp_on) {
5200                 l_tp_stride_func = get_tp_stride;
5201         }
5202         else {
5203                 l_tp_stride_func = get_default_stride;
5204         }
5205
5206         for (i=0;i<l_cp->th;++i) {
5207                 for (j=0;j<l_cp->tw;++j) {
5208                         OPJ_FLOAT32 l_offset = ((*l_tp_stride_func)(l_tcp)) / l_tcp->numlayers;
5209
5210                         /* 4 borders of the tile rescale on the image if necessary */
5211                         l_x0 = int_max(l_cp->tx0 + j * l_cp->tdx, l_image->x0);
5212                         l_y0 = int_max(l_cp->ty0 + i * l_cp->tdy, l_image->y0);
5213                         l_x1 = int_min(l_cp->tx0 + (j + 1) * l_cp->tdx, l_image->x1);
5214                         l_y1 = int_min(l_cp->ty0 + (i + 1) * l_cp->tdy, l_image->y1);
5215
5216                         l_rates = l_tcp->rates;
5217
5218                         /* Modification of the RATE >> */
5219                         if (*l_rates) {
5220                                 *l_rates =              (( (float) (l_size_pixel * (l_x1 - l_x0) * (l_y1 - l_y0)))
5221                                                                 /
5222                                                                 ((*l_rates) * l_bits_empty)
5223                                                                 )
5224                                                                 -
5225                                                                 l_offset;
5226                         }
5227
5228                         ++l_rates;
5229
5230                         for (k = 1; k < l_tcp->numlayers; ++k) {
5231                                 if (*l_rates) {
5232                                         *l_rates =              (( (OPJ_FLOAT32) (l_size_pixel * (l_x1 - l_x0) * (l_y1 - l_y0)))
5233                                                                         /
5234                                                                                 ((*l_rates) * l_bits_empty)
5235                                                                         )
5236                                                                         -
5237                                                                         l_offset;
5238                                 }
5239
5240                                 ++l_rates;
5241                         }
5242
5243                         ++l_tcp;
5244
5245                 }
5246         }
5247
5248         l_tcp = l_cp->tcps;
5249
5250         for (i=0;i<l_cp->th;++i) {
5251                 for     (j=0;j<l_cp->tw;++j) {
5252                         l_rates = l_tcp->rates;
5253
5254                         if (*l_rates) {
5255                                 *l_rates -= l_sot_remove;
5256
5257                                 if (*l_rates < 30) {
5258                                         *l_rates = 30;
5259                                 }
5260                         }
5261
5262                         ++l_rates;
5263
5264                         l_last_res = l_tcp->numlayers - 1;
5265
5266                         for (k = 1; k < l_last_res; ++k) {
5267
5268                                 if (*l_rates) {
5269                                         *l_rates -= l_sot_remove;
5270
5271                                         if (*l_rates < *(l_rates - 1) + 10) {
5272                                                 *l_rates  = (*(l_rates - 1)) + 20;
5273                                         }
5274                                 }
5275
5276                                 ++l_rates;
5277                         }
5278
5279                         if (*l_rates) {
5280                                 *l_rates -= (l_sot_remove + 2.f);
5281
5282                                 if (*l_rates < *(l_rates - 1) + 10) {
5283                                         *l_rates  = (*(l_rates - 1)) + 20;
5284                                 }
5285                         }
5286
5287                         ++l_tcp;
5288                 }
5289         }
5290
5291         l_img_comp = l_image->comps;
5292         l_tile_size = 0;
5293
5294         for (i=0;i<l_image->numcomps;++i) {
5295                 l_tile_size += (        uint_ceildiv(l_cp->tdx,l_img_comp->dx)
5296                                                         *
5297                                                         uint_ceildiv(l_cp->tdy,l_img_comp->dy)
5298                                                         *
5299                                                         l_img_comp->prec
5300                                                 );
5301
5302                 ++l_img_comp;
5303         }
5304
5305         l_tile_size = (OPJ_UINT32) (l_tile_size * 0.1625); /* 1.3/8 = 0.1625 */
5306
5307         l_tile_size += j2k_get_specific_header_sizes(p_j2k);
5308
5309         p_j2k->m_specific_param.m_encoder.m_encoded_tile_size = l_tile_size;
5310         p_j2k->m_specific_param.m_encoder.m_encoded_tile_data =
5311                         (OPJ_BYTE *) opj_malloc(p_j2k->m_specific_param.m_encoder.m_encoded_tile_size);
5312         if (p_j2k->m_specific_param.m_encoder.m_encoded_tile_data == 00) {
5313                 return OPJ_FALSE;
5314         }
5315
5316         if (l_cp->m_specific_param.m_enc.m_cinema) {
5317                 p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_buffer =
5318                                 (OPJ_BYTE *) opj_malloc(5*p_j2k->m_specific_param.m_encoder.m_total_tile_parts);
5319                 if (! p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_buffer) {
5320                         return OPJ_FALSE;
5321                 }
5322
5323                 p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_current =
5324                                 p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_buffer;
5325         }
5326
5327         return OPJ_TRUE;
5328 }
5329
5330 static void j2k_read_eoc(opj_j2k_t *j2k) {
5331         int i, tileno;
5332         opj_bool success = OPJ_FALSE;
5333
5334         /* if packets should be decoded */
5335         if (j2k->cp->limit_decoding != DECODE_ALL_BUT_PACKETS) {
5336                 opj_tcd_t *tcd = tcd_create(j2k->cinfo);
5337                 tcd_malloc_decode(tcd, j2k->image, j2k->cp);
5338                 for (i = 0; i < j2k->cp->tileno_size; i++) {
5339                         tcd_malloc_decode_tile(tcd, j2k->image, j2k->cp, i, j2k->cstr_info);
5340                         if (j2k->cp->tileno[i] != -1)
5341                         {
5342                                 tileno = j2k->cp->tileno[i];
5343                                 success = tcd_decode_tile(tcd, j2k->tile_data[tileno], j2k->tile_len[tileno], tileno, j2k->cstr_info);
5344                                 opj_free(j2k->tile_data[tileno]);
5345                                 j2k->tile_data[tileno] = NULL;
5346                                 tcd_free_decode_tile(tcd, i);
5347                         }
5348                         else
5349                                 success = OPJ_FALSE;
5350                         if (success == OPJ_FALSE) {
5351                                 j2k->state |= J2K_STATE_ERR;
5352                                 break;
5353                         }
5354                 }
5355                 tcd_free_decode(tcd);
5356                 tcd_destroy(tcd);
5357         }
5358         /* if packets should not be decoded  */
5359         else {
5360                 for (i = 0; i < j2k->cp->tileno_size; i++) {
5361                         tileno = j2k->cp->tileno[i];
5362                         opj_free(j2k->tile_data[tileno]);
5363                         j2k->tile_data[tileno] = NULL;
5364                 }
5365         }       
5366         if (j2k->state & J2K_STATE_ERR)
5367                 j2k->state = J2K_STATE_MT + J2K_STATE_ERR;
5368         else
5369                 j2k->state = J2K_STATE_MT; 
5370 }
5371
5372 /**
5373  * Reads a EOC marker (End Of Codestream)
5374  *
5375  * @param       p_header_data   the data contained in the SOD box.
5376  * @param       p_j2k                   the jpeg2000 codec.
5377  * @param       p_header_size   the size of the data contained in the SOD marker.
5378  * @param       p_manager               the user event manager.
5379 */
5380 #if 0
5381 opj_bool j2k_read_eoc_v2 (      opj_j2k_v2_t *p_j2k,
5382                                                         struct opj_stream_private *p_stream,
5383                                                         struct opj_event_mgr * p_manager )
5384 {
5385         OPJ_UINT32 i;
5386         opj_tcd_v2_t * l_tcd = 00;
5387         OPJ_UINT32 l_nb_tiles;
5388         opj_tcp_v2_t * l_tcp = 00;
5389         opj_bool l_success;
5390
5391         /* preconditions */
5392         assert(p_j2k != 00);
5393         assert(p_manager != 00);
5394         assert(p_stream != 00);
5395
5396         l_nb_tiles = p_j2k->m_cp.th * p_j2k->m_cp.tw;
5397         l_tcp = p_j2k->m_cp.tcps;
5398
5399         l_tcd = tcd_create_v2(OPJ_TRUE);
5400         if (l_tcd == 00) {
5401                 opj_event_msg_v2(p_manager, EVT_ERROR, "Cannot decode tile, memory error\n");
5402                 return OPJ_FALSE;
5403         }
5404
5405         for (i = 0; i < l_nb_tiles; ++i) {
5406                 if (l_tcp->m_data) {
5407                         if (! tcd_init_decode_tile(l_tcd, i)) {
5408                                 tcd_destroy_v2(l_tcd);
5409                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Cannot decode tile, memory error\n");
5410                                 return OPJ_FALSE;
5411                         }
5412
5413                         l_success = tcd_decode_tile_v2(l_tcd, l_tcp->m_data, l_tcp->m_data_size, i, p_j2k->cstr_index);
5414                         /* cleanup */
5415
5416                         if (! l_success) {
5417                                 p_j2k->m_specific_param.m_decoder.m_state |= J2K_STATE_ERR;
5418                                 break;
5419                         }
5420                 }
5421
5422                 j2k_tcp_destroy(l_tcp);
5423                 ++l_tcp;
5424         }
5425
5426         tcd_destroy_v2(l_tcd);
5427         return OPJ_TRUE;
5428 }
5429 #endif
5430
5431 /**
5432  * Gets the offset of the header.
5433  *
5434  * @param       p_stream                                the stream to write data to.
5435  * @param       p_j2k                           J2K codec.
5436  * @param       p_manager               the user event manager.
5437 */
5438 opj_bool j2k_get_end_header(opj_j2k_v2_t *p_j2k,
5439                                                         struct opj_stream_private *p_stream,
5440                                                         struct opj_event_mgr * p_manager )
5441 {
5442         /* preconditions */
5443         assert(p_j2k != 00);
5444         assert(p_manager != 00);
5445         assert(p_stream != 00);
5446
5447         p_j2k->cstr_index->main_head_end = opj_stream_tell(p_stream);
5448
5449         return OPJ_TRUE;
5450 }
5451
5452 /**
5453  * Writes the MCT marker (Multiple Component Transform)
5454  *
5455  * @param       p_stream                                the stream to write data to.
5456  * @param       p_j2k                           J2K codec.
5457  * @param       p_manager               the user event manager.
5458 */
5459 opj_bool j2k_write_mct_data_group(      opj_j2k_v2_t *p_j2k,
5460                                                                         struct opj_stream_private *p_stream,
5461                                                                         struct opj_event_mgr * p_manager )
5462 {
5463         OPJ_UINT32 i;
5464         opj_simple_mcc_decorrelation_data_t * l_mcc_record;
5465         opj_mct_data_t * l_mct_record;
5466         opj_tcp_v2_t * l_tcp;
5467
5468         /* preconditions */
5469         assert(p_j2k != 00);
5470         assert(p_stream != 00);
5471         assert(p_manager != 00);
5472
5473         if (! j2k_write_cbd(p_j2k,p_stream,p_manager)) {
5474                 return OPJ_FALSE;
5475         }
5476
5477         l_tcp = &(p_j2k->m_cp.tcps[p_j2k->m_current_tile_number]);
5478         l_mct_record = l_tcp->m_mct_records;
5479
5480         for (i=0;i<l_tcp->m_nb_mct_records;++i) {
5481
5482                 if (! j2k_write_mct_record(p_j2k,l_mct_record,p_stream,p_manager)) {
5483                         return OPJ_FALSE;
5484                 }
5485
5486                 ++l_mct_record;
5487         }
5488
5489         l_mcc_record = l_tcp->m_mcc_records;
5490
5491         for     (i=0;i<l_tcp->m_nb_mcc_records;++i) {
5492
5493                 if (! j2k_write_mcc_record(p_j2k,l_mcc_record,p_stream,p_manager)) {
5494                         return OPJ_FALSE;
5495                 }
5496
5497                 ++l_mcc_record;
5498         }
5499
5500         if (! j2k_write_mco(p_j2k,p_stream,p_manager)) {
5501                 return OPJ_FALSE;
5502         }
5503
5504         return OPJ_TRUE;
5505 }
5506
5507 /**
5508  * Writes the image components.
5509  *
5510  * @param       p_stream                                the stream to write data to.
5511  * @param       p_j2k                           J2K codec.
5512  * @param       p_manager               the user event manager.
5513 */
5514 opj_bool j2k_write_image_components(opj_j2k_v2_t *p_j2k,
5515                                                                         struct opj_stream_private *p_stream,
5516                                                                         struct opj_event_mgr * p_manager )
5517 {
5518         OPJ_UINT32 compno;
5519
5520         /* preconditions */
5521         assert(p_j2k != 00);
5522         assert(p_manager != 00);
5523         assert(p_stream != 00);
5524
5525         for (compno = 1; compno < p_j2k->m_private_image->numcomps; ++compno)
5526         {
5527                 if (! j2k_write_coc_v2(p_j2k,compno,p_stream, p_manager)) {
5528                         return OPJ_FALSE;
5529                 }
5530
5531                 if (! j2k_write_qcc_v2(p_j2k,compno,p_stream, p_manager)) {
5532                         return OPJ_FALSE;
5533                 }
5534         }
5535
5536         return OPJ_TRUE;
5537 }
5538
5539 /**
5540  * Writes regions of interests.
5541  *
5542  * @param       p_stream                                the stream to write data to.
5543  * @param       p_j2k                           J2K codec.
5544  * @param       p_manager               the user event manager.
5545 */
5546 opj_bool j2k_write_regions(     opj_j2k_v2_t *p_j2k,
5547                                                         struct opj_stream_private *p_stream,
5548                                                         struct opj_event_mgr * p_manager )
5549 {
5550         OPJ_UINT32 compno;
5551         const opj_tccp_t *l_tccp = 00;
5552
5553         /* preconditions */
5554         assert(p_j2k != 00);
5555         assert(p_manager != 00);
5556         assert(p_stream != 00);
5557
5558         l_tccp = p_j2k->m_cp.tcps->tccps;
5559
5560         for     (compno = 0; compno < p_j2k->m_private_image->numcomps; ++compno)  {
5561                 if (l_tccp->roishift) {
5562
5563                         if (! j2k_write_rgn_v2(p_j2k,0,compno,p_stream,p_manager)) {
5564                                 return OPJ_FALSE;
5565                         }
5566                 }
5567
5568                 ++l_tccp;
5569         }
5570
5571         return OPJ_TRUE;
5572 }
5573
5574 /**
5575  * Writes EPC ????
5576  *
5577  * @param       p_stream                the stream to write data to.
5578  * @param       p_j2k                   J2K codec.
5579  * @param       p_manager               the user event manager.
5580 */
5581 opj_bool j2k_write_epc( opj_j2k_v2_t *p_j2k,
5582                                                 struct opj_stream_private *p_stream,
5583                                                 struct opj_event_mgr * p_manager )
5584 {
5585         opj_codestream_index_t * l_cstr_index = 00;
5586
5587         /* preconditions */
5588         assert(p_j2k != 00);
5589         assert(p_manager != 00);
5590         assert(p_stream != 00);
5591
5592         l_cstr_index = p_j2k->cstr_index;
5593         if (l_cstr_index) {
5594                 l_cstr_index->codestream_size = opj_stream_tell(p_stream);
5595                 /* UniPG>> */
5596                 /* The following adjustment is done to adjust the codestream size */
5597                 /* if SOD is not at 0 in the buffer. Useful in case of JP2, where */
5598                 /* the first bunch of bytes is not in the codestream              */
5599                 l_cstr_index->codestream_size -= l_cstr_index->main_head_start;
5600                 /* <<UniPG */
5601         }
5602
5603 #ifdef USE_JPWL
5604         /* preparation of JPWL marker segments */
5605 #if 0
5606         if(cp->epc_on) {
5607
5608                 /* encode according to JPWL */
5609                 jpwl_encode(p_j2k, p_stream, image);
5610
5611         }
5612 #endif
5613   assert( 0 && "TODO" );
5614 #endif /* USE_JPWL */
5615
5616         return OPJ_TRUE;
5617 }
5618
5619 typedef struct opj_dec_mstabent {
5620         /** marker value */
5621         int id;
5622         /** value of the state when the marker can appear */
5623         int states;
5624         /** action linked to the marker */
5625         void (*handler) (opj_j2k_t *j2k);
5626 } opj_dec_mstabent_t;
5627
5628 opj_dec_mstabent_t j2k_dec_mstab[] = {
5629   /*{J2K_MS_SOC, J2K_STATE_MHSOC, j2k_read_soc},*/
5630   /*{J2K_MS_SOT, J2K_STATE_MH | J2K_STATE_TPHSOT, j2k_read_sot},*/
5631   /*{J2K_MS_SOD, J2K_STATE_TPH, j2k_read_sod},*/
5632   {J2K_MS_EOC, J2K_STATE_TPHSOT, j2k_read_eoc},
5633   /*{J2K_MS_SIZ, J2K_STATE_MHSIZ, j2k_read_siz},*/
5634   /*{J2K_MS_COD, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_cod},*/
5635   /*{J2K_MS_COC, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_coc},*/
5636   /*{J2K_MS_RGN, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_rgn},*/
5637   /*{J2K_MS_QCD, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_qcd},*/
5638   /*{J2K_MS_QCC, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_qcc},*/
5639   /*{J2K_MS_POC, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_poc},*/
5640   /*{J2K_MS_TLM, J2K_STATE_MH, j2k_read_tlm},*/
5641   /*{J2K_MS_PLM, J2K_STATE_MH, j2k_read_plm},*/
5642   /*{J2K_MS_PLT, J2K_STATE_TPH, j2k_read_plt},*/
5643   /*{J2K_MS_PPM, J2K_STATE_MH, j2k_read_ppm},*/
5644   /*{J2K_MS_PPT, J2K_STATE_TPH, j2k_read_ppt},*/
5645   {J2K_MS_SOP, 0, 0},
5646   /*{J2K_MS_CRG, J2K_STATE_MH, j2k_read_crg},*/
5647   /*{J2K_MS_COM, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_com},*/
5648
5649 #ifdef USE_JPWL
5650   {J2K_MS_EPC, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_epc},
5651   {J2K_MS_EPB, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_epb},
5652   {J2K_MS_ESD, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_esd},
5653   {J2K_MS_RED, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_red},
5654 #endif /* USE_JPWL */
5655 #ifdef USE_JPSEC
5656   {J2K_MS_SEC, J2K_STATE_MH, j2k_read_sec},
5657   {J2K_MS_INSEC, 0, j2k_read_insec},
5658 #endif /* USE_JPSEC */
5659
5660   {0, J2K_STATE_MH | J2K_STATE_TPH, j2k_read_unk}
5661 };
5662
5663 static void j2k_read_unk(opj_j2k_t *j2k) {
5664         opj_event_msg(j2k->cinfo, EVT_WARNING, "Unknown marker\n");
5665
5666 #ifdef USE_JPWL
5667         if (j2k->cp->correct) {
5668                 int m = 0, id, i;
5669                 int min_id = 0, min_dist = 17, cur_dist = 0, tmp_id;
5670                 cio_seek(j2k->cio, cio_tell(j2k->cio) - 2);
5671                 id = cio_read(j2k->cio, 2);
5672                 opj_event_msg(j2k->cinfo, EVT_ERROR,
5673                         "JPWL: really don't know this marker %x\n",
5674                         id);
5675                 if (!JPWL_ASSUME) {
5676                         opj_event_msg(j2k->cinfo, EVT_ERROR,
5677                                 "- possible synch loss due to uncorrectable codestream errors => giving up\n");
5678                         return;
5679                 }
5680                 /* OK, activate this at your own risk!!! */
5681                 /* we look for the marker at the minimum hamming distance from this */
5682                 while (j2k_dec_mstab[m].id) {
5683                         
5684                         /* 1's where they differ */
5685                         tmp_id = j2k_dec_mstab[m].id ^ id;
5686
5687                         /* compute the hamming distance between our id and the current */
5688                         cur_dist = 0;
5689                         for (i = 0; i < 16; i++) {
5690                                 if ((tmp_id >> i) & 0x0001) {
5691                                         cur_dist++;
5692                                 }
5693                         }
5694
5695                         /* if current distance is smaller, set the minimum */
5696                         if (cur_dist < min_dist) {
5697                                 min_dist = cur_dist;
5698                                 min_id = j2k_dec_mstab[m].id;
5699                         }
5700                         
5701                         /* jump to the next marker */
5702                         m++;
5703                 }
5704
5705                 /* do we substitute the marker? */
5706                 if (min_dist < JPWL_MAXIMUM_HAMMING) {
5707                         opj_event_msg(j2k->cinfo, EVT_ERROR,
5708                                 "- marker %x is at distance %d from the read %x\n",
5709                                 min_id, min_dist, id);
5710                         opj_event_msg(j2k->cinfo, EVT_ERROR,
5711                                 "- trying to substitute in place and crossing fingers!\n");
5712                         cio_seek(j2k->cio, cio_tell(j2k->cio) - 2);
5713                         cio_write(j2k->cio, min_id, 2);
5714
5715                         /* rewind */
5716                         cio_seek(j2k->cio, cio_tell(j2k->cio) - 2);
5717
5718                 }
5719
5720         };
5721 #endif /* USE_JPWL */
5722
5723 }
5724
5725 /**
5726  * Reads an unknown marker
5727  *
5728  * @param       p_stream                                the stream object to read from.
5729  * @param       p_j2k                   the jpeg2000 codec.
5730  * @param       p_manager               the user event manager.
5731  *
5732  * @return      true                    if the marker could be deduced.
5733 */
5734 opj_bool j2k_read_unk_v2 (      opj_j2k_v2_t *p_j2k,
5735                                                         struct opj_stream_private *p_stream,
5736                                                         OPJ_UINT32 *output_marker,
5737                                                         struct opj_event_mgr * p_manager
5738                                                         )
5739 {
5740         OPJ_UINT32 l_unknown_marker;
5741         const opj_dec_memory_marker_handler_t * l_marker_handler;
5742         OPJ_UINT32 l_size_unk = 2;
5743
5744         /* preconditions*/
5745         assert(p_j2k != 00);
5746         assert(p_manager != 00);
5747         assert(p_stream != 00);
5748
5749         opj_event_msg_v2(p_manager, EVT_WARNING, "Unknown marker\n");
5750
5751         while(1) {
5752                 /* Try to read 2 bytes (the next marker ID) from stream and copy them into the buffer*/
5753                 if (opj_stream_read_data(p_stream,p_j2k->m_specific_param.m_decoder.m_header_data,2,p_manager) != 2) {
5754                         opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
5755                         return OPJ_FALSE;
5756                 }
5757
5758                 /* read 2 bytes as the new marker ID*/
5759                 opj_read_bytes(p_j2k->m_specific_param.m_decoder.m_header_data,&l_unknown_marker,2);
5760
5761                 if (!(l_unknown_marker < 0xff00)) {
5762
5763                         /* Get the marker handler from the marker ID*/
5764                         l_marker_handler = j2k_get_marker_handler(l_unknown_marker);
5765
5766                         if (!(p_j2k->m_specific_param.m_decoder.m_state & l_marker_handler->states)) {
5767                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Marker is not compliant with its position\n");
5768                                 return OPJ_FALSE;
5769                         }
5770                         else {
5771                                 if (l_marker_handler->id != J2K_MS_UNK) {
5772                                         /* Add the marker to the codestream index*/
5773                                         if (l_marker_handler->id != J2K_MS_SOT)
5774                                                 j2k_add_mhmarker_v2(p_j2k->cstr_index, J2K_MS_UNK,
5775                                                                                         (OPJ_UINT32) opj_stream_tell(p_stream) - l_size_unk,
5776                                                                                         l_size_unk);
5777                                         break; /* next marker is known and well located */
5778                                 }
5779                                 else
5780                                         l_size_unk += 2;
5781                         }
5782                 }
5783         }
5784
5785         *output_marker = l_marker_handler->id ;
5786
5787         return OPJ_TRUE;
5788 }
5789
5790 /**
5791 Read the lookup table containing all the marker, status and action
5792 @param id Marker value
5793 */
5794 static opj_dec_mstabent_t *j2k_dec_mstab_lookup(int id) {
5795         opj_dec_mstabent_t *e;
5796         for (e = j2k_dec_mstab; e->id != 0; e++) {
5797                 if (e->id == id) {
5798                         break;
5799                 }
5800         }
5801         return e;
5802 }
5803
5804 /**
5805  * Writes the MCT marker (Multiple Component Transform)
5806  *
5807  * @param       p_stream                                the stream to write data to.
5808  * @param       p_j2k                           J2K codec.
5809  * @param       p_manager               the user event manager.
5810 */
5811 opj_bool j2k_write_mct_record(  opj_j2k_v2_t *p_j2k,
5812                                                                 opj_mct_data_t * p_mct_record,
5813                                                                 struct opj_stream_private *p_stream,
5814                                                                 struct opj_event_mgr * p_manager )
5815 {
5816         OPJ_UINT32 l_mct_size;
5817         OPJ_BYTE * l_current_data = 00;
5818         OPJ_UINT32 l_tmp;
5819
5820         /* preconditions */
5821         assert(p_j2k != 00);
5822         assert(p_manager != 00);
5823         assert(p_stream != 00);
5824
5825         l_mct_size = 10 + p_mct_record->m_data_size;
5826
5827         if (l_mct_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
5828                 p_j2k->m_specific_param.m_encoder.m_header_tile_data
5829                         = (OPJ_BYTE*)opj_realloc(
5830                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
5831                                 l_mct_size);
5832
5833                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
5834                         return OPJ_FALSE;
5835                 }
5836
5837                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_mct_size;
5838         }
5839
5840         l_current_data = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
5841
5842         opj_write_bytes(l_current_data,J2K_MS_MCT,2);                                   /* MCT */
5843         l_current_data += 2;
5844
5845         opj_write_bytes(l_current_data,l_mct_size-2,2);                                 /* Lmct */
5846         l_current_data += 2;
5847
5848         opj_write_bytes(l_current_data,0,2);                                                    /* Zmct */
5849         l_current_data += 2;
5850
5851         /* only one marker atm */
5852         l_tmp = (p_mct_record->m_index & 0xff) | (p_mct_record->m_array_type << 8) | (p_mct_record->m_element_type << 10);
5853
5854         opj_write_bytes(l_current_data,l_tmp,2);
5855         l_current_data += 2;
5856
5857         opj_write_bytes(l_current_data,0,2);                                                    /* Ymct */
5858         l_current_data+=2;
5859
5860         memcpy(l_current_data,p_mct_record->m_data,p_mct_record->m_data_size);
5861
5862         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_mct_size,p_manager) != l_mct_size) {
5863                 return OPJ_FALSE;
5864         }
5865
5866         return OPJ_TRUE;
5867 }
5868
5869 /**
5870  * Reads a MCT marker (Multiple Component Transform)
5871  *
5872  * @param       p_header_data   the data contained in the MCT box.
5873  * @param       p_j2k                   the jpeg2000 codec.
5874  * @param       p_header_size   the size of the data contained in the MCT marker.
5875  * @param       p_manager               the user event manager.
5876 */
5877 opj_bool j2k_read_mct ( opj_j2k_v2_t *p_j2k,
5878                                                 OPJ_BYTE * p_header_data,
5879                                                 OPJ_UINT32 p_header_size,
5880                                                 struct opj_event_mgr * p_manager )
5881 {
5882         OPJ_UINT32 i;
5883         opj_tcp_v2_t *l_tcp = 00;
5884         OPJ_UINT32 l_tmp;
5885         OPJ_UINT32 l_indix;
5886         opj_mct_data_t * l_mct_data;
5887
5888         /* preconditions */
5889         assert(p_header_data != 00);
5890         assert(p_j2k != 00);
5891
5892         l_tcp = p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH ?
5893                         &p_j2k->m_cp.tcps[p_j2k->m_current_tile_number] :
5894                         p_j2k->m_specific_param.m_decoder.m_default_tcp;
5895
5896         if (p_header_size < 2) {
5897                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCT marker\n");
5898                 return OPJ_FALSE;
5899         }
5900
5901         /* first marker */
5902         opj_read_bytes(p_header_data,&l_tmp,2);                         /* Zmct */
5903         p_header_data += 2;
5904         if (l_tmp != 0) {
5905                 opj_event_msg_v2(p_manager, EVT_WARNING, "Cannot take in charge mct data within multiple MCT records\n");
5906                 return OPJ_TRUE;
5907         }
5908
5909         if(p_header_size <= 6) {
5910                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCT marker\n");
5911                 return OPJ_FALSE;
5912         }
5913
5914         /* Imct -> no need for other values, take the first, type is double with decorrelation x0000 1101 0000 0000*/
5915         opj_read_bytes(p_header_data,&l_tmp,2);                         /* Imct */
5916         p_header_data += 2;
5917
5918         l_indix = l_tmp & 0xff;
5919         l_mct_data = l_tcp->m_mct_records;
5920
5921         for (i=0;i<l_tcp->m_nb_mct_records;++i) {
5922                 if (l_mct_data->m_index == l_indix) {
5923                         break;
5924                 }
5925                 ++l_mct_data;
5926         }
5927
5928         /* NOT FOUND */
5929         if (i == l_tcp->m_nb_mct_records) {
5930                 if (l_tcp->m_nb_mct_records == l_tcp->m_nb_max_mct_records) {
5931                         l_tcp->m_nb_max_mct_records += J2K_MCT_DEFAULT_NB_RECORDS;
5932
5933                         l_tcp->m_mct_records = (opj_mct_data_t*)opj_realloc(l_tcp->m_mct_records,l_tcp->m_nb_max_mct_records * sizeof(opj_mct_data_t));
5934                         if(! l_tcp->m_mct_records) {
5935                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCT marker\n");
5936                                 return OPJ_FALSE;
5937                         }
5938
5939                         l_mct_data = l_tcp->m_mct_records + l_tcp->m_nb_mct_records;
5940                         memset(l_mct_data ,0,(l_tcp->m_nb_max_mct_records - l_tcp->m_nb_mct_records) * sizeof(opj_mct_data_t));
5941                 }
5942
5943                 l_mct_data = l_tcp->m_mct_records + l_tcp->m_nb_mct_records;
5944         }
5945
5946         if (l_mct_data->m_data) {
5947                 opj_free(l_mct_data->m_data);
5948                 l_mct_data->m_data = 00;
5949         }
5950
5951         l_mct_data->m_index = l_indix;
5952         l_mct_data->m_array_type = (J2K_MCT_ARRAY_TYPE)((l_tmp  >> 8) & 3);
5953         l_mct_data->m_element_type = (J2K_MCT_ELEMENT_TYPE)((l_tmp  >> 10) & 3);
5954
5955         opj_read_bytes(p_header_data,&l_tmp,2);                         /* Ymct */
5956         p_header_data+=2;
5957         if (l_tmp != 0) {
5958                 opj_event_msg_v2(p_manager, EVT_WARNING, "Cannot take in charge multiple MCT markers\n");
5959                 return OPJ_TRUE;
5960         }
5961
5962         p_header_size -= 6;
5963
5964         l_mct_data->m_data = (OPJ_BYTE*)opj_malloc(p_header_size);
5965         if (! l_mct_data->m_data) {
5966                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCT marker\n");
5967                 return OPJ_FALSE;
5968         }
5969         memcpy(l_mct_data->m_data,p_header_data,p_header_size);
5970
5971         l_mct_data->m_data_size = p_header_size;
5972         ++l_tcp->m_nb_mct_records;
5973
5974         return OPJ_TRUE;
5975 }
5976
5977 /**
5978  * Writes the MCC marker (Multiple Component Collection)
5979  *
5980  * @param       p_stream                the stream to write data to.
5981  * @param       p_j2k                   J2K codec.
5982  * @param       p_manager               the user event manager.
5983 */
5984 opj_bool j2k_write_mcc_record(  opj_j2k_v2_t *p_j2k,
5985                                                                 struct opj_simple_mcc_decorrelation_data * p_mcc_record,
5986                                                                 struct opj_stream_private *p_stream,
5987                                                                 struct opj_event_mgr * p_manager )
5988 {
5989         OPJ_UINT32 i;
5990         OPJ_UINT32 l_mcc_size;
5991         OPJ_BYTE * l_current_data = 00;
5992         OPJ_UINT32 l_nb_bytes_for_comp;
5993         OPJ_UINT32 l_mask;
5994         OPJ_UINT32 l_tmcc;
5995
5996         /* preconditions */
5997         assert(p_j2k != 00);
5998         assert(p_manager != 00);
5999         assert(p_stream != 00);
6000
6001         if (p_mcc_record->m_nb_comps > 255 ) {
6002         l_nb_bytes_for_comp = 2;
6003                 l_mask = 0x8000;
6004         }
6005         else {
6006                 l_nb_bytes_for_comp = 1;
6007                 l_mask = 0;
6008         }
6009
6010         l_mcc_size = p_mcc_record->m_nb_comps * 2 * l_nb_bytes_for_comp + 19;
6011         if (l_mcc_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size)
6012         {
6013                 p_j2k->m_specific_param.m_encoder.m_header_tile_data
6014                         = (OPJ_BYTE*)opj_realloc(
6015                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
6016                                 l_mcc_size);
6017                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
6018                         return OPJ_FALSE;
6019                 }
6020
6021                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_mcc_size;
6022         }
6023
6024         l_current_data = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
6025
6026         opj_write_bytes(l_current_data,J2K_MS_MCC,2);                                   /* MCC */
6027         l_current_data += 2;
6028
6029         opj_write_bytes(l_current_data,l_mcc_size-2,2);                                 /* Lmcc */
6030         l_current_data += 2;
6031
6032         /* first marker */
6033         opj_write_bytes(l_current_data,0,2);                                    /* Zmcc */
6034         l_current_data += 2;
6035
6036         opj_write_bytes(l_current_data,p_mcc_record->m_index,1);                                        /* Imcc -> no need for other values, take the first */
6037         ++l_current_data;
6038
6039         /* only one marker atm */
6040         opj_write_bytes(l_current_data,0,2);                                    /* Ymcc */
6041         l_current_data+=2;
6042
6043         opj_write_bytes(l_current_data,1,2);                                    /* Qmcc -> number of collections -> 1 */
6044         l_current_data+=2;
6045
6046         opj_write_bytes(l_current_data,0x1,1);                                  /* Xmcci type of component transformation -> array based decorrelation */
6047         ++l_current_data;
6048
6049         opj_write_bytes(l_current_data,p_mcc_record->m_nb_comps | l_mask,2);    /* Nmcci number of input components involved and size for each component offset = 8 bits */
6050         l_current_data+=2;
6051
6052         for (i=0;i<p_mcc_record->m_nb_comps;++i) {
6053                 opj_write_bytes(l_current_data,i,l_nb_bytes_for_comp);                          /* Cmccij Component offset*/
6054                 l_current_data+=l_nb_bytes_for_comp;
6055         }
6056
6057         opj_write_bytes(l_current_data,p_mcc_record->m_nb_comps|l_mask,2);      /* Mmcci number of output components involved and size for each component offset = 8 bits */
6058         l_current_data+=2;
6059
6060         for (i=0;i<p_mcc_record->m_nb_comps;++i)
6061         {
6062                 opj_write_bytes(l_current_data,i,l_nb_bytes_for_comp);                          /* Wmccij Component offset*/
6063                 l_current_data+=l_nb_bytes_for_comp;
6064         }
6065
6066         l_tmcc = ((!p_mcc_record->m_is_irreversible)&1)<<16;
6067
6068         if (p_mcc_record->m_decorrelation_array) {
6069                 l_tmcc |= p_mcc_record->m_decorrelation_array->m_index;
6070         }
6071
6072         if (p_mcc_record->m_offset_array) {
6073                 l_tmcc |= ((p_mcc_record->m_offset_array->m_index)<<8);
6074         }
6075
6076         opj_write_bytes(l_current_data,l_tmcc,3);       /* Tmcci : use MCT defined as number 1 and irreversible array based. */
6077         l_current_data+=3;
6078
6079         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_mcc_size,p_manager) != l_mcc_size) {
6080                 return OPJ_FALSE;
6081         }
6082
6083         return OPJ_TRUE;
6084 }
6085
6086 /**
6087  * Reads a MCC marker (Multiple Component Collection)
6088  *
6089  * @param       p_header_data   the data contained in the MCC box.
6090  * @param       p_j2k                   the jpeg2000 codec.
6091  * @param       p_header_size   the size of the data contained in the MCC marker.
6092  * @param       p_manager               the user event manager.
6093 */
6094 opj_bool j2k_read_mcc ( opj_j2k_v2_t *p_j2k,
6095                                         OPJ_BYTE * p_header_data,
6096                                         OPJ_UINT32 p_header_size,
6097                                         struct opj_event_mgr * p_manager )
6098 {
6099         OPJ_UINT32 i,j;
6100         OPJ_UINT32 l_tmp;
6101         OPJ_UINT32 l_indix;
6102         opj_tcp_v2_t * l_tcp;
6103         opj_simple_mcc_decorrelation_data_t * l_mcc_record;
6104         opj_mct_data_t * l_mct_data;
6105         OPJ_UINT32 l_nb_collections;
6106         OPJ_UINT32 l_nb_comps;
6107         OPJ_UINT32 l_nb_bytes_by_comp;
6108
6109
6110         /* preconditions */
6111         assert(p_header_data != 00);
6112         assert(p_j2k != 00);
6113         assert(p_manager != 00);
6114
6115         l_tcp = p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH ?
6116                         &p_j2k->m_cp.tcps[p_j2k->m_current_tile_number] :
6117                         p_j2k->m_specific_param.m_decoder.m_default_tcp;
6118
6119         if (p_header_size < 2) {
6120                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCC marker\n");
6121                 return OPJ_FALSE;
6122         }
6123
6124         /* first marker */
6125         opj_read_bytes(p_header_data,&l_tmp,2);                         /* Zmcc */
6126         p_header_data += 2;
6127         if (l_tmp != 0) {
6128                 opj_event_msg_v2(p_manager, EVT_WARNING, "Cannot take in charge multiple data spanning\n");
6129                 return OPJ_TRUE;
6130         }
6131
6132         if (p_header_size < 7) {
6133                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCC marker\n");
6134                 return OPJ_FALSE;
6135         }
6136
6137         opj_read_bytes(p_header_data,&l_indix,1); /* Imcc -> no need for other values, take the first */
6138         ++p_header_data;
6139
6140         l_mcc_record = l_tcp->m_mcc_records;
6141
6142         for(i=0;i<l_tcp->m_nb_mcc_records;++i) {
6143                 if (l_mcc_record->m_index == l_indix) {
6144                         break;
6145                 }
6146                 ++l_mcc_record;
6147         }
6148
6149         /** NOT FOUND */
6150         if (i == l_tcp->m_nb_mcc_records) {
6151                 if (l_tcp->m_nb_mcc_records == l_tcp->m_nb_max_mcc_records) {
6152                         l_tcp->m_nb_max_mcc_records += J2K_MCC_DEFAULT_NB_RECORDS;
6153
6154                         l_tcp->m_mcc_records = (opj_simple_mcc_decorrelation_data_t*)
6155                                         opj_realloc(l_tcp->m_mcc_records,l_tcp->m_nb_max_mcc_records * sizeof(opj_simple_mcc_decorrelation_data_t));
6156                         if (! l_tcp->m_mcc_records) {
6157                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCC marker\n");
6158                                 return OPJ_FALSE;
6159                         }
6160                         l_mcc_record = l_tcp->m_mcc_records + l_tcp->m_nb_mcc_records;
6161                         memset(l_mcc_record,0,(l_tcp->m_nb_max_mcc_records-l_tcp->m_nb_mcc_records) * sizeof(opj_simple_mcc_decorrelation_data_t));
6162                 }
6163                 l_mcc_record = l_tcp->m_mcc_records + l_tcp->m_nb_mcc_records;
6164         }
6165         l_mcc_record->m_index = l_indix;
6166
6167         /* only one marker atm */
6168         opj_read_bytes(p_header_data,&l_tmp,2);                         /* Ymcc */
6169         p_header_data+=2;
6170         if (l_tmp != 0) {
6171                 opj_event_msg_v2(p_manager, EVT_WARNING, "Cannot take in charge multiple data spanning\n");
6172                 return OPJ_TRUE;
6173         }
6174
6175         opj_read_bytes(p_header_data,&l_nb_collections,2);                              /* Qmcc -> number of collections -> 1 */
6176         p_header_data+=2;
6177
6178         if (l_nb_collections > 1) {
6179                 opj_event_msg_v2(p_manager, EVT_WARNING, "Cannot take in charge multiple collections\n");
6180                 return OPJ_TRUE;
6181         }
6182
6183         p_header_size -= 7;
6184
6185         for (i=0;i<l_nb_collections;++i) {
6186                 if (p_header_size < 3) {
6187                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCC marker\n");
6188                         return OPJ_FALSE;
6189                 }
6190
6191                 opj_read_bytes(p_header_data,&l_tmp,1); /* Xmcci type of component transformation -> array based decorrelation */
6192                 ++p_header_data;
6193
6194                 if (l_tmp != 1) {
6195                         opj_event_msg_v2(p_manager, EVT_WARNING, "Cannot take in charge collections other than array decorrelation\n");
6196                         return OPJ_TRUE;
6197                 }
6198
6199                 opj_read_bytes(p_header_data,&l_nb_comps,2);
6200
6201                 p_header_data+=2;
6202                 p_header_size-=3;
6203
6204                 l_nb_bytes_by_comp = 1 + (l_nb_comps>>15);
6205                 l_mcc_record->m_nb_comps = l_nb_comps & 0x7fff;
6206
6207                 if (p_header_size < (l_nb_bytes_by_comp * l_mcc_record->m_nb_comps + 2)) {
6208                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCC marker\n");
6209                         return OPJ_FALSE;
6210                 }
6211
6212                 p_header_size -= (l_nb_bytes_by_comp * l_mcc_record->m_nb_comps + 2);
6213
6214                 for (j=0;j<l_mcc_record->m_nb_comps;++j) {
6215                         opj_read_bytes(p_header_data,&l_tmp,l_nb_bytes_by_comp);        /* Cmccij Component offset*/
6216                         p_header_data+=l_nb_bytes_by_comp;
6217
6218                         if (l_tmp != j) {
6219                                 opj_event_msg_v2(p_manager, EVT_WARNING, "Cannot take in charge collections with indix shuffle\n");
6220                                 return OPJ_TRUE;
6221                         }
6222                 }
6223
6224                 opj_read_bytes(p_header_data,&l_nb_comps,2);
6225                 p_header_data+=2;
6226
6227                 l_nb_bytes_by_comp = 1 + (l_nb_comps>>15);
6228                 l_nb_comps &= 0x7fff;
6229
6230                 if (l_nb_comps != l_mcc_record->m_nb_comps) {
6231                         opj_event_msg_v2(p_manager, EVT_WARNING, "Cannot take in charge collections without same number of indixes\n");
6232                         return OPJ_TRUE;
6233                 }
6234
6235                 if (p_header_size < (l_nb_bytes_by_comp * l_mcc_record->m_nb_comps + 3)) {
6236                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCC marker\n");
6237                         return OPJ_FALSE;
6238                 }
6239
6240                 p_header_size -= (l_nb_bytes_by_comp * l_mcc_record->m_nb_comps + 3);
6241
6242                 for (j=0;j<l_mcc_record->m_nb_comps;++j) {
6243                         opj_read_bytes(p_header_data,&l_tmp,l_nb_bytes_by_comp);        /* Wmccij Component offset*/
6244                         p_header_data+=l_nb_bytes_by_comp;
6245
6246                         if (l_tmp != j) {
6247                                 opj_event_msg_v2(p_manager, EVT_WARNING, "Cannot take in charge collections with indix shuffle\n");
6248                                 return OPJ_TRUE;
6249                         }
6250                 }
6251
6252                 opj_read_bytes(p_header_data,&l_tmp,3); /* Wmccij Component offset*/
6253                 p_header_data += 3;
6254
6255                 l_mcc_record->m_is_irreversible = ! ((l_tmp>>16) & 1);
6256                 l_mcc_record->m_decorrelation_array = 00;
6257                 l_mcc_record->m_offset_array = 00;
6258
6259                 l_indix = l_tmp & 0xff;
6260                 if (l_indix != 0) {
6261                         l_mct_data = l_tcp->m_mct_records;
6262                         for (j=0;j<l_tcp->m_nb_mct_records;++j) {
6263                                 if (l_mct_data->m_index == l_indix) {
6264                                         l_mcc_record->m_decorrelation_array = l_mct_data;
6265                                         break;
6266                                 }
6267                                 ++l_mct_data;
6268                         }
6269
6270                         if (l_mcc_record->m_decorrelation_array == 00) {
6271                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCC marker\n");
6272                                 return OPJ_FALSE;
6273                         }
6274                 }
6275
6276                 l_indix = (l_tmp >> 8) & 0xff;
6277                 if (l_indix != 0) {
6278                         l_mct_data = l_tcp->m_mct_records;
6279                         for (j=0;j<l_tcp->m_nb_mct_records;++j) {
6280                                 if (l_mct_data->m_index == l_indix) {
6281                                         l_mcc_record->m_offset_array = l_mct_data;
6282                                         break;
6283                                 }
6284                                 ++l_mct_data;
6285                         }
6286
6287                         if (l_mcc_record->m_offset_array == 00) {
6288                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCC marker\n");
6289                                 return OPJ_FALSE;
6290                         }
6291                 }
6292         }
6293
6294         if (p_header_size != 0) {
6295                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCC marker\n");
6296                 return OPJ_FALSE;
6297         }
6298
6299         ++l_tcp->m_nb_mcc_records;
6300
6301         return OPJ_TRUE;
6302 }
6303
6304
6305 /**
6306  * Writes the MCO marker (Multiple component transformation ordering)
6307  *
6308  * @param       p_stream                                the stream to write data to.
6309  * @param       p_j2k                           J2K codec.
6310  * @param       p_manager               the user event manager.
6311 */
6312 opj_bool j2k_write_mco( opj_j2k_v2_t *p_j2k,
6313                                                 struct opj_stream_private *p_stream,
6314                                                 struct opj_event_mgr * p_manager
6315                                   )
6316 {
6317         OPJ_BYTE * l_current_data = 00;
6318         OPJ_UINT32 l_mco_size;
6319         opj_tcp_v2_t * l_tcp = 00;
6320         opj_simple_mcc_decorrelation_data_t * l_mcc_record;
6321         OPJ_UINT32 i;
6322
6323         /* preconditions */
6324         assert(p_j2k != 00);
6325         assert(p_manager != 00);
6326         assert(p_stream != 00);
6327
6328         l_tcp =&(p_j2k->m_cp.tcps[p_j2k->m_current_tile_number]);
6329         l_current_data = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
6330
6331         l_mco_size = 5 + l_tcp->m_nb_mcc_records;
6332         if (l_mco_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
6333
6334                 p_j2k->m_specific_param.m_encoder.m_header_tile_data
6335                         = (OPJ_BYTE*)opj_realloc(
6336                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
6337                                 l_mco_size);
6338                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data)
6339                 {
6340                         return OPJ_FALSE;
6341                 }
6342
6343                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_mco_size;
6344         }
6345
6346         opj_write_bytes(l_current_data,J2K_MS_MCO,2);                   /* MCO */
6347         l_current_data += 2;
6348
6349         opj_write_bytes(l_current_data,l_mco_size-2,2);                                 /* Lmco */
6350         l_current_data += 2;
6351
6352         opj_write_bytes(l_current_data,l_tcp->m_nb_mcc_records,1);                                      /* Nmco : only one tranform stage*/
6353         ++l_current_data;
6354
6355         l_mcc_record = l_tcp->m_mcc_records;
6356         for     (i=0;i<l_tcp->m_nb_mcc_records;++i) {
6357                 opj_write_bytes(l_current_data,l_mcc_record->m_index,1);                                        /* Imco -> use the mcc indicated by 1*/
6358                 ++l_current_data;
6359
6360                 ++l_mcc_record;
6361         }
6362
6363         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_mco_size,p_manager) != l_mco_size) {
6364                 return OPJ_FALSE;
6365         }
6366
6367         return OPJ_TRUE;
6368 }
6369
6370 /**
6371  * Reads a MCO marker (Multiple Component Transform Ordering)
6372  *
6373  * @param       p_header_data   the data contained in the MCO box.
6374  * @param       p_j2k                   the jpeg2000 codec.
6375  * @param       p_header_size   the size of the data contained in the MCO marker.
6376  * @param       p_manager               the user event manager.
6377 */
6378 opj_bool j2k_read_mco ( opj_j2k_v2_t *p_j2k,
6379                                                 OPJ_BYTE * p_header_data,
6380                                                 OPJ_UINT32 p_header_size,
6381                                                 struct opj_event_mgr * p_manager )
6382 {
6383         OPJ_UINT32 l_tmp, i;
6384         OPJ_UINT32 l_nb_stages;
6385         opj_tcp_v2_t * l_tcp;
6386         opj_tccp_t * l_tccp;
6387         opj_image_t * l_image;
6388         opj_image_comp_t * l_img_comp;
6389
6390         /* preconditions */
6391         assert(p_header_data != 00);
6392         assert(p_j2k != 00);
6393         assert(p_manager != 00);
6394
6395         l_image = p_j2k->m_private_image;
6396         l_tcp = p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH ?
6397                         &p_j2k->m_cp.tcps[p_j2k->m_current_tile_number] :
6398                         p_j2k->m_specific_param.m_decoder.m_default_tcp;
6399
6400         if (p_header_size < 1) {
6401                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading MCO marker\n");
6402                 return OPJ_FALSE;
6403         }
6404
6405         opj_read_bytes(p_header_data,&l_nb_stages,1);                           /* Nmco : only one tranform stage*/
6406         ++p_header_data;
6407
6408         if (l_nb_stages > 1) {
6409                 opj_event_msg_v2(p_manager, EVT_WARNING, "Cannot take in charge multiple transformation stages.\n");
6410                 return OPJ_TRUE;
6411         }
6412
6413         if (p_header_size != l_nb_stages + 1) {
6414                 opj_event_msg_v2(p_manager, EVT_WARNING, "Error reading MCO marker\n");
6415                 return OPJ_FALSE;
6416         }
6417
6418         l_tccp = l_tcp->tccps;
6419         l_img_comp = l_image->comps;
6420
6421         for (i=0;i<l_image->numcomps;++i) {
6422                 l_tccp->m_dc_level_shift = 0;
6423                 ++l_tccp;
6424         }
6425
6426         if (l_tcp->m_mct_decoding_matrix) {
6427                 opj_free(l_tcp->m_mct_decoding_matrix);
6428                 l_tcp->m_mct_decoding_matrix = 00;
6429         }
6430
6431         for (i=0;i<l_nb_stages;++i) {
6432                 opj_read_bytes(p_header_data,&l_tmp,1);
6433                 ++p_header_data;
6434
6435                 if (! j2k_add_mct(l_tcp,p_j2k->m_private_image,l_tmp)) {
6436                         return OPJ_FALSE;
6437                 }
6438         }
6439
6440         return OPJ_TRUE;
6441 }
6442
6443 opj_bool j2k_add_mct(opj_tcp_v2_t * p_tcp, opj_image_t * p_image, OPJ_UINT32 p_index)
6444 {
6445         OPJ_UINT32 i;
6446         opj_simple_mcc_decorrelation_data_t * l_mcc_record;
6447         opj_mct_data_t * l_deco_array, * l_offset_array;
6448         OPJ_UINT32 l_data_size,l_mct_size, l_offset_size;
6449         OPJ_UINT32 l_nb_elem;
6450         OPJ_UINT32 * l_offset_data, * l_current_offset_data;
6451         opj_tccp_t * l_tccp;
6452
6453         /* preconditions */
6454         assert(p_tcp != 00);
6455
6456         l_mcc_record = p_tcp->m_mcc_records;
6457
6458         for (i=0;i<p_tcp->m_nb_mcc_records;++i) {
6459                 if (l_mcc_record->m_index == p_index) {
6460                         break;
6461                 }
6462         }
6463
6464         if (i==p_tcp->m_nb_mcc_records) {
6465                 /** element discarded **/
6466                 return OPJ_TRUE;
6467         }
6468
6469         if (l_mcc_record->m_nb_comps != p_image->numcomps) {
6470                 /** do not support number of comps != image */
6471                 return OPJ_TRUE;
6472         }
6473
6474         l_deco_array = l_mcc_record->m_decorrelation_array;
6475
6476         if (l_deco_array) {
6477                 l_data_size = MCT_ELEMENT_SIZE[l_deco_array->m_element_type] * p_image->numcomps * p_image->numcomps;
6478                 if (l_deco_array->m_data_size != l_data_size) {
6479                         return OPJ_FALSE;
6480                 }
6481
6482                 l_nb_elem = p_image->numcomps * p_image->numcomps;
6483                 l_mct_size = l_nb_elem * sizeof(OPJ_FLOAT32);
6484                 p_tcp->m_mct_decoding_matrix = (OPJ_FLOAT32*)opj_malloc(l_mct_size);
6485
6486                 if (! p_tcp->m_mct_decoding_matrix ) {
6487                         return OPJ_FALSE;
6488                 }
6489
6490                 j2k_mct_read_functions_to_float[l_deco_array->m_element_type](l_deco_array->m_data,p_tcp->m_mct_decoding_matrix,l_nb_elem);
6491         }
6492
6493         l_offset_array = l_mcc_record->m_offset_array;
6494
6495         if (l_offset_array) {
6496                 l_data_size = MCT_ELEMENT_SIZE[l_offset_array->m_element_type] * p_image->numcomps;
6497                 if (l_offset_array->m_data_size != l_data_size) {
6498                         return OPJ_FALSE;
6499                 }
6500
6501                 l_nb_elem = p_image->numcomps;
6502                 l_offset_size = l_nb_elem * sizeof(OPJ_UINT32);
6503                 l_offset_data = (OPJ_UINT32*)opj_malloc(l_offset_size);
6504
6505                 if (! l_offset_data ) {
6506                         return OPJ_FALSE;
6507                 }
6508
6509                 j2k_mct_read_functions_to_int32[l_offset_array->m_element_type](l_offset_array->m_data,l_offset_data,l_nb_elem);
6510
6511                 l_tccp = p_tcp->tccps;
6512                 l_current_offset_data = l_offset_data;
6513
6514                 for (i=0;i<p_image->numcomps;++i) {
6515                         l_tccp->m_dc_level_shift = *(l_current_offset_data++);
6516                         ++l_tccp;
6517                 }
6518
6519                 opj_free(l_offset_data);
6520         }
6521
6522         return OPJ_TRUE;
6523 }
6524
6525 /**
6526  * Writes the CBD marker (Component bit depth definition)
6527  *
6528  * @param       p_stream                                the stream to write data to.
6529  * @param       p_j2k                           J2K codec.
6530  * @param       p_manager               the user event manager.
6531 */
6532 opj_bool j2k_write_cbd( opj_j2k_v2_t *p_j2k,
6533                                                 struct opj_stream_private *p_stream,
6534                                                 struct opj_event_mgr * p_manager )
6535 {
6536         OPJ_UINT32 i;
6537         OPJ_UINT32 l_cbd_size;
6538         OPJ_BYTE * l_current_data = 00;
6539         opj_image_t *l_image = 00;
6540         opj_image_comp_t * l_comp = 00;
6541
6542         /* preconditions */
6543         assert(p_j2k != 00);
6544         assert(p_manager != 00);
6545         assert(p_stream != 00);
6546
6547         l_image = p_j2k->m_private_image;
6548         l_cbd_size = 6 + p_j2k->m_private_image->numcomps;
6549
6550         if (l_cbd_size > p_j2k->m_specific_param.m_encoder.m_header_tile_data_size) {
6551                 p_j2k->m_specific_param.m_encoder.m_header_tile_data
6552                         = (OPJ_BYTE*)opj_realloc(
6553                                 p_j2k->m_specific_param.m_encoder.m_header_tile_data,
6554                                 l_cbd_size);
6555
6556                 if (! p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
6557                         return OPJ_FALSE;
6558                 }
6559
6560                 p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = l_cbd_size;
6561         }
6562
6563         l_current_data = p_j2k->m_specific_param.m_encoder.m_header_tile_data;
6564
6565         opj_write_bytes(l_current_data,J2K_MS_CBD,2);                                   /* CBD */
6566         l_current_data += 2;
6567
6568         opj_write_bytes(l_current_data,l_cbd_size-2,2);                                 /* L_CBD */
6569         l_current_data += 2;
6570
6571         opj_write_bytes(l_current_data,l_image->numcomps, 2);           /* Ncbd */
6572         l_current_data+=2;
6573
6574         l_comp = l_image->comps;
6575
6576         for (i=0;i<l_image->numcomps;++i) {
6577                 opj_write_bytes(l_current_data, (l_comp->sgnd << 7) | (l_comp->prec - 1), 1);           /* Component bit depth */
6578                 ++l_current_data;
6579
6580                 ++l_comp;
6581         }
6582
6583         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_header_tile_data,l_cbd_size,p_manager) != l_cbd_size) {
6584                 return OPJ_FALSE;
6585         }
6586
6587         return OPJ_TRUE;
6588 }
6589
6590 /**
6591  * Reads a CBD marker (Component bit depth definition)
6592  * @param       p_header_data   the data contained in the CBD box.
6593  * @param       p_j2k                   the jpeg2000 codec.
6594  * @param       p_header_size   the size of the data contained in the CBD marker.
6595  * @param       p_manager               the user event manager.
6596 */
6597 opj_bool j2k_read_cbd ( opj_j2k_v2_t *p_j2k,
6598                                                 OPJ_BYTE * p_header_data,
6599                                                 OPJ_UINT32 p_header_size,
6600                                                 struct opj_event_mgr * p_manager)
6601 {
6602         OPJ_UINT32 l_nb_comp,l_num_comp;
6603         OPJ_UINT32 l_comp_def;
6604         OPJ_UINT32 i;
6605         opj_image_comp_t * l_comp = 00;
6606
6607         /* preconditions */
6608         assert(p_header_data != 00);
6609         assert(p_j2k != 00);
6610         assert(p_manager != 00);
6611
6612         l_num_comp = p_j2k->m_private_image->numcomps;
6613
6614         if (p_header_size != (p_j2k->m_private_image->numcomps + 2)) {
6615                 opj_event_msg_v2(p_manager, EVT_ERROR, "Crror reading CBD marker\n");
6616                 return OPJ_FALSE;
6617         }
6618
6619         opj_read_bytes(p_header_data,&l_nb_comp,2);                             /* Ncbd */
6620         p_header_data+=2;
6621
6622         if (l_nb_comp != l_num_comp) {
6623                 opj_event_msg_v2(p_manager, EVT_ERROR, "Crror reading CBD marker\n");
6624                 return OPJ_FALSE;
6625         }
6626
6627         l_comp = p_j2k->m_private_image->comps;
6628         for (i=0;i<l_num_comp;++i) {
6629                 opj_read_bytes(p_header_data,&l_comp_def,1);                    /* Component bit depth */
6630                 ++p_header_data;
6631         l_comp->sgnd = (l_comp_def>>7) & 1;
6632                 l_comp->prec = (l_comp_def&0x7f) + 1;
6633                 ++l_comp;
6634         }
6635
6636         return OPJ_TRUE;
6637 }
6638
6639
6640 /* ----------------------------------------------------------------------- */
6641 /* J2K / JPT decoder interface                                             */
6642 /* ----------------------------------------------------------------------- */
6643
6644
6645
6646 void j2k_destroy_decompress(opj_j2k_t *j2k) {
6647         int i = 0;
6648
6649         if(j2k->tile_len != NULL) {
6650                 opj_free(j2k->tile_len);
6651         }
6652         if(j2k->tile_data != NULL) {
6653                 opj_free(j2k->tile_data);
6654         }
6655         if(j2k->default_tcp != NULL) {
6656                 opj_tcp_t *default_tcp = j2k->default_tcp;
6657                 if(default_tcp->ppt_data_first != NULL) {
6658                         opj_free(default_tcp->ppt_data_first);
6659                 }
6660                 if(j2k->default_tcp->tccps != NULL) {
6661                         opj_free(j2k->default_tcp->tccps);
6662                 }
6663                 opj_free(j2k->default_tcp);
6664         }
6665         if(j2k->cp != NULL) {
6666                 opj_cp_t *cp = j2k->cp;
6667                 if(cp->tcps != NULL) {
6668                         for(i = 0; i < cp->tw * cp->th; i++) {
6669                                 if(cp->tcps[i].ppt_data_first != NULL) {
6670                                         opj_free(cp->tcps[i].ppt_data_first);
6671                                 }
6672                                 if(cp->tcps[i].tccps != NULL) {
6673                                         opj_free(cp->tcps[i].tccps);
6674                                 }
6675                         }
6676                         opj_free(cp->tcps);
6677                 }
6678                 if(cp->ppm_data_first != NULL) {
6679                         opj_free(cp->ppm_data_first);
6680                 }
6681                 if(cp->tileno != NULL) {
6682                         opj_free(cp->tileno);  
6683                 }
6684                 if(cp->comment != NULL) {
6685                         opj_free(cp->comment);
6686                 }
6687
6688                 opj_free(cp);
6689         }
6690         opj_free(j2k);
6691 }
6692
6693
6694 void opj_j2k_setup_decoder(opj_j2k_v2_t *j2k, opj_dparameters_t *parameters)
6695 {
6696         if(j2k && parameters) {
6697                 j2k->m_cp.m_specific_param.m_dec.m_layer = parameters->cp_layer;
6698                 j2k->m_cp.m_specific_param.m_dec.m_reduce = parameters->cp_reduce;
6699
6700 #ifdef USE_JPWL
6701                 j2k->m_cp.correct = parameters->jpwl_correct;
6702                 j2k->m_cp.exp_comps = parameters->jpwl_exp_comps;
6703                 j2k->m_cp.max_tiles = parameters->jpwl_max_tiles;
6704 #endif /* USE_JPWL */
6705         }
6706 }
6707
6708
6709
6710 /*
6711 * Read a JPT-stream and decode file
6712 *
6713 */
6714 opj_image_t* j2k_decode_jpt_stream(opj_j2k_t *j2k, opj_cio_t *cio,  opj_codestream_info_t *cstr_info) {
6715         opj_image_t *image = NULL;
6716         opj_jpt_msg_header_t header;
6717         int position;
6718         opj_common_ptr cinfo = j2k->cinfo;
6719
6720         OPJ_ARG_NOT_USED(cstr_info);
6721
6722         j2k->cio = cio;
6723
6724         /* create an empty image */
6725         image = opj_image_create0();
6726         j2k->image = image;
6727
6728         j2k->state = J2K_STATE_MHSOC;
6729         
6730         /* Initialize the header */
6731         jpt_init_msg_header(&header);
6732         /* Read the first header of the message */
6733         jpt_read_msg_header(cinfo, cio, &header);
6734         
6735         position = cio_tell(cio);
6736         if (header.Class_Id != 6) {     /* 6 : Main header data-bin message */
6737                 opj_image_destroy(image);
6738                 opj_event_msg(cinfo, EVT_ERROR, "[JPT-stream] : Expecting Main header first [class_Id %d] !\n", header.Class_Id);
6739                 return 0;
6740         }
6741         
6742         for (;;) {
6743                 opj_dec_mstabent_t *e = NULL;
6744                 int id;
6745                 
6746                 if (!cio_numbytesleft(cio)) {
6747                         j2k_read_eoc(j2k);
6748                         return image;
6749                 }
6750                 /* data-bin read -> need to read a new header */
6751                 if ((unsigned int) (cio_tell(cio) - position) == header.Msg_length) {
6752                         jpt_read_msg_header(cinfo, cio, &header);
6753                         position = cio_tell(cio);
6754                         if (header.Class_Id != 4) {     /* 4 : Tile data-bin message */
6755                                 opj_image_destroy(image);
6756                                 opj_event_msg(cinfo, EVT_ERROR, "[JPT-stream] : Expecting Tile info !\n");
6757                                 return 0;
6758                         }
6759                 }
6760                 
6761                 id = cio_read(cio, 2);
6762                 if (id >> 8 != 0xff) {
6763                         opj_image_destroy(image);
6764                         opj_event_msg(cinfo, EVT_ERROR, "%.8x: expected a marker instead of %x\n", cio_tell(cio) - 2, id);
6765                         return 0;
6766                 }
6767                 e = j2k_dec_mstab_lookup(id);
6768                 if (!(j2k->state & e->states)) {
6769                         opj_image_destroy(image);
6770                         opj_event_msg(cinfo, EVT_ERROR, "%.8x: unexpected marker %x\n", cio_tell(cio) - 2, id);
6771                         return 0;
6772                 }
6773                 if (e->handler) {
6774                         (*e->handler)(j2k);
6775                 }
6776                 if (j2k->state == J2K_STATE_MT) {
6777                         break;
6778                 }
6779                 if (j2k->state == J2K_STATE_NEOC) {
6780                         break;
6781                 }
6782         }
6783         if (j2k->state == J2K_STATE_NEOC) {
6784                 j2k_read_eoc(j2k);
6785         }
6786         
6787         if (j2k->state != J2K_STATE_MT) {
6788                 opj_event_msg(cinfo, EVT_WARNING, "Incomplete bitstream\n");
6789         }
6790
6791         return image;
6792 }
6793
6794 /* ----------------------------------------------------------------------- */
6795 /* J2K encoder interface                                                       */
6796 /* ----------------------------------------------------------------------- */
6797
6798 opj_j2k_t* j2k_create_compress(opj_common_ptr cinfo) {
6799         opj_j2k_t *j2k = (opj_j2k_t*) opj_calloc(1, sizeof(opj_j2k_t));
6800         if(j2k) {
6801                 j2k->cinfo = cinfo;
6802         }
6803         return j2k;
6804 }
6805
6806 opj_j2k_v2_t* j2k_create_compress_v2(void)
6807 {
6808         opj_j2k_v2_t *l_j2k = (opj_j2k_v2_t*) opj_malloc(sizeof(opj_j2k_v2_t));
6809         if (!l_j2k) {
6810                 return NULL;
6811         }
6812
6813         memset(l_j2k,0,sizeof(opj_j2k_v2_t));
6814
6815         l_j2k->m_is_decoder = 0;
6816         l_j2k->m_cp.m_is_decoder = 0;
6817
6818         l_j2k->m_specific_param.m_encoder.m_header_tile_data = (OPJ_BYTE *) opj_malloc(J2K_DEFAULT_HEADER_SIZE);
6819         if (! l_j2k->m_specific_param.m_encoder.m_header_tile_data) {
6820                 j2k_destroy(l_j2k);
6821                 return NULL;
6822         }
6823
6824         l_j2k->m_specific_param.m_encoder.m_header_tile_data_size = J2K_DEFAULT_HEADER_SIZE;
6825
6826         /* validation list creation*/
6827         l_j2k->m_validation_list = opj_procedure_list_create();
6828         if (! l_j2k->m_validation_list) {
6829                 j2k_destroy(l_j2k);
6830                 return NULL;
6831         }
6832
6833         /* execution list creation*/
6834         l_j2k->m_procedure_list = opj_procedure_list_create();
6835         if (! l_j2k->m_procedure_list) {
6836                 j2k_destroy(l_j2k);
6837                 return NULL;
6838         }
6839
6840         return l_j2k;
6841 }
6842
6843 void j2k_destroy_compress(opj_j2k_t *j2k) {
6844         int tileno;
6845
6846         if(!j2k) return;
6847         if(j2k->cp != NULL) {
6848                 opj_cp_t *cp = j2k->cp;
6849
6850                 if(cp->comment) {
6851                         opj_free(cp->comment);
6852                 }
6853                 if(cp->matrice) {
6854                         opj_free(cp->matrice);
6855                 }
6856                 for (tileno = 0; tileno < cp->tw * cp->th; tileno++) {
6857                         opj_free(cp->tcps[tileno].tccps);
6858                 }
6859                 opj_free(cp->tcps);
6860                 opj_free(cp);
6861         }
6862
6863         opj_free(j2k);
6864 }
6865
6866 void j2k_setup_encoder(opj_j2k_t *j2k, opj_cparameters_t *parameters, opj_image_t *image) {
6867         OPJ_UINT32 i,j;
6868   int tileno, numpocs_tile;
6869         opj_cp_t *cp = NULL;
6870
6871         if(!j2k || !parameters || ! image) {
6872                 return;
6873         }
6874
6875         /* create and initialize the coding parameters structure */
6876         cp = (opj_cp_t*) opj_calloc(1, sizeof(opj_cp_t));
6877
6878         /* keep a link to cp so that we can destroy it later in j2k_destroy_compress */
6879         j2k->cp = cp;
6880
6881         /* set default values for cp */
6882         cp->tw = 1;
6883         cp->th = 1;
6884
6885         /* 
6886         copy user encoding parameters 
6887         */
6888         cp->cinema = parameters->cp_cinema;
6889         cp->max_comp_size =     parameters->max_comp_size;
6890         cp->rsiz   = parameters->cp_rsiz;
6891         cp->disto_alloc = parameters->cp_disto_alloc;
6892         cp->fixed_alloc = parameters->cp_fixed_alloc;
6893         cp->fixed_quality = parameters->cp_fixed_quality;
6894
6895         /* mod fixed_quality */
6896         if(parameters->cp_matrice) {
6897                 size_t array_size = parameters->tcp_numlayers * parameters->numresolution * 3 * sizeof(int);
6898                 cp->matrice = (int *) opj_malloc(array_size);
6899                 memcpy(cp->matrice, parameters->cp_matrice, array_size);
6900         }
6901
6902         /* tiles */
6903         cp->tdx = parameters->cp_tdx;
6904         cp->tdy = parameters->cp_tdy;
6905
6906         /* tile offset */
6907         cp->tx0 = parameters->cp_tx0;
6908         cp->ty0 = parameters->cp_ty0;
6909
6910         /* comment string */
6911         if(parameters->cp_comment) {
6912                 cp->comment = (char*)opj_malloc(strlen(parameters->cp_comment) + 1);
6913                 if(cp->comment) {
6914                         strcpy(cp->comment, parameters->cp_comment);
6915                 }
6916         }
6917
6918         /*
6919         calculate other encoding parameters
6920         */
6921
6922         if (parameters->tile_size_on) {
6923                 cp->tw = int_ceildiv(image->x1 - cp->tx0, cp->tdx);
6924                 cp->th = int_ceildiv(image->y1 - cp->ty0, cp->tdy);
6925         } else {
6926                 cp->tdx = image->x1 - cp->tx0;
6927                 cp->tdy = image->y1 - cp->ty0;
6928         }
6929
6930         if(parameters->tp_on){
6931                 cp->tp_flag = parameters->tp_flag;
6932                 cp->tp_on = 1;
6933         }
6934         
6935         cp->img_size = 0;
6936         for(i=0;i<image->numcomps ;i++){
6937         cp->img_size += (image->comps[i].w *image->comps[i].h * image->comps[i].prec);
6938         }
6939
6940
6941 #ifdef USE_JPWL
6942         /*
6943         calculate JPWL encoding parameters
6944         */
6945
6946         if (parameters->jpwl_epc_on) {
6947                 OPJ_UINT32 i;
6948
6949                 /* set JPWL on */
6950                 cp->epc_on = OPJ_TRUE;
6951                 cp->info_on = OPJ_FALSE; /* no informative technique */
6952
6953                 /* set EPB on */
6954                 if ((parameters->jpwl_hprot_MH > 0) || (parameters->jpwl_hprot_TPH[0] > 0)) {
6955                         cp->epb_on = OPJ_TRUE;
6956                         
6957                         cp->hprot_MH = parameters->jpwl_hprot_MH;
6958                         for (i = 0; i < JPWL_MAX_NO_TILESPECS; i++) {
6959                                 cp->hprot_TPH_tileno[i] = parameters->jpwl_hprot_TPH_tileno[i];
6960                                 cp->hprot_TPH[i] = parameters->jpwl_hprot_TPH[i];
6961                         }
6962                         /* if tile specs are not specified, copy MH specs */
6963                         if (cp->hprot_TPH[0] == -1) {
6964                                 cp->hprot_TPH_tileno[0] = 0;
6965                                 cp->hprot_TPH[0] = parameters->jpwl_hprot_MH;
6966                         }
6967                         for (i = 0; i < JPWL_MAX_NO_PACKSPECS; i++) {
6968                                 cp->pprot_tileno[i] = parameters->jpwl_pprot_tileno[i];
6969                                 cp->pprot_packno[i] = parameters->jpwl_pprot_packno[i];
6970                                 cp->pprot[i] = parameters->jpwl_pprot[i];
6971                         }
6972                 }
6973
6974                 /* set ESD writing */
6975                 if ((parameters->jpwl_sens_size == 1) || (parameters->jpwl_sens_size == 2)) {
6976                         cp->esd_on = OPJ_TRUE;
6977
6978                         cp->sens_size = parameters->jpwl_sens_size;
6979                         cp->sens_addr = parameters->jpwl_sens_addr;
6980                         cp->sens_range = parameters->jpwl_sens_range;
6981
6982                         cp->sens_MH = parameters->jpwl_sens_MH;
6983                         for (i = 0; i < JPWL_MAX_NO_TILESPECS; i++) {
6984                                 cp->sens_TPH_tileno[i] = parameters->jpwl_sens_TPH_tileno[i];
6985                                 cp->sens_TPH[i] = parameters->jpwl_sens_TPH[i];
6986                         }
6987                 }
6988
6989                 /* always set RED writing to false: we are at the encoder */
6990                 cp->red_on = OPJ_FALSE;
6991
6992         } else {
6993                 cp->epc_on = OPJ_FALSE;
6994         }
6995 #endif /* USE_JPWL */
6996
6997
6998         /* initialize the mutiple tiles */
6999         /* ---------------------------- */
7000         cp->tcps = (opj_tcp_t*) opj_calloc(cp->tw * cp->th, sizeof(opj_tcp_t));
7001
7002         for (tileno = 0; tileno < cp->tw * cp->th; tileno++) {
7003                 opj_tcp_t *tcp = &cp->tcps[tileno];
7004                 tcp->numlayers = parameters->tcp_numlayers;
7005                 assert ( tcp->numlayers >= 0 );
7006                 for (j = 0; j < (OPJ_UINT32)tcp->numlayers; j++) {
7007                         if(cp->cinema){
7008                                 if (cp->fixed_quality) {
7009                                         tcp->distoratio[j] = parameters->tcp_distoratio[j];
7010                                 }
7011                                 tcp->rates[j] = parameters->tcp_rates[j];
7012                         }else{
7013                                 if (cp->fixed_quality) {        /* add fixed_quality */
7014                                         tcp->distoratio[j] = parameters->tcp_distoratio[j];
7015                                 } else {
7016                                         tcp->rates[j] = parameters->tcp_rates[j];
7017                                 }
7018                         }
7019                 }
7020                 tcp->csty = parameters->csty;
7021                 tcp->prg = parameters->prog_order;
7022                 tcp->mct = parameters->tcp_mct; 
7023
7024                 numpocs_tile = 0;
7025                 tcp->POC = 0;
7026                 if (parameters->numpocs) {
7027                         /* initialisation of POC */
7028                         tcp->POC = 1;
7029       assert( parameters->numpocs >= 0 );
7030                         for (i = 0; i < (OPJ_UINT32)parameters->numpocs; i++) {
7031                                 if((tileno == parameters->POC[i].tile - 1) || (parameters->POC[i].tile == -1)) {
7032                                         opj_poc_t *tcp_poc = &tcp->pocs[numpocs_tile];
7033                                         tcp_poc->resno0         = parameters->POC[numpocs_tile].resno0;
7034                                         tcp_poc->compno0        = parameters->POC[numpocs_tile].compno0;
7035                                         tcp_poc->layno1         = parameters->POC[numpocs_tile].layno1;
7036                                         tcp_poc->resno1         = parameters->POC[numpocs_tile].resno1;
7037                                         tcp_poc->compno1        = parameters->POC[numpocs_tile].compno1;
7038                                         tcp_poc->prg1           = parameters->POC[numpocs_tile].prg1;
7039                                         tcp_poc->tile           = parameters->POC[numpocs_tile].tile;
7040                                         numpocs_tile++;
7041                                 }
7042                         }
7043                         tcp->numpocs = numpocs_tile -1 ;
7044                 }else{ 
7045                         tcp->numpocs = 0;
7046                 }
7047
7048                 tcp->tccps = (opj_tccp_t*) opj_calloc(image->numcomps, sizeof(opj_tccp_t));
7049
7050                 for (i = 0; i < image->numcomps; i++) {
7051                         opj_tccp_t *tccp = &tcp->tccps[i];
7052                         tccp->csty = parameters->csty & 0x01;   /* 0 => one precinct || 1 => custom precinct  */
7053                         tccp->numresolutions = parameters->numresolution;
7054                         tccp->cblkw = int_floorlog2(parameters->cblockw_init);
7055                         tccp->cblkh = int_floorlog2(parameters->cblockh_init);
7056                         tccp->cblksty = parameters->mode;
7057                         tccp->qmfbid = parameters->irreversible ? 0 : 1;
7058                         tccp->qntsty = parameters->irreversible ? J2K_CCP_QNTSTY_SEQNT : J2K_CCP_QNTSTY_NOQNT;
7059                         tccp->numgbits = 2;
7060                         assert(parameters->roi_compno >= 0);
7061                         if (i == (OPJ_UINT32)parameters->roi_compno) {
7062                                 tccp->roishift = parameters->roi_shift;
7063                         } else {
7064                                 tccp->roishift = 0;
7065                         }
7066
7067                         if(parameters->cp_cinema)
7068                         {
7069                                 /*Precinct size for lowest frequency subband=128*/
7070                                 tccp->prcw[0] = 7;
7071                                 tccp->prch[0] = 7;
7072                                 /*Precinct size at all other resolutions = 256*/
7073                                 for (j = 1; j < tccp->numresolutions; j++) {
7074                                         tccp->prcw[j] = 8;
7075                                         tccp->prch[j] = 8;
7076                                 }
7077                         }else{
7078                                 if (parameters->csty & J2K_CCP_CSTY_PRT) {
7079                                         int p = 0;
7080                                         assert(tccp->numresolutions > 0);
7081                                         for (j = (OPJ_UINT32)(tccp->numresolutions - 1); (int)j >= 0; j--) {
7082                                                 if (p < parameters->res_spec) {
7083                                                         
7084                                                         if (parameters->prcw_init[p] < 1) {
7085                                                                 tccp->prcw[j] = 1;
7086                                                         } else {
7087                                                                 tccp->prcw[j] = int_floorlog2(parameters->prcw_init[p]);
7088                                                         }
7089                                                         
7090                                                         if (parameters->prch_init[p] < 1) {
7091                                                                 tccp->prch[j] = 1;
7092                                                         }else {
7093                                                                 tccp->prch[j] = int_floorlog2(parameters->prch_init[p]);
7094                                                         }
7095
7096                                                 } else {
7097                                                         int res_spec = parameters->res_spec;
7098                                                         int size_prcw = parameters->prcw_init[res_spec - 1] >> (p - (res_spec - 1));
7099                                                         int size_prch = parameters->prch_init[res_spec - 1] >> (p - (res_spec - 1));
7100                                                         
7101                                                         if (size_prcw < 1) {
7102                                                                 tccp->prcw[j] = 1;
7103                                                         } else {
7104                                                                 tccp->prcw[j] = int_floorlog2(size_prcw);
7105                                                         }
7106                                                         
7107                                                         if (size_prch < 1) {
7108                                                                 tccp->prch[j] = 1;
7109                                                         } else {
7110                                                                 tccp->prch[j] = int_floorlog2(size_prch);
7111                                                         }
7112                                                 }
7113                                                 p++;
7114                                                 /*printf("\nsize precinct for level %d : %d,%d\n", j,tccp->prcw[j], tccp->prch[j]); */
7115                                         }       /*end for*/
7116                                 } else {
7117                                         for (j = 0; j < tccp->numresolutions; j++) {
7118                                                 tccp->prcw[j] = 15;
7119                                                 tccp->prch[j] = 15;
7120                                         }
7121                                 }
7122                         }
7123
7124                         dwt_calc_explicit_stepsizes(tccp, image->comps[i].prec);
7125                 }
7126         }
7127 }
7128
7129 void j2k_setup_encoder_v2(      opj_j2k_v2_t *p_j2k,
7130                                                         opj_cparameters_t *parameters,
7131                                                         opj_image_t *image,
7132                                                         struct opj_event_mgr * p_manager)
7133 {
7134         OPJ_UINT32 i, j, tileno, numpocs_tile;
7135         opj_cp_v2_t *cp = 00;
7136         opj_bool l_res;
7137
7138         if(!p_j2k || !parameters || ! image) {
7139                 return;
7140         }
7141
7142         /* keep a link to cp so that we can destroy it later in j2k_destroy_compress */
7143         cp = &(p_j2k->m_cp);
7144
7145         /* set default values for cp */
7146         cp->tw = 1;
7147         cp->th = 1;
7148
7149         /*
7150         copy user encoding parameters
7151         */
7152         cp->m_specific_param.m_enc.m_cinema = parameters->cp_cinema;
7153         cp->m_specific_param.m_enc.m_max_comp_size =    parameters->max_comp_size;
7154         cp->rsiz   = parameters->cp_rsiz;
7155         cp->m_specific_param.m_enc.m_disto_alloc = parameters->cp_disto_alloc;
7156         cp->m_specific_param.m_enc.m_fixed_alloc = parameters->cp_fixed_alloc;
7157         cp->m_specific_param.m_enc.m_fixed_quality = parameters->cp_fixed_quality;
7158
7159         /* mod fixed_quality */
7160         if (parameters->cp_matrice) {
7161                 size_t array_size = parameters->tcp_numlayers * parameters->numresolution * 3 * sizeof(OPJ_INT32);
7162                 cp->m_specific_param.m_enc.m_matrice = (OPJ_INT32 *) opj_malloc(array_size);
7163                 memcpy(cp->m_specific_param.m_enc.m_matrice, parameters->cp_matrice, array_size);
7164         }
7165
7166         /* tiles */
7167         cp->tdx = parameters->cp_tdx;
7168         cp->tdy = parameters->cp_tdy;
7169
7170         /* tile offset */
7171         cp->tx0 = parameters->cp_tx0;
7172         cp->ty0 = parameters->cp_ty0;
7173
7174         /* comment string */
7175         if(parameters->cp_comment) {
7176                 cp->comment = (char*)opj_malloc(strlen(parameters->cp_comment) + 1);
7177                 if(cp->comment) {
7178                         strcpy(cp->comment, parameters->cp_comment);
7179                 }
7180         }
7181
7182         /*
7183         calculate other encoding parameters
7184         */
7185
7186         if (parameters->tile_size_on) {
7187                 cp->tw = int_ceildiv(image->x1 - cp->tx0, cp->tdx);
7188                 cp->th = int_ceildiv(image->y1 - cp->ty0, cp->tdy);
7189         } else {
7190                 cp->tdx = image->x1 - cp->tx0;
7191                 cp->tdy = image->y1 - cp->ty0;
7192         }
7193
7194         if (parameters->tp_on) {
7195                 cp->m_specific_param.m_enc.m_tp_flag = parameters->tp_flag;
7196                 cp->m_specific_param.m_enc.m_tp_on = 1;
7197         }
7198
7199 #ifdef USE_JPWL
7200         /*
7201         calculate JPWL encoding parameters
7202         */
7203
7204         if (parameters->jpwl_epc_on) {
7205                 OPJ_INT32 i;
7206
7207                 /* set JPWL on */
7208                 cp->epc_on = OPJ_TRUE;
7209                 cp->info_on = OPJ_FALSE; /* no informative technique */
7210
7211                 /* set EPB on */
7212                 if ((parameters->jpwl_hprot_MH > 0) || (parameters->jpwl_hprot_TPH[0] > 0)) {
7213                         cp->epb_on = OPJ_TRUE;
7214
7215                         cp->hprot_MH = parameters->jpwl_hprot_MH;
7216                         for (i = 0; i < JPWL_MAX_NO_TILESPECS; i++) {
7217                                 cp->hprot_TPH_tileno[i] = parameters->jpwl_hprot_TPH_tileno[i];
7218                                 cp->hprot_TPH[i] = parameters->jpwl_hprot_TPH[i];
7219                         }
7220                         /* if tile specs are not specified, copy MH specs */
7221                         if (cp->hprot_TPH[0] == -1) {
7222                                 cp->hprot_TPH_tileno[0] = 0;
7223                                 cp->hprot_TPH[0] = parameters->jpwl_hprot_MH;
7224                         }
7225                         for (i = 0; i < JPWL_MAX_NO_PACKSPECS; i++) {
7226                                 cp->pprot_tileno[i] = parameters->jpwl_pprot_tileno[i];
7227                                 cp->pprot_packno[i] = parameters->jpwl_pprot_packno[i];
7228                                 cp->pprot[i] = parameters->jpwl_pprot[i];
7229                         }
7230                 }
7231
7232                 /* set ESD writing */
7233                 if ((parameters->jpwl_sens_size == 1) || (parameters->jpwl_sens_size == 2)) {
7234                         cp->esd_on = OPJ_TRUE;
7235
7236                         cp->sens_size = parameters->jpwl_sens_size;
7237                         cp->sens_addr = parameters->jpwl_sens_addr;
7238                         cp->sens_range = parameters->jpwl_sens_range;
7239
7240                         cp->sens_MH = parameters->jpwl_sens_MH;
7241                         for (i = 0; i < JPWL_MAX_NO_TILESPECS; i++) {
7242                                 cp->sens_TPH_tileno[i] = parameters->jpwl_sens_TPH_tileno[i];
7243                                 cp->sens_TPH[i] = parameters->jpwl_sens_TPH[i];
7244                         }
7245                 }
7246
7247                 /* always set RED writing to false: we are at the encoder */
7248                 cp->red_on = OPJ_FALSE;
7249
7250         } else {
7251                 cp->epc_on = OPJ_FALSE;
7252         }
7253 #endif /* USE_JPWL */
7254
7255
7256         /* initialize the mutiple tiles */
7257         /* ---------------------------- */
7258         cp->tcps = (opj_tcp_v2_t*) opj_calloc(cp->tw * cp->th, sizeof(opj_tcp_v2_t));
7259         if (parameters->numpocs) {
7260                 /* initialisation of POC */
7261                 l_res = j2k_check_poc_val(parameters->POC,parameters->numpocs, parameters->numresolution, image->numcomps, parameters->tcp_numlayers, p_manager);
7262                 // TODO
7263         }
7264
7265         for (tileno = 0; tileno < cp->tw * cp->th; tileno++) {
7266                 opj_tcp_v2_t *tcp = &cp->tcps[tileno];
7267                 tcp->numlayers = parameters->tcp_numlayers;
7268
7269                 for (j = 0; j < tcp->numlayers; j++) {
7270                         if(cp->m_specific_param.m_enc.m_cinema){
7271                                 if (cp->m_specific_param.m_enc.m_fixed_quality) {
7272                                         tcp->distoratio[j] = parameters->tcp_distoratio[j];
7273                                 }
7274                                 tcp->rates[j] = parameters->tcp_rates[j];
7275                         }else{
7276                                 if (cp->m_specific_param.m_enc.m_fixed_quality) {       /* add fixed_quality */
7277                                         tcp->distoratio[j] = parameters->tcp_distoratio[j];
7278                                 } else {
7279                                         tcp->rates[j] = parameters->tcp_rates[j];
7280                                 }
7281                         }
7282                 }
7283
7284                 tcp->csty = parameters->csty;
7285                 tcp->prg = parameters->prog_order;
7286                 tcp->mct = parameters->tcp_mct;
7287
7288                 numpocs_tile = 0;
7289                 tcp->POC = 0;
7290
7291                 if (parameters->numpocs) {
7292                         /* initialisation of POC */
7293                         tcp->POC = 1;
7294                         // TODO
7295                         for (i = 0; i < (unsigned int) parameters->numpocs; i++) {
7296                                 if((tileno == parameters->POC[i].tile - 1) || (parameters->POC[i].tile == -1)) {
7297                                         opj_poc_t *tcp_poc = &tcp->pocs[numpocs_tile];
7298
7299                                         tcp_poc->resno0         = parameters->POC[numpocs_tile].resno0;
7300                                         tcp_poc->compno0        = parameters->POC[numpocs_tile].compno0;
7301                                         tcp_poc->layno1         = parameters->POC[numpocs_tile].layno1;
7302                                         tcp_poc->resno1         = parameters->POC[numpocs_tile].resno1;
7303                                         tcp_poc->compno1        = parameters->POC[numpocs_tile].compno1;
7304                                         tcp_poc->prg1           = parameters->POC[numpocs_tile].prg1;
7305                                         tcp_poc->tile           = parameters->POC[numpocs_tile].tile;
7306
7307                                         numpocs_tile++;
7308                                 }
7309                         }
7310
7311                         tcp->numpocs = numpocs_tile -1 ;
7312                 }else{
7313                         tcp->numpocs = 0;
7314                 }
7315
7316                 tcp->tccps = (opj_tccp_t*) opj_calloc(image->numcomps, sizeof(opj_tccp_t));
7317
7318                 if (parameters->mct_data) {
7319
7320                         opj_event_msg_v2(p_manager, EVT_ERROR, "MCT not supported for now\n");
7321                         return;
7322
7323                         /* TODO MSD : merge v2 add invert.c or used a external lib ?
7324                         OPJ_UINT32 lMctSize = image->numcomps * image->numcomps * sizeof(OPJ_FLOAT32);
7325                         OPJ_FLOAT32 * lTmpBuf = (OPJ_FLOAT32*)opj_malloc(lMctSize);
7326                         OPJ_INT32 * l_dc_shift = (OPJ_INT32 *) ((OPJ_BYTE *) parameters->mct_data + lMctSize);
7327
7328                         tcp->mct = 2;
7329                         tcp->m_mct_coding_matrix = (OPJ_FLOAT32*)opj_malloc(lMctSize);
7330                         memcpy(tcp->m_mct_coding_matrix,parameters->mct_data,lMctSize);
7331                         memcpy(lTmpBuf,parameters->mct_data,lMctSize);
7332
7333                         tcp->m_mct_decoding_matrix = (OPJ_FLOAT32*)opj_malloc(lMctSize);
7334                         assert(opj_matrix_inversion_f(lTmpBuf,(tcp->m_mct_decoding_matrix),image->numcomps));
7335
7336                         tcp->mct_norms = (OPJ_FLOAT64*)
7337                                         opj_malloc(image->numcomps * sizeof(OPJ_FLOAT64));
7338
7339                         opj_calculate_norms(tcp->mct_norms,image->numcomps,tcp->m_mct_decoding_matrix);
7340                         opj_free(lTmpBuf);
7341
7342                         for (i = 0; i < image->numcomps; i++) {
7343                                 opj_tccp_t *tccp = &tcp->tccps[i];
7344                                 tccp->m_dc_level_shift = l_dc_shift[i];
7345                         }
7346
7347                         j2k_setup_mct_encoding(tcp,image);
7348                         */
7349                 }
7350                 else {
7351                         for (i = 0; i < image->numcomps; i++) {
7352                                 opj_tccp_t *tccp = &tcp->tccps[i];
7353                                 opj_image_comp_t * l_comp = &(image->comps[i]);
7354
7355                                 if (! l_comp->sgnd) {
7356                                         tccp->m_dc_level_shift = 1 << (l_comp->prec - 1);
7357                                 }
7358                         }
7359                 }
7360
7361                 for (i = 0; i < image->numcomps; i++) {
7362                         opj_tccp_t *tccp = &tcp->tccps[i];
7363
7364                         tccp->csty = parameters->csty & 0x01;   /* 0 => one precinct || 1 => custom precinct  */
7365                         tccp->numresolutions = parameters->numresolution;
7366                         tccp->cblkw = int_floorlog2(parameters->cblockw_init);
7367                         tccp->cblkh = int_floorlog2(parameters->cblockh_init);
7368                         tccp->cblksty = parameters->mode;
7369                         tccp->qmfbid = parameters->irreversible ? 0 : 1;
7370                         tccp->qntsty = parameters->irreversible ? J2K_CCP_QNTSTY_SEQNT : J2K_CCP_QNTSTY_NOQNT;
7371                         tccp->numgbits = 2;
7372
7373                         if (i == parameters->roi_compno) {
7374                                 tccp->roishift = parameters->roi_shift;
7375                         } else {
7376                                 tccp->roishift = 0;
7377                         }
7378
7379                         if(parameters->cp_cinema) {
7380                                 //Precinct size for lowest frequency subband=128
7381                                 tccp->prcw[0] = 7;
7382                                 tccp->prch[0] = 7;
7383                                 //Precinct size at all other resolutions = 256
7384                                 for (j = 1; j < tccp->numresolutions; j++) {
7385                                         tccp->prcw[j] = 8;
7386                                         tccp->prch[j] = 8;
7387                                 }
7388                         }else{
7389                                 if (parameters->csty & J2K_CCP_CSTY_PRT) {
7390                                         OPJ_INT32 p = 0, it_res;
7391                                         for (it_res = tccp->numresolutions - 1; it_res >= 0; it_res--) {
7392                                                 if (p < parameters->res_spec) {
7393
7394                                                         if (parameters->prcw_init[p] < 1) {
7395                                                                 tccp->prcw[it_res] = 1;
7396                                                         } else {
7397                                                                 tccp->prcw[it_res] = int_floorlog2(parameters->prcw_init[p]);
7398                                                         }
7399
7400                                                         if (parameters->prch_init[p] < 1) {
7401                                                                 tccp->prch[it_res] = 1;
7402                                                         }else {
7403                                                                 tccp->prch[it_res] = int_floorlog2(parameters->prch_init[p]);
7404                                                         }
7405
7406                                                 } else {
7407                                                         int res_spec = parameters->res_spec;
7408                                                         int size_prcw = parameters->prcw_init[res_spec - 1] >> (p - (res_spec - 1));
7409                                                         int size_prch = parameters->prch_init[res_spec - 1] >> (p - (res_spec - 1));
7410
7411                                                         if (size_prcw < 1) {
7412                                                                 tccp->prcw[it_res] = 1;
7413                                                         } else {
7414                                                                 tccp->prcw[it_res] = int_floorlog2(size_prcw);
7415                                                         }
7416
7417                                                         if (size_prch < 1) {
7418                                                                 tccp->prch[it_res] = 1;
7419                                                         } else {
7420                                                                 tccp->prch[it_res] = int_floorlog2(size_prch);
7421                                                         }
7422                                                 }
7423                                                 p++;
7424                                                 /*printf("\nsize precinct for level %d : %d,%d\n", it_res,tccp->prcw[it_res], tccp->prch[it_res]); */
7425                                         }       //end for
7426                                 } else {
7427                                         for (j = 0; j < tccp->numresolutions; j++) {
7428                                                 tccp->prcw[j] = 15;
7429                                                 tccp->prch[j] = 15;
7430                                         }
7431                                 }
7432                         }
7433
7434                         dwt_calc_explicit_stepsizes(tccp, image->comps[i].prec);
7435                 }
7436         }
7437
7438         if (parameters->mct_data) {
7439                 opj_free(parameters->mct_data);
7440                 parameters->mct_data = 00;
7441         }
7442 }
7443
7444
7445 opj_bool j2k_encode(opj_j2k_t *j2k, opj_cio_t *cio, opj_image_t *image, opj_codestream_info_t *cstr_info) {
7446         int tileno;
7447   OPJ_UINT32 compno;
7448         opj_cp_t *cp = NULL;
7449
7450         opj_tcd_t *tcd = NULL;  /* TCD component */
7451
7452         j2k->cio = cio; 
7453         j2k->image = image;
7454
7455         cp = j2k->cp;
7456
7457         /* INDEX >> */
7458         j2k->cstr_info = cstr_info;
7459         if (cstr_info) {
7460                 OPJ_UINT32 compno;
7461                 cstr_info->tile = (opj_tile_info_t *) opj_malloc(cp->tw * cp->th * sizeof(opj_tile_info_t));
7462                 cstr_info->image_w = image->x1 - image->x0;
7463                 cstr_info->image_h = image->y1 - image->y0;
7464                 cstr_info->prog = (&cp->tcps[0])->prg;
7465                 cstr_info->tw = cp->tw;
7466                 cstr_info->th = cp->th;
7467                 cstr_info->tile_x = cp->tdx;    /* new version parser */
7468                 cstr_info->tile_y = cp->tdy;    /* new version parser */
7469                 cstr_info->tile_Ox = cp->tx0;   /* new version parser */
7470                 cstr_info->tile_Oy = cp->ty0;   /* new version parser */
7471                 cstr_info->numcomps = image->numcomps;
7472                 cstr_info->numlayers = (&cp->tcps[0])->numlayers;
7473                 cstr_info->numdecompos = (int*) opj_malloc(image->numcomps * sizeof(int));
7474                 for (compno=0; compno < image->numcomps; compno++) {
7475                         cstr_info->numdecompos[compno] = (&cp->tcps[0])->tccps->numresolutions - 1;
7476                 }
7477                 cstr_info->D_max = 0.0;         /* ADD Marcela */
7478                 cstr_info->main_head_start = cio_tell(cio); /* position of SOC */
7479                 cstr_info->maxmarknum = 100;
7480                 cstr_info->marker = (opj_marker_info_t *) opj_malloc(cstr_info->maxmarknum * sizeof(opj_marker_info_t));
7481                 cstr_info->marknum = 0;
7482         }
7483         /* << INDEX */
7484
7485         j2k_write_soc(j2k);
7486         j2k_write_siz(j2k);
7487         j2k_write_cod(j2k);
7488         j2k_write_qcd(j2k);
7489
7490         if(cp->cinema){
7491                 for (compno = 1; compno < image->numcomps; compno++) {
7492                         j2k_write_coc(j2k, compno);
7493                         j2k_write_qcc(j2k, compno);
7494                 }
7495         }
7496
7497         for (compno = 0; compno < image->numcomps; compno++) {
7498                 opj_tcp_t *tcp = &cp->tcps[0];
7499                 if (tcp->tccps[compno].roishift)
7500                         j2k_write_rgn(j2k, compno, 0);
7501         }
7502         if (cp->comment != NULL) {
7503                 j2k_write_com(j2k);
7504         }
7505
7506         j2k->totnum_tp = j2k_calculate_tp(cp,image->numcomps,image,j2k);
7507         /* TLM Marker*/
7508         if(cp->cinema){
7509                 j2k_write_tlm(j2k);
7510                 if (cp->cinema == CINEMA4K_24) {
7511                         j2k_write_poc(j2k);
7512                 }
7513         }
7514
7515         /* uncomment only for testing JPSEC marker writing */
7516         /* j2k_write_sec(j2k); */
7517
7518         /* INDEX >> */
7519         if(cstr_info) {
7520                 cstr_info->main_head_end = cio_tell(cio) - 1;
7521         }
7522         /* << INDEX */
7523         /**** Main Header ENDS here ***/
7524
7525         /* create the tile encoder */
7526         tcd = tcd_create(j2k->cinfo);
7527
7528         /* encode each tile */
7529         for (tileno = 0; tileno < cp->tw * cp->th; tileno++) {
7530                 int pino;
7531                 int tilepartno=0;
7532                 /* UniPG>> */
7533                 int acc_pack_num = 0;
7534                 /* <<UniPG */
7535
7536
7537                 opj_tcp_t *tcp = &cp->tcps[tileno];
7538                 opj_event_msg(j2k->cinfo, EVT_INFO, "tile number %d / %d\n", tileno + 1, cp->tw * cp->th);
7539
7540                 j2k->curtileno = tileno;
7541                 j2k->cur_tp_num = 0;
7542                 tcd->cur_totnum_tp = j2k->cur_totnum_tp[j2k->curtileno];
7543                 /* initialisation before tile encoding  */
7544                 if (tileno == 0) {
7545                         tcd_malloc_encode(tcd, image, cp, j2k->curtileno);
7546                 } else {
7547                         tcd_init_encode(tcd, image, cp, j2k->curtileno);
7548                 }
7549
7550                 /* INDEX >> */
7551                 if(cstr_info) {
7552                         cstr_info->tile[j2k->curtileno].start_pos = cio_tell(cio) + j2k->pos_correction;
7553                         cstr_info->tile[j2k->curtileno].maxmarknum = 10;
7554                         cstr_info->tile[j2k->curtileno].marker = (opj_marker_info_t *) opj_malloc(cstr_info->tile[j2k->curtileno].maxmarknum * sizeof(opj_marker_info_t));
7555                         cstr_info->tile[j2k->curtileno].marknum = 0;
7556                 }
7557                 /* << INDEX */
7558
7559                 for(pino = 0; pino <= tcp->numpocs; pino++) {
7560                         int tot_num_tp;
7561                         tcd->cur_pino=pino;
7562
7563                         /*Get number of tile parts*/
7564                         tot_num_tp = j2k_get_num_tp(cp,pino,tileno);
7565                         tcd->tp_pos = cp->tp_pos;
7566
7567                         for(tilepartno = 0; tilepartno < tot_num_tp ; tilepartno++){
7568                                 j2k->tp_num = tilepartno;
7569                                 /* INDEX >> */
7570                                 if(cstr_info)
7571                                         cstr_info->tile[j2k->curtileno].tp[j2k->cur_tp_num].tp_start_pos =
7572                                         cio_tell(cio) + j2k->pos_correction;
7573                                 /* << INDEX */
7574                                 j2k_write_sot(j2k);
7575
7576                                 if(j2k->cur_tp_num == 0 && cp->cinema == 0){
7577                                         for (compno = 1; compno < image->numcomps; compno++) {
7578                                                 j2k_write_coc(j2k, compno);
7579                                                 j2k_write_qcc(j2k, compno);
7580                                         }
7581                                         if (cp->tcps[tileno].numpocs) {
7582                                                 j2k_write_poc(j2k);
7583                                         }
7584                                 }
7585
7586                                 /* INDEX >> */
7587                                 if(cstr_info)
7588                                         cstr_info->tile[j2k->curtileno].tp[j2k->cur_tp_num].tp_end_header =
7589                                         cio_tell(cio) + j2k->pos_correction + 1;
7590                                 /* << INDEX */
7591
7592                                 j2k_write_sod(j2k, tcd);
7593
7594                                 /* INDEX >> */
7595                                 if(cstr_info) {
7596                                         cstr_info->tile[j2k->curtileno].tp[j2k->cur_tp_num].tp_end_pos =
7597                                                 cio_tell(cio) + j2k->pos_correction - 1;
7598                                         cstr_info->tile[j2k->curtileno].tp[j2k->cur_tp_num].tp_start_pack =
7599                                                 acc_pack_num;
7600                                         cstr_info->tile[j2k->curtileno].tp[j2k->cur_tp_num].tp_numpacks =
7601                                                 cstr_info->packno - acc_pack_num;
7602                                         acc_pack_num = cstr_info->packno;
7603                                 }
7604                                 /* << INDEX */
7605
7606                                 j2k->cur_tp_num++;
7607                         }                       
7608                 }
7609                 if(cstr_info) {
7610                         cstr_info->tile[j2k->curtileno].end_pos = cio_tell(cio) + j2k->pos_correction - 1;
7611                 }
7612
7613
7614                 /*
7615                 if (tile->PPT) { // BAD PPT !!! 
7616                 FILE *PPT_file;
7617                 int i;
7618                 PPT_file=fopen("PPT","rb");
7619                 fprintf(stderr,"%c%c%c%c",255,97,tile->len_ppt/256,tile->len_ppt%256);
7620                 for (i=0;i<tile->len_ppt;i++) {
7621                 unsigned char elmt;
7622                 fread(&elmt, 1, 1, PPT_file);
7623                 fwrite(&elmt,1,1,f);
7624                 }
7625                 fclose(PPT_file);
7626                 unlink("PPT");
7627                 }
7628                 */
7629
7630         }
7631
7632         /* destroy the tile encoder */
7633         tcd_free_encode(tcd);
7634         tcd_destroy(tcd);
7635
7636         opj_free(j2k->cur_totnum_tp);
7637
7638         j2k_write_eoc(j2k);
7639
7640         if(cstr_info) {
7641                 cstr_info->codestream_size = cio_tell(cio) + j2k->pos_correction;
7642                 /* UniPG>> */
7643                 /* The following adjustment is done to adjust the codestream size */
7644                 /* if SOD is not at 0 in the buffer. Useful in case of JP2, where */
7645                 /* the first bunch of bytes is not in the codestream              */
7646                 cstr_info->codestream_size -= cstr_info->main_head_start;
7647                 /* <<UniPG */
7648         }
7649
7650 #ifdef USE_JPWL
7651         /*
7652         preparation of JPWL marker segments
7653         */
7654         if(cp->epc_on) {
7655
7656                 /* encode according to JPWL */
7657                 jpwl_encode(j2k, cio, image);
7658
7659         }
7660 #endif /* USE_JPWL */
7661
7662         return OPJ_TRUE;
7663 }
7664
7665 static void j2k_add_mhmarker(opj_codestream_info_t *cstr_info, unsigned short int type, int pos, int len)
7666 {
7667         assert(cstr_info != 00);
7668
7669         /* expand the list? */
7670         if ((cstr_info->marknum + 1) > cstr_info->maxmarknum) {
7671                 cstr_info->maxmarknum = 100 + (int) ((float) cstr_info->maxmarknum * 1.0F);
7672                 cstr_info->marker = (opj_marker_info_t*)opj_realloc(cstr_info->marker, cstr_info->maxmarknum);
7673         }
7674
7675         /* add the marker */
7676         cstr_info->marker[cstr_info->marknum].type = type;
7677         cstr_info->marker[cstr_info->marknum].pos = pos;
7678         cstr_info->marker[cstr_info->marknum].len = len;
7679         cstr_info->marknum++;
7680
7681 }
7682
7683 static void j2k_add_mhmarker_v2(opj_codestream_index_t *cstr_index, OPJ_UINT32 type, OPJ_OFF_T pos, OPJ_UINT32 len)
7684 {
7685         assert(cstr_index != 00);
7686
7687         /* expand the list? */
7688         if ((cstr_index->marknum + 1) > cstr_index->maxmarknum) {
7689                 cstr_index->maxmarknum = 100 + (int) ((float) cstr_index->maxmarknum * 1.0F);
7690                 cstr_index->marker = (opj_marker_info_t*)opj_realloc(cstr_index->marker, cstr_index->maxmarknum *sizeof(opj_marker_info_t));
7691         }
7692
7693         /* add the marker */
7694         cstr_index->marker[cstr_index->marknum].type = (OPJ_UINT16)type;
7695         cstr_index->marker[cstr_index->marknum].pos = (OPJ_INT32)pos;
7696         cstr_index->marker[cstr_index->marknum].len = (OPJ_INT32)len;
7697         cstr_index->marknum++;
7698
7699 }
7700
7701 static void j2k_add_tlmarker( int tileno, opj_codestream_info_t *cstr_info, unsigned short int type, int pos, int len)
7702 {
7703         opj_marker_info_t *marker;
7704
7705         assert(cstr_info != 00);
7706
7707         /* expand the list? */
7708         if ((cstr_info->tile[tileno].marknum + 1) > cstr_info->tile[tileno].maxmarknum) {
7709                 cstr_info->tile[tileno].maxmarknum = 100 + (int) ((float) cstr_info->tile[tileno].maxmarknum * 1.0F);
7710                 cstr_info->tile[tileno].marker = (opj_marker_info_t*)opj_realloc(cstr_info->tile[tileno].marker, cstr_info->maxmarknum);
7711         }
7712
7713         marker = &(cstr_info->tile[tileno].marker[cstr_info->tile[tileno].marknum]);
7714
7715         /* add the marker */
7716         marker->type = type;
7717         marker->pos = pos;
7718         marker->len = len;
7719         cstr_info->tile[tileno].marknum++;
7720 }
7721
7722 static void j2k_add_tlmarker_v2(OPJ_UINT32 tileno, opj_codestream_index_t *cstr_index, OPJ_UINT32 type, OPJ_OFF_T pos, OPJ_UINT32 len)
7723 {
7724         assert(cstr_index != 00);
7725         assert(cstr_index->tile_index != 00);
7726
7727         /* expand the list? */
7728         if ((cstr_index->tile_index[tileno].marknum + 1) > cstr_index->tile_index[tileno].maxmarknum) {
7729                 cstr_index->tile_index[tileno].maxmarknum = 100 + (int) ((float) cstr_index->tile_index[tileno].maxmarknum * 1.0F);
7730                 cstr_index->tile_index[tileno].marker =
7731                                 (opj_marker_info_t*)opj_realloc(cstr_index->tile_index[tileno].marker,
7732                                                                                                 cstr_index->tile_index[tileno].maxmarknum *sizeof(opj_marker_info_t));
7733         }
7734
7735         /* add the marker */
7736         cstr_index->tile_index[tileno].marker[cstr_index->tile_index[tileno].marknum].type = (OPJ_UINT16)type;
7737         cstr_index->tile_index[tileno].marker[cstr_index->tile_index[tileno].marknum].pos = (OPJ_INT32)pos;
7738         cstr_index->tile_index[tileno].marker[cstr_index->tile_index[tileno].marknum].len = (OPJ_INT32)len;
7739         cstr_index->tile_index[tileno].marknum++;
7740
7741         if (type == J2K_MS_SOT) {
7742                 OPJ_UINT32 l_current_tile_part = cstr_index->tile_index[tileno].current_tpsno;
7743
7744                 if (cstr_index->tile_index[tileno].tp_index)
7745                         cstr_index->tile_index[tileno].tp_index[l_current_tile_part].start_pos = pos;
7746
7747         }
7748 }
7749
7750
7751 /*
7752  * -----------------------------------------------------------------------
7753  * -----------------------------------------------------------------------
7754  * -----------------------------------------------------------------------
7755  */
7756
7757 /**
7758  * Ends the decompression procedures and possibiliy add data to be read after the
7759  * codestream.
7760  */
7761 opj_bool j2k_end_decompress(
7762                                                 opj_j2k_v2_t *p_j2k,
7763                                                 opj_stream_private_t *p_stream,
7764                                                 opj_event_mgr_t * p_manager)
7765 {
7766   (void)p_j2k;
7767   (void)p_stream;
7768   (void)p_manager;
7769         return OPJ_TRUE;
7770 }
7771
7772 /**
7773  * Reads a jpeg2000 codestream header structure.
7774
7775  *
7776  * @param p_stream the stream to read data from.
7777  * @param p_j2k the jpeg2000 codec.
7778  * @param p_manager the user event manager.
7779  *
7780  * @return true if the box is valid.
7781  */
7782 opj_bool j2k_read_header(       struct opj_stream_private *p_stream,
7783                                                         opj_j2k_v2_t* p_j2k,
7784                                                         opj_image_t** p_image,
7785                                                         struct opj_event_mgr* p_manager )
7786 {
7787         /* preconditions */
7788         assert(p_j2k != 00);
7789         assert(p_stream != 00);
7790         assert(p_manager != 00);
7791
7792         /* create an empty image header */
7793         p_j2k->m_private_image = opj_image_create0();
7794         if (! p_j2k->m_private_image) {
7795                 return OPJ_FALSE;
7796         }
7797
7798         /* customization of the validation */
7799         j2k_setup_decoding_validation(p_j2k);
7800
7801         /* validation of the parameters codec */
7802         if (! j2k_exec(p_j2k, p_j2k->m_validation_list, p_stream,p_manager)) {
7803                 opj_image_destroy(p_j2k->m_private_image);
7804                 p_j2k->m_private_image = NULL;
7805                 return OPJ_FALSE;
7806         }
7807
7808         /* customization of the encoding */
7809         j2k_setup_header_reading(p_j2k);
7810
7811         /* read header */
7812         if (! j2k_exec (p_j2k,p_j2k->m_procedure_list,p_stream,p_manager)) {
7813                 opj_image_destroy(p_j2k->m_private_image);
7814                 p_j2k->m_private_image = NULL;
7815                 return OPJ_FALSE;
7816         }
7817
7818         *p_image = opj_image_create0();
7819         if (! (*p_image)) {
7820                 return OPJ_FALSE;
7821         }
7822
7823         /* Copy codestream image information to the output image */
7824         opj_copy_image_header(p_j2k->m_private_image, *p_image);
7825
7826     /*Allocate and initialize some elements of codestrem index*/
7827         if (!j2k_allocate_tile_element_cstr_index(p_j2k)){
7828                 return OPJ_FALSE;
7829         }
7830
7831         return OPJ_TRUE;
7832 }
7833
7834 /**
7835  * Sets up the procedures to do on reading header. Developpers wanting to extend the library can add their own reading procedures.
7836  */
7837 void j2k_setup_header_reading (opj_j2k_v2_t *p_j2k)
7838 {
7839         /* preconditions*/
7840         assert(p_j2k != 00);
7841
7842         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_read_header_procedure);
7843
7844         /* DEVELOPER CORNER, add your custom procedures */
7845         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_copy_default_tcp_and_create_tcd);
7846
7847 }
7848
7849 /**
7850  * Sets up the validation ,i.e. adds the procedures to lauch to make sure the codec parameters
7851  * are valid. Developpers wanting to extend the library can add their own validation procedures.
7852  */
7853 void j2k_setup_decoding_validation (opj_j2k_v2_t *p_j2k)
7854 {
7855         /* preconditions*/
7856         assert(p_j2k != 00);
7857
7858         opj_procedure_list_add_procedure(p_j2k->m_validation_list, (opj_procedure)j2k_build_decoder);
7859         opj_procedure_list_add_procedure(p_j2k->m_validation_list, (opj_procedure)j2k_decoding_validation);
7860         /* DEVELOPER CORNER, add your custom validation procedure */
7861
7862 }
7863
7864
7865 /**
7866  * The mct encoding validation procedure.
7867  *
7868  * @param       p_j2k                   the jpeg2000 codec to validate.
7869  * @param       p_stream                                the input stream to validate.
7870  * @param       p_manager               the user event manager.
7871  *
7872  * @return true if the parameters are correct.
7873  */
7874 opj_bool j2k_mct_validation (   opj_j2k_v2_t * p_j2k,
7875                                                                 opj_stream_private_t *p_stream,
7876                                                                 opj_event_mgr_t * p_manager )
7877 {
7878         opj_bool l_is_valid = OPJ_TRUE;
7879         OPJ_UINT32 i,j;
7880
7881         /* preconditions */
7882         assert(p_j2k != 00);
7883         assert(p_stream != 00);
7884         assert(p_manager != 00);
7885
7886         if ((p_j2k->m_cp.rsiz & 0x8200) == 0x8200) {
7887                 OPJ_UINT32 l_nb_tiles = p_j2k->m_cp.th * p_j2k->m_cp.tw;
7888                 opj_tcp_v2_t * l_tcp = p_j2k->m_cp.tcps;
7889
7890                 for (i=0;i<l_nb_tiles;++i) {
7891                         if (l_tcp->mct == 2) {
7892                                 opj_tccp_t * l_tccp = l_tcp->tccps;
7893                                 l_is_valid &= (l_tcp->m_mct_coding_matrix != 00);
7894
7895                                 for (j=0;j<p_j2k->m_private_image->numcomps;++j) {
7896                                         l_is_valid &= ! (l_tccp->qmfbid & 1);
7897                                         ++l_tccp;
7898                                 }
7899                         }
7900                         ++l_tcp;
7901                 }
7902         }
7903
7904         return l_is_valid;
7905 }
7906
7907 opj_bool j2k_setup_mct_encoding(opj_tcp_v2_t * p_tcp, opj_image_t * p_image)
7908 {
7909         OPJ_UINT32 i;
7910         OPJ_UINT32 l_indix = 1;
7911         opj_mct_data_t * l_mct_deco_data = 00,* l_mct_offset_data = 00;
7912         opj_simple_mcc_decorrelation_data_t * l_mcc_data;
7913         OPJ_UINT32 l_mct_size,l_nb_elem;
7914         OPJ_FLOAT32 * l_data, * l_current_data;
7915         opj_tccp_t * l_tccp;
7916
7917         // preconditions
7918         assert(p_tcp != 00);
7919
7920         if (p_tcp->mct != 2) {
7921                 return OPJ_TRUE;
7922         }
7923
7924         if (p_tcp->m_mct_decoding_matrix) {
7925                 if (p_tcp->m_nb_mct_records == p_tcp->m_nb_max_mct_records) {
7926                         p_tcp->m_nb_max_mct_records += J2K_MCT_DEFAULT_NB_RECORDS;
7927
7928                         p_tcp->m_mct_records = (opj_mct_data_t*)opj_realloc(p_tcp->m_mct_records,p_tcp->m_nb_max_mct_records * sizeof(opj_mct_data_t));
7929                         if (! p_tcp->m_mct_records) {
7930                                 return OPJ_FALSE;
7931                         }
7932                         l_mct_deco_data = p_tcp->m_mct_records + p_tcp->m_nb_mct_records;
7933
7934                         memset(l_mct_deco_data ,0,(p_tcp->m_nb_max_mct_records - p_tcp->m_nb_mct_records) * sizeof(opj_mct_data_t));
7935                 }
7936                 l_mct_deco_data = p_tcp->m_mct_records + p_tcp->m_nb_mct_records;
7937
7938                 if (l_mct_deco_data->m_data) {
7939                         opj_free(l_mct_deco_data->m_data);
7940                         l_mct_deco_data->m_data = 00;
7941                 }
7942
7943                 l_mct_deco_data->m_index = l_indix++;
7944                 l_mct_deco_data->m_array_type = MCT_TYPE_DECORRELATION;
7945                 l_mct_deco_data->m_element_type = MCT_TYPE_FLOAT;
7946                 l_nb_elem = p_image->numcomps * p_image->numcomps;
7947                 l_mct_size = l_nb_elem * MCT_ELEMENT_SIZE[l_mct_deco_data->m_element_type];
7948                 l_mct_deco_data->m_data = (OPJ_BYTE*)opj_malloc(l_mct_size );
7949
7950                 if (! l_mct_deco_data->m_data) {
7951                         return OPJ_FALSE;
7952                 }
7953
7954                 j2k_mct_write_functions_from_float[l_mct_deco_data->m_element_type](p_tcp->m_mct_decoding_matrix,l_mct_deco_data->m_data,l_nb_elem);
7955
7956                 l_mct_deco_data->m_data_size = l_mct_size;
7957                 ++p_tcp->m_nb_mct_records;
7958         }
7959
7960         if (p_tcp->m_nb_mct_records == p_tcp->m_nb_max_mct_records) {
7961                 p_tcp->m_nb_max_mct_records += J2K_MCT_DEFAULT_NB_RECORDS;
7962                 p_tcp->m_mct_records = (opj_mct_data_t*)opj_realloc(p_tcp->m_mct_records,p_tcp->m_nb_max_mct_records * sizeof(opj_mct_data_t));
7963
7964                 if (! p_tcp->m_mct_records) {
7965                         return OPJ_FALSE;
7966                 }
7967
7968                 l_mct_offset_data = p_tcp->m_mct_records + p_tcp->m_nb_mct_records;
7969                 memset(l_mct_offset_data ,0,(p_tcp->m_nb_max_mct_records - p_tcp->m_nb_mct_records) * sizeof(opj_mct_data_t));
7970
7971                 if (l_mct_deco_data) {
7972                         l_mct_deco_data = l_mct_offset_data - 1;
7973                 }
7974         }
7975
7976         l_mct_offset_data = p_tcp->m_mct_records + p_tcp->m_nb_mct_records;
7977
7978         if (l_mct_offset_data->m_data) {
7979                 opj_free(l_mct_offset_data->m_data);
7980                 l_mct_offset_data->m_data = 00;
7981         }
7982
7983         l_mct_offset_data->m_index = l_indix++;
7984         l_mct_offset_data->m_array_type = MCT_TYPE_OFFSET;
7985         l_mct_offset_data->m_element_type = MCT_TYPE_FLOAT;
7986         l_nb_elem = p_image->numcomps;
7987         l_mct_size = l_nb_elem * MCT_ELEMENT_SIZE[l_mct_offset_data->m_element_type];
7988         l_mct_offset_data->m_data = (OPJ_BYTE*)opj_malloc(l_mct_size );
7989
7990         if (! l_mct_offset_data->m_data) {
7991                 return OPJ_FALSE;
7992         }
7993
7994         l_data = (OPJ_FLOAT32*)opj_malloc(l_nb_elem * sizeof(OPJ_FLOAT32));
7995         if (! l_data) {
7996                 opj_free(l_mct_offset_data->m_data);
7997                 l_mct_offset_data->m_data = 00;
7998                 return OPJ_FALSE;
7999         }
8000
8001         l_tccp = p_tcp->tccps;
8002         l_current_data = l_data;
8003
8004         for (i=0;i<l_nb_elem;++i) {
8005                 *(l_current_data++) = (OPJ_FLOAT32) (l_tccp->m_dc_level_shift);
8006                 ++l_tccp;
8007         }
8008
8009         j2k_mct_write_functions_from_float[l_mct_offset_data->m_element_type](l_data,l_mct_offset_data->m_data,l_nb_elem);
8010
8011         opj_free(l_data);
8012
8013         l_mct_offset_data->m_data_size = l_mct_size;
8014
8015         ++p_tcp->m_nb_mct_records;
8016
8017         if (p_tcp->m_nb_mcc_records == p_tcp->m_nb_max_mcc_records) {
8018                 p_tcp->m_nb_max_mcc_records += J2K_MCT_DEFAULT_NB_RECORDS;
8019                 p_tcp->m_mcc_records = (opj_simple_mcc_decorrelation_data_t*)
8020                 opj_realloc(p_tcp->m_mcc_records,p_tcp->m_nb_max_mcc_records * sizeof(opj_simple_mcc_decorrelation_data_t));
8021
8022                 if (! p_tcp->m_mcc_records) {
8023                         return OPJ_FALSE;
8024                 }
8025                 l_mcc_data = p_tcp->m_mcc_records + p_tcp->m_nb_mcc_records;
8026                 memset(l_mcc_data ,0,(p_tcp->m_nb_max_mcc_records - p_tcp->m_nb_mcc_records) * sizeof(opj_simple_mcc_decorrelation_data_t));
8027
8028         }
8029
8030         l_mcc_data = p_tcp->m_mcc_records + p_tcp->m_nb_mcc_records;
8031         l_mcc_data->m_decorrelation_array = l_mct_deco_data;
8032         l_mcc_data->m_is_irreversible = 1;
8033         l_mcc_data->m_nb_comps = p_image->numcomps;
8034         l_mcc_data->m_index = l_indix++;
8035         l_mcc_data->m_offset_array = l_mct_offset_data;
8036         ++p_tcp->m_nb_mcc_records;
8037
8038         return OPJ_TRUE;
8039 }
8040
8041 /**
8042  * Builds the cp decoder parameters to use to decode tile.
8043  */
8044 opj_bool j2k_build_decoder (opj_j2k_v2_t * p_j2k,
8045                                                         opj_stream_private_t *p_stream,
8046                                                         opj_event_mgr_t * p_manager )
8047 {
8048         /* add here initialization of cp
8049            copy paste of setup_decoder */
8050   (void)p_j2k;
8051   (void)p_stream;
8052   (void)p_manager;
8053         return OPJ_TRUE;
8054 }
8055
8056 /**
8057  * Builds the cp encoder parameters to use to encode tile.
8058  */
8059 opj_bool j2k_build_encoder (opj_j2k_v2_t * p_j2k,
8060                                                         opj_stream_private_t *p_stream,
8061                                                         opj_event_mgr_t * p_manager )
8062 {
8063         /* add here initialization of cp
8064            copy paste of setup_encoder */
8065   (void)p_j2k;
8066   (void)p_stream;
8067   (void)p_manager;
8068         return OPJ_TRUE;
8069 }
8070
8071 /**
8072  * The default encoding validation procedure without any extension.
8073  *
8074  * @param       p_j2k                   the jpeg2000 codec to validate.
8075  * @param       p_stream                                the input stream to validate.
8076  * @param       p_manager               the user event manager.
8077  *
8078  * @return true if the parameters are correct.
8079  */
8080 opj_bool j2k_encoding_validation (      opj_j2k_v2_t * p_j2k,
8081                                                                         opj_stream_private_t *p_stream,
8082                                                                         opj_event_mgr_t * p_manager )
8083 {
8084         opj_bool l_is_valid = OPJ_TRUE;
8085
8086         /* preconditions */
8087         assert(p_j2k != 00);
8088         assert(p_stream != 00);
8089         assert(p_manager != 00);
8090
8091         /* STATE checking */
8092         /* make sure the state is at 0 */
8093         l_is_valid &= (p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_NONE);
8094
8095         /* POINTER validation */
8096         /* make sure a p_j2k codec is present */
8097         l_is_valid &= (p_j2k->m_procedure_list != 00);
8098         /* make sure a validation list is present */
8099         l_is_valid &= (p_j2k->m_validation_list != 00);
8100
8101         if ((p_j2k->m_cp.tdx) < (OPJ_UINT32) (1 << p_j2k->m_cp.tcps->tccps->numresolutions)) {
8102                 opj_event_msg_v2(p_manager, EVT_ERROR, "Number of resolutions is too high in comparison to the size of tiles\n");
8103                 return OPJ_FALSE;
8104         }
8105
8106         if ((p_j2k->m_cp.tdy) < (OPJ_UINT32) (1 << p_j2k->m_cp.tcps->tccps->numresolutions)) {
8107                 opj_event_msg_v2(p_manager, EVT_ERROR, "Number of resolutions is too high in comparison to the size of tiles\n");
8108                 return OPJ_FALSE;
8109         }
8110
8111         /* PARAMETER VALIDATION */
8112         return l_is_valid;
8113 }
8114
8115 /**
8116  * The default decoding validation procedure without any extension.
8117  *
8118  * @param       p_j2k                   the jpeg2000 codec to validate.
8119  * @param       p_stream                                the input stream to validate.
8120  * @param       p_manager               the user event manager.
8121  *
8122  * @return true if the parameters are correct.
8123  */
8124 opj_bool j2k_decoding_validation (
8125                                                                 opj_j2k_v2_t *p_j2k,
8126                                                                 opj_stream_private_t *p_stream,
8127                                                                 opj_event_mgr_t * p_manager
8128                                                           )
8129 {
8130         opj_bool l_is_valid = OPJ_TRUE;
8131
8132         /* preconditions*/
8133         assert(p_j2k != 00);
8134         assert(p_stream != 00);
8135         assert(p_manager != 00);
8136
8137
8138         /* STATE checking */
8139         /* make sure the state is at 0 */
8140 #ifdef TODO_MSD
8141         l_is_valid &= (p_j2k->m_specific_param.m_decoder.m_state == J2K_DEC_STATE_NONE);
8142 #endif
8143         l_is_valid &= (p_j2k->m_specific_param.m_decoder.m_state == 0x0000);
8144
8145         /* POINTER validation */
8146         /* make sure a p_j2k codec is present */
8147         /* make sure a procedure list is present */
8148         l_is_valid &= (p_j2k->m_procedure_list != 00);
8149         /* make sure a validation list is present */
8150         l_is_valid &= (p_j2k->m_validation_list != 00);
8151
8152         /* PARAMETER VALIDATION */
8153         return l_is_valid;
8154 }
8155
8156 opj_bool j2k_read_header_procedure(     opj_j2k_v2_t *p_j2k,
8157                                                                         struct opj_stream_private *p_stream,
8158                                                                         struct opj_event_mgr * p_manager)
8159 {
8160         OPJ_UINT32 l_current_marker;
8161         OPJ_UINT32 l_marker_size;
8162         const opj_dec_memory_marker_handler_t * l_marker_handler = 00;
8163
8164         /* preconditions */
8165         assert(p_stream != 00);
8166         assert(p_j2k != 00);
8167         assert(p_manager != 00);
8168
8169         /*  We enter in the main header */
8170         p_j2k->m_specific_param.m_decoder.m_state = J2K_STATE_MHSOC;
8171
8172         /* Try to read the SOC marker, the codestream must begin with SOC marker */
8173         if (! opj_j2k_read_soc(p_j2k,p_stream,p_manager)) {
8174                 opj_event_msg_v2(p_manager, EVT_ERROR, "Expected a SOC marker \n");
8175                 return OPJ_FALSE;
8176         }
8177
8178         /* Try to read 2 bytes (the next marker ID) from stream and copy them into the buffer */
8179         if (opj_stream_read_data(p_stream,p_j2k->m_specific_param.m_decoder.m_header_data,2,p_manager) != 2) {
8180                 opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8181                 return OPJ_FALSE;
8182         }
8183
8184         /* Read 2 bytes as the new marker ID */
8185         opj_read_bytes(p_j2k->m_specific_param.m_decoder.m_header_data,&l_current_marker,2);
8186
8187         /* Try to read until the SOT is detected */
8188         while (l_current_marker != J2K_MS_SOT) {
8189
8190                 /* Check if the current marker ID is valid */
8191                 if (l_current_marker < 0xff00) {
8192                         opj_event_msg_v2(p_manager, EVT_ERROR, "We expected read a marker ID (0xff--) instead of %.8x\n", l_current_marker);
8193                         return OPJ_FALSE;
8194                 }
8195
8196                 /* Get the marker handler from the marker ID */
8197                 l_marker_handler = j2k_get_marker_handler(l_current_marker);
8198
8199                 /* Manage case where marker is unknown */
8200                 if (l_marker_handler->id == J2K_MS_UNK) {
8201                         if (! j2k_read_unk_v2(p_j2k, p_stream, &l_current_marker, p_manager)){
8202                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Unknow marker have been detected and generated error.\n");
8203                                 return OPJ_FALSE;
8204                         }
8205
8206                         if (l_current_marker == J2K_MS_SOT)
8207                                 break; /* SOT marker is detected main header is completely read */
8208                         else    /* Get the marker handler from the marker ID */
8209                                 l_marker_handler = j2k_get_marker_handler(l_current_marker);
8210                 }
8211
8212                 /* Check if the marker is known and if it is the right place to find it */
8213                 if (! (p_j2k->m_specific_param.m_decoder.m_state & l_marker_handler->states) ) {
8214                         opj_event_msg_v2(p_manager, EVT_ERROR, "Marker is not compliant with its position\n");
8215                         return OPJ_FALSE;
8216                 }
8217
8218                 /* Try to read 2 bytes (the marker size) from stream and copy them into the buffer */
8219                 if (opj_stream_read_data(p_stream,p_j2k->m_specific_param.m_decoder.m_header_data,2,p_manager) != 2) {
8220                         opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8221                         return OPJ_FALSE;
8222                 }
8223
8224                 /* read 2 bytes as the marker size */
8225                 opj_read_bytes(p_j2k->m_specific_param.m_decoder.m_header_data,&l_marker_size,2);
8226                 l_marker_size -= 2; /* Subtract the size of the marker ID already read */
8227
8228                 /* Check if the marker size is compatible with the header data size */
8229                 if (l_marker_size > p_j2k->m_specific_param.m_decoder.m_header_data_size) {
8230                         p_j2k->m_specific_param.m_decoder.m_header_data = (OPJ_BYTE*)
8231                                         opj_realloc(p_j2k->m_specific_param.m_decoder.m_header_data,l_marker_size);
8232                         if (p_j2k->m_specific_param.m_decoder.m_header_data == 00) {
8233                                 return OPJ_FALSE;
8234                         }
8235                         p_j2k->m_specific_param.m_decoder.m_header_data_size = l_marker_size;
8236                 }
8237
8238                 /* Try to read the rest of the marker segment from stream and copy them into the buffer */
8239                 if (opj_stream_read_data(p_stream,p_j2k->m_specific_param.m_decoder.m_header_data,l_marker_size,p_manager) != l_marker_size) {
8240                         opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8241                         return OPJ_FALSE;
8242                 }
8243
8244                 /* Read the marker segment with the correct marker handler */
8245                 if (! (*(l_marker_handler->handler))(p_j2k,p_j2k->m_specific_param.m_decoder.m_header_data,l_marker_size,p_manager)) {
8246                         opj_event_msg_v2(p_manager, EVT_ERROR, "Marker handler function failed to read the marker segment\n");
8247                         return OPJ_FALSE;
8248                 }
8249
8250                 /* Add the marker to the codestream index*/
8251                 j2k_add_mhmarker_v2(p_j2k->cstr_index,
8252                                                         l_marker_handler->id,
8253                                                         (OPJ_UINT32) opj_stream_tell(p_stream) - l_marker_size - 4,
8254                                                         l_marker_size + 4 );
8255
8256                 /* Try to read 2 bytes (the next marker ID) from stream and copy them into the buffer */
8257                 if (opj_stream_read_data(p_stream,p_j2k->m_specific_param.m_decoder.m_header_data,2,p_manager) != 2) {
8258                         opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8259                         return OPJ_FALSE;
8260                 }
8261
8262                 /* read 2 bytes as the new marker ID */
8263                 opj_read_bytes(p_j2k->m_specific_param.m_decoder.m_header_data,&l_current_marker,2);
8264         }
8265
8266         opj_event_msg_v2(p_manager, EVT_INFO, "Main header has been correctly decoded.\n");
8267
8268         /* Position of the last element if the main header */
8269         p_j2k->cstr_index->main_head_end = (OPJ_UINT32) opj_stream_tell(p_stream) - 2;
8270
8271         /* Next step: read a tile-part header */
8272         p_j2k->m_specific_param.m_decoder.m_state = J2K_STATE_TPHSOT;
8273
8274         return OPJ_TRUE;
8275 }
8276
8277 /**
8278  * Excutes the given procedures on the given codec.
8279  *
8280  * @param       p_procedure_list        the list of procedures to execute
8281  * @param       p_j2k                                   the jpeg2000 codec to execute the procedures on.
8282  * @param       p_stream                                        the stream to execute the procedures on.
8283  * @param       p_manager                       the user manager.
8284  *
8285  * @return      true                            if all the procedures were successfully executed.
8286  */
8287 opj_bool j2k_exec (     opj_j2k_v2_t * p_j2k,
8288                                         opj_procedure_list_t * p_procedure_list,
8289                                         opj_stream_private_t *p_stream,
8290                                         opj_event_mgr_t * p_manager )
8291 {
8292         opj_bool (** l_procedure) (opj_j2k_v2_t * ,opj_stream_private_t *,opj_event_mgr_t *) = 00;
8293         opj_bool l_result = OPJ_TRUE;
8294         OPJ_UINT32 l_nb_proc, i;
8295
8296         /* preconditions*/
8297         assert(p_procedure_list != 00);
8298         assert(p_j2k != 00);
8299         assert(p_stream != 00);
8300         assert(p_manager != 00);
8301
8302
8303         l_nb_proc = opj_procedure_list_get_nb_procedures(p_procedure_list);
8304         l_procedure = (opj_bool (**) (opj_j2k_v2_t * ,opj_stream_private_t *,opj_event_mgr_t *)) opj_procedure_list_get_first_procedure(p_procedure_list);
8305
8306         for     (i=0;i<l_nb_proc;++i) {
8307                 l_result = l_result && ((*l_procedure) (p_j2k,p_stream,p_manager));
8308                 ++l_procedure;
8309         }
8310
8311         /* and clear the procedure list at the end.*/
8312         opj_procedure_list_clear(p_procedure_list);
8313         return l_result;
8314 }
8315
8316 /* FIXME DOC*/
8317 opj_bool j2k_copy_default_tcp_and_create_tcd
8318                                                 (
8319                                                 opj_j2k_v2_t * p_j2k,
8320                                                 opj_stream_private_t *p_stream,
8321                                                 opj_event_mgr_t * p_manager
8322                                                 )
8323 {
8324         opj_tcp_v2_t * l_tcp = 00;
8325         opj_tcp_v2_t * l_default_tcp = 00;
8326         OPJ_UINT32 l_nb_tiles;
8327         OPJ_UINT32 i,j;
8328         opj_tccp_t *l_current_tccp = 00;
8329         OPJ_UINT32 l_tccp_size;
8330         OPJ_UINT32 l_mct_size;
8331         opj_image_t * l_image;
8332         OPJ_UINT32 l_mcc_records_size,l_mct_records_size;
8333         opj_mct_data_t * l_src_mct_rec, *l_dest_mct_rec;
8334         opj_simple_mcc_decorrelation_data_t * l_src_mcc_rec, *l_dest_mcc_rec;
8335         OPJ_UINT32 l_offset;
8336
8337         /* preconditions */
8338         assert(p_j2k != 00);
8339         assert(p_stream != 00);
8340         assert(p_manager != 00);
8341
8342         l_image = p_j2k->m_private_image;
8343         l_nb_tiles = p_j2k->m_cp.th * p_j2k->m_cp.tw;
8344         l_tcp = p_j2k->m_cp.tcps;
8345         l_tccp_size = l_image->numcomps * sizeof(opj_tccp_t);
8346         l_default_tcp = p_j2k->m_specific_param.m_decoder.m_default_tcp;
8347         l_mct_size = l_image->numcomps * l_image->numcomps * sizeof(OPJ_FLOAT32);
8348
8349         /* For each tile */
8350         for (i=0; i<l_nb_tiles; ++i) {
8351                 /* keep the tile-compo coding parameters pointer of the current tile coding parameters*/
8352                 l_current_tccp = l_tcp->tccps;
8353                 /*Copy default coding parameters into the current tile coding parameters*/
8354                 memcpy(l_tcp, l_default_tcp, sizeof(opj_tcp_v2_t));
8355                 /* Initialize some values of the current tile coding parameters*/
8356                 l_tcp->ppt = 0;
8357                 l_tcp->ppt_data = 00;
8358                 /* Reconnect the tile-compo coding parameters pointer to the current tile coding parameters*/
8359                 l_tcp->tccps = l_current_tccp;
8360
8361                 /* Get the mct_decoding_matrix of the dflt_tile_cp and copy them into the current tile cp*/
8362                 if (l_default_tcp->m_mct_decoding_matrix) {
8363                         l_tcp->m_mct_decoding_matrix = (OPJ_FLOAT32*)opj_malloc(l_mct_size);
8364                         if (! l_tcp->m_mct_decoding_matrix ) {
8365                                 return OPJ_FALSE;
8366                         }
8367                         memcpy(l_tcp->m_mct_decoding_matrix,l_default_tcp->m_mct_decoding_matrix,l_mct_size);
8368                 }
8369
8370                 /* Get the mct_record of the dflt_tile_cp and copy them into the current tile cp*/
8371                 l_mct_records_size = l_default_tcp->m_nb_max_mct_records * sizeof(opj_mct_data_t);
8372                 l_tcp->m_mct_records = (opj_mct_data_t*)opj_malloc(l_mct_records_size);
8373                 if (! l_tcp->m_mct_records) {
8374                         return OPJ_FALSE;
8375                 }
8376                 memcpy(l_tcp->m_mct_records, l_default_tcp->m_mct_records,l_mct_records_size);
8377
8378                 /* Copy the mct record data from dflt_tile_cp to the current tile*/
8379                 l_src_mct_rec = l_default_tcp->m_mct_records;
8380                 l_dest_mct_rec = l_tcp->m_mct_records;
8381
8382                 for (j=0;j<l_default_tcp->m_nb_mct_records;++j) {
8383
8384                         if (l_src_mct_rec->m_data) {
8385
8386                                 l_dest_mct_rec->m_data = (OPJ_BYTE*) opj_malloc(l_src_mct_rec->m_data_size);
8387                                 if(! l_dest_mct_rec->m_data) {
8388                                         return OPJ_FALSE;
8389                                 }
8390                                 memcpy(l_dest_mct_rec->m_data,l_src_mct_rec->m_data,l_src_mct_rec->m_data_size);
8391                         }
8392
8393                         ++l_src_mct_rec;
8394                         ++l_dest_mct_rec;
8395                 }
8396
8397                 /* Get the mcc_record of the dflt_tile_cp and copy them into the current tile cp*/
8398                 l_mcc_records_size = l_default_tcp->m_nb_max_mcc_records * sizeof(opj_simple_mcc_decorrelation_data_t);
8399                 l_tcp->m_mcc_records = (opj_simple_mcc_decorrelation_data_t*) opj_malloc(l_mcc_records_size);
8400                 if (! l_tcp->m_mcc_records) {
8401                         return OPJ_FALSE;
8402                 }
8403                 memcpy(l_tcp->m_mcc_records,l_default_tcp->m_mcc_records,l_mcc_records_size);
8404
8405                 /* Copy the mcc record data from dflt_tile_cp to the current tile*/
8406                 l_src_mcc_rec = l_default_tcp->m_mcc_records;
8407                 l_dest_mcc_rec = l_tcp->m_mcc_records;
8408
8409                 for (j=0;j<l_default_tcp->m_nb_max_mcc_records;++j) {
8410
8411                         if (l_src_mcc_rec->m_decorrelation_array) {
8412                                 l_offset = l_src_mcc_rec->m_decorrelation_array - l_default_tcp->m_mct_records;
8413                                 l_dest_mcc_rec->m_decorrelation_array = l_tcp->m_mct_records + l_offset;
8414                         }
8415
8416                         if (l_src_mcc_rec->m_offset_array) {
8417                                 l_offset = l_src_mcc_rec->m_offset_array - l_default_tcp->m_mct_records;
8418                                 l_dest_mcc_rec->m_offset_array = l_tcp->m_mct_records + l_offset;
8419                         }
8420
8421                         ++l_src_mcc_rec;
8422                         ++l_dest_mcc_rec;
8423                 }
8424
8425                 /* Copy all the dflt_tile_compo_cp to the current tile cp */
8426                 memcpy(l_current_tccp,l_default_tcp->tccps,l_tccp_size);
8427
8428                 /* Move to next tile cp*/
8429                 ++l_tcp;
8430         }
8431
8432         /* Create the current tile decoder*/
8433         p_j2k->m_tcd = (opj_tcd_v2_t*)tcd_create_v2(OPJ_TRUE); /* FIXME why a cast ? */
8434         if (! p_j2k->m_tcd ) {
8435                 return OPJ_FALSE;
8436         }
8437
8438         if ( !tcd_init_v2(p_j2k->m_tcd, l_image, &(p_j2k->m_cp)) ) {
8439                 tcd_destroy_v2(p_j2k->m_tcd);
8440                 p_j2k->m_tcd = 00;
8441                 opj_event_msg_v2(p_manager, EVT_ERROR, "Cannot decode tile, memory error\n");
8442                 return OPJ_FALSE;
8443         }
8444
8445         return OPJ_TRUE;
8446 }
8447
8448 /**
8449  * Reads the lookup table containing all the marker, status and action, and returns the handler associated
8450  * with the marker value.
8451  * @param       p_id            Marker value to look up
8452  *
8453  * @return      the handler associated with the id.
8454 */
8455 const opj_dec_memory_marker_handler_t * j2k_get_marker_handler (OPJ_UINT32 p_id)
8456 {
8457         const opj_dec_memory_marker_handler_t *e;
8458         for (e = j2k_memory_marker_handler_tab; e->id != 0; ++e) {
8459                 if (e->id == p_id) {
8460                         break; /* we find a handler corresponding to the marker ID*/
8461                 }
8462         }
8463         return e;
8464 }
8465
8466
8467 /**
8468  * Destroys a jpeg2000 codec.
8469  *
8470  * @param       p_j2k   the jpeg20000 structure to destroy.
8471  */
8472 void j2k_destroy (opj_j2k_v2_t *p_j2k)
8473 {
8474         if (p_j2k == 00) {
8475                 return;
8476         }
8477
8478         if (p_j2k->m_is_decoder) {
8479
8480                 if (p_j2k->m_specific_param.m_decoder.m_default_tcp != 00) {
8481                         j2k_tcp_destroy(p_j2k->m_specific_param.m_decoder.m_default_tcp);
8482                         opj_free(p_j2k->m_specific_param.m_decoder.m_default_tcp);
8483                         p_j2k->m_specific_param.m_decoder.m_default_tcp = 00;
8484                 }
8485
8486                 if (p_j2k->m_specific_param.m_decoder.m_header_data != 00) {
8487                         opj_free(p_j2k->m_specific_param.m_decoder.m_header_data);
8488                         p_j2k->m_specific_param.m_decoder.m_header_data = 00;
8489                         p_j2k->m_specific_param.m_decoder.m_header_data_size = 0;
8490                 }
8491         }
8492         else {
8493
8494                 if (p_j2k->m_specific_param.m_encoder.m_encoded_tile_data) {
8495                         opj_free(p_j2k->m_specific_param.m_encoder.m_encoded_tile_data);
8496                         p_j2k->m_specific_param.m_encoder.m_encoded_tile_data = 00;
8497                 }
8498
8499                 if (p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_buffer) {
8500                         opj_free(p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_buffer);
8501                         p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_buffer = 00;
8502                         p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_current = 00;
8503                 }
8504
8505                 if (p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
8506                         opj_free(p_j2k->m_specific_param.m_encoder.m_header_tile_data);
8507                         p_j2k->m_specific_param.m_encoder.m_header_tile_data = 00;
8508                         p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = 0;
8509                 }
8510         }
8511
8512         tcd_destroy_v2(p_j2k->m_tcd);
8513
8514         j2k_cp_destroy(&(p_j2k->m_cp));
8515         memset(&(p_j2k->m_cp),0,sizeof(opj_cp_v2_t));
8516
8517         opj_procedure_list_destroy(p_j2k->m_procedure_list);
8518         p_j2k->m_procedure_list = 00;
8519
8520         opj_procedure_list_destroy(p_j2k->m_validation_list);
8521         p_j2k->m_procedure_list = 00;
8522
8523         j2k_destroy_cstr_index(p_j2k->cstr_index);
8524         p_j2k->cstr_index = NULL;
8525
8526         opj_image_destroy(p_j2k->m_private_image);
8527         p_j2k->m_private_image = NULL;
8528
8529         opj_image_destroy(p_j2k->m_output_image);
8530         p_j2k->m_output_image = NULL;
8531
8532         opj_free(p_j2k);
8533 }
8534
8535 void j2k_destroy_cstr_index (opj_codestream_index_t *p_cstr_ind)
8536 {
8537         if (p_cstr_ind) {
8538
8539                 if (p_cstr_ind->marker) {
8540                         opj_free(p_cstr_ind->marker);
8541                         p_cstr_ind->marker = NULL;
8542                 }
8543
8544                 if (p_cstr_ind->tile_index) {
8545                         OPJ_UINT32 it_tile = 0;
8546
8547                         for (it_tile=0; it_tile < p_cstr_ind->nb_of_tiles; it_tile++) {
8548
8549                                 if(p_cstr_ind->tile_index[it_tile].packet_index) {
8550                                         opj_free(p_cstr_ind->tile_index[it_tile].packet_index);
8551                                         p_cstr_ind->tile_index[it_tile].packet_index = NULL;
8552                                 }
8553
8554                                 if(p_cstr_ind->tile_index[it_tile].tp_index){
8555                                         opj_free(p_cstr_ind->tile_index[it_tile].tp_index);
8556                                         p_cstr_ind->tile_index[it_tile].tp_index = NULL;
8557                                 }
8558
8559                                 if(p_cstr_ind->tile_index[it_tile].marker){
8560                                         opj_free(p_cstr_ind->tile_index[it_tile].marker);
8561                                         p_cstr_ind->tile_index[it_tile].marker = NULL;
8562
8563                                 }
8564                         }
8565
8566                         opj_free( p_cstr_ind->tile_index);
8567                         p_cstr_ind->tile_index = NULL;
8568                 }
8569
8570                 opj_free(p_cstr_ind);
8571         }
8572 }
8573
8574
8575
8576 /**
8577  * Destroys a tile coding parameter structure.
8578  *
8579  * @param       p_tcp           the tile coding parameter to destroy.
8580  */
8581 void j2k_tcp_destroy (opj_tcp_v2_t *p_tcp)
8582 {
8583         if (p_tcp == 00) {
8584                 return;
8585         }
8586
8587         if (p_tcp->ppt_buffer != 00) {
8588                 opj_free(p_tcp->ppt_buffer);
8589                 p_tcp->ppt_buffer = 00;
8590         }
8591
8592         if (p_tcp->tccps != 00) {
8593                 opj_free(p_tcp->tccps);
8594                 p_tcp->tccps = 00;
8595         }
8596
8597         if (p_tcp->m_mct_coding_matrix != 00) {
8598                 opj_free(p_tcp->m_mct_coding_matrix);
8599                 p_tcp->m_mct_coding_matrix = 00;
8600         }
8601
8602         if (p_tcp->m_mct_decoding_matrix != 00) {
8603                 opj_free(p_tcp->m_mct_decoding_matrix);
8604                 p_tcp->m_mct_decoding_matrix = 00;
8605         }
8606
8607         if (p_tcp->m_mcc_records) {
8608                 opj_free(p_tcp->m_mcc_records);
8609                 p_tcp->m_mcc_records = 00;
8610                 p_tcp->m_nb_max_mcc_records = 0;
8611                 p_tcp->m_nb_mcc_records = 0;
8612         }
8613
8614         if (p_tcp->m_mct_records) {
8615                 opj_mct_data_t * l_mct_data = p_tcp->m_mct_records;
8616                 OPJ_UINT32 i;
8617
8618                 for (i=0;i<p_tcp->m_nb_mct_records;++i) {
8619                         if (l_mct_data->m_data) {
8620                                 opj_free(l_mct_data->m_data);
8621                                 l_mct_data->m_data = 00;
8622                         }
8623
8624                         ++l_mct_data;
8625                 }
8626
8627                 opj_free(p_tcp->m_mct_records);
8628                 p_tcp->m_mct_records = 00;
8629         }
8630
8631         if (p_tcp->mct_norms != 00) {
8632                 opj_free(p_tcp->mct_norms);
8633                 p_tcp->mct_norms = 00;
8634         }
8635
8636         j2k_tcp_data_destroy(p_tcp);
8637
8638 }
8639
8640 /**
8641  * Destroys the data inside a tile coding parameter structure.
8642  *
8643  * @param       p_tcp           the tile coding parameter which contain data to destroy.
8644  */
8645 void j2k_tcp_data_destroy (opj_tcp_v2_t *p_tcp)
8646 {
8647         if (p_tcp->m_data) {
8648                 opj_free(p_tcp->m_data);
8649                 p_tcp->m_data = NULL;
8650                 p_tcp->m_data_size = 0;
8651         }
8652 }
8653
8654 /**
8655  * Destroys a coding parameter structure.
8656  *
8657  * @param       p_cp            the coding parameter to destroy.
8658  */
8659 void j2k_cp_destroy (opj_cp_v2_t *p_cp)
8660 {
8661         OPJ_UINT32 l_nb_tiles;
8662         opj_tcp_v2_t * l_current_tile = 00;
8663         OPJ_UINT32 i;
8664
8665         if
8666                 (p_cp == 00)
8667         {
8668                 return;
8669         }
8670         if
8671                 (p_cp->tcps != 00)
8672         {
8673                 l_current_tile = p_cp->tcps;
8674                 l_nb_tiles = p_cp->th * p_cp->tw;
8675
8676                 for
8677                         (i = 0; i < l_nb_tiles; ++i)
8678                 {
8679                         j2k_tcp_destroy(l_current_tile);
8680                         ++l_current_tile;
8681                 }
8682                 opj_free(p_cp->tcps);
8683                 p_cp->tcps = 00;
8684         }
8685         if
8686                 (p_cp->ppm_buffer != 00)
8687         {
8688                 opj_free(p_cp->ppm_buffer);
8689                 p_cp->ppm_buffer = 00;
8690         }
8691         if
8692                 (p_cp->comment != 00)
8693         {
8694                 opj_free(p_cp->comment);
8695                 p_cp->comment = 00;
8696         }
8697         if
8698                 (! p_cp->m_is_decoder)
8699         {
8700                 if
8701                         (p_cp->m_specific_param.m_enc.m_matrice)
8702                 {
8703                         opj_free(p_cp->m_specific_param.m_enc.m_matrice);
8704                         p_cp->m_specific_param.m_enc.m_matrice = 00;
8705                 }
8706         }
8707 }
8708
8709
8710
8711 /**
8712  * Reads a tile header.
8713  * @param       p_j2k           the jpeg2000 codec.
8714  * @param       p_stream                        the stream to write data to.
8715  * @param       p_manager       the user event manager.
8716  */
8717 opj_bool j2k_read_tile_header(  opj_j2k_v2_t * p_j2k,
8718                                                                 OPJ_UINT32 * p_tile_index,
8719                                                                 OPJ_UINT32 * p_data_size,
8720                                                                 OPJ_INT32 * p_tile_x0, OPJ_INT32 * p_tile_y0,
8721                                                                 OPJ_INT32 * p_tile_x1, OPJ_INT32 * p_tile_y1,
8722                                                                 OPJ_UINT32 * p_nb_comps,
8723                                                                 opj_bool * p_go_on,
8724                                                                 opj_stream_private_t *p_stream,
8725                                                                 opj_event_mgr_t * p_manager )
8726 {
8727         OPJ_UINT32 l_current_marker = J2K_MS_SOT;
8728         OPJ_UINT32 l_marker_size;
8729         const opj_dec_memory_marker_handler_t * l_marker_handler = 00;
8730         opj_tcp_v2_t * l_tcp = NULL;
8731         OPJ_UINT32 l_nb_tiles;
8732
8733         /* preconditions */
8734         assert(p_stream != 00);
8735         assert(p_j2k != 00);
8736         assert(p_manager != 00);
8737
8738         /* Reach the End Of Codestream ?*/
8739         if (p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_EOC){
8740                 l_current_marker = J2K_MS_EOC;
8741         }
8742         /* We need to encounter a SOT marker (a new tile-part header) */
8743         else if (p_j2k->m_specific_param.m_decoder.m_state != J2K_STATE_TPHSOT){
8744                 return OPJ_FALSE;
8745         }
8746
8747         /* Read into the codestream until reach the EOC or ! can_decode ??? FIXME */
8748         while ( (!p_j2k->m_specific_param.m_decoder.m_can_decode) && (l_current_marker != J2K_MS_EOC) ) {
8749
8750                 /* Try to read until the Start Of Data is detected */
8751                 while (l_current_marker != J2K_MS_SOD) {
8752
8753                         /* Try to read 2 bytes (the marker size) from stream and copy them into the buffer */
8754                         if (opj_stream_read_data(p_stream,p_j2k->m_specific_param.m_decoder.m_header_data,2,p_manager) != 2) {
8755                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8756                                 return OPJ_FALSE;
8757                         }
8758
8759                         /* Read 2 bytes from the buffer as the marker size */
8760                         opj_read_bytes(p_j2k->m_specific_param.m_decoder.m_header_data,&l_marker_size,2);
8761
8762                         /* Why this condition? FIXME */
8763                         if (p_j2k->m_specific_param.m_decoder.m_state & J2K_STATE_TPH){
8764                                 p_j2k->m_specific_param.m_decoder.m_sot_length -= (l_marker_size + 2);
8765                         }
8766                         l_marker_size -= 2; /* Subtract the size of the marker ID already read */
8767
8768                         /* Get the marker handler from the marker ID */
8769                         l_marker_handler = j2k_get_marker_handler(l_current_marker);
8770
8771                         /* Check if the marker is known and if it is the right place to find it */
8772                         if (! (p_j2k->m_specific_param.m_decoder.m_state & l_marker_handler->states) ) {
8773                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Marker is not compliant with its position\n");
8774                                 return OPJ_FALSE;
8775                         }
8776 /* FIXME manage case of unknown marker as in the main header ? */
8777
8778                         /* Check if the marker size is compatible with the header data size */
8779                         if (l_marker_size > p_j2k->m_specific_param.m_decoder.m_header_data_size) {
8780                                 p_j2k->m_specific_param.m_decoder.m_header_data = (OPJ_BYTE*)
8781                                         opj_realloc(p_j2k->m_specific_param.m_decoder.m_header_data,l_marker_size);
8782                                 if (p_j2k->m_specific_param.m_decoder.m_header_data == 00) {
8783                                         return OPJ_FALSE;
8784                                 }
8785                                 p_j2k->m_specific_param.m_decoder.m_header_data_size = l_marker_size;
8786                         }
8787
8788                         /* Try to read the rest of the marker segment from stream and copy them into the buffer */
8789                         if (opj_stream_read_data(p_stream,p_j2k->m_specific_param.m_decoder.m_header_data,l_marker_size,p_manager) != l_marker_size) {
8790                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8791                                 return OPJ_FALSE;
8792                         }
8793
8794                         /* Read the marker segment with the correct marker handler */
8795                         if (! (*(l_marker_handler->handler))(p_j2k,p_j2k->m_specific_param.m_decoder.m_header_data,l_marker_size,p_manager)) {
8796                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Fail to read the current marker segment (%#x)\n", l_current_marker);
8797                                 return OPJ_FALSE;
8798                         }
8799
8800                         /* Add the marker to the codestream index*/
8801                         j2k_add_tlmarker_v2(p_j2k->m_current_tile_number,
8802                                                                 p_j2k->cstr_index,
8803                                                                 l_marker_handler->id,
8804                                                                 (OPJ_UINT32) opj_stream_tell(p_stream) - l_marker_size - 4,
8805                                                                 l_marker_size + 4 );
8806
8807                         /* Keep the position of the last SOT marker read */
8808                         if ( l_marker_handler->id == J2K_MS_SOT ) {
8809                                 OPJ_UINT32 sot_pos = (OPJ_UINT32) opj_stream_tell(p_stream) - l_marker_size - 4 ;
8810                                 if (sot_pos > p_j2k->m_specific_param.m_decoder.m_last_sot_read_pos)
8811                                 {
8812                                         p_j2k->m_specific_param.m_decoder.m_last_sot_read_pos = sot_pos;
8813                                 }
8814                         }
8815
8816
8817                         if (p_j2k->m_specific_param.m_decoder.m_skip_data) {
8818                                 /* Skip the rest of the tile part header*/
8819                                 if (opj_stream_skip(p_stream,p_j2k->m_specific_param.m_decoder.m_sot_length,p_manager) != p_j2k->m_specific_param.m_decoder.m_sot_length) {
8820                                         opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8821                                         return OPJ_FALSE;
8822                                 }
8823                                 l_current_marker = J2K_MS_SOD; /* Normally we reached a SOD */
8824                         }
8825                         else {
8826                                 /* Try to read 2 bytes (the next marker ID) from stream and copy them into the buffer*/
8827                                 if (opj_stream_read_data(p_stream,p_j2k->m_specific_param.m_decoder.m_header_data,2,p_manager) != 2) {
8828                                         opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8829                                         return OPJ_FALSE;
8830                                 }
8831                                 /* Read 2 bytes from the buffer as the new marker ID */
8832                                 opj_read_bytes(p_j2k->m_specific_param.m_decoder.m_header_data,&l_current_marker,2);
8833                         }
8834                 }
8835
8836                 /* If we didn't skip data before, we need to read the SOD marker*/
8837                 if (! p_j2k->m_specific_param.m_decoder.m_skip_data) {
8838                         /* Try to read the SOD marker and skip data ? FIXME */
8839                         if (! opj_j2k_read_sod(p_j2k, p_stream, p_manager)) {
8840                                 return OPJ_FALSE;
8841                         }
8842
8843
8844
8845                         if (! p_j2k->m_specific_param.m_decoder.m_can_decode){
8846                                 /* Try to read 2 bytes (the next marker ID) from stream and copy them into the buffer */
8847                                 if (opj_stream_read_data(p_stream,p_j2k->m_specific_param.m_decoder.m_header_data,2,p_manager) != 2) {
8848                                         opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8849                                         return OPJ_FALSE;
8850                                 }
8851
8852                                 /* Read 2 bytes from buffer as the new marker ID */
8853                                 opj_read_bytes(p_j2k->m_specific_param.m_decoder.m_header_data,&l_current_marker,2);
8854                         }
8855                 }
8856                 else {
8857                         /* Indicate we will try to read a new tile-part header*/
8858                         p_j2k->m_specific_param.m_decoder.m_skip_data = 0;
8859                         p_j2k->m_specific_param.m_decoder.m_can_decode = 0;
8860                         p_j2k->m_specific_param.m_decoder.m_state = J2K_STATE_TPHSOT;
8861
8862                         /* Try to read 2 bytes (the next marker ID) from stream and copy them into the buffer */
8863                         if (opj_stream_read_data(p_stream,p_j2k->m_specific_param.m_decoder.m_header_data,2,p_manager) != 2) {
8864                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8865                                 return OPJ_FALSE;
8866                         }
8867
8868                         /* Read 2 bytes from buffer as the new marker ID */
8869                         opj_read_bytes(p_j2k->m_specific_param.m_decoder.m_header_data,&l_current_marker,2);
8870                 }
8871         }
8872
8873         /* Current marker is the EOC marker ?*/
8874         if (l_current_marker == J2K_MS_EOC) {
8875                 if (p_j2k->m_specific_param.m_decoder.m_state != J2K_STATE_EOC ){
8876                         p_j2k->m_current_tile_number = 0;
8877                         p_j2k->m_specific_param.m_decoder.m_state = J2K_STATE_EOC;
8878                 }
8879         }
8880
8881         /* FIXME DOC ???*/
8882         if ( ! p_j2k->m_specific_param.m_decoder.m_can_decode) {
8883                 l_tcp = p_j2k->m_cp.tcps + p_j2k->m_current_tile_number;
8884                 l_nb_tiles = p_j2k->m_cp.th * p_j2k->m_cp.tw;
8885
8886                 while( (p_j2k->m_current_tile_number < l_nb_tiles) && (l_tcp->m_data == 00) ) {
8887                         ++p_j2k->m_current_tile_number;
8888                         ++l_tcp;
8889                 }
8890
8891                 if (p_j2k->m_current_tile_number == l_nb_tiles) {
8892                         *p_go_on = OPJ_FALSE;
8893                         return OPJ_TRUE;
8894                 }
8895         }
8896
8897         /*FIXME ???*/
8898         if (! tcd_init_decode_tile(p_j2k->m_tcd, p_j2k->m_current_tile_number)) {
8899                 opj_event_msg_v2(p_manager, EVT_ERROR, "Cannot decode tile, memory error\n");
8900                 return OPJ_FALSE;
8901         }
8902
8903         opj_event_msg_v2(p_manager, EVT_INFO, "Header of tile %d / %d has been read.\n",
8904                         p_j2k->m_current_tile_number, (p_j2k->m_cp.th * p_j2k->m_cp.tw) - 1);
8905
8906         *p_tile_index = p_j2k->m_current_tile_number;
8907         *p_go_on = OPJ_TRUE;
8908         *p_data_size = tcd_get_decoded_tile_size(p_j2k->m_tcd);
8909         *p_tile_x0 = p_j2k->m_tcd->tcd_image->tiles->x0;
8910         *p_tile_y0 = p_j2k->m_tcd->tcd_image->tiles->y0;
8911         *p_tile_x1 = p_j2k->m_tcd->tcd_image->tiles->x1;
8912         *p_tile_y1 = p_j2k->m_tcd->tcd_image->tiles->y1;
8913         *p_nb_comps = p_j2k->m_tcd->tcd_image->tiles->numcomps;
8914
8915          p_j2k->m_specific_param.m_decoder.m_state |= 0x0080;/* FIXME J2K_DEC_STATE_DATA;*/
8916
8917         return OPJ_TRUE;
8918 }
8919
8920
8921 opj_bool j2k_decode_tile (      opj_j2k_v2_t * p_j2k,
8922                                                         OPJ_UINT32 p_tile_index,
8923                                                         OPJ_BYTE * p_data,
8924                                                         OPJ_UINT32 p_data_size,
8925                                                         opj_stream_private_t *p_stream,
8926                                                         opj_event_mgr_t * p_manager )
8927 {
8928         OPJ_UINT32 l_current_marker;
8929         OPJ_BYTE l_data [2];
8930         opj_tcp_v2_t * l_tcp;
8931
8932         /* preconditions */
8933         assert(p_stream != 00);
8934         assert(p_j2k != 00);
8935         assert(p_manager != 00);
8936
8937         if ( !(p_j2k->m_specific_param.m_decoder.m_state & 0x0080/*FIXME J2K_DEC_STATE_DATA*/)
8938                 || (p_tile_index != p_j2k->m_current_tile_number) ) {
8939                 return OPJ_FALSE;
8940         }
8941
8942         l_tcp = &(p_j2k->m_cp.tcps[p_tile_index]);
8943         if (! l_tcp->m_data) {
8944                 j2k_tcp_destroy(l_tcp);
8945                 return OPJ_FALSE;
8946         }
8947
8948         if (! tcd_decode_tile_v2(       p_j2k->m_tcd,
8949                                                                 l_tcp->m_data,
8950                                                                 l_tcp->m_data_size,
8951                                                                 p_tile_index,
8952                                                                 p_j2k->cstr_index) ) {
8953                 j2k_tcp_destroy(l_tcp);
8954                 p_j2k->m_specific_param.m_decoder.m_state |= 0x8000;/*FIXME J2K_DEC_STATE_ERR;*/
8955                 return OPJ_FALSE;
8956         }
8957
8958         if (! tcd_update_tile_data(p_j2k->m_tcd,p_data,p_data_size)) {
8959                 return OPJ_FALSE;
8960         }
8961
8962         /* To avoid to destroy the tcp which can be useful when we try to decode a tile decoded before (cf j2k_random_tile_access)
8963          * we destroy just the data which will be re-read in read_tile_header*/
8964         /*j2k_tcp_destroy(l_tcp);
8965         p_j2k->m_tcd->tcp = 0;*/
8966         j2k_tcp_data_destroy(l_tcp);
8967
8968         p_j2k->m_specific_param.m_decoder.m_can_decode = 0;
8969         p_j2k->m_specific_param.m_decoder.m_state &= (~ (0x0080));/* FIXME J2K_DEC_STATE_DATA);*/
8970
8971         if (p_j2k->m_specific_param.m_decoder.m_state != 0x0100){ /*FIXME J2K_DEC_STATE_EOC)*/
8972                 if (opj_stream_read_data(p_stream,l_data,2,p_manager) != 2) {
8973                         opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short\n");
8974                         return OPJ_FALSE;
8975                 }
8976
8977                 opj_read_bytes(l_data,&l_current_marker,2);
8978
8979                 if (l_current_marker == J2K_MS_EOC) {
8980                         p_j2k->m_current_tile_number = 0;
8981                         p_j2k->m_specific_param.m_decoder.m_state =  0x0100;/*FIXME J2K_DEC_STATE_EOC;*/
8982                 }
8983                 else if (l_current_marker != J2K_MS_SOT)
8984                 {
8985                         opj_event_msg_v2(p_manager, EVT_ERROR, "Stream too short, expected SOT\n");
8986                         return OPJ_FALSE;
8987                 }
8988         }
8989
8990         return OPJ_TRUE;
8991 }
8992
8993
8994 opj_bool j2k_update_image_data (opj_tcd_v2_t * p_tcd, OPJ_BYTE * p_data, opj_image_t* p_output_image)
8995 {
8996         OPJ_UINT32 i,j,k = 0;
8997         OPJ_UINT32 l_width_src,l_height_src;
8998         OPJ_UINT32 l_width_dest,l_height_dest;
8999         OPJ_INT32 l_offset_x0_src, l_offset_y0_src, l_offset_x1_src, l_offset_y1_src;
9000         OPJ_INT32 l_start_offset_src, l_line_offset_src, l_end_offset_src ;
9001         OPJ_UINT32 l_start_x_dest , l_start_y_dest;
9002         OPJ_UINT32 l_x0_dest, l_y0_dest, l_x1_dest, l_y1_dest;
9003         OPJ_INT32 l_start_offset_dest, l_line_offset_dest;
9004
9005         opj_image_comp_t * l_img_comp_src = 00;
9006         opj_image_comp_t * l_img_comp_dest = 00;
9007
9008         opj_tcd_tilecomp_v2_t * l_tilec = 00;
9009         opj_image_t * l_image_src = 00;
9010         OPJ_UINT32 l_size_comp, l_remaining;
9011         OPJ_INT32 * l_dest_ptr;
9012         opj_tcd_resolution_v2_t* l_res= 00;
9013
9014         l_tilec = p_tcd->tcd_image->tiles->comps;
9015         l_image_src = p_tcd->image;
9016         l_img_comp_src = l_image_src->comps;
9017
9018         l_img_comp_dest = p_output_image->comps;
9019
9020         for (i=0; i<l_image_src->numcomps; i++) {
9021
9022                 /* Allocate output component buffer if necessary */
9023                 if (!l_img_comp_dest->data) {
9024
9025                         l_img_comp_dest->data = (OPJ_INT32*) opj_calloc(l_img_comp_dest->w * l_img_comp_dest->h, sizeof(OPJ_INT32));
9026                         if (! l_img_comp_dest->data) {
9027                                 return OPJ_FALSE;
9028                         }
9029                 }
9030
9031                 /* Copy info from decoded comp image to output image */
9032                 l_img_comp_dest->resno_decoded = l_img_comp_src->resno_decoded;
9033
9034                 /*-----*/
9035                 /* Compute the precision of the output buffer */
9036                 l_size_comp = l_img_comp_src->prec >> 3; /*(/ 8)*/
9037                 l_remaining = l_img_comp_src->prec & 7;  /* (%8) */
9038                 l_res = l_tilec->resolutions + l_img_comp_src->resno_decoded;
9039
9040                 if (l_remaining) {
9041                         ++l_size_comp;
9042                 }
9043
9044                 if (l_size_comp == 3) {
9045                         l_size_comp = 4;
9046                 }
9047                 /*-----*/
9048
9049                 /* Current tile component size*/
9050                 /*if (i == 0) {
9051                 fprintf(stdout, "SRC: l_res_x0=%d, l_res_x1=%d, l_res_y0=%d, l_res_y1=%d\n",
9052                                 l_res->x0, l_res->x1, l_res->y0, l_res->y1);
9053                 }*/
9054
9055                 l_width_src = (l_res->x1 - l_res->x0);
9056                 l_height_src = (l_res->y1 - l_res->y0);
9057
9058                 /* Border of the current output component*/
9059                 l_x0_dest = int_ceildivpow2(l_img_comp_dest->x0, l_img_comp_dest->factor);
9060                 l_y0_dest = int_ceildivpow2(l_img_comp_dest->y0, l_img_comp_dest->factor);
9061                 l_x1_dest = l_x0_dest + l_img_comp_dest->w;
9062                 l_y1_dest = l_y0_dest + l_img_comp_dest->h;
9063
9064                 /*if (i == 0) {
9065                 fprintf(stdout, "DEST: l_x0_dest=%d, l_x1_dest=%d, l_y0_dest=%d, l_y1_dest=%d (%d)\n",
9066                                 l_x0_dest, l_x1_dest, l_y0_dest, l_y1_dest, l_img_comp_dest->factor );
9067                 }*/
9068
9069                 /*-----*/
9070                 /* Compute the area (l_offset_x0_src, l_offset_y0_src, l_offset_x1_src, l_offset_y1_src)
9071                  * of the input buffer (decoded tile component) which will be move
9072                  * in the output buffer. Compute the area of the output buffer (l_start_x_dest,
9073                  * l_start_y_dest, l_width_dest, l_height_dest)  which will be modified
9074                  * by this input area.
9075                  * */
9076                 assert( l_res->x0 >= 0);
9077                 assert( l_res->x1 >= 0);
9078                 if ( l_x0_dest < (OPJ_UINT32)l_res->x0 ) {
9079                         l_start_x_dest = l_res->x0 - l_x0_dest;
9080                         l_offset_x0_src = 0;
9081
9082                         if ( l_x1_dest >= (OPJ_UINT32)l_res->x1 ) {
9083                                 l_width_dest = l_width_src;
9084                                 l_offset_x1_src = 0;
9085                         }
9086                         else {
9087                                 l_width_dest = l_x1_dest - l_res->x0 ;
9088                                 l_offset_x1_src = l_width_src - l_width_dest;
9089                         }
9090                 }
9091                 else {
9092                         l_start_x_dest = 0 ;
9093                         l_offset_x0_src = l_x0_dest - l_res->x0;
9094
9095                         if ( l_x1_dest >= (OPJ_UINT32)l_res->x1 ) {
9096                                 l_width_dest = l_width_src - l_offset_x0_src;
9097                                 l_offset_x1_src = 0;
9098                         }
9099                         else {
9100                                 l_width_dest = l_img_comp_dest->w ;
9101                                 l_offset_x1_src = l_res->x1 - l_x1_dest;
9102                         }
9103                 }
9104
9105                 if ( l_y0_dest < (OPJ_UINT32)l_res->y0 ) {
9106                         l_start_y_dest = l_res->y0 - l_y0_dest;
9107                         l_offset_y0_src = 0;
9108
9109                         if ( l_y1_dest >= (OPJ_UINT32)l_res->y1 ) {
9110                                 l_height_dest = l_height_src;
9111                                 l_offset_y1_src = 0;
9112                         }
9113                         else {
9114                                 l_height_dest = l_y1_dest - l_res->y0 ;
9115                                 l_offset_y1_src =  l_height_src - l_height_dest;
9116                         }
9117                 }
9118                 else {
9119                         l_start_y_dest = 0 ;
9120                         l_offset_y0_src = l_y0_dest - l_res->y0;
9121
9122                         if ( l_y1_dest >= (OPJ_UINT32)l_res->y1 ) {
9123                                 l_height_dest = l_height_src - l_offset_y0_src;
9124                                 l_offset_y1_src = 0;
9125                         }
9126                         else {
9127                                 l_height_dest = l_img_comp_dest->h ;
9128                                 l_offset_y1_src = l_res->y1 - l_y1_dest;
9129                         }
9130                 }
9131
9132                 if( (l_offset_x0_src < 0 ) || (l_offset_y0_src < 0 ) || (l_offset_x1_src < 0 ) || (l_offset_y1_src < 0 ) ){
9133                         return OPJ_FALSE;
9134                 }
9135                 /*-----*/
9136
9137                 /* Compute the input buffer offset */
9138                 l_start_offset_src = l_offset_x0_src + l_offset_y0_src * l_width_src;
9139                 l_line_offset_src = l_offset_x1_src + l_offset_x0_src;
9140                 l_end_offset_src = l_offset_y1_src * l_width_src - l_offset_x0_src;
9141
9142                 /* Compute the output buffer offset */
9143                 l_start_offset_dest = l_start_x_dest + l_start_y_dest * l_img_comp_dest->w;
9144                 l_line_offset_dest = l_img_comp_dest->w - l_width_dest;
9145
9146                 /* Move the output buffer to the first place where we will write*/
9147                 l_dest_ptr = l_img_comp_dest->data + l_start_offset_dest;
9148
9149                 /*if (i == 0) {
9150                         fprintf(stdout, "COMPO[%d]:\n",i);
9151                         fprintf(stdout, "SRC: l_start_x_src=%d, l_start_y_src=%d, l_width_src=%d, l_height_src=%d\n"
9152                                         "\t tile offset:%d, %d, %d, %d\n"
9153                                         "\t buffer offset: %d; %d, %d\n",
9154                                         l_res->x0, l_res->y0, l_width_src, l_height_src,
9155                                         l_offset_x0_src, l_offset_y0_src, l_offset_x1_src, l_offset_y1_src,
9156                                         l_start_offset_src, l_line_offset_src, l_end_offset_src);
9157
9158                         fprintf(stdout, "DEST: l_start_x_dest=%d, l_start_y_dest=%d, l_width_dest=%d, l_height_dest=%d\n"
9159                                         "\t start offset: %d, line offset= %d\n",
9160                                         l_start_x_dest, l_start_y_dest, l_width_dest, l_height_dest, l_start_offset_dest, l_line_offset_dest);
9161                 }*/
9162
9163
9164                 switch (l_size_comp) {
9165                         case 1:
9166                                 {
9167                                         OPJ_CHAR * l_src_ptr = (OPJ_CHAR*) p_data;
9168                                         l_src_ptr += l_start_offset_src; /* Move to the first place where we will read*/
9169
9170                                         if (l_img_comp_src->sgnd) {
9171                                                 for (j = 0 ; j < l_height_dest ; ++j) {
9172                                                         for ( k = 0 ; k < l_width_dest ; ++k) {
9173                                                                 *(l_dest_ptr++) = (OPJ_INT32) (*(l_src_ptr++)); /* Copy only the data needed for the output image */
9174                                                         }
9175
9176                                                         l_dest_ptr+= l_line_offset_dest; /* Move to the next place where we will write */
9177                                                         l_src_ptr += l_line_offset_src ; /* Move to the next place where we will read */
9178                                                 }
9179                                         }
9180                                         else {
9181                                                 for ( j = 0 ; j < l_height_dest ; ++j ) {
9182                                                         for ( k = 0 ; k < l_width_dest ; ++k) {
9183                                                                 *(l_dest_ptr++) = (OPJ_INT32) ((*(l_src_ptr++))&0xff);
9184                                                         }
9185
9186                                                         l_dest_ptr+= l_line_offset_dest;
9187                                                         l_src_ptr += l_line_offset_src;
9188                                                 }
9189                                         }
9190
9191                                         l_src_ptr += l_end_offset_src; /* Move to the end of this component-part of the input buffer */
9192                                         p_data = (OPJ_BYTE*) l_src_ptr; /* Keep the current position for the next component-part */
9193                                 }
9194                                 break;
9195                         case 2:
9196                                 {
9197                                         OPJ_INT16 * l_src_ptr = (OPJ_INT16 *) p_data;
9198                                         l_src_ptr += l_start_offset_src;
9199
9200                                         if (l_img_comp_src->sgnd) {
9201                                                 for (j=0;j<l_height_dest;++j) {
9202                                                         for (k=0;k<l_width_dest;++k) {
9203                                                                 *(l_dest_ptr++) = *(l_src_ptr++);
9204                                                         }
9205
9206                                                         l_dest_ptr+= l_line_offset_dest;
9207                                                         l_src_ptr += l_line_offset_src ;
9208                                                 }
9209                                         }
9210                                         else {
9211                                                 for (j=0;j<l_height_dest;++j) {
9212                                                         for (k=0;k<l_width_dest;++k) {
9213                                                                 *(l_dest_ptr++) = (*(l_src_ptr++))&0xffff;
9214                                                         }
9215
9216                                                         l_dest_ptr+= l_line_offset_dest;
9217                                                         l_src_ptr += l_line_offset_src ;
9218                                                 }
9219                                         }
9220
9221                                         l_src_ptr += l_end_offset_src;
9222                                         p_data = (OPJ_BYTE*) l_src_ptr;
9223                                 }
9224                                 break;
9225                         case 4:
9226                                 {
9227                                         OPJ_INT32 * l_src_ptr = (OPJ_INT32 *) p_data;
9228                                         l_src_ptr += l_start_offset_src;
9229
9230                                         for (j=0;j<l_height_dest;++j) {
9231                                                 for (k=0;k<l_width_dest;++k) {
9232                                                         *(l_dest_ptr++) = (*(l_src_ptr++));
9233                                                 }
9234
9235                                                 l_dest_ptr+= l_line_offset_dest;
9236                                                 l_src_ptr += l_line_offset_src ;
9237                                         }
9238
9239                                         l_src_ptr += l_end_offset_src;
9240                                         p_data = (OPJ_BYTE*) l_src_ptr;
9241                                 }
9242                                 break;
9243                 }
9244
9245                 ++l_img_comp_dest;
9246                 ++l_img_comp_src;
9247                 ++l_tilec;
9248         }
9249
9250         return OPJ_TRUE;
9251 }
9252
9253 /**
9254  * Sets the given area to be decoded. This function should be called right after opj_read_header and before any tile header reading.
9255  *
9256  * @param       p_j2k                   the jpeg2000 codec.
9257  * @param       p_start_x               the left position of the rectangle to decode (in image coordinates).
9258  * @param       p_end_x                 the right position of the rectangle to decode (in image coordinates).
9259  * @param       p_start_y               the up position of the rectangle to decode (in image coordinates).
9260  * @param       p_end_y                 the bottom position of the rectangle to decode (in image coordinates).
9261  * @param       p_manager               the user event manager
9262  *
9263  * @return      true                    if the area could be set.
9264  */
9265 opj_bool j2k_set_decode_area(   opj_j2k_v2_t *p_j2k,
9266                                                                 opj_image_t* p_image,
9267                                                                 OPJ_INT32 p_start_x, OPJ_INT32 p_start_y,
9268                                                                 OPJ_INT32 p_end_x, OPJ_INT32 p_end_y,
9269                                                                 struct opj_event_mgr * p_manager )
9270 {
9271         opj_cp_v2_t * l_cp = &(p_j2k->m_cp);
9272         opj_image_t * l_image = p_j2k->m_private_image;
9273
9274         OPJ_UINT32 it_comp;
9275         OPJ_INT32 l_comp_x1, l_comp_y1;
9276         opj_image_comp_t* l_img_comp = NULL;
9277
9278         /* Check if we are read the main header */
9279         if (p_j2k->m_specific_param.m_decoder.m_state != J2K_STATE_TPHSOT) { /* FIXME J2K_DEC_STATE_TPHSOT)*/
9280                 opj_event_msg_v2(p_manager, EVT_ERROR, "Need to decode the main header before begin to decode the remaining codestream");
9281                 return OPJ_FALSE;
9282         }
9283
9284         if ( !p_start_x && !p_start_y && !p_end_x && !p_end_y){
9285                 opj_event_msg_v2(p_manager, EVT_INFO, "No decoded area parameters, set the decoded area to the whole image\n");
9286
9287                 p_j2k->m_specific_param.m_decoder.m_start_tile_x = 0;
9288                 p_j2k->m_specific_param.m_decoder.m_start_tile_y = 0;
9289                 p_j2k->m_specific_param.m_decoder.m_end_tile_x = l_cp->tw;
9290                 p_j2k->m_specific_param.m_decoder.m_end_tile_y = l_cp->th;
9291
9292                 return OPJ_TRUE;
9293         }
9294
9295         /* ----- */
9296         /* Check if the positions provided by the user are correct */
9297
9298         /* Left */
9299         assert(p_start_x >= 0 );
9300         assert(p_start_y >= 0 );
9301
9302         if ((OPJ_UINT32)p_start_x > l_image->x1 ) {
9303                 opj_event_msg_v2(p_manager, EVT_ERROR,
9304                         "Left position of the decoded area (region_x0=%d) is outside the image area (Xsiz=%d).\n",
9305                         p_start_x, l_image->x1);
9306                 return OPJ_FALSE;
9307         }
9308         else if ((OPJ_UINT32)p_start_x < l_image->x0){
9309                 opj_event_msg_v2(p_manager, EVT_WARNING,
9310                                 "Left position of the decoded area (region_x0=%d) is outside the image area (XOsiz=%d).\n",
9311                                 p_start_x, l_image->x0);
9312                 p_j2k->m_specific_param.m_decoder.m_start_tile_x = 0;
9313                 p_image->x0 = l_image->x0;
9314         }
9315         else {
9316                 p_j2k->m_specific_param.m_decoder.m_start_tile_x = (p_start_x - l_cp->tx0) / l_cp->tdx;
9317                 p_image->x0 = p_start_x;
9318         }
9319
9320         /* Up */
9321         if ((OPJ_UINT32)p_start_y > l_image->y1){
9322                 opj_event_msg_v2(p_manager, EVT_ERROR,
9323                                 "Up position of the decoded area (region_y0=%d) is outside the image area (Ysiz=%d).\n",
9324                                 p_start_y, l_image->y1);
9325                 return OPJ_FALSE;
9326         }
9327         else if ((OPJ_UINT32)p_start_y < l_image->y0){
9328                 opj_event_msg_v2(p_manager, EVT_WARNING,
9329                                 "Up position of the decoded area (region_y0=%d) is outside the image area (YOsiz=%d).\n",
9330                                 p_start_y, l_image->y0);
9331                 p_j2k->m_specific_param.m_decoder.m_start_tile_y = 0;
9332                 p_image->y0 = l_image->y0;
9333         }
9334         else {
9335                 p_j2k->m_specific_param.m_decoder.m_start_tile_y = (p_start_y - l_cp->ty0) / l_cp->tdy;
9336                 p_image->y0 = p_start_y;
9337         }
9338
9339         /* Right */
9340         assert((OPJ_UINT32)p_end_x > 0);
9341         assert((OPJ_UINT32)p_end_y > 0);
9342         if ((OPJ_UINT32)p_end_x < l_image->x0) {
9343                 opj_event_msg_v2(p_manager, EVT_ERROR,
9344                         "Right position of the decoded area (region_x1=%d) is outside the image area (XOsiz=%d).\n",
9345                         p_end_x, l_image->x0);
9346                 return OPJ_FALSE;
9347         }
9348         else if ((OPJ_UINT32)p_end_x > l_image->x1) {
9349                 opj_event_msg_v2(p_manager, EVT_WARNING,
9350                         "Right position of the decoded area (region_x1=%d) is outside the image area (Xsiz=%d).\n",
9351                         p_end_x, l_image->x1);
9352                 p_j2k->m_specific_param.m_decoder.m_end_tile_x = l_cp->tw;
9353                 p_image->x1 = l_image->x1;
9354         }
9355         else {
9356                 p_j2k->m_specific_param.m_decoder.m_end_tile_x = int_ceildiv((p_end_x - l_cp->tx0), l_cp->tdx);
9357                 p_image->x1 = p_end_x;
9358         }
9359
9360         /* Bottom */
9361         if ((OPJ_UINT32)p_end_y < l_image->y0) {
9362                 opj_event_msg_v2(p_manager, EVT_ERROR,
9363                         "Bottom position of the decoded area (region_y1=%d) is outside the image area (YOsiz=%d).\n",
9364                         p_end_y, l_image->y0);
9365                 return OPJ_FALSE;
9366         }
9367         if ((OPJ_UINT32)p_end_y > l_image->y1){
9368                 opj_event_msg_v2(p_manager, EVT_WARNING,
9369                         "Bottom position of the decoded area (region_y1=%d) is outside the image area (Ysiz=%d).\n",
9370                         p_end_y, l_image->y1);
9371                 p_j2k->m_specific_param.m_decoder.m_end_tile_y = l_cp->th;
9372                 p_image->y1 = l_image->y1;
9373         }
9374         else{
9375                 p_j2k->m_specific_param.m_decoder.m_end_tile_y = int_ceildiv((p_end_y - l_cp->ty0), l_cp->tdy);
9376                 p_image->y1 = p_end_y;
9377         }
9378         /* ----- */
9379
9380         p_j2k->m_specific_param.m_decoder.m_discard_tiles = 1;
9381
9382         l_img_comp = p_image->comps;
9383         for (it_comp=0; it_comp < p_image->numcomps; ++it_comp)
9384         {
9385                 OPJ_INT32 l_h,l_w;
9386
9387                 l_img_comp->x0 = int_ceildiv(p_image->x0, l_img_comp->dx);
9388                 l_img_comp->y0 = int_ceildiv(p_image->y0, l_img_comp->dy);
9389                 l_comp_x1 = int_ceildiv(p_image->x1, l_img_comp->dx);
9390                 l_comp_y1 = int_ceildiv(p_image->y1, l_img_comp->dy);
9391
9392                 l_w = int_ceildivpow2(l_comp_x1, l_img_comp->factor)
9393                                 - int_ceildivpow2(l_img_comp->x0, l_img_comp->factor);
9394                 if (l_w < 0){
9395                         opj_event_msg_v2(p_manager, EVT_ERROR,
9396                                 "Size x of the decoded component image is incorrect (comp[%d].w=%d).\n",
9397                                 it_comp, l_w);
9398                         return OPJ_FALSE;
9399                 }
9400                 l_img_comp->w = l_w;
9401
9402                 l_h = int_ceildivpow2(l_comp_y1, l_img_comp->factor)
9403                                 - int_ceildivpow2(l_img_comp->y0, l_img_comp->factor);
9404                 if (l_h < 0){
9405                         opj_event_msg_v2(p_manager, EVT_ERROR,
9406                                 "Size y of the decoded component image is incorrect (comp[%d].h=%d).\n",
9407                                 it_comp, l_h);
9408                         return OPJ_FALSE;
9409                 }
9410                 l_img_comp->h = l_h;
9411
9412                 l_img_comp++;
9413         }
9414
9415         opj_event_msg_v2( p_manager, EVT_INFO,"Setting decoding area to %d,%d,%d,%d\n",
9416                         p_image->x0, p_image->y0, p_image->x1, p_image->y1);
9417
9418
9419         return OPJ_TRUE;
9420 }
9421
9422
9423 /* ----------------------------------------------------------------------- */
9424 /* J2K / JPT decoder interface                                             */
9425 /* ----------------------------------------------------------------------- */
9426 /**
9427  * Creates a J2K decompression structure.
9428  *
9429  * @return a handle to a J2K decompressor if successful, NULL otherwise.
9430 */
9431 opj_j2k_v2_t* opj_j2k_create_decompress(void)
9432 {
9433         opj_j2k_v2_t *l_j2k = (opj_j2k_v2_t*) opj_malloc(sizeof(opj_j2k_v2_t));
9434         if (!l_j2k) {
9435                 return 00;
9436         }
9437         memset(l_j2k,0,sizeof(opj_j2k_v2_t));
9438
9439         l_j2k->m_is_decoder = 1;
9440         l_j2k->m_cp.m_is_decoder = 1;
9441
9442         l_j2k->m_specific_param.m_decoder.m_default_tcp = (opj_tcp_v2_t*) opj_malloc(sizeof(opj_tcp_v2_t));
9443         if (!l_j2k->m_specific_param.m_decoder.m_default_tcp) {
9444                 j2k_destroy(l_j2k);
9445                 return 00;
9446         }
9447         memset(l_j2k->m_specific_param.m_decoder.m_default_tcp,0,sizeof(opj_tcp_v2_t));
9448
9449         l_j2k->m_specific_param.m_decoder.m_header_data = (OPJ_BYTE *) opj_malloc(J2K_DEFAULT_HEADER_SIZE);
9450         if (! l_j2k->m_specific_param.m_decoder.m_header_data) {
9451                 j2k_destroy(l_j2k);
9452                 return 00;
9453         }
9454
9455         l_j2k->m_specific_param.m_decoder.m_header_data_size = J2K_DEFAULT_HEADER_SIZE;
9456
9457         l_j2k->m_specific_param.m_decoder.m_tile_ind_to_dec = -1 ;
9458
9459         l_j2k->m_specific_param.m_decoder.m_last_sot_read_pos = 0 ;
9460
9461         /* codestream index creation */
9462         l_j2k->cstr_index = j2k_create_cstr_index();
9463
9464                         /*(opj_codestream_index_t*) opj_malloc(sizeof(opj_codestream_index_t));
9465         if (!l_j2k->cstr_index){
9466                 j2k_destroy(l_j2k);
9467                 return NULL;
9468         }
9469
9470         l_j2k->cstr_index->marker = (opj_marker_info_t*) opj_malloc(100 * sizeof(opj_marker_info_t));
9471 */
9472
9473         /* validation list creation */
9474         l_j2k->m_validation_list = opj_procedure_list_create();
9475         if (! l_j2k->m_validation_list) {
9476                 j2k_destroy(l_j2k);
9477                 return 00;
9478         }
9479
9480         /* execution list creation */
9481         l_j2k->m_procedure_list = opj_procedure_list_create();
9482         if (! l_j2k->m_procedure_list) {
9483                 j2k_destroy(l_j2k);
9484                 return 00;
9485         }
9486
9487         return l_j2k;
9488 }
9489
9490
9491 opj_codestream_index_t* j2k_create_cstr_index(void)
9492 {
9493         opj_codestream_index_t* cstr_index = (opj_codestream_index_t*)
9494                         opj_calloc(1,sizeof(opj_codestream_index_t));
9495         if (!cstr_index)
9496                 return NULL;
9497
9498         cstr_index->maxmarknum = 100;
9499         cstr_index->marknum = 0;
9500         cstr_index->marker = (opj_marker_info_t*)
9501                         opj_calloc(cstr_index->maxmarknum, sizeof(opj_marker_info_t));
9502         if (!cstr_index-> marker)
9503                 return NULL;
9504
9505         cstr_index->tile_index = NULL;
9506
9507         return cstr_index;
9508 }
9509
9510
9511 /**
9512  * Gets the size taken by writing a SPCod or SPCoc for the given tile and component.
9513  *
9514  * @param       p_tile_no               the tile index.
9515  * @param       p_comp_no               the component being outputted.
9516  * @param       p_j2k                   the J2K codec.
9517  *
9518  * @return      the number of bytes taken by the SPCod element.
9519  */
9520 OPJ_UINT32 j2k_get_SPCod_SPCoc_size (   opj_j2k_v2_t *p_j2k,
9521                                                                                 OPJ_UINT32 p_tile_no,
9522                                                                                 OPJ_UINT32 p_comp_no )
9523 {
9524         opj_cp_v2_t *l_cp = 00;
9525         opj_tcp_v2_t *l_tcp = 00;
9526         opj_tccp_t *l_tccp = 00;
9527
9528         /* preconditions */
9529         assert(p_j2k != 00);
9530
9531         l_cp = &(p_j2k->m_cp);
9532         l_tcp = &l_cp->tcps[p_tile_no];
9533         l_tccp = &l_tcp->tccps[p_comp_no];
9534
9535         /* preconditions again */
9536         assert(p_tile_no < (l_cp->tw * l_cp->th));
9537         assert(p_comp_no < p_j2k->m_private_image->numcomps);
9538
9539         if (l_tccp->csty & J2K_CCP_CSTY_PRT) {
9540                 return 5 + l_tccp->numresolutions;
9541         }
9542         else {
9543                 return 5;
9544         }
9545 }
9546
9547 /**
9548  * Writes a SPCod or SPCoc element, i.e. the coding style of a given component of a tile.
9549  *
9550  * @param       p_comp_no       the component number to output.
9551  * @param       p_stream                        the stream to write data to.
9552  * @param       p_j2k                   J2K codec.
9553  * @param       p_manager       the user event manager.
9554  *
9555 */
9556 opj_bool j2k_write_SPCod_SPCoc( opj_j2k_v2_t *p_j2k,
9557                                                                 OPJ_UINT32 p_tile_no,
9558                                                                 OPJ_UINT32 p_comp_no,
9559                                                                 OPJ_BYTE * p_data,
9560                                                                 OPJ_UINT32 * p_header_size,
9561                                                                 struct opj_event_mgr * p_manager )
9562 {
9563         OPJ_UINT32 i;
9564         opj_cp_v2_t *l_cp = 00;
9565         opj_tcp_v2_t *l_tcp = 00;
9566         opj_tccp_t *l_tccp = 00;
9567
9568         /* preconditions */
9569         assert(p_j2k != 00);
9570         assert(p_header_size != 00);
9571         assert(p_manager != 00);
9572         assert(p_data != 00);
9573
9574         l_cp = &(p_j2k->m_cp);
9575         l_tcp = &l_cp->tcps[p_tile_no];
9576         l_tccp = &l_tcp->tccps[p_comp_no];
9577
9578         /* preconditions again */
9579         assert(p_tile_no < (l_cp->tw * l_cp->th));
9580         assert(p_comp_no <(p_j2k->m_private_image->numcomps));
9581
9582         if (*p_header_size < 5) {
9583                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error writing SPCod SPCoc element\n");
9584                 return OPJ_FALSE;
9585         }
9586
9587         opj_write_bytes(p_data,l_tccp->numresolutions - 1, 1);  /* SPcoc (D) */
9588         ++p_data;
9589
9590         opj_write_bytes(p_data,l_tccp->cblkw - 2, 1);                   /* SPcoc (E) */
9591         ++p_data;
9592
9593         opj_write_bytes(p_data,l_tccp->cblkh - 2, 1);                   /* SPcoc (F) */
9594         ++p_data;
9595
9596         opj_write_bytes(p_data,l_tccp->cblksty, 1);                             /* SPcoc (G) */
9597         ++p_data;
9598
9599         opj_write_bytes(p_data,l_tccp->qmfbid, 1);                              /* SPcoc (H) */
9600         ++p_data;
9601
9602         *p_header_size = *p_header_size - 5;
9603
9604         if (l_tccp->csty & J2K_CCP_CSTY_PRT) {
9605
9606                 if (*p_header_size < l_tccp->numresolutions) {
9607                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error writting SPCod SPCoc element\n");
9608                         return OPJ_FALSE;
9609                 }
9610
9611                 for (i = 0; i < l_tccp->numresolutions; ++i) {
9612                         opj_write_bytes(p_data,l_tccp->prcw[i] + (l_tccp->prch[i] << 4), 1);    /* SPcoc (I_i) */
9613                         ++p_data;
9614                 }
9615
9616                 *p_header_size = *p_header_size - l_tccp->numresolutions;
9617         }
9618
9619         return OPJ_TRUE;
9620 }
9621
9622 /**
9623  * Reads a SPCod or SPCoc element, i.e. the coding style of a given component of a tile.
9624  * @param       p_header_data   the data contained in the COM box.
9625  * @param       p_j2k                   the jpeg2000 codec.
9626  * @param       p_header_size   the size of the data contained in the COM marker.
9627  * @param       p_manager               the user event manager.
9628 */
9629 opj_bool j2k_read_SPCod_SPCoc(
9630                                                     opj_j2k_v2_t *p_j2k,
9631                                                         OPJ_UINT32 compno,
9632                                                         OPJ_BYTE * p_header_data,
9633                                                         OPJ_UINT32 * p_header_size,
9634                                                         struct opj_event_mgr * p_manager
9635                                                         )
9636 {
9637         OPJ_UINT32 i, l_tmp;
9638         opj_cp_v2_t *l_cp = NULL;
9639         opj_tcp_v2_t *l_tcp = NULL;
9640         opj_tccp_t *l_tccp = NULL;
9641         OPJ_BYTE * l_current_ptr = NULL;
9642
9643         /* preconditions */
9644         assert(p_j2k != 00);
9645         assert(p_manager != 00);
9646         assert(p_header_data != 00);
9647
9648         l_cp = &(p_j2k->m_cp);
9649         l_tcp = (p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH) ?
9650                                 &l_cp->tcps[p_j2k->m_current_tile_number] :
9651                                 p_j2k->m_specific_param.m_decoder.m_default_tcp;
9652
9653         /* precondition again */
9654         assert(compno < p_j2k->m_private_image->numcomps);
9655
9656         l_tccp = &l_tcp->tccps[compno];
9657         l_current_ptr = p_header_data;
9658
9659         /* make sure room is sufficient */
9660         if (*p_header_size < 5) {
9661                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading SPCod SPCoc element\n");
9662                 return OPJ_FALSE;
9663         }
9664
9665         opj_read_bytes(l_current_ptr, &l_tccp->numresolutions ,1);              /* SPcox (D) */
9666         ++l_tccp->numresolutions;                                                                               /* tccp->numresolutions = read() + 1 */
9667         ++l_current_ptr;
9668
9669         /* If user wants to remove more resolutions than the codestream contains, return error */
9670         if (l_cp->m_specific_param.m_dec.m_reduce >= l_tccp->numresolutions) {
9671                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error decoding component %d.\nThe number of resolutions to remove is higher than the number "
9672                                         "of resolutions of this component\nModify the cp_reduce parameter.\n\n", compno);
9673                 p_j2k->m_specific_param.m_decoder.m_state |= 0x8000;/* FIXME J2K_DEC_STATE_ERR;*/
9674                 return OPJ_FALSE;
9675         }
9676
9677         opj_read_bytes(l_current_ptr,&l_tccp->cblkw ,1);                /* SPcoc (E) */
9678         ++l_current_ptr;
9679         l_tccp->cblkw += 2;
9680
9681         opj_read_bytes(l_current_ptr,&l_tccp->cblkh ,1);                /* SPcoc (F) */
9682         ++l_current_ptr;
9683         l_tccp->cblkh += 2;
9684
9685         opj_read_bytes(l_current_ptr,&l_tccp->cblksty ,1);              /* SPcoc (G) */
9686         ++l_current_ptr;
9687
9688         opj_read_bytes(l_current_ptr,&l_tccp->qmfbid ,1);               /* SPcoc (H) */
9689         ++l_current_ptr;
9690
9691         *p_header_size = *p_header_size - 5;
9692
9693         /* use custom precinct size ? */
9694         if (l_tccp->csty & J2K_CCP_CSTY_PRT) {
9695                 if (*p_header_size < l_tccp->numresolutions) {
9696                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading SPCod SPCoc element\n");
9697                         return OPJ_FALSE;
9698                 }
9699
9700                 for     (i = 0; i < l_tccp->numresolutions; ++i) {
9701                         opj_read_bytes(l_current_ptr,&l_tmp ,1);                /* SPcoc (I_i) */
9702                         ++l_current_ptr;
9703                         l_tccp->prcw[i] = l_tmp & 0xf;
9704                         l_tccp->prch[i] = l_tmp >> 4;
9705                 }
9706
9707                 *p_header_size = *p_header_size - l_tccp->numresolutions;
9708         }
9709         else {
9710                 /* set default size for the precinct width and height */
9711                 for     (i = 0; i < l_tccp->numresolutions; ++i) {
9712                         l_tccp->prcw[i] = 15;
9713                         l_tccp->prch[i] = 15;
9714                 }
9715         }
9716
9717 #ifdef WIP_REMOVE_MSD
9718         /* INDEX >> */
9719         if (p_j2k->cstr_info && compno == 0) {
9720                 OPJ_UINT32 l_data_size = l_tccp->numresolutions * sizeof(OPJ_UINT32);
9721
9722                 p_j2k->cstr_info->tile[p_j2k->m_current_tile_number].tccp_info[compno].cblkh = l_tccp->cblkh;
9723                 p_j2k->cstr_info->tile[p_j2k->m_current_tile_number].tccp_info[compno].cblkw = l_tccp->cblkw;
9724                 p_j2k->cstr_info->tile[p_j2k->m_current_tile_number].tccp_info[compno].numresolutions = l_tccp->numresolutions;
9725                 p_j2k->cstr_info->tile[p_j2k->m_current_tile_number].tccp_info[compno].cblksty = l_tccp->cblksty;
9726                 p_j2k->cstr_info->tile[p_j2k->m_current_tile_number].tccp_info[compno].qmfbid = l_tccp->qmfbid;
9727
9728
9729                 memcpy(p_j2k->cstr_info->tile[p_j2k->m_current_tile_number].pdx,l_tccp->prcw, l_data_size);
9730                 memcpy(p_j2k->cstr_info->tile[p_j2k->m_current_tile_number].pdy,l_tccp->prch, l_data_size);
9731         }
9732         /* << INDEX */
9733 #endif
9734
9735         return OPJ_TRUE;
9736 }
9737
9738 /**
9739  * Copies the tile component parameters of all the component from the first tile component.
9740  *
9741  * @param               p_j2k           the J2k codec.
9742  */
9743 void j2k_copy_tile_component_parameters( opj_j2k_v2_t *p_j2k )
9744 {
9745         /* loop */
9746         OPJ_UINT32 i;
9747         opj_cp_v2_t *l_cp = NULL;
9748         opj_tcp_v2_t *l_tcp = NULL;
9749         opj_tccp_t *l_ref_tccp = NULL, *l_copied_tccp = NULL;
9750         OPJ_UINT32 l_prc_size;
9751
9752         /* preconditions */
9753         assert(p_j2k != 00);
9754
9755         l_cp = &(p_j2k->m_cp);
9756         l_tcp = (p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH) ? /* FIXME J2K_DEC_STATE_TPH*/
9757                                 &l_cp->tcps[p_j2k->m_current_tile_number] :
9758                                 p_j2k->m_specific_param.m_decoder.m_default_tcp;
9759
9760         l_ref_tccp = &l_tcp->tccps[0];
9761         l_copied_tccp = l_ref_tccp + 1;
9762         l_prc_size = l_ref_tccp->numresolutions * sizeof(OPJ_UINT32);
9763
9764         for     (i=1; i<p_j2k->m_private_image->numcomps; ++i) {
9765                 l_copied_tccp->numresolutions = l_ref_tccp->numresolutions;
9766                 l_copied_tccp->cblkw = l_ref_tccp->cblkw;
9767                 l_copied_tccp->cblkh = l_ref_tccp->cblkh;
9768                 l_copied_tccp->cblksty = l_ref_tccp->cblksty;
9769                 l_copied_tccp->qmfbid = l_ref_tccp->qmfbid;
9770                 memcpy(l_copied_tccp->prcw,l_ref_tccp->prcw,l_prc_size);
9771                 memcpy(l_copied_tccp->prch,l_ref_tccp->prch,l_prc_size);
9772                 ++l_copied_tccp;
9773         }
9774 }
9775
9776 /**
9777  * Gets the size taken by writing SQcd or SQcc element, i.e. the quantization values of a band in the QCD or QCC.
9778  *
9779  * @param       p_tile_no               the tile index.
9780  * @param       p_comp_no               the component being outputted.
9781  * @param       p_j2k                   the J2K codec.
9782  *
9783  * @return      the number of bytes taken by the SPCod element.
9784  */
9785 OPJ_UINT32 j2k_get_SQcd_SQcc_size (     opj_j2k_v2_t *p_j2k,
9786                                                                         OPJ_UINT32 p_tile_no,
9787                                                                         OPJ_UINT32 p_comp_no )
9788 {
9789         OPJ_UINT32 l_num_bands;
9790
9791         opj_cp_v2_t *l_cp = 00;
9792         opj_tcp_v2_t *l_tcp = 00;
9793         opj_tccp_t *l_tccp = 00;
9794
9795         /* preconditions */
9796         assert(p_j2k != 00);
9797
9798         l_cp = &(p_j2k->m_cp);
9799         l_tcp = &l_cp->tcps[p_tile_no];
9800         l_tccp = &l_tcp->tccps[p_comp_no];
9801
9802         /* preconditions again */
9803         assert(p_tile_no < l_cp->tw * l_cp->th);
9804         assert(p_comp_no < p_j2k->m_private_image->numcomps);
9805
9806         l_num_bands = (l_tccp->qntsty == J2K_CCP_QNTSTY_SIQNT) ? 1 : (l_tccp->numresolutions * 3 - 2);
9807
9808         if (l_tccp->qntsty == J2K_CCP_QNTSTY_NOQNT)  {
9809                 return 1 + l_num_bands;
9810         }
9811         else {
9812                 return 1 + 2*l_num_bands;
9813         }
9814 }
9815
9816 /**
9817  * Writes a SQcd or SQcc element, i.e. the quantization values of a band.
9818  *
9819  * @param       p_tile_no               the tile to output.
9820  * @param       p_comp_no               the component number to output.
9821  * @param       p_data                  the data buffer.
9822  * @param       p_header_size   pointer to the size of the data buffer, it is changed by the function.
9823  * @param       p_j2k                           J2K codec.
9824  * @param       p_manager               the user event manager.
9825  *
9826 */
9827 opj_bool j2k_write_SQcd_SQcc(   opj_j2k_v2_t *p_j2k,
9828                                                                 OPJ_UINT32 p_tile_no,
9829                                                                 OPJ_UINT32 p_comp_no,
9830                                                                 OPJ_BYTE * p_data,
9831                                                                 OPJ_UINT32 * p_header_size,
9832                                                                 struct opj_event_mgr * p_manager )
9833 {
9834         OPJ_UINT32 l_header_size;
9835         OPJ_UINT32 l_band_no, l_num_bands;
9836         OPJ_UINT32 l_expn,l_mant;
9837
9838         opj_cp_v2_t *l_cp = 00;
9839         opj_tcp_v2_t *l_tcp = 00;
9840         opj_tccp_t *l_tccp = 00;
9841
9842         /* preconditions */
9843         assert(p_j2k != 00);
9844         assert(p_header_size != 00);
9845         assert(p_manager != 00);
9846         assert(p_data != 00);
9847
9848         l_cp = &(p_j2k->m_cp);
9849         l_tcp = &l_cp->tcps[p_tile_no];
9850         l_tccp = &l_tcp->tccps[p_comp_no];
9851
9852         /* preconditions again */
9853         assert(p_tile_no < l_cp->tw * l_cp->th);
9854         assert(p_comp_no <p_j2k->m_private_image->numcomps);
9855
9856         l_num_bands = (l_tccp->qntsty == J2K_CCP_QNTSTY_SIQNT) ? 1 : (l_tccp->numresolutions * 3 - 2);
9857
9858         if (l_tccp->qntsty == J2K_CCP_QNTSTY_NOQNT)  {
9859                 l_header_size = 1 + l_num_bands;
9860
9861                 if (*p_header_size < l_header_size) {
9862                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error writing SQcd SQcc element\n");
9863                         return OPJ_FALSE;
9864                 }
9865
9866                 opj_write_bytes(p_data,l_tccp->qntsty + (l_tccp->numgbits << 5), 1);    /* Sqcx */
9867                 ++p_data;
9868
9869                 for (l_band_no = 0; l_band_no < l_num_bands; ++l_band_no) {
9870                         l_expn = l_tccp->stepsizes[l_band_no].expn;
9871                         opj_write_bytes(p_data, l_expn << 3, 1);        /* SPqcx_i */
9872                         ++p_data;
9873                 }
9874         }
9875         else {
9876                 l_header_size = 1 + 2*l_num_bands;
9877
9878                 if (*p_header_size < l_header_size) {
9879                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error writing SQcd SQcc element\n");
9880                         return OPJ_FALSE;
9881                 }
9882
9883                 opj_write_bytes(p_data,l_tccp->qntsty + (l_tccp->numgbits << 5), 1);    /* Sqcx */
9884                 ++p_data;
9885
9886                 for (l_band_no = 0; l_band_no < l_num_bands; ++l_band_no) {
9887                         l_expn = l_tccp->stepsizes[l_band_no].expn;
9888                         l_mant = l_tccp->stepsizes[l_band_no].mant;
9889
9890                         opj_write_bytes(p_data, (l_expn << 11) + l_mant, 2);    /* SPqcx_i */
9891                         p_data += 2;
9892                 }
9893         }
9894
9895         *p_header_size = *p_header_size - l_header_size;
9896
9897         return OPJ_TRUE;
9898 }
9899
9900 /**
9901  * Reads a SQcd or SQcc element, i.e. the quantization values of a band.
9902  *
9903  * @param       p_comp_no               the component being targeted.
9904  * @param       p_header_data   the data contained in the COM box.
9905  * @param       p_j2k                   the jpeg2000 codec.
9906  * @param       p_header_size   the size of the data contained in the COM marker.
9907  * @param       p_manager               the user event manager.
9908 */
9909 opj_bool j2k_read_SQcd_SQcc(
9910                                                         opj_j2k_v2_t *p_j2k,
9911                                                         OPJ_UINT32 p_comp_no,
9912                                                         OPJ_BYTE* p_header_data,
9913                                                         OPJ_UINT32 * p_header_size,
9914                                                         struct opj_event_mgr * p_manager
9915                                                         )
9916 {
9917         /* loop*/
9918         OPJ_UINT32 l_band_no;
9919         opj_cp_v2_t *l_cp = 00;
9920         opj_tcp_v2_t *l_tcp = 00;
9921         opj_tccp_t *l_tccp = 00;
9922         OPJ_BYTE * l_current_ptr = 00;
9923         OPJ_UINT32 l_tmp, l_num_band;
9924
9925         /* preconditions*/
9926         assert(p_j2k != 00);
9927         assert(p_manager != 00);
9928         assert(p_header_data != 00);
9929
9930         l_cp = &(p_j2k->m_cp);
9931         /* come from tile part header or main header ?*/
9932         l_tcp = (p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH) ? /*FIXME J2K_DEC_STATE_TPH*/
9933                                 &l_cp->tcps[p_j2k->m_current_tile_number] :
9934                                 p_j2k->m_specific_param.m_decoder.m_default_tcp;
9935
9936         /* precondition again*/
9937         assert(p_comp_no <  p_j2k->m_private_image->numcomps);
9938
9939         l_tccp = &l_tcp->tccps[p_comp_no];
9940         l_current_ptr = p_header_data;
9941
9942         if (*p_header_size < 1) {
9943                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error reading SQcd or SQcc element\n");
9944                 return OPJ_FALSE;
9945         }
9946         *p_header_size -= 1;
9947
9948         opj_read_bytes(l_current_ptr, &l_tmp ,1);                       /* Sqcx */
9949         ++l_current_ptr;
9950
9951         l_tccp->qntsty = l_tmp & 0x1f;
9952         l_tccp->numgbits = l_tmp >> 5;
9953         if (l_tccp->qntsty == J2K_CCP_QNTSTY_SIQNT) {
9954         l_num_band = 1;
9955         }
9956         else {
9957                 l_num_band = (l_tccp->qntsty == J2K_CCP_QNTSTY_NOQNT) ?
9958                         (*p_header_size) :
9959                         (*p_header_size) / 2;
9960
9961                 if( l_num_band > J2K_MAXBANDS ) {
9962                         opj_event_msg_v2(p_manager, EVT_WARNING, "While reading CCP_QNTSTY element inside QCD or QCC marker segment, "
9963                                 "number of subbands (%d) is greater to J2K_MAXBANDS (%d). So we limit the number of elements stored to "
9964                                 "J2K_MAXBANDS (%d) and skip the rest. \n", l_num_band, J2K_MAXBANDS, J2K_MAXBANDS);
9965                         /*return OPJ_FALSE;*/
9966                 }
9967         }
9968
9969 #ifdef USE_JPWL
9970         if (l_cp->correct) {
9971
9972                 /* if JPWL is on, we check whether there are too many subbands */
9973                 if (/*(l_num_band < 0) ||*/ (l_num_band >= J2K_MAXBANDS)) {
9974                         opj_event_msg_v2(p_manager, JPWL_ASSUME ? EVT_WARNING : EVT_ERROR,
9975                                 "JPWL: bad number of subbands in Sqcx (%d)\n",
9976                                 l_num_band);
9977                         if (!JPWL_ASSUME) {
9978                                 opj_event_msg_v2(p_manager, EVT_ERROR, "JPWL: giving up\n");
9979                                 return OPJ_FALSE;
9980                         }
9981                         /* we try to correct */
9982                         l_num_band = 1;
9983                         opj_event_msg_v2(p_manager, EVT_WARNING, "- trying to adjust them\n"
9984                                 "- setting number of bands to %d => HYPOTHESIS!!!\n",
9985                                 l_num_band);
9986                 };
9987
9988         };
9989 #endif /* USE_JPWL */
9990
9991         if (l_tccp->qntsty == J2K_CCP_QNTSTY_NOQNT) {
9992                 for     (l_band_no = 0; l_band_no < l_num_band; l_band_no++) {
9993                         opj_read_bytes(l_current_ptr, &l_tmp ,1);                       /* SPqcx_i */
9994                         ++l_current_ptr;
9995                         if (l_band_no < J2K_MAXBANDS){
9996                                 l_tccp->stepsizes[l_band_no].expn = l_tmp>>3;
9997                                 l_tccp->stepsizes[l_band_no].mant = 0;
9998                         }
9999                 }
10000                 *p_header_size = *p_header_size - l_num_band;
10001         }
10002         else {
10003                 for     (l_band_no = 0; l_band_no < l_num_band; l_band_no++) {
10004                         opj_read_bytes(l_current_ptr, &l_tmp ,2);                       /* SPqcx_i */
10005                         l_current_ptr+=2;
10006                         if (l_band_no < J2K_MAXBANDS){
10007                                 l_tccp->stepsizes[l_band_no].expn = l_tmp >> 11;
10008                                 l_tccp->stepsizes[l_band_no].mant = l_tmp & 0x7ff;
10009                         }
10010                 }
10011                 *p_header_size = *p_header_size - 2*l_num_band;
10012         }
10013
10014         /* Add Antonin : if scalar_derived -> compute other stepsizes */
10015         if (l_tccp->qntsty == J2K_CCP_QNTSTY_SIQNT) {
10016                 for (l_band_no = 1; l_band_no < J2K_MAXBANDS; l_band_no++) {
10017                         l_tccp->stepsizes[l_band_no].expn =
10018                                 ((l_tccp->stepsizes[0].expn) - ((l_band_no - 1) / 3) > 0) ?
10019                                         (l_tccp->stepsizes[0].expn) - ((l_band_no - 1) / 3) : 0;
10020                         l_tccp->stepsizes[l_band_no].mant = l_tccp->stepsizes[0].mant;
10021                 }
10022         }
10023
10024         return OPJ_TRUE;
10025 }
10026
10027 /**
10028  * Copies the tile component parameters of all the component from the first tile component.
10029  *
10030  * @param               p_j2k           the J2k codec.
10031  */
10032 void j2k_copy_tile_quantization_parameters( opj_j2k_v2_t *p_j2k )
10033 {
10034         OPJ_UINT32 i;
10035         opj_cp_v2_t *l_cp = NULL;
10036         opj_tcp_v2_t *l_tcp = NULL;
10037         opj_tccp_t *l_ref_tccp = NULL;
10038         opj_tccp_t *l_copied_tccp = NULL;
10039         OPJ_UINT32 l_size;
10040
10041         /* preconditions */
10042         assert(p_j2k != 00);
10043
10044         l_cp = &(p_j2k->m_cp);
10045         l_tcp = p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_TPH ?
10046                         &l_cp->tcps[p_j2k->m_current_tile_number] :
10047                         p_j2k->m_specific_param.m_decoder.m_default_tcp;
10048
10049         l_ref_tccp = &l_tcp->tccps[0];
10050         l_copied_tccp = l_ref_tccp + 1;
10051         l_size = J2K_MAXBANDS * sizeof(opj_stepsize_t);
10052
10053         for     (i=1;i<p_j2k->m_private_image->numcomps;++i) {
10054                 l_copied_tccp->qntsty = l_ref_tccp->qntsty;
10055                 l_copied_tccp->numgbits = l_ref_tccp->numgbits;
10056                 memcpy(l_copied_tccp->stepsizes,l_ref_tccp->stepsizes,l_size);
10057                 ++l_copied_tccp;
10058         }
10059 }
10060
10061 /**
10062  * Dump some elements from the J2K decompression structure .
10063  *
10064  *@param p_j2k                          the jpeg2000 codec.
10065  *@param flag                           flag to describe what elments are dump.
10066  *@param out_stream                     output stream where dump the elements.
10067  *
10068 */
10069 void j2k_dump (opj_j2k_v2_t* p_j2k, OPJ_INT32 flag, FILE* out_stream)
10070 {
10071         /* Check if the flag is compatible with j2k file*/
10072         if ( (flag & OPJ_JP2_INFO) || (flag & OPJ_JP2_IND)){
10073                 fprintf(out_stream, "Wrong flag\n");
10074                 return;
10075         }
10076
10077         /* Dump the image_header */
10078         if (flag & OPJ_IMG_INFO){
10079                 if (p_j2k->m_private_image)
10080                         j2k_dump_image_header(p_j2k->m_private_image, 0, out_stream);
10081         }
10082
10083         /* Dump the codestream info from main header */
10084         if (flag & OPJ_J2K_MH_INFO){
10085                 j2k_dump_MH_info(p_j2k, out_stream);
10086         }
10087
10088
10089         /* Dump the codestream info of the current tile */
10090         if (flag & OPJ_J2K_TH_INFO){
10091
10092         }
10093
10094         /* Dump the codestream index from main header */
10095         if (flag & OPJ_J2K_MH_IND){
10096                 j2k_dump_MH_index(p_j2k, out_stream);
10097         }
10098
10099         /* Dump the codestream index of the current tile */
10100         if (flag & OPJ_J2K_TH_IND){
10101
10102         }
10103
10104 }
10105
10106 /**
10107  * Dump index elements of the codestream extract from the main header.
10108  *
10109  *@param p_j2k                          the jpeg2000 codec.
10110  *@param out_stream                     output stream where dump the elements.
10111  *
10112 */
10113 void j2k_dump_MH_index(opj_j2k_v2_t* p_j2k, FILE* out_stream)
10114 {
10115         opj_codestream_index_t* cstr_index = p_j2k->cstr_index;
10116         OPJ_UINT32 it_marker, it_tile, it_tile_part;
10117
10118         fprintf(out_stream, "Codestream index from main header: {\n");
10119
10120         fprintf(out_stream, "\t Main header start position=%" PRIi64 "\n"
10121                                     "\t Main header end position=%" PRIi64 "\n",
10122                         cstr_index->main_head_start, cstr_index->main_head_end);
10123
10124         fprintf(out_stream, "\t Marker list: {\n");
10125
10126         if (cstr_index->marker){
10127                 for (it_marker=0; it_marker < cstr_index->marknum ; it_marker++){
10128                         fprintf(out_stream, "\t\t type=%#x, pos=%" PRIi64 ", len=%d\n",
10129                                         cstr_index->marker[it_marker].type,
10130                                         cstr_index->marker[it_marker].pos,
10131                                         cstr_index->marker[it_marker].len );
10132                 }
10133         }
10134
10135         fprintf(out_stream, "\t }\n");
10136
10137
10138         if (cstr_index->tile_index){
10139
10140         /* Simple test to avoid to write empty information*/
10141         OPJ_UINT32 l_acc_nb_of_tile_part = 0;
10142         for (it_tile=0; it_tile < cstr_index->nb_of_tiles ; it_tile++){
10143                         l_acc_nb_of_tile_part += cstr_index->tile_index[it_tile].nb_tps;
10144         }
10145
10146         if (l_acc_nb_of_tile_part)
10147         {
10148             fprintf(out_stream, "\t Tile index: {\n");
10149        
10150                     for (it_tile=0; it_tile < cstr_index->nb_of_tiles ; it_tile++){
10151                             OPJ_UINT32 nb_of_tile_part = cstr_index->tile_index[it_tile].nb_tps;
10152
10153                             fprintf(out_stream, "\t\t nb of tile-part in tile [%d]=%d\n", it_tile, nb_of_tile_part);
10154
10155                             if (cstr_index->tile_index[it_tile].tp_index){
10156                                     for (it_tile_part =0; it_tile_part < nb_of_tile_part; it_tile_part++){
10157                                             fprintf(out_stream, "\t\t\t tile-part[%d]: star_pos=%" PRIi64 ", end_header=%" PRIi64 ", end_pos=%" PRIi64 ".\n",
10158                                                             it_tile_part,
10159                                                             cstr_index->tile_index[it_tile].tp_index[it_tile_part].start_pos,
10160                                                             cstr_index->tile_index[it_tile].tp_index[it_tile_part].end_header,
10161                                                             cstr_index->tile_index[it_tile].tp_index[it_tile_part].end_pos);
10162                                     }
10163                             }
10164
10165                             if (cstr_index->tile_index[it_tile].marker){
10166                                     for (it_marker=0; it_marker < cstr_index->tile_index[it_tile].marknum ; it_marker++){
10167                                             fprintf(out_stream, "\t\t type=%#x, pos=%" PRIi64 ", len=%d\n",
10168                                                             cstr_index->tile_index[it_tile].marker[it_marker].type,
10169                                                             cstr_index->tile_index[it_tile].marker[it_marker].pos,
10170                                                             cstr_index->tile_index[it_tile].marker[it_marker].len );
10171                                     }
10172                             }
10173                     }
10174                     fprintf(out_stream,"\t }\n");
10175         }
10176         }
10177
10178         fprintf(out_stream,"}\n");
10179
10180 }
10181
10182 /**
10183  * Dump info elements of the codestream extract from the main header.
10184  *
10185  *@param p_j2k                          the jpeg2000 codec.
10186  *@param out_stream                     output stream where dump the elements.
10187  *
10188 */
10189 void j2k_dump_MH_info(opj_j2k_v2_t* p_j2k, FILE* out_stream)
10190 {
10191         opj_tcp_v2_t * l_default_tile=NULL;
10192
10193         fprintf(out_stream, "Codestream info from main header: {\n");
10194
10195         fprintf(out_stream, "\t tx0=%d, ty0=%d\n", p_j2k->m_cp.tx0, p_j2k->m_cp.ty0);
10196         fprintf(out_stream, "\t tdx=%d, tdy=%d\n", p_j2k->m_cp.tdx, p_j2k->m_cp.tdy);
10197         fprintf(out_stream, "\t tw=%d, th=%d\n", p_j2k->m_cp.tw, p_j2k->m_cp.th);
10198
10199         l_default_tile = p_j2k->m_specific_param.m_decoder.m_default_tcp;
10200         if (l_default_tile)
10201         {
10202                 OPJ_INT32 compno;
10203                 OPJ_INT32 numcomps = p_j2k->m_private_image->numcomps;
10204
10205                 fprintf(out_stream, "\t default tile {\n");
10206                 fprintf(out_stream, "\t\t csty=%#x\n", l_default_tile->csty);
10207                 fprintf(out_stream, "\t\t prg=%#x\n", l_default_tile->prg);
10208                 fprintf(out_stream, "\t\t numlayers=%d\n", l_default_tile->numlayers);
10209                 fprintf(out_stream, "\t\t mct=%x\n", l_default_tile->mct);
10210
10211                 for (compno = 0; compno < numcomps; compno++) {
10212                         opj_tccp_t *l_tccp = &(l_default_tile->tccps[compno]);
10213                         OPJ_UINT32 resno;
10214       OPJ_INT32 bandno, numbands;
10215
10216                         /* coding style*/
10217                         fprintf(out_stream, "\t\t comp %d {\n", compno);
10218                         fprintf(out_stream, "\t\t\t csty=%#x\n", l_tccp->csty);
10219                         fprintf(out_stream, "\t\t\t numresolutions=%d\n", l_tccp->numresolutions);
10220                         fprintf(out_stream, "\t\t\t cblkw=2^%d\n", l_tccp->cblkw);
10221                         fprintf(out_stream, "\t\t\t cblkh=2^%d\n", l_tccp->cblkh);
10222                         fprintf(out_stream, "\t\t\t cblksty=%#x\n", l_tccp->cblksty);
10223                         fprintf(out_stream, "\t\t\t qmfbid=%d\n", l_tccp->qmfbid);
10224
10225                         fprintf(out_stream, "\t\t\t preccintsize (w,h)=");
10226                         for (resno = 0; resno < l_tccp->numresolutions; resno++) {
10227                                 fprintf(out_stream, "(%d,%d) ", l_tccp->prcw[resno], l_tccp->prch[resno]);
10228                         }
10229                         fprintf(out_stream, "\n");
10230
10231                         /* quantization style*/
10232                         fprintf(out_stream, "\t\t\t qntsty=%d\n", l_tccp->qntsty);
10233                         fprintf(out_stream, "\t\t\t numgbits=%d\n", l_tccp->numgbits);
10234                         fprintf(out_stream, "\t\t\t stepsizes (m,e)=");
10235                         numbands = (l_tccp->qntsty == J2K_CCP_QNTSTY_SIQNT) ? 1 : l_tccp->numresolutions * 3 - 2;
10236                         for (bandno = 0; bandno < numbands; bandno++) {
10237                                 fprintf(out_stream, "(%d,%d) ", l_tccp->stepsizes[bandno].mant,
10238                                         l_tccp->stepsizes[bandno].expn);
10239                         }
10240                         fprintf(out_stream, "\n");
10241
10242                         /* RGN value*/
10243                         fprintf(out_stream, "\t\t\t roishift=%d\n", l_tccp->roishift);
10244
10245                         fprintf(out_stream, "\t\t }\n");
10246                 } /*end of component of default tile*/
10247                 fprintf(out_stream, "\t }\n"); /*end of default tile*/
10248
10249         }
10250
10251         fprintf(out_stream, "}\n");
10252
10253 }
10254
10255 /**
10256  * Dump an image header structure.
10257  *
10258  *@param img_header                     the image header to dump.
10259  *@param dev_dump_flag          flag to describe if we are in the case of this function is use outside j2k_dump function
10260  *@param out_stream                     output stream where dump the elements.
10261  */
10262 void j2k_dump_image_header(opj_image_t* img_header, opj_bool dev_dump_flag, FILE* out_stream)
10263 {
10264         char tab[2];
10265
10266         if (dev_dump_flag){
10267                 fprintf(stdout, "[DEV] Dump an image_header struct {\n");
10268                 tab[0] = '\0';
10269         }
10270         else {
10271                 fprintf(out_stream, "Image info {\n");
10272                 tab[0] = '\t';tab[1] = '\0';
10273         }
10274
10275         fprintf(out_stream, "%s x0=%d, y0=%d\n", tab, img_header->x0, img_header->y0);
10276         fprintf(out_stream,     "%s x1=%d, y1=%d\n", tab, img_header->x1, img_header->y1);
10277         fprintf(out_stream, "%s numcomps=%d\n", tab, img_header->numcomps);
10278
10279         if (img_header->comps){
10280                 OPJ_UINT32 compno;
10281                 for (compno = 0; compno < img_header->numcomps; compno++) {
10282                         fprintf(out_stream, "%s\t component %d {\n", tab, compno);
10283                         j2k_dump_image_comp_header(&(img_header->comps[compno]), dev_dump_flag, out_stream);
10284                         fprintf(out_stream,"%s}\n",tab);
10285                 }
10286         }
10287
10288         fprintf(out_stream, "}\n");
10289 }
10290
10291 /**
10292  * Dump a component image header structure.
10293  *
10294  *@param comp_header            the component image header to dump.
10295  *@param dev_dump_flag          flag to describe if we are in the case of this function is use outside j2k_dump function
10296  *@param out_stream                     output stream where dump the elements.
10297  */
10298 void j2k_dump_image_comp_header(opj_image_comp_t* comp_header, opj_bool dev_dump_flag, FILE* out_stream)
10299 {
10300         char tab[3];
10301
10302         if (dev_dump_flag){
10303                 fprintf(stdout, "[DEV] Dump an image_comp_header struct {\n");
10304                 tab[0] = '\0';
10305         }       else {
10306                 tab[0] = '\t';tab[1] = '\t';tab[2] = '\0';
10307         }
10308
10309         fprintf(out_stream, "%s dx=%d, dy=%d\n", tab, comp_header->dx, comp_header->dy);
10310         fprintf(out_stream, "%s prec=%d\n", tab, comp_header->prec);
10311         fprintf(out_stream, "%s sgnd=%d\n", tab, comp_header->sgnd);
10312
10313         if (dev_dump_flag)
10314                 fprintf(out_stream, "}\n");
10315 }
10316
10317
10318 /**
10319  * Get the codestream info from a JPEG2000 codec.
10320  *
10321  *@param        p_j2k                           the component image header to dump.
10322  *
10323  *@return       the codestream information extract from the jpg2000 codec
10324  */
10325 opj_codestream_info_v2_t* j2k_get_cstr_info(opj_j2k_v2_t* p_j2k)
10326 {
10327         OPJ_UINT16 compno;
10328         OPJ_UINT16 numcomps = p_j2k->m_private_image->numcomps;
10329         opj_tcp_v2_t *l_default_tile;
10330         opj_codestream_info_v2_t* cstr_info = (opj_codestream_info_v2_t*) opj_calloc(1,sizeof(opj_codestream_info_v2_t));
10331
10332         cstr_info->nbcomps = p_j2k->m_private_image->numcomps;
10333
10334         cstr_info->tx0 = p_j2k->m_cp.tx0;
10335         cstr_info->ty0 = p_j2k->m_cp.ty0;
10336         cstr_info->tdx = p_j2k->m_cp.tdx;
10337         cstr_info->tdy = p_j2k->m_cp.tdy;
10338         cstr_info->tw = p_j2k->m_cp.tw;
10339         cstr_info->th = p_j2k->m_cp.th;
10340
10341         cstr_info->tile_info = NULL; /* Not fill from the main header*/
10342
10343         l_default_tile = p_j2k->m_specific_param.m_decoder.m_default_tcp;
10344
10345         cstr_info->m_default_tile_info.csty = l_default_tile->csty;
10346         cstr_info->m_default_tile_info.prg = l_default_tile->prg;
10347         cstr_info->m_default_tile_info.numlayers = l_default_tile->numlayers;
10348         cstr_info->m_default_tile_info.mct = l_default_tile->mct;
10349
10350         cstr_info->m_default_tile_info.tccp_info = (opj_tccp_info_t*) opj_calloc(cstr_info->nbcomps, sizeof(opj_tccp_info_t));
10351
10352         for (compno = 0; compno < numcomps; compno++) {
10353                 opj_tccp_t *l_tccp = &(l_default_tile->tccps[compno]);
10354                 opj_tccp_info_t *l_tccp_info = &(cstr_info->m_default_tile_info.tccp_info[compno]);
10355                 OPJ_INT32 bandno, numbands;
10356
10357                 /* coding style*/
10358                 l_tccp_info->csty = l_tccp->csty;
10359                 l_tccp_info->numresolutions = l_tccp->numresolutions;
10360                 l_tccp_info->cblkw = l_tccp->cblkw;
10361                 l_tccp_info->cblkh = l_tccp->cblkh;
10362                 l_tccp_info->cblksty = l_tccp->cblksty;
10363                 l_tccp_info->qmfbid = l_tccp->qmfbid;
10364                 if (l_tccp->numresolutions < J2K_MAXRLVLS)
10365                 {
10366                         memcpy(l_tccp_info->prch, l_tccp->prch, l_tccp->numresolutions);
10367                         memcpy(l_tccp_info->prcw, l_tccp->prcw, l_tccp->numresolutions);
10368                 }
10369
10370                 /* quantization style*/
10371                 l_tccp_info->qntsty = l_tccp->qntsty;
10372                 l_tccp_info->numgbits = l_tccp->numgbits;
10373
10374                 numbands = (l_tccp->qntsty == J2K_CCP_QNTSTY_SIQNT) ? 1 : l_tccp->numresolutions * 3 - 2;
10375                 if (numbands < J2K_MAXBANDS) {
10376                         for (bandno = 0; bandno < numbands; bandno++) {
10377                                 l_tccp_info->stepsizes_mant[bandno] = l_tccp->stepsizes[bandno].mant;
10378                                 l_tccp_info->stepsizes_expn[bandno] = l_tccp->stepsizes[bandno].expn;
10379                         }
10380                 }
10381
10382                 /* RGN value*/
10383                 l_tccp_info->roishift = l_tccp->roishift;
10384         }
10385
10386
10387         return cstr_info;
10388 }
10389
10390 /**
10391  * Get the codestream index from a JPEG2000 codec.
10392  *
10393  *@param        p_j2k                           the component image header to dump.
10394  *
10395  *@return       the codestream index extract from the jpg2000 codec
10396  */
10397 opj_codestream_index_t* j2k_get_cstr_index(opj_j2k_v2_t* p_j2k)
10398 {
10399         opj_codestream_index_t* l_cstr_index = (opj_codestream_index_t*)
10400                         opj_calloc(1,sizeof(opj_codestream_index_t));
10401         if (!l_cstr_index)
10402                 return NULL;
10403
10404         l_cstr_index->main_head_start = p_j2k->cstr_index->main_head_start;
10405         l_cstr_index->main_head_end = p_j2k->cstr_index->main_head_end;
10406         l_cstr_index->codestream_size = p_j2k->cstr_index->codestream_size;
10407
10408         l_cstr_index->marknum = p_j2k->cstr_index->marknum;
10409         l_cstr_index->marker = (opj_marker_info_t*)opj_malloc(l_cstr_index->marknum*sizeof(opj_marker_info_t));
10410         if (!l_cstr_index->marker){
10411                 opj_free( l_cstr_index);
10412                 return NULL;
10413         }
10414
10415         if (p_j2k->cstr_index->marker)
10416                 memcpy(l_cstr_index->marker, p_j2k->cstr_index->marker, l_cstr_index->marknum * sizeof(opj_marker_info_t) );
10417         else{
10418                 opj_free(l_cstr_index->marker);
10419                 l_cstr_index->marker = NULL;
10420         }
10421
10422         l_cstr_index->nb_of_tiles = p_j2k->cstr_index->nb_of_tiles;
10423         l_cstr_index->tile_index = (opj_tile_index_t*)opj_calloc(l_cstr_index->nb_of_tiles, sizeof(opj_tile_index_t) );
10424         if (!l_cstr_index->tile_index){
10425                 opj_free( l_cstr_index->marker);
10426                 opj_free( l_cstr_index);
10427                 return NULL;
10428         }
10429
10430         if (!p_j2k->cstr_index->tile_index){
10431                 opj_free(l_cstr_index->tile_index);
10432                 l_cstr_index->tile_index = NULL;
10433         }
10434         else {
10435                 OPJ_UINT32 it_tile = 0;
10436                 for (it_tile = 0; it_tile < l_cstr_index->nb_of_tiles; it_tile++ ){
10437
10438                         /* Tile Marker*/
10439                         l_cstr_index->tile_index[it_tile].marknum = p_j2k->cstr_index->tile_index[it_tile].marknum;
10440
10441                         l_cstr_index->tile_index[it_tile].marker =
10442                                 (opj_marker_info_t*)opj_malloc(l_cstr_index->tile_index[it_tile].marknum*sizeof(opj_marker_info_t));
10443
10444                         if (!l_cstr_index->tile_index[it_tile].marker) {
10445                                 OPJ_UINT32 it_tile_free;
10446
10447                                 for (it_tile_free=0; it_tile_free < it_tile; it_tile_free++){
10448                                         opj_free(l_cstr_index->tile_index[it_tile_free].marker);
10449                                 }
10450
10451                                 opj_free( l_cstr_index->tile_index);
10452                                 opj_free( l_cstr_index->marker);
10453                                 opj_free( l_cstr_index);
10454                                 return NULL;
10455                         }
10456
10457                         if (p_j2k->cstr_index->tile_index[it_tile].marker)
10458                                 memcpy( l_cstr_index->tile_index[it_tile].marker,
10459                                                 p_j2k->cstr_index->tile_index[it_tile].marker,
10460                                                 l_cstr_index->tile_index[it_tile].marknum * sizeof(opj_marker_info_t) );
10461                         else{
10462                                 opj_free(l_cstr_index->tile_index[it_tile].marker);
10463                                 l_cstr_index->tile_index[it_tile].marker = NULL;
10464                         }
10465
10466                         /* Tile part index*/
10467                         l_cstr_index->tile_index[it_tile].nb_tps = p_j2k->cstr_index->tile_index[it_tile].nb_tps;
10468
10469                         l_cstr_index->tile_index[it_tile].tp_index =
10470                                 (opj_tp_index_t*)opj_malloc(l_cstr_index->tile_index[it_tile].nb_tps*sizeof(opj_tp_index_t));
10471
10472                         if(!l_cstr_index->tile_index[it_tile].tp_index){
10473                                 OPJ_UINT32 it_tile_free;
10474
10475                                 for (it_tile_free=0; it_tile_free < it_tile; it_tile_free++){
10476                                         opj_free(l_cstr_index->tile_index[it_tile_free].marker);
10477                                         opj_free(l_cstr_index->tile_index[it_tile_free].tp_index);
10478                                 }
10479
10480                                 opj_free( l_cstr_index->tile_index);
10481                                 opj_free( l_cstr_index->marker);
10482                                 opj_free( l_cstr_index);
10483                                 return NULL;
10484                         }
10485
10486                         if (p_j2k->cstr_index->tile_index[it_tile].tp_index){
10487                                 memcpy( l_cstr_index->tile_index[it_tile].tp_index,
10488                                                 p_j2k->cstr_index->tile_index[it_tile].tp_index,
10489                                                 l_cstr_index->tile_index[it_tile].nb_tps * sizeof(opj_tp_index_t) );
10490                         }
10491                         else{
10492                                 opj_free(l_cstr_index->tile_index[it_tile].tp_index);
10493                                 l_cstr_index->tile_index[it_tile].tp_index = NULL;
10494                         }
10495
10496                         /* Packet index (NOT USED)*/
10497                         l_cstr_index->tile_index[it_tile].nb_packet = 0;
10498                         l_cstr_index->tile_index[it_tile].packet_index = NULL;
10499
10500                 }
10501         }
10502
10503         return l_cstr_index;
10504 }
10505
10506 opj_bool j2k_allocate_tile_element_cstr_index(opj_j2k_v2_t *p_j2k)
10507 {
10508         OPJ_UINT32 it_tile=0;
10509
10510         p_j2k->cstr_index->nb_of_tiles = p_j2k->m_cp.tw * p_j2k->m_cp.th;
10511         p_j2k->cstr_index->tile_index = (opj_tile_index_t*)opj_calloc(p_j2k->cstr_index->nb_of_tiles, sizeof(opj_tile_index_t));
10512         if (!p_j2k->cstr_index->tile_index)
10513                 return OPJ_FALSE;
10514
10515         for (it_tile=0; it_tile < p_j2k->cstr_index->nb_of_tiles; it_tile++){
10516                 p_j2k->cstr_index->tile_index[it_tile].maxmarknum = 100;
10517                 p_j2k->cstr_index->tile_index[it_tile].marknum = 0;
10518                 p_j2k->cstr_index->tile_index[it_tile].marker = (opj_marker_info_t*)
10519                                 opj_calloc(p_j2k->cstr_index->tile_index[it_tile].maxmarknum, sizeof(opj_marker_info_t));
10520                 if (!p_j2k->cstr_index->tile_index[it_tile].marker)
10521                         return OPJ_FALSE;
10522         }
10523
10524         return OPJ_TRUE;
10525 }
10526
10527 /**
10528  * Reads the tiles.
10529  */
10530 opj_bool j2k_decode_tiles (     opj_j2k_v2_t *p_j2k,
10531                                                         opj_stream_private_t *p_stream,
10532                                                         opj_event_mgr_t * p_manager)
10533 {
10534         opj_bool l_go_on = OPJ_TRUE;
10535         OPJ_UINT32 l_current_tile_no;
10536         OPJ_UINT32 l_data_size,l_max_data_size;
10537         OPJ_INT32 l_tile_x0,l_tile_y0,l_tile_x1,l_tile_y1;
10538         OPJ_UINT32 l_nb_comps;
10539         OPJ_BYTE * l_current_data;
10540
10541         l_current_data = (OPJ_BYTE*)opj_malloc(1000);
10542         if (! l_current_data) {
10543                 return OPJ_FALSE;
10544         }
10545         l_max_data_size = 1000;
10546
10547
10548
10549         while (OPJ_TRUE) {
10550                 if (! j2k_read_tile_header(     p_j2k,
10551                                                                         &l_current_tile_no,
10552                                                                         &l_data_size,
10553                                                                         &l_tile_x0, &l_tile_y0,
10554                                                                         &l_tile_x1, &l_tile_y1,
10555                                                                         &l_nb_comps,
10556                                                                         &l_go_on,
10557                                                                         p_stream,
10558                                                                         p_manager)) {
10559                         opj_free(l_current_data);
10560                         return OPJ_FALSE;
10561                 }
10562
10563                 if (! l_go_on) {
10564                         break;
10565                 }
10566
10567                 if (l_data_size > l_max_data_size) {
10568                         l_current_data = (OPJ_BYTE*)opj_realloc(l_current_data,l_data_size);
10569                         if (! l_current_data) {
10570                                 opj_free(l_current_data);
10571                                 return OPJ_FALSE;
10572                         }
10573
10574                         l_max_data_size = l_data_size;
10575                 }
10576
10577                 if (! j2k_decode_tile(p_j2k,l_current_tile_no,l_current_data,l_data_size,p_stream,p_manager)) {
10578                         opj_free(l_current_data);
10579                         return OPJ_FALSE;
10580                 }
10581                 opj_event_msg_v2(p_manager, EVT_INFO, "Tile %d/%d has been decoded.\n", l_current_tile_no +1, p_j2k->m_cp.th * p_j2k->m_cp.tw);
10582
10583                 if (! j2k_update_image_data(p_j2k->m_tcd,l_current_data, p_j2k->m_output_image)) {
10584                         opj_free(l_current_data);
10585                         return OPJ_FALSE;
10586                 }
10587                 opj_event_msg_v2(p_manager, EVT_INFO, "Image data has been updated with tile %d.\n\n", l_current_tile_no + 1);
10588
10589         }
10590
10591         opj_free(l_current_data);
10592
10593         return OPJ_TRUE;
10594 }
10595
10596 /**
10597  * Sets up the procedures to do on decoding data. Developpers wanting to extend the library can add their own reading procedures.
10598  */
10599 static void j2k_setup_decoding (opj_j2k_v2_t *p_j2k)
10600 {
10601         /* preconditions*/
10602         assert(p_j2k != 00);
10603
10604         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_decode_tiles);
10605         /* DEVELOPER CORNER, add your custom procedures */
10606
10607 }
10608
10609 /*
10610  * Read and decode one tile.
10611  */
10612 static opj_bool j2k_decode_one_tile (   opj_j2k_v2_t *p_j2k,
10613                                                                 opj_stream_private_t *p_stream,
10614                                                                 opj_event_mgr_t * p_manager)
10615 {
10616         opj_bool l_go_on = OPJ_TRUE;
10617         OPJ_UINT32 l_current_tile_no;
10618         OPJ_UINT32 l_tile_no_to_dec;
10619         OPJ_UINT32 l_data_size,l_max_data_size;
10620         OPJ_INT32 l_tile_x0,l_tile_y0,l_tile_x1,l_tile_y1;
10621         OPJ_UINT32 l_nb_comps;
10622         OPJ_BYTE * l_current_data;
10623
10624         l_current_data = (OPJ_BYTE*)opj_malloc(1000);
10625         if (! l_current_data) {
10626                 return OPJ_FALSE;
10627         }
10628         l_max_data_size = 1000;
10629
10630         /*Allocate and initialize some elements of codestrem index if not already done*/
10631         if( !p_j2k->cstr_index->tile_index)
10632         {
10633                 if (!j2k_allocate_tile_element_cstr_index(p_j2k)){
10634                         opj_free(l_current_data);
10635                         return OPJ_FALSE;
10636                 }
10637         }
10638         /* Move into the codestream to the first SOT used to decode the desired tile */
10639         l_tile_no_to_dec = p_j2k->m_specific_param.m_decoder.m_tile_ind_to_dec;
10640         if (p_j2k->cstr_index->tile_index)
10641                 if(p_j2k->cstr_index->tile_index->tp_index)
10642                 {
10643                         if ( ! p_j2k->cstr_index->tile_index[l_tile_no_to_dec].nb_tps) {
10644                                 /* the index for this tile has not been built,
10645                                  *  so move to the last SOT read */
10646                                 if ( opj_stream_read_seek(p_stream, p_j2k->m_specific_param.m_decoder.m_last_sot_read_pos+2, p_manager) ){
10647                                         opj_event_msg_v2(p_manager, EVT_ERROR, "Problem with seek function\n");
10648                                         return OPJ_FALSE;
10649                                 }
10650                         }
10651                         else{
10652                                 if (opj_stream_read_seek(p_stream, p_j2k->cstr_index->tile_index[l_tile_no_to_dec].tp_index[0].start_pos+2, p_manager)) {
10653                                         opj_event_msg_v2(p_manager, EVT_ERROR, "Problem with seek function\n");
10654                                         return OPJ_FALSE;
10655                                 }
10656                         }
10657                         /* Special case if we have previously read the EOC marker (if the previous tile getted is the last ) */
10658                         if(p_j2k->m_specific_param.m_decoder.m_state == J2K_STATE_EOC)
10659                                 p_j2k->m_specific_param.m_decoder.m_state = J2K_STATE_TPHSOT;
10660                 }
10661
10662         while (OPJ_TRUE) {
10663                 if (! j2k_read_tile_header(     p_j2k,
10664                                                                         &l_current_tile_no,
10665                                                                         &l_data_size,
10666                                                                         &l_tile_x0, &l_tile_y0,
10667                                                                         &l_tile_x1, &l_tile_y1,
10668                                                                         &l_nb_comps,
10669                                                                         &l_go_on,
10670                                                                         p_stream,
10671                                                                         p_manager)) {
10672                         opj_free(l_current_data);
10673                         return OPJ_FALSE;
10674                 }
10675
10676
10677                 if (! l_go_on) {
10678                         break;
10679                 }
10680
10681                 if (l_data_size > l_max_data_size) {
10682                         l_current_data = (OPJ_BYTE*)opj_realloc(l_current_data,l_data_size);
10683                         if (! l_current_data) {
10684                                 opj_free(l_current_data);
10685                                 return OPJ_FALSE;
10686                         }
10687
10688                         l_max_data_size = l_data_size;
10689                 }
10690
10691
10692
10693                 if (! j2k_decode_tile(p_j2k,l_current_tile_no,l_current_data,l_data_size,p_stream,p_manager)) {
10694                         opj_free(l_current_data);
10695                         return OPJ_FALSE;
10696                 }
10697                 opj_event_msg_v2(p_manager, EVT_INFO, "Tile %d/%d has been decoded.\n", l_current_tile_no, (p_j2k->m_cp.th * p_j2k->m_cp.tw) - 1);
10698
10699                 if (! j2k_update_image_data(p_j2k->m_tcd,l_current_data, p_j2k->m_output_image)) {
10700                         opj_free(l_current_data);
10701                         return OPJ_FALSE;
10702                 }
10703                 opj_event_msg_v2(p_manager, EVT_INFO, "Image data has been updated with tile %d.\n\n", l_current_tile_no);
10704
10705                 if(l_current_tile_no == l_tile_no_to_dec)
10706                 {
10707                         /* move into the codestream to the the first SOT (FIXME or not move?)*/
10708                         if (!(opj_stream_read_seek(p_stream, p_j2k->cstr_index->main_head_end + 2, p_manager) ) ) {
10709                                 opj_event_msg_v2(p_manager, EVT_ERROR, "Problem with seek function\n");
10710                                 return OPJ_FALSE;
10711                         }
10712                         break;
10713                 }
10714                 else {
10715                         opj_event_msg_v2(p_manager, EVT_WARNING, "Tile read, decode and updated is not the desired (%d vs %d).\n", l_current_tile_no, l_tile_no_to_dec);
10716                 }
10717
10718         }
10719
10720         opj_free(l_current_data);
10721
10722         return OPJ_TRUE;
10723 }
10724
10725
10726 /**
10727  * Sets up the procedures to do on decoding one tile. Developpers wanting to extend the library can add their own reading procedures.
10728  */
10729 static void j2k_setup_decoding_tile (opj_j2k_v2_t *p_j2k)
10730 {
10731         /* preconditions*/
10732         assert(p_j2k != 00);
10733
10734         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_decode_one_tile);
10735         /* DEVELOPER CORNER, add your custom procedures */
10736
10737 }
10738
10739
10740 /**
10741  * Decodes the tiles of the stream.
10742  */
10743 opj_bool opj_j2k_decode(opj_j2k_v2_t * p_j2k,
10744                                                 opj_stream_private_t * p_stream,
10745                                                 opj_image_t * p_image,
10746                                                 opj_event_mgr_t * p_manager)
10747 {
10748         OPJ_UINT32 compno;
10749
10750         if (!p_image)
10751                 return OPJ_FALSE;
10752
10753         p_j2k->m_output_image = opj_image_create0();
10754         if (! (p_j2k->m_output_image)) {
10755                 return OPJ_FALSE;
10756         }
10757         opj_copy_image_header(p_image, p_j2k->m_output_image);
10758
10759         /* customization of the decoding */
10760         j2k_setup_decoding(p_j2k);
10761
10762         /* Decode the codestream */
10763         if (! j2k_exec (p_j2k,p_j2k->m_procedure_list,p_stream,p_manager)) {
10764                 opj_image_destroy(p_j2k->m_private_image);
10765                 p_j2k->m_private_image = NULL;
10766                 return OPJ_FALSE;
10767         }
10768
10769         /* Move data and copy one information from codec to output image*/
10770         for (compno = 0; compno < p_image->numcomps; compno++) {
10771                 p_image->comps[compno].resno_decoded = p_j2k->m_output_image->comps[compno].resno_decoded;
10772                 p_image->comps[compno].data = p_j2k->m_output_image->comps[compno].data;
10773                 p_j2k->m_output_image->comps[compno].data = NULL;
10774         }
10775
10776         return OPJ_TRUE;
10777 }
10778
10779
10780 /**
10781  * Get the decoded tile.
10782  *
10783  * @param       p_j2k                   the jpeg2000 codestream codec.
10784  * @param       p_stream                input_stream
10785  * @param       p_image                 output image.   .
10786  * @param       p_manager               the user event manager
10787  * @param       tile_index              index of the tile we want decode
10788  *
10789  * @return      true                    if succeed.
10790  */
10791 opj_bool j2k_get_tile(  opj_j2k_v2_t *p_j2k,
10792                                                 opj_stream_private_t *p_stream,
10793                                                 opj_image_t* p_image,
10794                                                 struct opj_event_mgr * p_manager,
10795                                                 OPJ_UINT32 tile_index )
10796 {
10797         OPJ_UINT32 compno;
10798         OPJ_UINT32 l_tile_x, l_tile_y;
10799         opj_image_comp_t* l_img_comp;
10800
10801         if (!p_image) {
10802                 opj_event_msg_v2(p_manager, EVT_ERROR, "We need an image previously created.\n");
10803                 return OPJ_FALSE;
10804         }
10805
10806         if ( /*(tile_index < 0) &&*/ (tile_index >= p_j2k->m_cp.tw * p_j2k->m_cp.th) ){
10807                 opj_event_msg_v2(p_manager, EVT_ERROR, "Tile index provided by the user is incorrect %d (max = %d) \n", tile_index, (p_j2k->m_cp.tw * p_j2k->m_cp.th) - 1);
10808                 return OPJ_FALSE;
10809         }
10810
10811         /* Compute the dimension of the desired tile*/
10812         l_tile_x = tile_index % p_j2k->m_cp.tw;
10813         l_tile_y = tile_index / p_j2k->m_cp.tw;
10814
10815         p_image->x0 = l_tile_x * p_j2k->m_cp.tdx + p_j2k->m_cp.tx0;
10816         if (p_image->x0 < p_j2k->m_private_image->x0)
10817                 p_image->x0 = p_j2k->m_private_image->x0;
10818         p_image->x1 = (l_tile_x + 1) * p_j2k->m_cp.tdx + p_j2k->m_cp.tx0;
10819         if (p_image->x1 > p_j2k->m_private_image->x1)
10820                 p_image->x1 = p_j2k->m_private_image->x1;
10821
10822         p_image->y0 = l_tile_y * p_j2k->m_cp.tdy + p_j2k->m_cp.ty0;
10823         if (p_image->y0 < p_j2k->m_private_image->y0)
10824                 p_image->y0 = p_j2k->m_private_image->y0;
10825         p_image->y1 = (l_tile_y + 1) * p_j2k->m_cp.tdy + p_j2k->m_cp.ty0;
10826         if (p_image->y1 > p_j2k->m_private_image->y1)
10827                 p_image->y1 = p_j2k->m_private_image->y1;
10828
10829         l_img_comp = p_image->comps;
10830         for (compno=0; compno < p_image->numcomps; ++compno)
10831         {
10832                 OPJ_INT32 l_comp_x1, l_comp_y1;
10833
10834                 l_img_comp->factor = p_j2k->m_private_image->comps[compno].factor;
10835
10836                 l_img_comp->x0 = int_ceildiv(p_image->x0, l_img_comp->dx);
10837                 l_img_comp->y0 = int_ceildiv(p_image->y0, l_img_comp->dy);
10838                 l_comp_x1 = int_ceildiv(p_image->x1, l_img_comp->dx);
10839                 l_comp_y1 = int_ceildiv(p_image->y1, l_img_comp->dy);
10840
10841                 l_img_comp->w = int_ceildivpow2(l_comp_x1, l_img_comp->factor) - int_ceildivpow2(l_img_comp->x0, l_img_comp->factor);
10842                 l_img_comp->h = int_ceildivpow2(l_comp_y1, l_img_comp->factor) - int_ceildivpow2(l_img_comp->y0, l_img_comp->factor);
10843
10844                 l_img_comp++;
10845         }
10846
10847         /* Destroy the previous output image*/
10848         if (p_j2k->m_output_image)
10849                 opj_image_destroy(p_j2k->m_output_image);
10850
10851         /* Create the ouput image from the information previously computed*/
10852         p_j2k->m_output_image = opj_image_create0();
10853         if (! (p_j2k->m_output_image)) {
10854                 return OPJ_FALSE;
10855         }
10856         opj_copy_image_header(p_image, p_j2k->m_output_image);
10857
10858         p_j2k->m_specific_param.m_decoder.m_tile_ind_to_dec = tile_index;
10859
10860         /* customization of the decoding */
10861         j2k_setup_decoding_tile(p_j2k);
10862
10863         /* Decode the codestream */
10864         if (! j2k_exec (p_j2k,p_j2k->m_procedure_list,p_stream,p_manager)) {
10865                 opj_image_destroy(p_j2k->m_private_image);
10866                 p_j2k->m_private_image = NULL;
10867                 return OPJ_FALSE;
10868         }
10869
10870         /* Move data and copy one information from codec to output image*/
10871         for (compno = 0; compno < p_image->numcomps; compno++) {
10872                 p_image->comps[compno].resno_decoded = p_j2k->m_output_image->comps[compno].resno_decoded;
10873
10874                 if (p_image->comps[compno].data)
10875                         opj_free(p_image->comps[compno].data);
10876
10877                 p_image->comps[compno].data = p_j2k->m_output_image->comps[compno].data;
10878
10879                 p_j2k->m_output_image->comps[compno].data = NULL;
10880         }
10881
10882         return OPJ_TRUE;
10883 }
10884
10885 opj_bool j2k_set_decoded_resolution_factor(opj_j2k_v2_t *p_j2k, OPJ_UINT32 res_factor, opj_event_mgr_t * p_manager)
10886 {
10887         OPJ_UINT32 it_comp;
10888
10889         p_j2k->m_cp.m_specific_param.m_dec.m_reduce = res_factor;
10890
10891         if (p_j2k->m_private_image) {
10892                 if (p_j2k->m_private_image->comps) {
10893                         if (p_j2k->m_specific_param.m_decoder.m_default_tcp) {
10894                                 if (p_j2k->m_specific_param.m_decoder.m_default_tcp->tccps) {
10895                                         for (it_comp = 0 ; it_comp < p_j2k->m_private_image->numcomps; it_comp++) {
10896                                                 OPJ_UINT32 max_res = p_j2k->m_specific_param.m_decoder.m_default_tcp->tccps[it_comp].numresolutions;
10897                                                 if ( res_factor >= max_res){
10898                                                         opj_event_msg_v2(p_manager, EVT_ERROR, "Resolution factor is greater than the maximum resolution in the component.\n");
10899                                                         return OPJ_FALSE;
10900                                                 }
10901                                                 p_j2k->m_private_image->comps[it_comp].factor = res_factor;
10902                                         }
10903                                         return OPJ_TRUE;
10904                                 }
10905                         }
10906                 }
10907         }
10908
10909         return OPJ_FALSE;
10910 }
10911
10912
10913 /**
10914  * Encodes all the tiles in a row.
10915  */
10916 opj_bool j2k_encode_v2( opj_j2k_v2_t * p_j2k,
10917                                                 opj_stream_private_t *p_stream,
10918                                                 opj_event_mgr_t * p_manager )
10919 {
10920         OPJ_UINT32 i;
10921         OPJ_UINT32 l_nb_tiles;
10922         OPJ_UINT32 l_max_tile_size, l_current_tile_size;
10923         OPJ_BYTE * l_current_data;
10924
10925         /* preconditions */
10926         assert(p_j2k != 00);
10927         assert(p_stream != 00);
10928         assert(p_manager != 00);
10929
10930         l_current_data = (OPJ_BYTE*)opj_malloc(1000);
10931         if (! l_current_data) {
10932                 return OPJ_FALSE;
10933         }
10934         l_max_tile_size = 1000;
10935
10936         l_nb_tiles = p_j2k->m_cp.th * p_j2k->m_cp.tw;
10937         for (i=0;i<l_nb_tiles;++i) {
10938                 if (! j2k_pre_write_tile(p_j2k,i,p_stream,p_manager)) {
10939                         opj_free(l_current_data);
10940                         return OPJ_FALSE;
10941                 }
10942
10943                 l_current_tile_size = tcd_get_encoded_tile_size(p_j2k->m_tcd);
10944                 if (l_current_tile_size > l_max_tile_size) {
10945                         l_current_data = (OPJ_BYTE*)opj_realloc(l_current_data,l_current_tile_size);
10946                         if (! l_current_data) {
10947                                 return OPJ_FALSE;
10948                         }
10949                         l_max_tile_size = l_current_tile_size;
10950                 }
10951
10952                 j2k_get_tile_data(p_j2k->m_tcd,l_current_data);
10953
10954                 if (! j2k_post_write_tile (p_j2k,l_current_data,l_current_tile_size,p_stream,p_manager)) {
10955                         return OPJ_FALSE;
10956                 }
10957         }
10958
10959         opj_free(l_current_data);
10960         return OPJ_TRUE;
10961 }
10962
10963 /**
10964  * Ends the compression procedures and possibility add data to be read after the
10965  * codestream.
10966  */
10967 opj_bool j2k_end_compress(      opj_j2k_v2_t *p_j2k,
10968                                                         opj_stream_private_t *p_stream,
10969                                                         struct opj_event_mgr * p_manager)
10970 {
10971         /* customization of the encoding */
10972         j2k_setup_end_compress(p_j2k);
10973
10974         if (! j2k_exec (p_j2k, p_j2k->m_procedure_list, p_stream, p_manager))
10975         {
10976                 return OPJ_FALSE;
10977         }
10978
10979         return OPJ_TRUE;
10980 }
10981
10982
10983 /**
10984  * Starts a compression scheme, i.e. validates the codec parameters, writes the header.
10985  *
10986  * @param       p_j2k           the jpeg2000 codec.
10987  * @param       p_stream        the stream object.
10988  * @param       p_manager       the user event manager.
10989  *
10990  * @return true if the codec is valid.
10991  */
10992 opj_bool j2k_start_compress(opj_j2k_v2_t *p_j2k,
10993                                                         opj_stream_private_t *p_stream,
10994                                                         opj_image_t * p_image,
10995                                                         opj_event_mgr_t * p_manager)
10996 {
10997         /* preconditions */
10998         assert(p_j2k != 00);
10999         assert(p_stream != 00);
11000         assert(p_manager != 00);
11001
11002         p_j2k->m_private_image = opj_image_create0();
11003         opj_copy_image_header(p_image, p_j2k->m_private_image);
11004
11005         // TODO_MSD: Find a better way
11006         if (p_image->comps) {
11007                 OPJ_UINT32 it_comp;
11008                 for (it_comp = 0 ; it_comp < p_image->numcomps; it_comp++) {
11009                         if (p_image->comps[it_comp].data) {
11010                                 p_j2k->m_private_image->comps[it_comp].data =p_image->comps[it_comp].data;
11011                                 p_image->comps[it_comp].data = NULL;
11012
11013                         }
11014                 }
11015         }
11016
11017         /* customization of the validation */
11018         j2k_setup_encoding_validation (p_j2k);
11019
11020         /* validation of the parameters codec */
11021         if (! j2k_exec(p_j2k,p_j2k->m_validation_list,p_stream,p_manager)) {
11022                 return OPJ_FALSE;
11023         }
11024
11025         /* customization of the encoding */
11026         j2k_setup_header_writting(p_j2k);
11027
11028         /* write header */
11029         if (! j2k_exec (p_j2k,p_j2k->m_procedure_list,p_stream,p_manager)) {
11030                 return OPJ_FALSE;
11031         }
11032
11033         return OPJ_TRUE;
11034 }
11035
11036 /*
11037  *
11038  */
11039 opj_bool j2k_pre_write_tile (   opj_j2k_v2_t * p_j2k,
11040                                                                 OPJ_UINT32 p_tile_index,
11041                                                                 opj_stream_private_t *p_stream,
11042                                                                 opj_event_mgr_t * p_manager )
11043 {
11044   (void)p_stream;
11045         if (p_tile_index != p_j2k->m_current_tile_number) {
11046                 opj_event_msg_v2(p_manager, EVT_ERROR, "The given tile index does not match." );
11047                 return OPJ_FALSE;
11048         }
11049
11050         opj_event_msg_v2(p_manager, EVT_INFO, "tile number %d / %d\n", p_j2k->m_current_tile_number + 1, p_j2k->m_cp.tw * p_j2k->m_cp.th);
11051
11052         p_j2k->m_specific_param.m_encoder.m_current_tile_part_number = 0;
11053         p_j2k->m_tcd->cur_totnum_tp = p_j2k->m_cp.tcps[p_tile_index].m_nb_tile_parts;
11054         p_j2k->m_specific_param.m_encoder.m_current_poc_tile_part_number = 0;
11055
11056         /* initialisation before tile encoding  */
11057         if (! tcd_init_encode_tile(p_j2k->m_tcd, p_j2k->m_current_tile_number)) {
11058                 return OPJ_FALSE;
11059         }
11060
11061         return OPJ_TRUE;
11062 }
11063
11064 /*
11065  *
11066  */
11067 void j2k_get_tile_data (opj_tcd_v2_t * p_tcd, OPJ_BYTE * p_data)
11068 {
11069         OPJ_UINT32 i,j,k = 0;
11070         OPJ_UINT32 l_width,l_height,l_stride, l_offset_x,l_offset_y, l_image_width;
11071         opj_image_comp_t * l_img_comp = 00;
11072         opj_tcd_tilecomp_v2_t * l_tilec = 00;
11073         opj_image_t * l_image = 00;
11074         OPJ_UINT32 l_size_comp, l_remaining;
11075         OPJ_INT32 * l_src_ptr;
11076         l_tilec = p_tcd->tcd_image->tiles->comps;
11077         l_image = p_tcd->image;
11078         l_img_comp = l_image->comps;
11079
11080         for (i=0;i<p_tcd->image->numcomps;++i) {
11081                 l_size_comp = l_img_comp->prec >> 3; /* (/8) */
11082                 l_remaining = l_img_comp->prec & 7;  /* (%8) */
11083                 if (l_remaining) {
11084                         ++l_size_comp;
11085                 }
11086
11087                 if (l_size_comp == 3) {
11088                         l_size_comp = 4;
11089                 }
11090
11091                 l_width = (l_tilec->x1 - l_tilec->x0);
11092                 l_height = (l_tilec->y1 - l_tilec->y0);
11093                 l_offset_x = int_ceildiv(l_image->x0, l_img_comp->dx);
11094                 l_offset_y = int_ceildiv(l_image->y0, l_img_comp->dy);
11095                 l_image_width = int_ceildiv(l_image->x1 - l_image->x0, l_img_comp->dx);
11096                 l_stride = l_image_width - l_width;
11097                 l_src_ptr = l_img_comp->data + (l_tilec->x0 - l_offset_x) + (l_tilec->y0 - l_offset_y) * l_image_width;
11098
11099                 switch (l_size_comp) {
11100                         case 1:
11101                                 {
11102                                         OPJ_CHAR * l_dest_ptr = (OPJ_CHAR*) p_data;
11103                                         if (l_img_comp->sgnd) {
11104                                                 for     (j=0;j<l_height;++j) {
11105                                                         for (k=0;k<l_width;++k) {
11106                                                                 *(l_dest_ptr) = (OPJ_CHAR) (*l_src_ptr);
11107                                                                 ++l_dest_ptr;
11108                                                                 ++l_src_ptr;
11109                                                         }
11110                                                         l_src_ptr += l_stride;
11111                                                 }
11112                                         }
11113                                         else {
11114                                                 for (j=0;j<l_height;++j) {
11115                                                         for (k=0;k<l_width;++k) {
11116                                                                 *(l_dest_ptr) = (*l_src_ptr)&0xff;
11117                                                                 ++l_dest_ptr;
11118                                                                 ++l_src_ptr;
11119                                                         }
11120                                                         l_src_ptr += l_stride;
11121                                                 }
11122                                         }
11123
11124                                         p_data = (OPJ_BYTE*) l_dest_ptr;
11125                                 }
11126                                 break;
11127                         case 2:
11128                                 {
11129                                         OPJ_INT16 * l_dest_ptr = (OPJ_INT16 *) p_data;
11130                                         if (l_img_comp->sgnd) {
11131                                                 for (j=0;j<l_height;++j) {
11132                                                         for (k=0;k<l_width;++k) {
11133                                                                 *(l_dest_ptr++) = (OPJ_INT16) (*(l_src_ptr++));
11134                                                         }
11135                                                         l_src_ptr += l_stride;
11136                                                 }
11137                                         }
11138                                         else {
11139                                                 for (j=0;j<l_height;++j) {
11140                                                         for (k=0;k<l_width;++k) {
11141                                                                 *(l_dest_ptr++) = (*(l_src_ptr++))&0xffff;
11142                                                         }
11143                                                         l_src_ptr += l_stride;
11144                                                 }
11145                                         }
11146
11147                                         p_data = (OPJ_BYTE*) l_dest_ptr;
11148                                 }
11149                                 break;
11150                         case 4:
11151                                 {
11152                                         OPJ_INT32 * l_dest_ptr = (OPJ_INT32 *) p_data;
11153                                         for (j=0;j<l_height;++j) {
11154                                                 for (k=0;k<l_width;++k) {
11155                                                         *(l_dest_ptr++) = *(l_src_ptr++);
11156                                                 }
11157                                                 l_src_ptr += l_stride;
11158                                         }
11159
11160                                         p_data = (OPJ_BYTE*) l_dest_ptr;
11161                                 }
11162                                 break;
11163                 }
11164
11165                 ++l_img_comp;
11166                 ++l_tilec;
11167         }
11168 }
11169
11170
11171 /**
11172  * Write a tile.
11173  * @param       p_j2k           the jpeg2000 codec.
11174  * @param       p_stream        the stream to write data to.
11175  * @param       p_manager       the user event manager.
11176  */
11177 opj_bool j2k_post_write_tile (  opj_j2k_v2_t * p_j2k,
11178                                                                 OPJ_BYTE * p_data,
11179                                                                 OPJ_UINT32 p_data_size,
11180                                                                 opj_stream_private_t *p_stream,
11181                                                                 opj_event_mgr_t * p_manager )
11182 {
11183         opj_tcd_v2_t * l_tcd = 00;
11184         opj_cp_v2_t * l_cp = 00;
11185         opj_tcp_v2_t * l_tcp = 00;
11186         OPJ_UINT32 l_nb_bytes_written;
11187         OPJ_BYTE * l_current_data = 00;
11188         OPJ_UINT32 l_tile_size = 0;
11189         OPJ_UINT32 l_available_data;
11190
11191         /* preconditions */
11192         assert(p_j2k->m_specific_param.m_encoder.m_encoded_tile_data);
11193
11194         l_tcd = p_j2k->m_tcd;
11195         l_cp = &(p_j2k->m_cp);
11196         l_tcp = l_cp->tcps + p_j2k->m_current_tile_number;
11197
11198         l_tile_size = p_j2k->m_specific_param.m_encoder.m_encoded_tile_size;
11199         l_available_data = l_tile_size;
11200         l_current_data = p_j2k->m_specific_param.m_encoder.m_encoded_tile_data;
11201
11202         if (! tcd_copy_tile_data(l_tcd,p_data,p_data_size)) {
11203                 opj_event_msg_v2(p_manager, EVT_ERROR, "Size mismatch between tile data and sent data." );
11204                 return OPJ_FALSE;
11205         }
11206
11207         l_nb_bytes_written = 0;
11208         if (! j2k_write_first_tile_part(p_j2k,l_current_data,&l_nb_bytes_written,l_available_data,p_stream,p_manager)) {
11209                 return OPJ_FALSE;
11210         }
11211         l_current_data += l_nb_bytes_written;
11212         l_available_data -= l_nb_bytes_written;
11213
11214         l_nb_bytes_written = 0;
11215         if (! j2k_write_all_tile_parts(p_j2k,l_current_data,&l_nb_bytes_written,l_available_data,p_stream,p_manager)) {
11216                 return OPJ_FALSE;
11217         }
11218
11219         l_available_data -= l_nb_bytes_written;
11220         l_nb_bytes_written = l_tile_size - l_available_data;
11221
11222         if ( opj_stream_write_data(     p_stream,
11223                                                                 p_j2k->m_specific_param.m_encoder.m_encoded_tile_data,
11224                                                                 l_nb_bytes_written,p_manager) != l_nb_bytes_written) {
11225                 return OPJ_FALSE;
11226         }
11227
11228         ++p_j2k->m_current_tile_number;
11229
11230         return OPJ_TRUE;
11231 }
11232
11233
11234 /**
11235  * Sets up the validation ,i.e. adds the procedures to lauch to make sure the codec parameters
11236  * are valid. Developers wanting to extend the library can add their own validation procedures.
11237  */
11238 void j2k_setup_end_compress (opj_j2k_v2_t *p_j2k)
11239 {
11240         /* preconditions */
11241         assert(p_j2k != 00);
11242
11243         /* DEVELOPER CORNER, insert your custom procedures */
11244         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_eoc_v2 );
11245
11246         if (p_j2k->m_cp.m_specific_param.m_enc.m_cinema) {
11247                 opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_updated_tlm);
11248         }
11249
11250         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_epc );
11251         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_end_encoding );
11252         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_destroy_header_memory);
11253 }
11254
11255 /**
11256  * Sets up the validation ,i.e. adds the procedures to lauch to make sure the codec parameters
11257  * are valid. Developers wanting to extend the library can add their own validation procedures.
11258  */
11259 void j2k_setup_encoding_validation (opj_j2k_v2_t *p_j2k)
11260 {
11261         /* preconditions */
11262         assert(p_j2k != 00);
11263
11264         opj_procedure_list_add_procedure(p_j2k->m_validation_list, (opj_procedure)j2k_build_encoder);
11265         opj_procedure_list_add_procedure(p_j2k->m_validation_list, (opj_procedure)j2k_encoding_validation);
11266
11267         /* DEVELOPER CORNER, add your custom validation procedure */
11268         opj_procedure_list_add_procedure(p_j2k->m_validation_list, (opj_procedure)j2k_mct_validation);
11269 }
11270
11271
11272 /**
11273  * Sets up the procedures to do on writing header.
11274  * Developers wanting to extend the library can add their own writing procedures.
11275  */
11276 void j2k_setup_header_writting (opj_j2k_v2_t *p_j2k)
11277 {
11278         /* preconditions */
11279         assert(p_j2k != 00);
11280
11281         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_init_info );
11282         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_soc_v2 );
11283         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_siz_v2 );
11284         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_cod_v2 );
11285         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_qcd_v2 );
11286
11287
11288         if (p_j2k->m_cp.m_specific_param.m_enc.m_cinema) {
11289                 opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_image_components );
11290                 opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_tlm_v2 );
11291
11292                 if (p_j2k->m_cp.m_specific_param.m_enc.m_cinema == CINEMA4K_24) {
11293                         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_poc_v2 );
11294                 }
11295         }
11296
11297         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_regions);
11298
11299         if (p_j2k->m_cp.comment != 00)  {
11300                 opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_com_v2);
11301         }
11302
11303         /* DEVELOPER CORNER, insert your custom procedures */
11304         if (p_j2k->m_cp.rsiz & MCT) {
11305                 opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_write_mct_data_group );
11306         }
11307         /* End of Developer Corner */
11308
11309         if (p_j2k->cstr_index) {
11310                 opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_get_end_header );
11311         }
11312
11313         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_create_tcd);
11314         opj_procedure_list_add_procedure(p_j2k->m_procedure_list,(opj_procedure)j2k_update_rates);
11315 }
11316
11317
11318 opj_bool j2k_write_first_tile_part (opj_j2k_v2_t *p_j2k,
11319                                                                         OPJ_BYTE * p_data,
11320                                                                         OPJ_UINT32 * p_data_written,
11321                                                                         OPJ_UINT32 p_total_data_size,
11322                                                                         opj_stream_private_t *p_stream,
11323                                                                         struct opj_event_mgr * p_manager )
11324 {
11325         OPJ_UINT32 compno;
11326         OPJ_UINT32 l_nb_bytes_written = 0;
11327         OPJ_UINT32 l_current_nb_bytes_written;
11328         OPJ_BYTE * l_begin_data = 00;
11329
11330         opj_tcp_v2_t *l_tcp = 00;
11331         opj_tcd_v2_t * l_tcd = 00;
11332         opj_cp_v2_t * l_cp = 00;
11333
11334         l_tcd = p_j2k->m_tcd;
11335         l_cp = &(p_j2k->m_cp);
11336         l_tcp = l_cp->tcps + p_j2k->m_current_tile_number;
11337
11338         l_tcd->cur_pino = 0;
11339
11340         /*Get number of tile parts*/
11341         p_j2k->m_specific_param.m_encoder.m_current_poc_tile_part_number = 0;
11342
11343         /* INDEX >> */
11344         /* << INDEX */
11345
11346         l_current_nb_bytes_written = 0;
11347         l_begin_data = p_data;
11348         if (! j2k_write_sot_v2(p_j2k,p_data,&l_current_nb_bytes_written,p_stream,p_manager))
11349         {
11350                 return OPJ_FALSE;
11351         }
11352
11353         l_nb_bytes_written += l_current_nb_bytes_written;
11354         p_data += l_current_nb_bytes_written;
11355         p_total_data_size -= l_current_nb_bytes_written;
11356
11357         if (l_cp->m_specific_param.m_enc.m_cinema == 0) {
11358                 for (compno = 1; compno < p_j2k->m_private_image->numcomps; compno++) {
11359                         l_current_nb_bytes_written = 0;
11360                         j2k_write_coc_in_memory(p_j2k,compno,p_data,&l_current_nb_bytes_written,p_manager);
11361                         l_nb_bytes_written += l_current_nb_bytes_written;
11362                         p_data += l_current_nb_bytes_written;
11363                         p_total_data_size -= l_current_nb_bytes_written;
11364
11365                         l_current_nb_bytes_written = 0;
11366                         j2k_write_qcc_in_memory(p_j2k,compno,p_data,&l_current_nb_bytes_written,p_manager);
11367                         l_nb_bytes_written += l_current_nb_bytes_written;
11368                         p_data += l_current_nb_bytes_written;
11369                         p_total_data_size -= l_current_nb_bytes_written;
11370                 }
11371
11372                 if (l_cp->tcps[p_j2k->m_current_tile_number].numpocs) {
11373                         l_current_nb_bytes_written = 0;
11374                         j2k_write_poc_in_memory(p_j2k,p_data,&l_current_nb_bytes_written,p_manager);
11375                         l_nb_bytes_written += l_current_nb_bytes_written;
11376                         p_data += l_current_nb_bytes_written;
11377                         p_total_data_size -= l_current_nb_bytes_written;
11378                 }
11379         }
11380
11381         l_current_nb_bytes_written = 0;
11382         if (! j2k_write_sod_v2(p_j2k,l_tcd,p_data,&l_current_nb_bytes_written,p_total_data_size,p_stream,p_manager)) {
11383                 return OPJ_FALSE;
11384         }
11385
11386         l_nb_bytes_written += l_current_nb_bytes_written;
11387         * p_data_written = l_nb_bytes_written;
11388
11389         /* Writing Psot in SOT marker */
11390         opj_write_bytes(l_begin_data + 6,l_nb_bytes_written,4);                                 /* PSOT */
11391
11392         if (l_cp->m_specific_param.m_enc.m_cinema){
11393                 j2k_update_tlm(p_j2k,l_nb_bytes_written);
11394         }
11395
11396         return OPJ_TRUE;
11397 }
11398
11399 opj_bool j2k_write_all_tile_parts(      opj_j2k_v2_t *p_j2k,
11400                                                                         OPJ_BYTE * p_data,
11401                                                                         OPJ_UINT32 * p_data_written,
11402                                                                         OPJ_UINT32 p_total_data_size,
11403                                                                         opj_stream_private_t *p_stream,
11404                                                                         struct opj_event_mgr * p_manager
11405                                                                 )
11406 {
11407         OPJ_UINT32 tilepartno=0;
11408         OPJ_UINT32 l_nb_bytes_written = 0;
11409         OPJ_UINT32 l_current_nb_bytes_written;
11410         OPJ_UINT32 l_part_tile_size;
11411         OPJ_UINT32 tot_num_tp;
11412         OPJ_UINT32 pino;
11413
11414         OPJ_BYTE * l_begin_data;
11415         opj_tcp_v2_t *l_tcp = 00;
11416         opj_tcd_v2_t * l_tcd = 00;
11417         opj_cp_v2_t * l_cp = 00;
11418
11419
11420         l_tcd = p_j2k->m_tcd;
11421         l_cp = &(p_j2k->m_cp);
11422         l_tcp = l_cp->tcps + p_j2k->m_current_tile_number;
11423
11424         /*Get number of tile parts*/
11425         tot_num_tp = j2k_get_num_tp_v2(l_cp,0,p_j2k->m_current_tile_number);
11426
11427         for (tilepartno = 1; tilepartno < tot_num_tp ; ++tilepartno) {
11428                 p_j2k->m_specific_param.m_encoder.m_current_poc_tile_part_number = tilepartno;
11429                 l_current_nb_bytes_written = 0;
11430                 l_part_tile_size = 0;
11431                 l_begin_data = p_data;
11432
11433                 if (! j2k_write_sot_v2(p_j2k,p_data,&l_current_nb_bytes_written,p_stream,p_manager)) {
11434                         return OPJ_FALSE;
11435                 }
11436
11437                 l_nb_bytes_written += l_current_nb_bytes_written;
11438                 p_data += l_current_nb_bytes_written;
11439                 p_total_data_size -= l_current_nb_bytes_written;
11440                 l_part_tile_size += l_nb_bytes_written;
11441
11442                 l_current_nb_bytes_written = 0;
11443                 if (! j2k_write_sod_v2(p_j2k,l_tcd,p_data,&l_current_nb_bytes_written,p_total_data_size,p_stream,p_manager)) {
11444                         return OPJ_FALSE;
11445                 }
11446
11447                 p_data += l_current_nb_bytes_written;
11448                 l_nb_bytes_written += l_current_nb_bytes_written;
11449                 p_total_data_size -= l_current_nb_bytes_written;
11450                 l_part_tile_size += l_nb_bytes_written;
11451
11452                 /* Writing Psot in SOT marker */
11453                 opj_write_bytes(l_begin_data + 6,l_part_tile_size,4);                                   /* PSOT */
11454
11455                 if (l_cp->m_specific_param.m_enc.m_cinema) {
11456                         j2k_update_tlm(p_j2k,l_part_tile_size);
11457                 }
11458
11459                 ++p_j2k->m_specific_param.m_encoder.m_current_tile_part_number;
11460         }
11461
11462         for (pino = 1; pino <= l_tcp->numpocs; ++pino) {
11463                 l_tcd->cur_pino = pino;
11464
11465                 /*Get number of tile parts*/
11466                 tot_num_tp = j2k_get_num_tp_v2(l_cp,pino,p_j2k->m_current_tile_number);
11467                 for (tilepartno = 0; tilepartno < tot_num_tp ; ++tilepartno) {
11468                         p_j2k->m_specific_param.m_encoder.m_current_poc_tile_part_number = tilepartno;
11469                         l_current_nb_bytes_written = 0;
11470                         l_part_tile_size = 0;
11471                         l_begin_data = p_data;
11472
11473                         if (! j2k_write_sot_v2(p_j2k,p_data,&l_current_nb_bytes_written,p_stream,p_manager)) {
11474                                 return OPJ_FALSE;
11475                         }
11476
11477                         l_nb_bytes_written += l_current_nb_bytes_written;
11478                         p_data += l_current_nb_bytes_written;
11479                         p_total_data_size -= l_current_nb_bytes_written;
11480                         l_part_tile_size += l_current_nb_bytes_written;
11481
11482                         l_current_nb_bytes_written = 0;
11483
11484                         if (! j2k_write_sod_v2(p_j2k,l_tcd,p_data,&l_current_nb_bytes_written,p_total_data_size,p_stream,p_manager)) {
11485                                 return OPJ_FALSE;
11486                         }
11487
11488                         l_nb_bytes_written += l_current_nb_bytes_written;
11489                         p_data += l_current_nb_bytes_written;
11490                         p_total_data_size -= l_current_nb_bytes_written;
11491                         l_part_tile_size += l_current_nb_bytes_written;
11492
11493                         /* Writing Psot in SOT marker */
11494                         opj_write_bytes(l_begin_data + 6,l_part_tile_size,4);                                   /* PSOT */
11495
11496                         if (l_cp->m_specific_param.m_enc.m_cinema) {
11497                                 j2k_update_tlm(p_j2k,l_part_tile_size);
11498                         }
11499
11500                         ++p_j2k->m_specific_param.m_encoder.m_current_tile_part_number;
11501                 }
11502         }
11503
11504         *p_data_written = l_nb_bytes_written;
11505
11506         return OPJ_TRUE;
11507 }
11508
11509 /**
11510  * Writes the updated tlm.
11511  *
11512  * @param       p_stream                the stream to write data to.
11513  * @param       p_j2k                   J2K codec.
11514  * @param       p_manager               the user event manager.
11515 */
11516 opj_bool j2k_write_updated_tlm( opj_j2k_v2_t *p_j2k,
11517                                                                 struct opj_stream_private *p_stream,
11518                                                                 struct opj_event_mgr * p_manager )
11519 {
11520         OPJ_UINT32 l_tlm_size;
11521         OPJ_SIZE_T l_tlm_position, l_current_position;
11522
11523         /* preconditions */
11524         assert(p_j2k != 00);
11525         assert(p_manager != 00);
11526         assert(p_stream != 00);
11527
11528         l_tlm_size = 5 * p_j2k->m_specific_param.m_encoder.m_total_tile_parts;
11529         l_tlm_position = 6 + p_j2k->m_specific_param.m_encoder.m_tlm_start;
11530         l_current_position = opj_stream_tell(p_stream);
11531
11532         if (! opj_stream_seek(p_stream,l_tlm_position,p_manager)) {
11533                 return OPJ_FALSE;
11534         }
11535
11536         if (opj_stream_write_data(p_stream,p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_buffer,l_tlm_size,p_manager) != l_tlm_size) {
11537                 return OPJ_FALSE;
11538         }
11539
11540         if (! opj_stream_seek(p_stream,l_current_position,p_manager)) {
11541                 return OPJ_FALSE;
11542         }
11543
11544         return OPJ_TRUE;
11545 }
11546
11547
11548 /**
11549  * Ends the encoding, i.e. frees memory.
11550  *
11551  * @param       p_stream                                the stream to write data to.
11552  * @param       p_j2k                           J2K codec.
11553  * @param       p_manager               the user event manager.
11554 */
11555 opj_bool j2k_end_encoding(      opj_j2k_v2_t *p_j2k,
11556                                                         struct opj_stream_private *p_stream,
11557                                                         struct opj_event_mgr * p_manager )
11558 {
11559         /* preconditions */
11560         assert(p_j2k != 00);
11561         assert(p_manager != 00);
11562         assert(p_stream != 00);
11563
11564         tcd_destroy_v2(p_j2k->m_tcd);
11565         p_j2k->m_tcd = 00;
11566
11567         if (p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_buffer) {
11568                 opj_free(p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_buffer);
11569                 p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_buffer = 0;
11570                 p_j2k->m_specific_param.m_encoder.m_tlm_sot_offsets_current = 0;
11571         }
11572
11573         if (p_j2k->m_specific_param.m_encoder.m_encoded_tile_data) {
11574                 opj_free(p_j2k->m_specific_param.m_encoder.m_encoded_tile_data);
11575                 p_j2k->m_specific_param.m_encoder.m_encoded_tile_data = 0;
11576         }
11577
11578         p_j2k->m_specific_param.m_encoder.m_encoded_tile_size = 0;
11579
11580         return OPJ_TRUE;
11581 }
11582
11583 /**
11584  * Destroys the memory associated with the decoding of headers.
11585  */
11586 opj_bool j2k_destroy_header_memory (opj_j2k_v2_t * p_j2k,
11587                                                                         opj_stream_private_t *p_stream,
11588                                                                         opj_event_mgr_t * p_manager )
11589 {
11590         /* preconditions */
11591         assert(p_j2k != 00);
11592         assert(p_stream != 00);
11593         assert(p_manager != 00);
11594
11595         if (p_j2k->m_specific_param.m_encoder.m_header_tile_data) {
11596                 opj_free(p_j2k->m_specific_param.m_encoder.m_header_tile_data);
11597                 p_j2k->m_specific_param.m_encoder.m_header_tile_data = 0;
11598         }
11599
11600         p_j2k->m_specific_param.m_encoder.m_header_tile_data_size = 0;
11601
11602         return OPJ_TRUE;
11603 }
11604
11605
11606 /**
11607  * Inits the Info
11608  *
11609  * @param       p_stream                                the stream to write data to.
11610  * @param       p_j2k                           J2K codec.
11611  * @param       p_manager               the user event manager.
11612 */
11613 opj_bool j2k_init_info( opj_j2k_v2_t *p_j2k,
11614                                                 struct opj_stream_private *p_stream,
11615                                                 struct opj_event_mgr * p_manager )
11616 {
11617         opj_codestream_info_t * l_cstr_info = 00;
11618
11619         /* preconditions */
11620         assert(p_j2k != 00);
11621         assert(p_manager != 00);
11622         assert(p_stream != 00);
11623   (void)l_cstr_info;
11624
11625         /* TODO mergeV2: check this part which use cstr_info */
11626         /*l_cstr_info = p_j2k->cstr_info;
11627
11628         if (l_cstr_info)  {
11629                 OPJ_UINT32 compno;
11630                 l_cstr_info->tile = (opj_tile_info_t *) opj_malloc(p_j2k->m_cp.tw * p_j2k->m_cp.th * sizeof(opj_tile_info_t));
11631
11632                 l_cstr_info->image_w = p_j2k->m_image->x1 - p_j2k->m_image->x0;
11633                 l_cstr_info->image_h = p_j2k->m_image->y1 - p_j2k->m_image->y0;
11634
11635                 l_cstr_info->prog = (&p_j2k->m_cp.tcps[0])->prg;
11636
11637                 l_cstr_info->tw = p_j2k->m_cp.tw;
11638                 l_cstr_info->th = p_j2k->m_cp.th;
11639
11640                 l_cstr_info->tile_x = p_j2k->m_cp.tdx;*/        /* new version parser */
11641                 /*l_cstr_info->tile_y = p_j2k->m_cp.tdy;*/      /* new version parser */
11642                 /*l_cstr_info->tile_Ox = p_j2k->m_cp.tx0;*/     /* new version parser */
11643                 /*l_cstr_info->tile_Oy = p_j2k->m_cp.ty0;*/     /* new version parser */
11644
11645                 /*l_cstr_info->numcomps = p_j2k->m_image->numcomps;
11646
11647                 l_cstr_info->numlayers = (&p_j2k->m_cp.tcps[0])->numlayers;
11648
11649                 l_cstr_info->numdecompos = (OPJ_INT32*) opj_malloc(p_j2k->m_image->numcomps * sizeof(OPJ_INT32));
11650
11651                 for (compno=0; compno < p_j2k->m_image->numcomps; compno++) {
11652                         l_cstr_info->numdecompos[compno] = (&p_j2k->m_cp.tcps[0])->tccps->numresolutions - 1;
11653                 }
11654
11655                 l_cstr_info->D_max = 0.0;       */      /* ADD Marcela */
11656
11657                 /*l_cstr_info->main_head_start = opj_stream_tell(p_stream);*/ /* position of SOC */
11658
11659                 /*l_cstr_info->maxmarknum = 100;
11660                 l_cstr_info->marker = (opj_marker_info_t *) opj_malloc(l_cstr_info->maxmarknum * sizeof(opj_marker_info_t));
11661                 l_cstr_info->marknum = 0;
11662         }*/
11663
11664         return j2k_calculate_tp_v2(p_j2k,&(p_j2k->m_cp),&p_j2k->m_specific_param.m_encoder.m_total_tile_parts,p_j2k->m_private_image,p_manager);
11665 }
11666
11667 /**
11668  * Creates a tile-coder decoder.
11669  *
11670  * @param       p_stream                the stream to write data to.
11671  * @param       p_j2k                   J2K codec.
11672  * @param       p_manager               the user event manager.
11673 */
11674 opj_bool j2k_create_tcd(opj_j2k_v2_t *p_j2k,
11675                                                 struct opj_stream_private *p_stream,
11676                                                 struct opj_event_mgr * p_manager )
11677 {
11678         /* preconditions */
11679         assert(p_j2k != 00);
11680         assert(p_manager != 00);
11681         assert(p_stream != 00);
11682
11683         p_j2k->m_tcd = tcd_create_v2(OPJ_FALSE);
11684
11685         if (! p_j2k->m_tcd) {
11686                 opj_event_msg_v2(p_manager, EVT_ERROR, "Not enough memory to create Tile Coder\n");
11687                 return OPJ_FALSE;
11688         }
11689
11690         if (! tcd_init_v2(p_j2k->m_tcd,p_j2k->m_private_image,&p_j2k->m_cp)) {
11691                 tcd_destroy_v2(p_j2k->m_tcd);
11692                 p_j2k->m_tcd = 00;
11693                 return OPJ_FALSE;
11694         }
11695
11696         return OPJ_TRUE;
11697 }
11698
11699
11700 /**
11701  * Writes a tile.
11702  * @param       p_j2k           the jpeg2000 codec.
11703  * @param       p_stream                        the stream to write data to.
11704  * @param       p_manager       the user event manager.
11705  */
11706 opj_bool j2k_write_tile (opj_j2k_v2_t * p_j2k,
11707                                                  OPJ_UINT32 p_tile_index,
11708                                                  OPJ_BYTE * p_data,
11709                                                  OPJ_UINT32 p_data_size,
11710                                                  opj_stream_private_t *p_stream,
11711                                                  opj_event_mgr_t * p_manager )
11712 {
11713         if (! j2k_pre_write_tile(p_j2k,p_tile_index,p_stream,p_manager)) {
11714                 opj_event_msg_v2(p_manager, EVT_ERROR, "Error while j2k_pre_write_tile with tile index = %d\n", p_tile_index);
11715                 return OPJ_FALSE;
11716         }
11717         else {
11718                 if (! j2k_post_write_tile(p_j2k,p_data,p_data_size,p_stream,p_manager)) {
11719                         opj_event_msg_v2(p_manager, EVT_ERROR, "Error while j2k_post_write_tile with tile index = %d\n", p_tile_index);
11720                         return OPJ_FALSE;
11721                 }
11722         }
11723
11724         return OPJ_TRUE;
11725 }