2 * Copyright (c) 2001-2003, David Janssens
\r
3 * Copyright (c) 2002-2003, Yannick Verschueren
\r
4 * Copyright (c) 2003-2005, Francois Devaux and Antonin Descampe
\r
5 * Copyright (c) 2005, Herv� Drolon, FreeImage Team
\r
6 * Copyright (c) 2002-2005, Communications and remote sensing Laboratory, Universite catholique de Louvain, Belgium
\r
7 * Copyright (c) 2005-2006, Dept. of Electronic and Information Engineering, Universita' degli Studi di Perugia, Italy
\r
8 * All rights reserved.
\r
10 * Redistribution and use in source and binary forms, with or without
\r
11 * modification, are permitted provided that the following conditions
\r
13 * 1. Redistributions of source code must retain the above copyright
\r
14 * notice, this list of conditions and the following disclaimer.
\r
15 * 2. Redistributions in binary form must reproduce the above copyright
\r
16 * notice, this list of conditions and the following disclaimer in the
\r
17 * documentation and/or other materials provided with the distribution.
\r
19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS `AS IS'
\r
20 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
\r
21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
\r
22 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
\r
23 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
\r
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
\r
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
\r
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
\r
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
\r
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
\r
29 * POSSIBILITY OF SUCH DAMAGE.
\r
34 #include "../libopenjpeg/opj_includes.h"
\r
36 /** Minimum and maximum values for the double->pfp conversion */
\r
38 #define MAX_V1 17293822569102704640.0
\r
39 #define MIN_V2 0.000030517578125
\r
40 #define MAX_V2 131040.0
\r
42 /** conversion between a double precision floating point
\r
43 number and the corresponding pseudo-floating point used
\r
44 to represent sensitivity values
\r
45 @param V the double precision value
\r
46 @param bytes the number of bytes of the representation
\r
47 @return the pseudo-floating point value (cast accordingly)
\r
49 unsigned short int jpwl_double_to_pfp(double V, int bytes);
\r
51 /** conversion between a pseudo-floating point used
\r
52 to represent sensitivity values and the corresponding
\r
53 double precision floating point number
\r
54 @param em the pseudo-floating point value (cast accordingly)
\r
55 @param bytes the number of bytes of the representation
\r
56 @return the double precision value
\r
58 double jpwl_pfp_to_double(unsigned short int em, int bytes);
\r
60 /*-------------------------------------------------------------*/
\r
62 int jpwl_markcomp(const void *arg1, const void *arg2)
\r
64 /* Compare the two markers' positions */
\r
65 double diff = (((jpwl_marker_t *) arg1)->dpos - ((jpwl_marker_t *) arg2)->dpos);
\r
75 int jpwl_epbs_add(opj_j2k_t *j2k, jpwl_marker_t *jwmarker, int *jwmarker_num,
\r
76 bool latest, bool packed, bool insideMH, int *idx, int hprot,
\r
77 double place_pos, int tileno,
\r
78 unsigned long int pre_len, unsigned long int post_len) {
\r
80 jpwl_epb_ms_t *epb_mark = NULL;
\r
82 int k_pre, k_post, n_pre, n_post;
\r
84 unsigned long int L1, L2, dL4, max_postlen, epbs_len = 0;
\r
86 /* We find RS(n,k) for EPB parms and pre-data, if any */
\r
87 if (insideMH && (*idx == 0)) {
\r
88 /* First EPB in MH */
\r
91 } else if (!insideMH && (*idx == 0)) {
\r
92 /* First EPB in TH */
\r
96 /* Following EPBs in MH or TH */
\r
101 /* Find lengths, Figs. B3 and B4 */
\r
102 /* size of pre data: pre_buf(pre_len) + EPB(2) + Lepb(2) + Depb(1) + LDPepb(4) + Pepb(4) */
\r
105 /* size of pre-data redundancy */
\r
106 /* (redundancy per codeword) * (number of codewords, rounded up) */
\r
107 L2 = (n_pre - k_pre) * (unsigned long int) ceil((double) L1 / (double) k_pre);
\r
109 /* Find protection type for post data and its associated redundancy field length*/
\r
110 if ((hprot == 16) || (hprot == 32)) {
\r
111 /* there is a CRC for post-data */
\r
113 n_post = post_len + (hprot >> 3);
\r
114 /*L3 = hprot >> 3;*/ /* 2 (CRC-16) or 4 (CRC-32) bytes */
\r
116 } else if ((hprot >= 37) && (hprot <= 128)) {
\r
117 /* there is a RS for post-data */
\r
122 /* Use predefined codes */
\r
127 /* Create the EPB(s) */
\r
128 while (post_len > 0) {
\r
130 /* maximum postlen in order to respect EPB size
\r
131 (we use 65450 instead of 65535 for keeping room for EPB parms)*/
\r
132 /* (message word size) * (number of containable parity words) */
\r
133 max_postlen = k_post * (unsigned long int) floor(65450.0 / (double) (n_post - k_post));
\r
135 /* maximum postlen in order to respect EPB size */
\r
137 /* (we use (65500 - L2) instead of 65535 for keeping room for EPB parms + pre-data) */
\r
138 /* (message word size) * (number of containable parity words) */
\r
139 max_postlen = k_post * (unsigned long int) floor((double) (65500 - L2) / (double) (n_post - k_post));
\r
142 /* (we use 65500 instead of 65535 for keeping room for EPB parms) */
\r
143 /* (message word size) * (number of containable parity words) */
\r
144 max_postlen = k_post * (unsigned long int) floor(65500.0 / (double) (n_post - k_post));
\r
146 /* length to use */
\r
147 dL4 = min(max_postlen, post_len);
\r
149 if (epb_mark = jpwl_epb_create(
\r
150 j2k, /* this encoder handle */
\r
151 latest ? (dL4 < max_postlen) : false, /* is it the latest? */
\r
152 packed, /* is it packed? */
\r
153 tileno, /* we are in TPH */
\r
154 *idx, /* its index */
\r
155 hprot, /* protection type parameters of following data */
\r
156 0, /* pre-data: nothing for now */
\r
157 dL4 /* post-data: the stub computed previously */
\r
160 /* Add this marker to the 'insertanda' list */
\r
161 if (*jwmarker_num < JPWL_MAX_NO_MARKERS) {
\r
162 jwmarker[*jwmarker_num].id = J2K_MS_EPB; /* its type */
\r
163 jwmarker[*jwmarker_num].epbmark = epb_mark; /* the EPB */
\r
164 jwmarker[*jwmarker_num].pos = (int) place_pos; /* after SOT */
\r
165 jwmarker[*jwmarker_num].dpos = place_pos + 0.0000001 * (double)(*idx); /* not very first! */
\r
166 jwmarker[*jwmarker_num].len = epb_mark->Lepb; /* its length */
\r
167 jwmarker[*jwmarker_num].len_ready = true; /* ready */
\r
168 jwmarker[*jwmarker_num].pos_ready = true; /* ready */
\r
169 jwmarker[*jwmarker_num].parms_ready = true; /* ready */
\r
170 jwmarker[*jwmarker_num].data_ready = false; /* not ready */
\r
174 /* increment epb index */
\r
177 /* decrease postlen */
\r
180 /* increase the total length of EPBs */
\r
181 epbs_len += epb_mark->Lepb + 2;
\r
184 /* ooops, problems */
\r
185 opj_event_msg(j2k->cinfo, EVT_ERROR, "Could not create TPH EPB for UEP in tile %d\n", tileno);
\r
193 jpwl_epb_ms_t *jpwl_epb_create(opj_j2k_t *j2k, bool latest, bool packed, int tileno, int idx, int hprot,
\r
194 unsigned long int pre_len, unsigned long int post_len) {
\r
196 jpwl_epb_ms_t *epb = NULL;
\r
197 unsigned short int data_len = 0;
\r
198 unsigned short int L2, L3;
\r
199 unsigned long int L1, L4;
\r
200 unsigned char *predata_in = NULL;
\r
202 bool insideMH = (tileno == -1);
\r
205 if (!(epb = (jpwl_epb_ms_t *) opj_malloc((size_t) 1 * sizeof (jpwl_epb_ms_t)))) {
\r
206 opj_event_msg(j2k->cinfo, EVT_ERROR, "Could not allocate room for one EPB MS\n");
\r
210 /* We set RS(n,k) for EPB parms and pre-data, if any */
\r
211 if (insideMH && (idx == 0)) {
\r
212 /* First EPB in MH */
\r
215 } else if (!insideMH && (idx == 0)) {
\r
216 /* First EPB in TH */
\r
220 /* Following EPBs in MH or TH */
\r
225 /* Find lengths, Figs. B3 and B4 */
\r
226 /* size of pre data: pre_buf(pre_len) + EPB(2) + Lepb(2) + Depb(1) + LDPepb(4) + Pepb(4) */
\r
228 epb->pre_len = pre_len;
\r
230 /* size of pre-data redundancy */
\r
231 /* (redundancy per codeword) * (number of codewords, rounded up) */
\r
232 L2 = (epb->n_pre - epb->k_pre) * (unsigned short int) ceil((double) L1 / (double) epb->k_pre);
\r
234 /* length of post-data */
\r
236 epb->post_len = post_len;
\r
238 /* Find protection type for post data and its associated redundancy field length*/
\r
239 if ((hprot == 16) || (hprot == 32)) {
\r
240 /* there is a CRC for post-data */
\r
241 epb->Pepb = 0x10000000 | ((unsigned long int) hprot >> 5); /* 0=CRC-16, 1=CRC-32 */
\r
242 epb->k_post = post_len;
\r
243 epb->n_post = post_len + (hprot >> 3);
\r
244 /*L3 = hprot >> 3;*/ /* 2 (CRC-16) or 4 (CRC-32) bytes */
\r
246 } else if ((hprot >= 37) && (hprot <= 128)) {
\r
247 /* there is a RS for post-data */
\r
248 epb->Pepb = 0x20000020 | (((unsigned long int) hprot & 0x000000FF) << 8);
\r
250 epb->n_post = hprot;
\r
252 } else if (hprot == 1) {
\r
253 /* Use predefined codes */
\r
254 epb->Pepb = (unsigned long int) 0x00000000;
\r
255 epb->n_post = epb->n_pre;
\r
256 epb->k_post = epb->k_pre;
\r
258 } else if (hprot == 0) {
\r
259 /* Placeholder EPB: only protects its parameters, no protection method */
\r
260 epb->Pepb = (unsigned long int) 0xFFFFFFFF;
\r
265 opj_event_msg(j2k->cinfo, EVT_ERROR, "Invalid protection value for EPB h = %d\n", hprot);
\r
269 epb->hprot = hprot;
\r
271 /* (redundancy per codeword) * (number of codewords, rounded up) */
\r
272 L3 = (epb->n_post - epb->k_post) * (unsigned short int) ceil((double) L4 / (double) epb->k_post);
\r
274 /* private fields */
\r
275 epb->tileno = tileno;
\r
277 /* Fill some fields of the EPB */
\r
279 /* total length of the EPB MS (less the EPB marker itself): */
\r
280 /* Lepb(2) + Depb(1) + LDPepb(4) + Pepb(4) + pre_redundancy + post-redundancy */
\r
281 epb->Lepb = 11 + L2 + L3;
\r
284 epb->Depb = ((packed & 0x0001) << 7) | ((latest & 0x0001) << 6) | (idx & 0x003F);
\r
286 /* length of data protected by EPB: */
\r
287 epb->LDPepb = L1 + L4;
\r
292 void jpwl_epb_write(jpwl_epb_ms_t *epb, unsigned char *buf) {
\r
295 *(buf++) = (unsigned char) (J2K_MS_EPB >> 8);
\r
296 *(buf++) = (unsigned char) (J2K_MS_EPB >> 0);
\r
299 *(buf++) = (unsigned char) (epb->Lepb >> 8);
\r
300 *(buf++) = (unsigned char) (epb->Lepb >> 0);
\r
303 *(buf++) = (unsigned char) (epb->Depb >> 0);
\r
306 *(buf++) = (unsigned char) (epb->LDPepb >> 24);
\r
307 *(buf++) = (unsigned char) (epb->LDPepb >> 16);
\r
308 *(buf++) = (unsigned char) (epb->LDPepb >> 8);
\r
309 *(buf++) = (unsigned char) (epb->LDPepb >> 0);
\r
312 *(buf++) = (unsigned char) (epb->Pepb >> 24);
\r
313 *(buf++) = (unsigned char) (epb->Pepb >> 16);
\r
314 *(buf++) = (unsigned char) (epb->Pepb >> 8);
\r
315 *(buf++) = (unsigned char) (epb->Pepb >> 0);
\r
318 /*memcpy(buf, epb->data, (size_t) epb->Lepb - 11);*/
\r
319 memset(buf, 0, (size_t) epb->Lepb - 11);
\r
323 jpwl_epc_ms_t *jpwl_epc_create(opj_j2k_t *j2k, bool esd_on, bool red_on, bool epb_on, bool info_on) {
\r
325 jpwl_epc_ms_t *epc = NULL;
\r
328 if (!(epc = (jpwl_epc_ms_t *) malloc((size_t) 1 * sizeof (jpwl_epc_ms_t)))) {
\r
329 opj_event_msg(j2k->cinfo, EVT_ERROR, "Could not allocate room for EPC MS\n");
\r
333 /* Set the EPC parameters */
\r
334 epc->esd_on = esd_on;
\r
335 epc->epb_on = epb_on;
\r
336 epc->red_on = red_on;
\r
337 epc->info_on = info_on;
\r
339 /* Fill the EPC fields with default values */
\r
341 epc->Pcrc = 0x0000;
\r
342 epc->DL = 0x00000000;
\r
343 epc->Pepc = ((j2k->cp->esd_on & 0x0001) << 4) | ((j2k->cp->red_on & 0x0001) << 5) |
\r
344 ((j2k->cp->epb_on & 0x0001) << 6) | ((j2k->cp->info_on & 0x0001) << 7);
\r
349 bool jpwl_epb_fill(opj_j2k_t *j2k, jpwl_epb_ms_t *epb, unsigned char *buf, unsigned char *post_buf) {
\r
351 unsigned long int L1, L2, L3, L4;
\r
353 unsigned long int P, NN_P;
\r
355 /* Operating buffer */
\r
356 static unsigned char codeword[NN], *parityword;
\r
358 unsigned char *L1_buf, *L2_buf;
\r
359 /* these ones are static, since we need to keep memory of
\r
360 the exact place from one call to the other */
\r
361 static unsigned char *L3_buf, *L4_buf;
\r
363 /* some consistency check */
\r
365 opj_event_msg(j2k->cinfo, EVT_ERROR, "There is no operating buffer for EPBs\n");
\r
369 if (!post_buf && !L4_buf) {
\r
370 opj_event_msg(j2k->cinfo, EVT_ERROR, "There is no operating buffer for EPBs data\n");
\r
375 * Compute parity bytes on pre-data, ALWAYS present (at least only for EPB parms)
\r
378 /* Initialize RS structures */
\r
379 P = epb->n_pre - epb->k_pre;
\r
381 memset(codeword, 0, NN);
\r
382 parityword = codeword + NN_P;
\r
385 /* pre-data begins pre_len bytes before of EPB buf */
\r
386 L1_buf = buf - epb->pre_len;
\r
387 L1 = epb->pre_len + 13;
\r
389 /* redundancy for pre-data begins immediately after EPB parms */
\r
391 L2 = (epb->n_pre - epb->k_pre) * (unsigned short int) ceil((double) L1 / (double) epb->k_pre);
\r
394 the position of L4 buffer can be:
\r
395 1) passed as a parameter: in that case use it
\r
396 2) null: in that case use the previous (static) one
\r
400 L4 = epb->post_len;
\r
402 /* post-data redundancy begins immediately after pre-data redundancy */
\r
403 L3_buf = L2_buf + L2;
\r
404 L3 = (epb->n_post - epb->k_post) * (unsigned short int) ceil((double) L4 / (double) epb->k_post);
\r
406 /* let's check whether EPB length is sufficient to contain all these data */
\r
407 if (epb->Lepb < (11 + L2 + L3))
\r
408 opj_event_msg(j2k->cinfo, EVT_ERROR, "There is no room in EPB data field for writing redundancy data\n");
\r
409 /*printf("Env. %d, nec. %d (%d + %d)\n", epb->Lepb - 11, L2 + L3, L2, L3);*/
\r
411 /* Compute redundancy of pre-data message words */
\r
413 while (remaining) {
\r
415 /* copy message data into codeword buffer */
\r
416 if (remaining < epb->k_pre) {
\r
417 /* the last message word is zero-padded */
\r
418 memset(codeword, 0, NN);
\r
419 memcpy(codeword, L1_buf, remaining);
\r
420 L1_buf += remaining;
\r
424 memcpy(codeword, L1_buf, epb->k_pre);
\r
425 L1_buf += epb->k_pre;
\r
426 remaining -= epb->k_pre;
\r
430 /* Encode the buffer and obtain parity bytes */
\r
431 if (encode_rs(codeword, parityword))
\r
432 opj_event_msg(j2k->cinfo, EVT_WARNING,
\r
433 "Possible encoding error in codeword @ position #%d\n", (L1_buf - buf) / epb->k_pre);
\r
435 /* copy parity bytes only in redundancy buffer */
\r
436 memcpy(L2_buf, parityword, P);
\r
438 /* advance parity buffer */
\r
443 * Compute parity bytes on post-data, may be absent if there are no data
\r
445 /*printf("Hprot is %d (tileno=%d, k_pre=%d, n_pre=%d, k_post=%d, n_post=%d, pre_len=%d, post_len=%d)\n",
\r
446 epb->hprot, epb->tileno, epb->k_pre, epb->n_pre, epb->k_post, epb->n_post, epb->pre_len,
\r
448 if (epb->hprot < 0) {
\r
450 /* there should be no EPB */
\r
452 } else if (epb->hprot == 0) {
\r
454 /* no protection for the data */
\r
455 /* advance anyway */
\r
456 L4_buf += epb->post_len;
\r
458 } else if (epb->hprot == 16) {
\r
461 unsigned short int mycrc = 0x0000;
\r
463 /* compute the CRC field (excluding itself) */
\r
465 while (remaining--)
\r
466 jpwl_updateCRC16(&mycrc, *(L4_buf++));
\r
468 /* write the CRC field */
\r
469 *(L3_buf++) = (unsigned char) (mycrc >> 8);
\r
470 *(L3_buf++) = (unsigned char) (mycrc >> 0);
\r
472 } else if (epb->hprot == 32) {
\r
475 unsigned long int mycrc = 0x00000000;
\r
477 /* compute the CRC field (excluding itself) */
\r
479 while (remaining--)
\r
480 jpwl_updateCRC32(&mycrc, *(L4_buf++));
\r
482 /* write the CRC field */
\r
483 *(L3_buf++) = (unsigned char) (mycrc >> 24);
\r
484 *(L3_buf++) = (unsigned char) (mycrc >> 16);
\r
485 *(L3_buf++) = (unsigned char) (mycrc >> 8);
\r
486 *(L3_buf++) = (unsigned char) (mycrc >> 0);
\r
492 /* Initialize RS structures */
\r
493 P = epb->n_post - epb->k_post;
\r
495 memset(codeword, 0, NN);
\r
496 parityword = codeword + NN_P;
\r
499 /* Compute redundancy of post-data message words */
\r
501 while (remaining) {
\r
503 /* copy message data into codeword buffer */
\r
504 if (remaining < epb->k_post) {
\r
505 /* the last message word is zero-padded */
\r
506 memset(codeword, 0, NN);
\r
507 memcpy(codeword, L4_buf, remaining);
\r
508 L4_buf += remaining;
\r
512 memcpy(codeword, L4_buf, epb->k_post);
\r
513 L4_buf += epb->k_post;
\r
514 remaining -= epb->k_post;
\r
518 /* Encode the buffer and obtain parity bytes */
\r
519 if (encode_rs(codeword, parityword))
\r
520 opj_event_msg(j2k->cinfo, EVT_WARNING,
\r
521 "Possible encoding error in codeword @ position #%d\n", (L4_buf - buf) / epb->k_post);
\r
523 /* copy parity bytes only in redundancy buffer */
\r
524 memcpy(L3_buf, parityword, P);
\r
526 /* advance parity buffer */
\r
536 bool jpwl_correct(opj_j2k_t *j2k) {
\r
538 opj_cio_t *cio = j2k->cio;
\r
540 static bool mh_done = false;
\r
541 int mark_pos, id, len, skips, sot_pos;
\r
542 unsigned long int Psot = 0;
\r
544 /* go back to marker position */
\r
545 mark_pos = cio_tell(cio) - 2;
\r
546 cio_seek(cio, mark_pos);
\r
548 if ((j2k->state == J2K_STATE_MHSOC) && !mh_done) {
\r
550 int mark_val = 0, skipnum = 0;
\r
554 first thing to do, if we are here, is to look whether
\r
555 51 (skipnum) positions ahead there is an EPB, in case of MH
\r
559 first thing to do, if we are here, is to look whether
\r
560 45 (skipnum) positions ahead there is an EPB, in case of MH
\r
562 /* SIZ SIZ_FIELDS SIZ_COMPS FOLLOWING_MARKER */
\r
563 skipnum = 2 + 38 + 3 * j2k->cp->exp_comps + 2;
\r
564 if ((cio->bp + skipnum) < cio->end) {
\r
566 cio_skip(cio, skipnum);
\r
568 /* check that you are not going beyond the end of codestream */
\r
570 /* call EPB corrector */
\r
571 status = jpwl_epb_correct(j2k, /* J2K decompressor handle */
\r
572 cio->bp, /* pointer to EPB in codestream buffer */
\r
573 0, /* EPB type: MH */
\r
574 skipnum, /* length of pre-data */
\r
575 -1, /* length of post-data: -1 means auto */
\r
580 /* read the marker value */
\r
581 mark_val = (*(cio->bp) << 8) | *(cio->bp + 1);
\r
583 if (status && (mark_val == J2K_MS_EPB)) {
\r
593 if (true /*(j2k->state == J2K_STATE_TPHSOT) || (j2k->state == J2K_STATE_TPH)*/) {
\r
594 /* else, look if 12 positions ahead there is an EPB, in case of TPH */
\r
595 cio_seek(cio, mark_pos);
\r
596 if ((cio->bp + 12) < cio->end) {
\r
600 /* call EPB corrector */
\r
601 status = jpwl_epb_correct(j2k, /* J2K decompressor handle */
\r
602 cio->bp, /* pointer to EPB in codestream buffer */
\r
603 1, /* EPB type: TPH */
\r
604 12, /* length of pre-data */
\r
605 -1, /* length of post-data: -1 means auto */
\r
617 /* for now, don't use this code */
\r
619 /* else, look if here is an EPB, in case of other */
\r
620 if (mark_pos > 64) {
\r
621 /* it cannot stay before the first MH EPB */
\r
622 cio_seek(cio, mark_pos);
\r
625 /* call EPB corrector */
\r
626 status = jpwl_epb_correct(j2k, /* J2K decompressor handle */
\r
627 cio->bp, /* pointer to EPB in codestream buffer */
\r
628 2, /* EPB type: TPH */
\r
629 0, /* length of pre-data */
\r
630 -1, /* length of post-data: -1 means auto */
\r
639 /* nope, no EPBs probably, or they are so damaged that we can give up */
\r
644 /* AN ATTEMPT OF PARSER */
\r
645 /* NOT USED ACTUALLY */
\r
647 /* go to the beginning of the file */
\r
651 j2k->state = J2K_STATE_MHSOC;
\r
653 /* cycle all over the markers */
\r
654 while (cio_tell(cio) < cio->length) {
\r
656 /* read the marker */
\r
657 mark_pos = cio_tell(cio);
\r
658 id = cio_read(cio, 2);
\r
661 printf("Marker@%d: %X\n", cio_tell(cio) - 2, id);
\r
663 /* do an action in response to the read marker */
\r
666 /* short markers */
\r
670 j2k->state = J2K_STATE_MHSIZ;
\r
677 j2k->state = J2K_STATE_MT;
\r
682 /* particular case of SOD */
\r
684 len = Psot - (mark_pos - sot_pos) - 2;
\r
692 j2k->state = J2K_STATE_TPH;
\r
693 sot_pos = mark_pos; /* position of SOT */
\r
694 len = cio_read(cio, 2); /* read the length field */
\r
695 cio_skip(cio, 2); /* this field is unnecessary */
\r
696 Psot = cio_read(cio, 4); /* tile length */
\r
702 j2k->state = J2K_STATE_MH;
\r
703 /* read the length field */
\r
704 len = cio_read(cio, 2);
\r
710 /* read the length field */
\r
711 len = cio_read(cio, 2);
\r
717 /* skip to marker's end */
\r
718 cio_skip(cio, skips);
\r
725 bool jpwl_epb_correct(opj_j2k_t *j2k, unsigned char *buffer, int type, int pre_len, int post_len, int *conn,
\r
726 unsigned char **L4_bufp) {
\r
728 /* Operating buffer */
\r
729 unsigned char codeword[NN], *parityword;
\r
731 unsigned long int P, NN_P;
\r
732 unsigned long int L1, L4;
\r
733 int remaining, n_pre, k_pre, n_post, k_post;
\r
737 int orig_pos = cio_tell(j2k->cio);
\r
739 unsigned char *L1_buf, *L2_buf;
\r
740 unsigned char *L3_buf, *L4_buf;
\r
742 unsigned long int LDPepb, Pepb;
\r
743 unsigned short int Lepb;
\r
744 unsigned char Depb;
\r
745 char str1[25] = "";
\r
746 int myconn, errnum = 0;
\r
747 bool errflag = false;
\r
749 opj_cio_t *cio = j2k->cio;
\r
751 /* check for common errors */
\r
753 opj_event_msg(j2k->cinfo, EVT_ERROR, "The EPB pointer is a NULL buffer\n");
\r
757 /* set bignesses */
\r
760 /* pre-data correction */
\r
782 /* automatic setup */
\r
787 opj_event_msg(j2k->cinfo, EVT_ERROR, "Unknown expected EPB type\n");
\r
793 /* Initialize RS structures */
\r
796 tt = (int) floor((float) P / 2.0F);
\r
797 memset(codeword, 0, NN);
\r
798 parityword = codeword + NN_P;
\r
801 /* Correct pre-data message words */
\r
802 L1_buf = buffer - pre_len;
\r
803 L2_buf = buffer + 13;
\r
805 while (remaining) {
\r
807 /* always zero-pad codewords */
\r
808 /* (this is required, since after decoding the zeros in the long codeword
\r
809 could change, and keep unchanged in subsequent calls) */
\r
810 memset(codeword, 0, NN);
\r
812 /* copy codeword buffer into message bytes */
\r
813 if (remaining < k_pre)
\r
814 memcpy(codeword, L1_buf, remaining);
\r
816 memcpy(codeword, L1_buf, k_pre);
\r
818 /* copy redundancy buffer in parity bytes */
\r
819 memcpy(parityword, L2_buf, P);
\r
821 /* Decode the buffer and possibly obtain corrected bytes */
\r
822 status = eras_dec_rs(codeword, NULL, 0);
\r
823 if (status == -1) {
\r
824 /*if (conn == NULL)
\r
825 opj_event_msg(j2k->cinfo, EVT_WARNING,
\r
826 "Possible decoding error in codeword @ position #%d\n", (L1_buf - buffer) / k_pre);*/
\r
828 /* we can try to safely get out from the function:
\r
829 if we are here, either this is not an EPB or the first codeword
\r
830 is too damaged to be helpful */
\r
833 } else if (status == 0) {
\r
834 /*if (conn == NULL)
\r
835 opj_event_msg(j2k->cinfo, EVT_INFO, "codeword is correctly decoded\n");*/
\r
837 } else if (status < tt) {
\r
838 /*if (conn == NULL)
\r
839 opj_event_msg(j2k->cinfo, EVT_WARNING, "%d errors corrected in codeword\n", status);*/
\r
843 /*if (conn == NULL)
\r
844 opj_event_msg(j2k->cinfo, EVT_WARNING, "EPB correction capability exceeded\n");
\r
850 /* advance parity buffer */
\r
851 if ((status >= 0) && (status < tt))
\r
852 /* copy back corrected parity only if all is OK */
\r
853 memcpy(L2_buf, parityword, P);
\r
856 /* advance message buffer */
\r
857 if (remaining < k_pre) {
\r
858 if ((status >= 0) && (status < tt))
\r
859 /* copy back corrected data only if all is OK */
\r
860 memcpy(L1_buf, codeword, remaining);
\r
861 L1_buf += remaining;
\r
865 if ((status >= 0) && (status < tt))
\r
866 /* copy back corrected data only if all is OK */
\r
867 memcpy(L1_buf, codeword, k_pre);
\r
869 remaining -= k_pre;
\r
874 /* print summary */
\r
878 opj_event_msg(j2k->cinfo, EVT_INFO, "+ %d symbol errors corrected (Ps=%.1e)\n", errnum,
\r
879 (float) errnum / ((float) n_pre * (float) L1 / (float) k_pre));*/
\r
881 /*opj_event_msg(j2k->cinfo, EVT_INFO, "+ there were unrecoverable errors\n");*/
\r
887 /* presumably, now, EPB parameters are correct */
\r
888 /* let's get them */
\r
890 /* Simply read the EPB parameters */
\r
893 cio_skip(cio, 2); /* the marker */
\r
894 Lepb = cio_read(cio, 2);
\r
895 Depb = cio_read(cio, 1);
\r
896 LDPepb = cio_read(cio, 4);
\r
897 Pepb = cio_read(cio, 4);
\r
899 /* What does Pepb tells us about the protection method? */
\r
900 if (((Pepb & 0xF0000000) >> 28) == 0)
\r
901 sprintf(str1, "pred"); /* predefined */
\r
902 else if (((Pepb & 0xF0000000) >> 28) == 1)
\r
903 sprintf(str1, "crc-%d", 16 * ((Pepb & 0x00000001) + 1)); /* CRC mode */
\r
904 else if (((Pepb & 0xF0000000) >> 28) == 2)
\r
905 sprintf(str1, "rs(%d,32)", (Pepb & 0x0000FF00) >> 8); /* RS mode */
\r
906 else if (Pepb == 0xFFFFFFFF)
\r
907 sprintf(str1, "nometh"); /* RS mode */
\r
909 sprintf(str1, "unknown"); /* unknown */
\r
911 /* Now we write them to screen */
\r
912 if (!conn && post_len)
\r
913 opj_event_msg(j2k->cinfo, EVT_INFO,
\r
914 "EPB(%d): (%sl, %sp, %u), %lu, %s\n",
\r
915 cio_tell(cio) - 13,
\r
916 (Depb & 0x40) ? "" : "n", /* latest EPB or not? */
\r
917 (Depb & 0x80) ? "" : "n", /* packed or unpacked EPB? */
\r
918 (Depb & 0x3F), /* EPB index value */
\r
919 LDPepb, /*length of the data protected by the EPB */
\r
920 str1); /* protection method */
\r
923 /* well, we need to investigate how long is the connected length of packed EPBs */
\r
925 if ((Depb & 0x40) == 0) /* not latest in header */
\r
926 jpwl_epb_correct(j2k, /* J2K decompressor handle */
\r
927 buffer + Lepb + 2, /* pointer to next EPB in codestream buffer */
\r
928 2, /* EPB type: should be of other type */
\r
929 0, /* only EPB fields */
\r
930 0, /* do not look after */
\r
938 printf("connected = %d\n", myconn);*/
\r
940 /*cio_seek(j2k->cio, orig_pos);
\r
944 the position of L4 buffer is at the end of currently connected EPBs
\r
947 L4_buf = buffer + myconn;
\r
948 else if (!(*L4_bufp))
\r
949 L4_buf = buffer + myconn;
\r
952 if (post_len == -1)
\r
953 L4 = LDPepb - pre_len - 13;
\r
954 else if (post_len == 0)
\r
961 /* Do a further check here on the read parameters */
\r
962 if (L4 > (unsigned long) cio_numbytesleft(j2k->cio))
\r
966 /* we are ready for decoding the remaining data */
\r
967 if (((Pepb & 0xF0000000) >> 28) == 1) {
\r
969 if ((16 * ((Pepb & 0x00000001) + 1)) == 16) {
\r
972 unsigned short int mycrc = 0x0000, filecrc = 0x0000;
\r
974 /* compute the CRC field */
\r
976 while (remaining--)
\r
977 jpwl_updateCRC16(&mycrc, *(L4_buf++));
\r
979 /* read the CRC field */
\r
980 filecrc = *(L3_buf++) << 8;
\r
981 filecrc |= *(L3_buf++);
\r
983 /* check the CRC field */
\r
984 if (mycrc == filecrc) {
\r
986 opj_event_msg(j2k->cinfo, EVT_INFO, "- CRC is OK\n");
\r
989 opj_event_msg(j2k->cinfo, EVT_WARNING, "- CRC is KO (r=%d, c=%d)\n", filecrc, mycrc);
\r
994 if ((16 * ((Pepb & 0x00000001) + 1)) == 32) {
\r
997 unsigned long int mycrc = 0x00000000, filecrc = 0x00000000;
\r
999 /* compute the CRC field */
\r
1001 while (remaining--)
\r
1002 jpwl_updateCRC32(&mycrc, *(L4_buf++));
\r
1004 /* read the CRC field */
\r
1005 filecrc = *(L3_buf++) << 24;
\r
1006 filecrc |= *(L3_buf++) << 16;
\r
1007 filecrc |= *(L3_buf++) << 8;
\r
1008 filecrc |= *(L3_buf++);
\r
1010 /* check the CRC field */
\r
1011 if (mycrc == filecrc) {
\r
1013 opj_event_msg(j2k->cinfo, EVT_INFO, "- CRC is OK\n");
\r
1016 opj_event_msg(j2k->cinfo, EVT_WARNING, "- CRC is KO (r=%d, c=%d)\n", filecrc, mycrc);
\r
1021 } else if ((((Pepb & 0xF0000000) >> 28) == 2) || (((Pepb & 0xF0000000) >> 28) == 0)) {
\r
1022 /* RS coding here */
\r
1024 if (((Pepb & 0xF0000000) >> 28) == 0) {
\r
1032 n_post = (Pepb & 0x0000FF00) >> 8;
\r
1035 /* Initialize RS structures */
\r
1036 P = n_post - k_post;
\r
1038 tt = (int) floor((float) P / 2.0F);
\r
1039 memset(codeword, 0, NN);
\r
1040 parityword = codeword + NN_P;
\r
1043 /* Correct post-data message words */
\r
1044 /*L4_buf = buffer + Lepb + 2;*/
\r
1047 while (remaining) {
\r
1049 /* always zero-pad codewords */
\r
1050 /* (this is required, since after decoding the zeros in the long codeword
\r
1051 could change, and keep unchanged in subsequent calls) */
\r
1052 memset(codeword, 0, NN);
\r
1054 /* copy codeword buffer into message bytes */
\r
1055 if (remaining < k_post)
\r
1056 memcpy(codeword, L4_buf, remaining);
\r
1058 memcpy(codeword, L4_buf, k_post);
\r
1060 /* copy redundancy buffer in parity bytes */
\r
1061 memcpy(parityword, L3_buf, P);
\r
1063 /* Decode the buffer and possibly obtain corrected bytes */
\r
1064 status = eras_dec_rs(codeword, NULL, 0);
\r
1065 if (status == -1) {
\r
1066 /*if (conn == NULL)
\r
1067 opj_event_msg(j2k->cinfo, EVT_WARNING,
\r
1068 "Possible decoding error in codeword @ position #%d\n", (L4_buf - (buffer + Lepb + 2)) / k_post);*/
\r
1071 } else if (status == 0) {
\r
1072 /*if (conn == NULL)
\r
1073 opj_event_msg(j2k->cinfo, EVT_INFO, "codeword is correctly decoded\n");*/
\r
1075 } else if (status < tt) {
\r
1076 /*if (conn == NULL)
\r
1077 opj_event_msg(j2k->cinfo, EVT_WARNING, "%d errors corrected in codeword\n", status);*/
\r
1081 /*if (conn == NULL)
\r
1082 opj_event_msg(j2k->cinfo, EVT_WARNING, "EPB correction capability exceeded\n");
\r
1088 /* advance parity buffer */
\r
1089 if ((status >= 0) && (status < tt))
\r
1090 /* copy back corrected data only if all is OK */
\r
1091 memcpy(L3_buf, parityword, P);
\r
1094 /* advance message buffer */
\r
1095 if (remaining < k_post) {
\r
1096 if ((status >= 0) && (status < tt))
\r
1097 /* copy back corrected data only if all is OK */
\r
1098 memcpy(L4_buf, codeword, remaining);
\r
1099 L4_buf += remaining;
\r
1103 if ((status >= 0) && (status < tt))
\r
1104 /* copy back corrected data only if all is OK */
\r
1105 memcpy(L4_buf, codeword, k_post);
\r
1107 remaining -= k_post;
\r
1113 /* give back the L4_buf address */
\r
1115 *L4_bufp = L4_buf;
\r
1117 /* print summary */
\r
1121 opj_event_msg(j2k->cinfo, EVT_INFO, "- %d symbol errors corrected (Ps=%.1e)\n", errnum,
\r
1122 (float) errnum / (float) LDPepb);
\r
1124 opj_event_msg(j2k->cinfo, EVT_INFO, "- there were unrecoverable errors\n");
\r
1128 cio_seek(j2k->cio, orig_pos);
\r
1133 void jpwl_epc_write(jpwl_epc_ms_t *epc, unsigned char *buf) {
\r
1136 *(buf++) = (unsigned char) (J2K_MS_EPC >> 8);
\r
1137 *(buf++) = (unsigned char) (J2K_MS_EPC >> 0);
\r
1140 *(buf++) = (unsigned char) (epc->Lepc >> 8);
\r
1141 *(buf++) = (unsigned char) (epc->Lepc >> 0);
\r
1144 *(buf++) = (unsigned char) (epc->Pcrc >> 8);
\r
1145 *(buf++) = (unsigned char) (epc->Pcrc >> 0);
\r
1148 *(buf++) = (unsigned char) (epc->DL >> 24);
\r
1149 *(buf++) = (unsigned char) (epc->DL >> 16);
\r
1150 *(buf++) = (unsigned char) (epc->DL >> 8);
\r
1151 *(buf++) = (unsigned char) (epc->DL >> 0);
\r
1154 *(buf++) = (unsigned char) (epc->Pepc >> 0);
\r
1157 /*memcpy(buf, epc->data, (size_t) epc->Lepc - 9);*/
\r
1158 memset(buf, 0, (size_t) epc->Lepc - 9);
\r
1161 int jpwl_esds_add(opj_j2k_t *j2k, jpwl_marker_t *jwmarker, int *jwmarker_num,
\r
1162 int comps, unsigned char addrm, unsigned char ad_size,
\r
1163 unsigned char senst, unsigned char se_size,
\r
1164 double place_pos, int tileno) {
\r
1169 jpwl_esd_ms_t *jpwl_esd_create(opj_j2k_t *j2k, int comp, unsigned char addrm, unsigned char ad_size,
\r
1170 unsigned char senst, unsigned char se_size, int tileno,
\r
1171 unsigned long int svalnum, void *sensval) {
\r
1173 jpwl_esd_ms_t *esd = NULL;
\r
1176 if (!(esd = (jpwl_esd_ms_t *) malloc((size_t) 1 * sizeof (jpwl_esd_ms_t)))) {
\r
1177 opj_event_msg(j2k->cinfo, EVT_ERROR, "Could not allocate room for ESD MS\n");
\r
1181 /* if relative sensitivity, activate byte range mode */
\r
1185 /* size of sensval's ... */
\r
1186 if ((ad_size != 0) && (ad_size != 2) && (ad_size != 4)) {
\r
1187 opj_event_msg(j2k->cinfo, EVT_ERROR, "Address size %d for ESD MS is forbidden\n", ad_size);
\r
1190 if ((se_size != 1) && (se_size != 2)) {
\r
1191 opj_event_msg(j2k->cinfo, EVT_ERROR, "Sensitivity size %d for ESD MS is forbidden\n", se_size);
\r
1195 /* ... depends on the addressing mode */
\r
1200 ad_size = 0; /* as per the standard */
\r
1201 esd->sensval_size = se_size;
\r
1206 /* auto sense address size */
\r
1208 /* if there are more than 66% of (2^16 - 1) bytes, switch to 4 bytes
\r
1209 (we keep space for possible EPBs being inserted) */
\r
1210 ad_size = (j2k->image_info->codestream_size > (1 * 65535 / 3)) ? 4 : 2;
\r
1211 esd->sensval_size = ad_size + ad_size + se_size;
\r
1214 /* packet range */
\r
1216 /* auto sense address size */
\r
1218 /* if there are more than 2^16 - 1 packets, switch to 4 bytes */
\r
1219 ad_size = (j2k->image_info->num > 65535) ? 4 : 2;
\r
1220 esd->sensval_size = ad_size + ad_size + se_size;
\r
1224 opj_event_msg(j2k->cinfo, EVT_ERROR, "Address mode %d for ESD MS is unimplemented\n", addrm);
\r
1228 opj_event_msg(j2k->cinfo, EVT_ERROR, "Address mode %d for ESD MS is forbidden\n", addrm);
\r
1232 /* set or unset sensitivity values */
\r
1233 if (svalnum <= 0) {
\r
1237 /* just based on the portions of a codestream */
\r
1239 /* MH + no. of THs + no. of packets */
\r
1240 svalnum = 1 + (j2k->image_info->tw * j2k->image_info->th) * (1 + j2k->image_info->num);
\r
1243 /* all the ones that are based on the packets */
\r
1246 /* MH: all the packets and all the tiles info is written */
\r
1247 svalnum = j2k->image_info->tw * j2k->image_info->th * j2k->image_info->num;
\r
1249 /* TPH: only that tile info is written */
\r
1250 svalnum = j2k->image_info->num;
\r
1256 /* fill private fields */
\r
1257 esd->senst = senst;
\r
1258 esd->ad_size = ad_size;
\r
1259 esd->se_size = se_size;
\r
1260 esd->addrm = addrm;
\r
1261 esd->svalnum = svalnum;
\r
1262 esd->numcomps = j2k->image->numcomps;
\r
1263 esd->tileno = tileno;
\r
1265 /* Set the ESD parameters */
\r
1266 /* length, excluding data field */
\r
1267 if (esd->numcomps < 257)
\r
1268 esd->Lesd = 4 + (unsigned short int) (esd->svalnum * esd->sensval_size);
\r
1270 esd->Lesd = 5 + (unsigned short int) (esd->svalnum * esd->sensval_size);
\r
1272 /* component data field */
\r
1276 /* we are averaging */
\r
1281 esd->Pesd |= (esd->addrm & 0x03) << 6; /* addressing mode */
\r
1282 esd->Pesd |= (esd->senst & 0x07) << 3; /* sensitivity type */
\r
1283 esd->Pesd |= ((esd->se_size >> 1) & 0x01) << 2; /* sensitivity size */
\r
1284 esd->Pesd |= ((esd->ad_size >> 2) & 0x01) << 1; /* addressing size */
\r
1285 esd->Pesd |= (comp < 0) ? 0x01 : 0x00; /* averaging components */
\r
1287 /* if pointer to sensval is NULL, we can fill data field by ourselves */
\r
1290 /* old code moved to jpwl_esd_fill() */
\r
1294 /* we set the data field as the sensitivity values poinnter passed to the function */
\r
1295 esd->data = (unsigned char *) sensval;
\r
1301 bool jpwl_esd_fill(opj_j2k_t *j2k, jpwl_esd_ms_t *esd, unsigned char *buf) {
\r
1304 unsigned long int vv;
\r
1305 unsigned long int addr1, addr2;
\r
1306 double dvalue, Omax2, tmp, TSE, MSE, oldMSE, PSNR, oldPSNR;
\r
1307 unsigned short int pfpvalue;
\r
1308 unsigned long int addrmask = 0x00000000;
\r
1309 bool doneMH = false, doneTPH = false;
\r
1311 /* sensitivity values in image info are as follows:
\r
1312 - for each tile, distotile is the starting distortion for that tile, sum of all components
\r
1313 - for each packet in a tile, disto is the distortion reduction caused by that packet to that tile
\r
1314 - the TSE for a single tile should be given by distotile - sum(disto) , for all components
\r
1315 - the MSE for a single tile is given by TSE / nbpix , for all components
\r
1316 - the PSNR for a single tile is given by 10*log10( Omax^2 / MSE) , for all components
\r
1317 (Omax is given by 2^bpp - 1 for unsigned images and by 2^(bpp - 1) - 1 for signed images
\r
1320 /* browse all components and find Omax */
\r
1322 for (i = 0; i < j2k->image->numcomps; i++) {
\r
1323 tmp = pow(2.0, (double) (j2k->image->comps[i].sgnd ?
\r
1324 (j2k->image->comps[i].bpp - 1) : (j2k->image->comps[i].bpp))) - 1;
\r
1328 Omax2 = Omax2 * Omax2;
\r
1330 /* if pointer of esd->data is not null, simply write down all the values byte by byte */
\r
1332 for (i = 0; i < (int) esd->svalnum; i++)
\r
1333 *(buf++) = esd->data[i];
\r
1337 /* addressing mask */
\r
1338 if (esd->ad_size == 2)
\r
1339 addrmask = 0x0000FFFF; /* two bytes */
\r
1341 addrmask = 0xFFFFFFFF; /* four bytes */
\r
1343 /* set on precise point where sensitivity starts */
\r
1344 if (esd->numcomps < 257)
\r
1349 /* let's fill the data fields */
\r
1350 for (vv = (esd->tileno < 0) ? 0 : (j2k->image_info->num * esd->tileno); vv < esd->svalnum; vv++) {
\r
1352 int thistile = vv / j2k->image_info->num, thispacket = vv % j2k->image_info->num;
\r
1354 /* skip for the hack some lines below */
\r
1355 if (thistile == j2k->image_info->tw * j2k->image_info->th)
\r
1358 /* starting tile distortion */
\r
1359 if (thispacket == 0) {
\r
1360 TSE = j2k->image_info->tile[thistile].distotile;
\r
1361 oldMSE = TSE / j2k->image_info->tile[thistile].nbpix;
\r
1362 oldPSNR = 10.0 * log10(Omax2 / oldMSE);
\r
1366 TSE -= j2k->image_info->tile[thistile].packet[thispacket].disto;
\r
1369 MSE = TSE / j2k->image_info->tile[thistile].nbpix;
\r
1372 PSNR = 10.0 * log10(Omax2 / MSE);
\r
1374 /* fill the address range */
\r
1375 switch (esd->addrm) {
\r
1379 /* nothing, there is none */
\r
1384 /* start address of packet */
\r
1385 addr1 = (j2k->image_info->tile[thistile].packet[thispacket].start_pos) & addrmask;
\r
1386 /* end address of packet */
\r
1387 addr2 = (j2k->image_info->tile[thistile].packet[thispacket].end_pos) & addrmask;
\r
1390 /* packet range */
\r
1392 /* not implemented here */
\r
1393 opj_event_msg(j2k->cinfo, EVT_WARNING, "Addressing mode packet_range is not implemented\n");
\r
1396 /* unknown addressing method */
\r
1398 /* not implemented here */
\r
1399 opj_event_msg(j2k->cinfo, EVT_WARNING, "Unknown addressing mode\n");
\r
1404 /* hack for writing relative sensitivity of MH and TPHs */
\r
1405 if ((esd->senst == 0) && (thispacket == 0)) {
\r
1408 if ((thistile == 0) && !doneMH) {
\r
1409 /* we have to manage MH addresses */
\r
1410 addr1 = 0; /* start of MH */
\r
1411 addr2 = j2k->image_info->main_head_end; /* end of MH */
\r
1412 /* set special dvalue for this MH */
\r
1414 doneMH = true; /* don't come here anymore */
\r
1415 vv--; /* wrap back loop counter */
\r
1417 } else if (!doneTPH) {
\r
1418 /* we have to manage TPH addresses */
\r
1419 addr1 = j2k->image_info->tile[thistile].start_pos;
\r
1420 addr2 = j2k->image_info->tile[thistile].end_header;
\r
1421 /* set special dvalue for this TPH */
\r
1423 doneTPH = true; /* don't come here till the next tile */
\r
1424 vv--; /* wrap back loop counter */
\r
1428 doneTPH = false; /* reset TPH counter */
\r
1430 /* write the addresses to the buffer */
\r
1431 switch (esd->ad_size) {
\r
1439 *(buf++) = (unsigned char) (addr1 >> 8);
\r
1440 *(buf++) = (unsigned char) (addr1 >> 0);
\r
1441 *(buf++) = (unsigned char) (addr2 >> 8);
\r
1442 *(buf++) = (unsigned char) (addr2 >> 0);
\r
1447 *(buf++) = (unsigned char) (addr1 >> 24);
\r
1448 *(buf++) = (unsigned char) (addr1 >> 16);
\r
1449 *(buf++) = (unsigned char) (addr1 >> 8);
\r
1450 *(buf++) = (unsigned char) (addr1 >> 0);
\r
1451 *(buf++) = (unsigned char) (addr2 >> 24);
\r
1452 *(buf++) = (unsigned char) (addr2 >> 16);
\r
1453 *(buf++) = (unsigned char) (addr2 >> 8);
\r
1454 *(buf++) = (unsigned char) (addr2 >> 0);
\r
1463 /* let's fill the value field */
\r
1464 switch (esd->senst) {
\r
1466 /* relative sensitivity */
\r
1468 /* we just write down the packet ordering */
\r
1469 if (dvalue == -10)
\r
1471 dvalue = MAX_V1 + 1000.0; /* this will cause pfpvalue set to 0xFFFF */
\r
1472 else if (dvalue == -1)
\r
1474 dvalue = MAX_V1 + 1000.0; /* this will cause pfpvalue set to 0xFFFF */
\r
1476 /* packet: first is most important, and then in decreasing order
\r
1477 down to the last, which counts for 1 */
\r
1478 dvalue = jpwl_pfp_to_double(j2k->image_info->num - thispacket, esd->se_size);
\r
1483 /* !!! WRONG: let's put here disto field of packets !!! */
\r
1487 /* MSE reduction */
\r
1489 dvalue = oldMSE - MSE;
\r
1498 /* PSNR increase */
\r
1500 dvalue = PSNR - oldPSNR;
\r
1507 opj_event_msg(j2k->cinfo, EVT_WARNING, "MAXERR sensitivity mode is not implemented\n");
\r
1518 opj_event_msg(j2k->cinfo, EVT_WARNING, "Reserved sensitivity mode is not implemented\n");
\r
1526 /* compute the pseudo-floating point value */
\r
1527 pfpvalue = jpwl_double_to_pfp(dvalue, esd->se_size);
\r
1529 /* write the pfp value to the buffer */
\r
1530 switch (esd->se_size) {
\r
1534 *(buf++) = (unsigned char) (pfpvalue >> 0);
\r
1539 *(buf++) = (unsigned char) (pfpvalue >> 8);
\r
1540 *(buf++) = (unsigned char) (pfpvalue >> 0);
\r
1549 void jpwl_esd_write(jpwl_esd_ms_t *esd, unsigned char *buf) {
\r
1552 *(buf++) = (unsigned char) (J2K_MS_ESD >> 8);
\r
1553 *(buf++) = (unsigned char) (J2K_MS_ESD >> 0);
\r
1556 *(buf++) = (unsigned char) (esd->Lesd >> 8);
\r
1557 *(buf++) = (unsigned char) (esd->Lesd >> 0);
\r
1560 if (esd->numcomps >= 257)
\r
1561 *(buf++) = (unsigned char) (esd->Cesd >> 8);
\r
1562 *(buf++) = (unsigned char) (esd->Cesd >> 0);
\r
1565 *(buf++) = (unsigned char) (esd->Pesd >> 0);
\r
1568 if (esd->numcomps < 257)
\r
1569 memset(buf, 0xAA, (size_t) esd->Lesd - 4);
\r
1570 /*memcpy(buf, esd->data, (size_t) esd->Lesd - 4);*/
\r
1572 memset(buf, 0xAA, (size_t) esd->Lesd - 5);
\r
1573 /*memcpy(buf, esd->data, (size_t) esd->Lesd - 5);*/
\r
1576 unsigned short int jpwl_double_to_pfp(double V, int bytes) {
\r
1578 unsigned short int em, e, m;
\r
1587 } else if (V > MAX_V1) {
\r
1591 e = (unsigned short int) (floor(log(V) * 1.44269504088896) / 4.0);
\r
1592 m = (unsigned short int) (0.5 + (V / (pow(2.0, (double) (4 * e)))));
\r
1594 em = ((e & 0x000F) << 4) + (m & 0x000F);
\r
1602 } else if (V > MAX_V2) {
\r
1606 e = (unsigned short int) floor(log(V) * 1.44269504088896) + 15;
\r
1607 m = (unsigned short int) (0.5 + 2048.0 * ((V / (pow(2.0, (double) e - 15.0))) - 1.0));
\r
1609 em = ((e & 0x001F) << 11) + (m & 0x07FF);
\r
1621 double jpwl_pfp_to_double(unsigned short int em, int bytes) {
\r
1628 V = (double) (em & 0x0F) * pow(2.0, (double) (em & 0xF0));
\r
1633 V = pow(2.0, (double) ((em & 0xF800) >> 11) - 15.0) * (1.0 + (double) (em & 0x07FF) / 2048.0);
\r
1646 bool jpwl_update_info(opj_j2k_t *j2k, jpwl_marker_t *jwmarker, int jwmarker_num) {
\r
1649 unsigned long int addlen;
\r
1651 opj_image_info_t *info = j2k->image_info;
\r
1652 int tileno, packno, numtiles = info->th * info->tw, numpacks = info->num;
\r
1654 if (!j2k || !jwmarker ) {
\r
1655 opj_event_msg(j2k->cinfo, EVT_ERROR, "J2K handle or JPWL markers list badly allocated\n");
\r
1659 /* main_head_end: how many markers are there before? */
\r
1661 for (mm = 0; mm < jwmarker_num; mm++)
\r
1662 if (jwmarker[mm].pos < (unsigned long int) info->main_head_end)
\r
1663 addlen += jwmarker[mm].len + 2;
\r
1664 info->main_head_end += addlen;
\r
1666 /* codestream_size: always increment with all markers */
\r
1668 for (mm = 0; mm < jwmarker_num; mm++)
\r
1669 addlen += jwmarker[mm].len + 2;
\r
1670 info->codestream_size += addlen;
\r
1672 /* navigate through all the tiles */
\r
1673 for (tileno = 0; tileno < numtiles; tileno++) {
\r
1675 /* start_pos: increment with markers before SOT */
\r
1677 for (mm = 0; mm < jwmarker_num; mm++)
\r
1678 if (jwmarker[mm].pos < (unsigned long int) info->tile[tileno].start_pos)
\r
1679 addlen += jwmarker[mm].len + 2;
\r
1680 info->tile[tileno].start_pos += addlen;
\r
1682 /* end_header: increment with markers before of it */
\r
1684 for (mm = 0; mm < jwmarker_num; mm++)
\r
1685 if (jwmarker[mm].pos < (unsigned long int) info->tile[tileno].end_header)
\r
1686 addlen += jwmarker[mm].len + 2;
\r
1687 info->tile[tileno].end_header += addlen;
\r
1689 /* end_pos: increment with markers before the end of this tile */
\r
1690 /* code is disabled, since according to JPWL no markers can be beyond TPH */
\r
1692 for (mm = 0; mm < jwmarker_num; mm++)
\r
1693 if (jwmarker[mm].pos < (unsigned long int) info->tile[tileno].end_pos)
\r
1694 addlen += jwmarker[mm].len + 2;*/
\r
1695 info->tile[tileno].end_pos += addlen;
\r
1697 /* navigate through all the packets in this tile */
\r
1698 for (packno = 0; packno < numpacks; packno++) {
\r
1700 /* start_pos: increment with markers before the packet */
\r
1701 /* disabled for the same reason as before */
\r
1703 for (mm = 0; mm < jwmarker_num; mm++)
\r
1704 if (jwmarker[mm].pos < (unsigned long int) info->tile[tileno].packet[packno].start_pos)
\r
1705 addlen += jwmarker[mm].len + 2;*/
\r
1706 info->tile[tileno].packet[packno].start_pos += addlen;
\r
1708 /* end_pos: increment if marker is before the end of packet */
\r
1709 /* disabled for the same reason as before */
\r
1711 for (mm = 0; mm < jwmarker_num; mm++)
\r
1712 if (jwmarker[mm].pos < (unsigned long int) info->tile[tileno].packet[packno].end_pos)
\r
1713 addlen += jwmarker[mm].len + 2;*/
\r
1714 info->tile[tileno].packet[packno].end_pos += addlen;
\r
1722 #endif /* USE_JPWL */