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