[trunk] Start FolderReorgProposal task
[openjpeg.git] / src / bin / jp2 / index.c
1 /*
2  * Copyright (c) 2002-2007, Communications and Remote Sensing Laboratory, Universite catholique de Louvain (UCL), Belgium
3  * Copyright (c) 2002-2007, Professor Benoit Macq
4  * Copyright (c) 2003-2007, Francois-Olivier Devaux 
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS `AS IS'
17  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19  * ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
20  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26  * POSSIBILITY OF SUCH DAMAGE.
27  */
28
29 #include <stdio.h>
30 #include <math.h>
31 #include <string.h>
32 #include "openjpeg.h"
33 #include "index.h"
34 #include "opj_inttypes.h"
35
36 /* ------------------------------------------------------------------------------------ */
37
38 /**
39 Write a structured index to a file
40 @param cstr_info Codestream information 
41 @param index Index filename
42 @return Returns 0 if successful, returns 1 otherwise
43 */
44 int write_index_file(opj_codestream_info_t *cstr_info, char *index) {
45         int tileno, compno, layno, resno, precno, pack_nb, x, y;
46         FILE *stream = NULL;
47         double total_disto = 0;
48 /* UniPG>> */
49         int tilepartno;
50         char disto_on, numpix_on;
51
52 #ifdef USE_JPWL
53         if (!strcmp(index, JPWL_PRIVATEINDEX_NAME))
54                 return 0;
55 #endif /* USE_JPWL */
56 /* <<UniPG */
57
58         if (!cstr_info)         
59                 return 1;
60
61         stream = fopen(index, "w");
62         if (!stream) {
63                 fprintf(stderr, "failed to open index file [%s] for writing\n", index);
64                 return 1;
65         }
66         
67         if (cstr_info->tile[0].distotile)
68                 disto_on = 1;
69         else 
70                 disto_on = 0;
71
72         if (cstr_info->tile[0].numpix)
73                 numpix_on = 1;
74         else 
75                 numpix_on = 0;
76
77         fprintf(stream, "%d %d\n", cstr_info->image_w, cstr_info->image_h);
78         fprintf(stream, "%d\n", cstr_info->prog);
79         fprintf(stream, "%d %d\n", cstr_info->tile_x, cstr_info->tile_y);
80         fprintf(stream, "%d %d\n", cstr_info->tw, cstr_info->th);
81         fprintf(stream, "%d\n", cstr_info->numcomps);
82         fprintf(stream, "%d\n", cstr_info->numlayers);
83         fprintf(stream, "%d\n", cstr_info->numdecompos[0]); /* based on component 0 */
84
85         for (resno = cstr_info->numdecompos[0]; resno >= 0; resno--) {
86                 fprintf(stream, "[%d,%d] ", 
87                         (1 << cstr_info->tile[0].pdx[resno]), (1 << cstr_info->tile[0].pdx[resno]));    /* based on tile 0 and component 0 */
88         }
89
90         fprintf(stream, "\n");
91 /* UniPG>> */
92         fprintf(stream, "%d\n", cstr_info->main_head_start);
93 /* <<UniPG */
94         fprintf(stream, "%d\n", cstr_info->main_head_end);
95         fprintf(stream, "%d\n", cstr_info->codestream_size);
96         
97         fprintf(stream, "\nINFO ON TILES\n");
98         fprintf(stream, "tileno start_pos  end_hd  end_tile   nbparts");
99         if (disto_on)
100                 fprintf(stream,"         disto");
101         if (numpix_on)
102                 fprintf(stream,"     nbpix");
103         if (disto_on && numpix_on)
104                 fprintf(stream,"  disto/nbpix");
105         fprintf(stream, "\n");
106
107         for (tileno = 0; tileno < cstr_info->tw * cstr_info->th; tileno++) {
108                 fprintf(stream, "%4d %9d %9d %9d %9d", 
109                         cstr_info->tile[tileno].tileno,
110                         cstr_info->tile[tileno].start_pos,
111                         cstr_info->tile[tileno].end_header,
112                         cstr_info->tile[tileno].end_pos,
113                         cstr_info->tile[tileno].num_tps);
114                 if (disto_on)
115                         fprintf(stream," %9e", cstr_info->tile[tileno].distotile);
116                 if (numpix_on)
117                         fprintf(stream," %9d", cstr_info->tile[tileno].numpix);
118                 if (disto_on && numpix_on)
119                         fprintf(stream," %9e", cstr_info->tile[tileno].distotile / cstr_info->tile[tileno].numpix);
120                 fprintf(stream, "\n");
121         }
122                 
123         for (tileno = 0; tileno < cstr_info->tw * cstr_info->th; tileno++) {
124                 OPJ_OFF_T start_pos, end_ph_pos, end_pos;
125                 double disto = 0;
126                 int max_numdecompos = 0;
127                 pack_nb = 0;
128
129                 for (compno = 0; compno < cstr_info->numcomps; compno++) {
130                         if (max_numdecompos < cstr_info->numdecompos[compno])
131                                 max_numdecompos = cstr_info->numdecompos[compno];
132                 }       
133
134                 fprintf(stream, "\nTILE %d DETAILS\n", tileno); 
135                 fprintf(stream, "part_nb tileno  start_pack num_packs  start_pos end_tph_pos   end_pos\n");
136                 for (tilepartno = 0; tilepartno < cstr_info->tile[tileno].num_tps; tilepartno++)
137                         fprintf(stream, "%4d %9d   %9d %9d  %9d %11d %9d\n",
138                                 tilepartno, tileno,
139                                 cstr_info->tile[tileno].tp[tilepartno].tp_start_pack,
140                                 cstr_info->tile[tileno].tp[tilepartno].tp_numpacks,
141                                 cstr_info->tile[tileno].tp[tilepartno].tp_start_pos,
142                                 cstr_info->tile[tileno].tp[tilepartno].tp_end_header,
143                                 cstr_info->tile[tileno].tp[tilepartno].tp_end_pos
144                                 );
145
146                 if (cstr_info->prog == LRCP) {  /* LRCP */
147                         fprintf(stream, "LRCP\npack_nb tileno layno resno compno precno start_pos end_ph_pos end_pos");
148                         if (disto_on)
149                                 fprintf(stream, " disto");
150                         fprintf(stream,"\n");
151
152                         for (layno = 0; layno < cstr_info->numlayers; layno++) {
153                                 for (resno = 0; resno < max_numdecompos + 1; resno++) {
154                                         for (compno = 0; compno < cstr_info->numcomps; compno++) {
155                                                 int prec_max;
156                                                 if (resno > cstr_info->numdecompos[compno])
157                                                         break;
158                                                 prec_max = cstr_info->tile[tileno].pw[resno] * cstr_info->tile[tileno].ph[resno];
159                                                 for (precno = 0; precno < prec_max; precno++) {
160                                                         start_pos = cstr_info->tile[tileno].packet[pack_nb].start_pos;
161                                                         end_ph_pos = cstr_info->tile[tileno].packet[pack_nb].end_ph_pos;
162                                                         end_pos = cstr_info->tile[tileno].packet[pack_nb].end_pos;
163                                                         disto = cstr_info->tile[tileno].packet[pack_nb].disto;
164                                                         fprintf(stream, "%4d %6d %7d %5d %6d  %6d    %6" PRId64 "     %6" PRId64 " %7" PRId64,
165                                                                 pack_nb, tileno, layno, resno, compno, precno, start_pos, end_ph_pos, end_pos);
166                                                         if (disto_on)
167                                                                 fprintf(stream, " %8e", disto);
168                                                         fprintf(stream, "\n");
169                                                         total_disto += disto;
170                                                         pack_nb++;
171                                                 }
172                                         }
173                                 }
174                         }
175                 } /* LRCP */
176
177                 else if (cstr_info->prog == RLCP) {     /* RLCP */                      
178                         fprintf(stream, "RLCP\npack_nb tileno resno layno compno precno start_pos end_ph_pos end_pos\n");
179                         if (disto_on)
180                                 fprintf(stream, " disto");
181                         fprintf(stream,"\n");
182
183                         for (resno = 0; resno < max_numdecompos + 1; resno++) {
184                                 for (layno = 0; layno < cstr_info->numlayers; layno++) {
185                                         for (compno = 0; compno < cstr_info->numcomps; compno++) {
186                                                 int prec_max; 
187                                                 if (resno > cstr_info->numdecompos[compno])
188                                                         break;
189                                                 prec_max = cstr_info->tile[tileno].pw[resno] * cstr_info->tile[tileno].ph[resno];
190                                                 for (precno = 0; precno < prec_max; precno++) {
191                                                         start_pos = cstr_info->tile[tileno].packet[pack_nb].start_pos;
192                                                         end_ph_pos = cstr_info->tile[tileno].packet[pack_nb].end_ph_pos;
193                                                         end_pos = cstr_info->tile[tileno].packet[pack_nb].end_pos;
194                                                         disto = cstr_info->tile[tileno].packet[pack_nb].disto;
195                                                         fprintf(stream, "%4d %6d %5d %7d %6d %6d %9" PRId64 "   %9" PRId64 " %7" PRId64,
196                                                                 pack_nb, tileno, resno, layno, compno, precno, start_pos, end_ph_pos, end_pos);
197                                                         if (disto_on)
198                                                                 fprintf(stream, " %8e", disto);
199                                                         fprintf(stream, "\n");
200                                                         total_disto += disto;
201                                                         pack_nb++;
202                                                 }
203                                         }
204                                 }
205                         }
206                 } /* RLCP */
207
208                 else if (cstr_info->prog == RPCL) {     /* RPCL */
209
210                         fprintf(stream, "RPCL\npack_nb tileno resno precno compno layno start_pos end_ph_pos end_pos"); 
211                         if (disto_on)
212                                 fprintf(stream, " disto");
213                         fprintf(stream,"\n");
214
215                         for (resno = 0; resno < max_numdecompos + 1; resno++) {
216                                 int numprec = cstr_info->tile[tileno].pw[resno] * cstr_info->tile[tileno].ph[resno];
217                                 for (precno = 0; precno < numprec; precno++) {                                                          
218                                         /* I suppose components have same XRsiz, YRsiz */
219                                         int x0 = cstr_info->tile_Ox + tileno - (int)floor((float)tileno/(float)cstr_info->tw ) * cstr_info->tw * cstr_info->tile_x;
220                                         int y0 = cstr_info->tile_Ox + (int)floor( (float)tileno/(float)cstr_info->tw ) * cstr_info->tile_y;
221                                         int x1 = x0 + cstr_info->tile_x;
222                                         int y1 = y0 + cstr_info->tile_y;
223                                         for (compno = 0; compno < cstr_info->numcomps; compno++) {                                      
224                                                 int pcnx = cstr_info->tile[tileno].pw[resno];
225                                                 int pcx = (int) pow( 2, cstr_info->tile[tileno].pdx[resno] + cstr_info->numdecompos[compno] - resno );
226                                                 int pcy = (int) pow( 2, cstr_info->tile[tileno].pdy[resno] + cstr_info->numdecompos[compno] - resno );
227                                                 int precno_x = precno - (int) floor( (float)precno/(float)pcnx ) * pcnx;
228                                                 int precno_y = (int) floor( (float)precno/(float)pcnx );
229                                                 if (resno > cstr_info->numdecompos[compno])
230                                                         break;
231                                                 for(y = y0; y < y1; y++) {                                                      
232                                                         if (precno_y*pcy == y ) {
233                                                                 for (x = x0; x < x1; x++) {                                                                     
234                                                                         if (precno_x*pcx == x ) {
235                                                                                 for (layno = 0; layno < cstr_info->numlayers; layno++) {
236                                                                                         start_pos = cstr_info->tile[tileno].packet[pack_nb].start_pos;
237                                                                                         end_ph_pos = cstr_info->tile[tileno].packet[pack_nb].end_ph_pos;
238                                                                                         end_pos = cstr_info->tile[tileno].packet[pack_nb].end_pos;
239                                                                                         disto = cstr_info->tile[tileno].packet[pack_nb].disto;
240                                                                                         fprintf(stream, "%4d %6d %5d %6d %6d %7d %9" PRId64 "   %9" PRId64 " %7" PRId64,
241                                                                                                 pack_nb, tileno, resno, precno, compno, layno, start_pos, end_ph_pos, end_pos); 
242                                                                                         if (disto_on)
243                                                                                                 fprintf(stream, " %8e", disto);
244                                                                                         fprintf(stream, "\n");
245                                                                                         total_disto += disto;
246                                                                                         pack_nb++; 
247                                                                                 }
248                                                                         }
249                                                                 }/* x = x0..x1 */
250                                                         } 
251                                                 }  /* y = y0..y1 */
252                                         } /* precno */
253                                 } /* compno */
254                         } /* resno */
255                 } /* RPCL */
256
257                 else if (cstr_info->prog == PCRL) {     /* PCRL */
258                         /* I suppose components have same XRsiz, YRsiz */
259                         int x0 = cstr_info->tile_Ox + tileno - (int)floor( (float)tileno/(float)cstr_info->tw ) * cstr_info->tw * cstr_info->tile_x;
260                         int y0 = cstr_info->tile_Ox + (int)floor( (float)tileno/(float)cstr_info->tw ) * cstr_info->tile_y;
261                         int x1 = x0 + cstr_info->tile_x;
262                         int y1 = y0 + cstr_info->tile_y;
263
264                         /* Count the maximum number of precincts */
265                         int max_numprec = 0;
266                         for (resno = 0; resno < max_numdecompos + 1; resno++) {
267                                 int numprec = cstr_info->tile[tileno].pw[resno] * cstr_info->tile[tileno].ph[resno];
268                                 if (numprec > max_numprec)
269                                         max_numprec = numprec;
270                         }
271
272                         fprintf(stream, "PCRL\npack_nb tileno precno compno resno layno start_pos end_ph_pos end_pos"); 
273                         if (disto_on)
274                                 fprintf(stream, " disto");
275                         fprintf(stream,"\n");
276
277                         for (precno = 0; precno < max_numprec; precno++) {
278                                 for (compno = 0; compno < cstr_info->numcomps; compno++) {
279                                         for (resno = 0; resno < cstr_info->numdecompos[compno] + 1; resno++) {
280                                                 int numprec = cstr_info->tile[tileno].pw[resno] * cstr_info->tile[tileno].ph[resno];
281                                                 int pcnx = cstr_info->tile[tileno].pw[resno];
282                                                 int pcx = (int) pow( 2, cstr_info->tile[tileno].pdx[resno] + cstr_info->numdecompos[compno] - resno );
283                                                 int pcy = (int) pow( 2, cstr_info->tile[tileno].pdy[resno] + cstr_info->numdecompos[compno] - resno );
284                                                 int precno_x = precno - (int) floor( (float)precno/(float)pcnx ) * pcnx;
285                                                 int precno_y = (int) floor( (float)precno/(float)pcnx );
286                                                 if (precno >= numprec)
287                                                         continue;
288                                                 for(y = y0; y < y1; y++) {                                                      
289                                                         if (precno_y*pcy == y ) {
290                                                                 for (x = x0; x < x1; x++) {                                                                     
291                                                                         if (precno_x*pcx == x ) {
292                                                                                 for (layno = 0; layno < cstr_info->numlayers; layno++) {
293                                                                                         start_pos = cstr_info->tile[tileno].packet[pack_nb].start_pos;
294                                                                                         end_ph_pos = cstr_info->tile[tileno].packet[pack_nb].end_ph_pos;
295                                                                                         end_pos = cstr_info->tile[tileno].packet[pack_nb].end_pos;
296                                                                                         disto = cstr_info->tile[tileno].packet[pack_nb].disto;
297                                                                                         fprintf(stream, "%4d %6d %6d %6d %5d %7d %9" PRId64 "   %9" PRId64 " %7" PRId64,
298                                                                                                 pack_nb, tileno, precno, compno, resno, layno, start_pos, end_ph_pos, end_pos); 
299                                                                                         if (disto_on)
300                                                                                                 fprintf(stream, " %8e", disto);
301                                                                                         fprintf(stream, "\n");
302                                                                                         total_disto += disto;
303                                                                                         pack_nb++; 
304                                                                                 }
305                                                                         }
306                                                                 }/* x = x0..x1 */
307                                                         } 
308                                                 }  /* y = y0..y1 */
309                                         } /* resno */
310                                 } /* compno */
311                         } /* precno */
312                 } /* PCRL */
313
314                 else {  /* CPRL */
315                         /* Count the maximum number of precincts */
316                         int max_numprec = 0;
317                         for (resno = 0; resno < max_numdecompos + 1; resno++) {
318                                 int numprec = cstr_info->tile[tileno].pw[resno] * cstr_info->tile[tileno].ph[resno];
319                                 if (numprec > max_numprec)
320                                         max_numprec = numprec;
321                         }
322
323                         fprintf(stream, "CPRL\npack_nb tileno compno precno resno layno start_pos end_ph_pos end_pos"); 
324                         if (disto_on)
325                                 fprintf(stream, " disto");
326                         fprintf(stream,"\n");
327
328                         for (compno = 0; compno < cstr_info->numcomps; compno++) {
329                                 /* I suppose components have same XRsiz, YRsiz */
330                                 int x0 = cstr_info->tile_Ox + tileno - (int)floor( (float)tileno/(float)cstr_info->tw ) * cstr_info->tw * cstr_info->tile_x;
331                                 int y0 = cstr_info->tile_Ox + (int)floor( (float)tileno/(float)cstr_info->tw ) * cstr_info->tile_y;
332                                 int x1 = x0 + cstr_info->tile_x;
333                                 int y1 = y0 + cstr_info->tile_y;
334
335                                 for (precno = 0; precno < max_numprec; precno++) {
336                                         for (resno = 0; resno < cstr_info->numdecompos[compno] + 1; resno++) {
337                                                 int numprec = cstr_info->tile[tileno].pw[resno] * cstr_info->tile[tileno].ph[resno];
338                                                 int pcnx = cstr_info->tile[tileno].pw[resno];
339                                                 int pcx = (int) pow( 2, cstr_info->tile[tileno].pdx[resno] + cstr_info->numdecompos[compno] - resno );
340                                                 int pcy = (int) pow( 2, cstr_info->tile[tileno].pdy[resno] + cstr_info->numdecompos[compno] - resno );
341                                                 int precno_x = precno - (int) floor( (float)precno/(float)pcnx ) * pcnx;
342                                                 int precno_y = (int) floor( (float)precno/(float)pcnx );
343                                                 if (precno >= numprec)
344                                                         continue;
345
346                                                 for(y = y0; y < y1; y++) {
347                                                         if (precno_y*pcy == y ) {
348                                                                 for (x = x0; x < x1; x++) {
349                                                                         if (precno_x*pcx == x ) {
350                                                                                 for (layno = 0; layno < cstr_info->numlayers; layno++) {
351                                                                                         start_pos = cstr_info->tile[tileno].packet[pack_nb].start_pos;
352                                                                                         end_ph_pos = cstr_info->tile[tileno].packet[pack_nb].end_ph_pos;
353                                                                                         end_pos = cstr_info->tile[tileno].packet[pack_nb].end_pos;
354                                                                                         disto = cstr_info->tile[tileno].packet[pack_nb].disto;
355                                                                                         fprintf(stream, "%4d %6d %6d %6d %5d %7d %9" PRId64 "   %9" PRId64 " %7" PRId64,
356                                                                                                 pack_nb, tileno, compno, precno, resno, layno, start_pos, end_ph_pos, end_pos); 
357                                                                                         if (disto_on)
358                                                                                                 fprintf(stream, " %8e", disto);
359                                                                                         fprintf(stream, "\n");
360                                                                                         total_disto += disto;
361                                                                                         pack_nb++; 
362                                                                                 }
363                                                                         }
364                                                                 }/* x = x0..x1 */
365                                                         }
366                                                 } /* y = y0..y1 */
367                                         } /* resno */
368                                 } /* precno */
369                         } /* compno */
370                 } /* CPRL */   
371         } /* tileno */
372         
373         if (disto_on) {
374                 fprintf(stream, "%8e\n", cstr_info->D_max); /* SE max */        
375                 fprintf(stream, "%.8e\n", total_disto); /* SE totale */
376         }
377 /* UniPG>> */
378         /* print the markers' list */
379         if (cstr_info->marknum) {
380                 fprintf(stream, "\nMARKER LIST\n");
381                 fprintf(stream, "%d\n", cstr_info->marknum);
382                 fprintf(stream, "type\tstart_pos    length\n");
383                 for (x = 0; x < cstr_info->marknum; x++)
384                         fprintf(stream, "%X\t%9" PRId64 " %9d\n", cstr_info->marker[x].type, cstr_info->marker[x].pos, cstr_info->marker[x].len);
385         }
386 /* <<UniPG */
387         fclose(stream);
388
389         fprintf(stderr,"Generated index file %s\n", index);
390
391         return 0;
392 }