📄 jbig.c
字号:
/* prevent uint32 overflow: s->l0 * 2 ^ s->d < 2 ^ 32 */ if (s->d > 31 || (s->d != 0 && s->l0 >= (1UL << (32 - s->d)))) return; if (s->yd1 < s->yd) s->yd1 = s->yd; if (s->yd1 > s->yd) s->options |= JBG_VLENGTH; /* ensure correct zero padding of bitmap at the final byte of each line */ if (s->xd & 7) { bpl = jbg_ceil_half(s->xd, 3); /* bytes per line */ for (plane = 0; plane < s->planes; plane++) for (y = 0; y < s->yd; y++) s->lhp[0][plane][y * bpl + bpl - 1] &= ~((1 << (8 - (s->xd & 7))) - 1); } /* prepare BIH */ buf[0] = s->dl; buf[1] = s->dh; buf[2] = s->planes; buf[3] = 0; xd = jbg_ceil_half(s->xd, s->d - s->dh); yd = jbg_ceil_half(s->yd1, s->d - s->dh); buf[4] = (unsigned char)(xd >> 24); buf[5] = (unsigned char)((xd >> 16) & 0xff); buf[6] = (unsigned char)((xd >> 8) & 0xff); buf[7] = (unsigned char)(xd & 0xff); buf[8] = (unsigned char)(yd >> 24); buf[9] = (unsigned char)((yd >> 16) & 0xff); buf[10] = (unsigned char)((yd >> 8) & 0xff); buf[11] = (unsigned char)(yd & 0xff); buf[12] = (unsigned char)(s->l0 >> 24); buf[13] = (unsigned char)((s->l0 >> 16) & 0xff); buf[14] = (unsigned char)((s->l0 >> 8) & 0xff); buf[15] = (unsigned char)(s->l0 & 0xff); buf[16] = (unsigned char)(s->mx); buf[17] = (unsigned char)(s->my); buf[18] = (unsigned char)(s->order); buf[19] = (unsigned char)(s->options & 0x7f);#if 0 /* sanitize L0 (if it was set to 0xffffffff for T.85-style NEWLEN tests) */ if (s->l0 > (s->yd >> s->d)) s->l0 = s->yd >> s->d;#endif /* calculate number of stripes that will be required */ s->stripes = jbg_stripes(s->l0, s->yd, s->d); /* allocate buffers for SDE pointers */ if (s->sde == NULL) { s->sde = (struct jbg_buf ****) checked_malloc(s->stripes, sizeof(struct jbg_buf ***)); for (stripe = 0; stripe < s->stripes; stripe++) { s->sde[stripe] = (struct jbg_buf ***) checked_malloc(s->d + 1, sizeof(struct jbg_buf **)); for (layer = 0; layer < s->d + 1; layer++) { s->sde[stripe][layer] = (struct jbg_buf **) checked_malloc(s->planes, sizeof(struct jbg_buf *)); for (plane = 0; plane < s->planes; plane++) s->sde[stripe][layer][plane] = SDE_TODO; } } } /* output BIH */ s->data_out(buf, 20, s->file); if ((s->options & (JBG_DPON | JBG_DPPRIV | JBG_DPLAST)) == (JBG_DPON | JBG_DPPRIV)) { /* write private table */ jbg_int2dppriv(dpbuf, s->dppriv); s->data_out(dpbuf, 1728, s->file); }#if 0 /* * Encode everything first. This is a simple-minded alternative to * all the tricky on-demand encoding logic in output_sde() for * debugging purposes. */ for (layer = s->dh; layer >= s->dl; layer--) { for (plane = 0; plane < s->planes; plane++) { if (layer > 0) resolution_reduction(s, plane, layer); for (stripe = 0; stripe < s->stripes; stripe++) encode_sde(s, stripe, layer, plane); s->highres[plane] ^= 1; } }#endif /* * Generic loops over all SDEs. Which loop represents layer, plane and * stripe depends on the option flags. */ /* start and end value vor each loop */ is[iindex[order][STRIPE]] = 0; ie[iindex[order][STRIPE]] = s->stripes - 1; is[iindex[order][LAYER]] = s->dl; ie[iindex[order][LAYER]] = s->dh; is[iindex[order][PLANE]] = 0; ie[iindex[order][PLANE]] = s->planes - 1; for (ii[0] = is[0]; ii[0] <= ie[0]; ii[0]++) for (ii[1] = is[1]; ii[1] <= ie[1]; ii[1]++) for (ii[2] = is[2]; ii[2] <= ie[2]; ii[2]++) { stripe = ii[iindex[order][STRIPE]]; if (s->order & JBG_HITOLO) layer = s->dh - (ii[iindex[order][LAYER]] - s->dl); else layer = ii[iindex[order][LAYER]]; plane = ii[iindex[order][PLANE]]; output_sde(s, stripe, layer, plane); /* * When we generate a NEWLEN test case (s->yd1 > s->yd), output * NEWLEN after last stripe if we have only a single * resolution layer or plane (see ITU-T T.85 profile), otherwise * output NEWLEN before last stripe. */ if (s->yd1 > s->yd && (stripe == s->stripes - 1 || (stripe == s->stripes - 2 && (s->dl != s->dh || s->planes > 1)))) { s->yd1 = s->yd; yd = jbg_ceil_half(s->yd, s->d - s->dh); buf[0] = MARKER_ESC; buf[1] = MARKER_NEWLEN; buf[2] = (unsigned char)(yd >> 24); buf[3] = (unsigned char)((yd >> 16) & 0xff); buf[4] = (unsigned char)((yd >> 8) & 0xff); buf[5] = (unsigned char)(yd & 0xff); s->data_out(buf, 6, s->file);#ifdef DEBUG fprintf(stderr, "NEWLEN: yd=%lu\n", yd);#endif if (stripe == s->stripes - 1) { buf[1] = MARKER_SDNORM; s->data_out(buf, 2, s->file); } } } return;}void jbg_enc_free(struct jbg_enc_state *s){ unsigned long stripe; int layer, plane;#ifdef DEBUG fprintf(stderr, "jbg_enc_free(%p)\n", (void *) s);#endif /* clear buffers for SDEs */ if (s->sde) { for (stripe = 0; stripe < s->stripes; stripe++) { for (layer = 0; layer < s->d + 1; layer++) { for (plane = 0; plane < s->planes; plane++) if (s->sde[stripe][layer][plane] != SDE_DONE && s->sde[stripe][layer][plane] != SDE_TODO) jbg_buf_free(&s->sde[stripe][layer][plane]); checked_free(s->sde[stripe][layer]); } checked_free(s->sde[stripe]); } checked_free(s->sde); } /* clear free_list */ jbg_buf_free(&s->free_list); /* clear memory for arithmetic encoder states */ checked_free(s->s); /* clear memory for differential-layer typical prediction buffer */ checked_free(s->tp); /* clear memory for adaptive template pixel offsets */ checked_free(s->tx); /* clear lowres image buffers */ if (s->lhp[1]) { for (plane = 0; plane < s->planes; plane++) checked_free(s->lhp[1][plane]); checked_free(s->lhp[1]); } /* clear buffer for index of highres image in lhp */ checked_free(s->highres); return;}/* * Convert the error codes used by jbg_dec_in() into a string * written in the selected language and character set. */const char *jbg_strerror(int errnum, int language){ if (errnum < 0 || errnum >= NEMSG) return "Unknown error code passed to jbg_strerror()"; if (language < 0 || language >= NEMSG_LANG) return "Unknown language code passed to jbg_strerror()"; return errmsg[language][errnum];}/* * The constructor for a decoder */void jbg_dec_init(struct jbg_dec_state *s){ s->order = 0; s->d = -1; s->bie_len = 0; s->buf_len = 0; s->dppriv = NULL; s->xmax = 4294967295UL; s->ymax = 4294967295UL; s->dmax = 256; s->s = NULL; return;}/* * Specify a maximum image size for the decoder. If the JBIG file has * the order bit ILEAVE, but not the bit SEQ set, then the decoder * will abort to decode after the image has reached the maximal * resolution layer which is still not wider than xmax or higher than * ymax. */void jbg_dec_maxsize(struct jbg_dec_state *s, unsigned long xmax, unsigned long ymax){ if (xmax > 0) s->xmax = xmax; if (ymax > 0) s->ymax = ymax; return;}/* * Decode the new len PSDC bytes to which data points and add them to * the current stripe. Return the number of bytes which have actually * been read (this will be less than len if a marker segment was * part of the data or if the final byte was 0xff were this code * can not determine, whether we have a marker segment. */static size_t decode_pscd(struct jbg_dec_state *s, unsigned char *data, size_t len){ unsigned long stripe; unsigned int layer, plane; unsigned long hl, ll, y, hx, hy, lx, ly, hbpl, lbpl; unsigned char *hp, *lp1, *lp2, *p1, *q1; register unsigned long line_h1, line_h2, line_h3; register unsigned long line_l1, line_l2, line_l3; struct jbg_ardec_state *se; unsigned long x; long o; unsigned a; int n; int pix, cx = 0, slntp, tx; /* SDE loop variables */ stripe = s->ii[iindex[s->order & 7][STRIPE]]; layer = s->ii[iindex[s->order & 7][LAYER]]; plane = s->ii[iindex[s->order & 7][PLANE]]; /* forward data to arithmetic decoder */ se = s->s[plane] + layer - s->dl; se->pscd_ptr = data; se->pscd_end = data + len; /* number of lines per stripe in highres image */ hl = s->l0 << layer; /* number of lines per stripe in lowres image */ ll = hl >> 1; /* current line number in highres image */ y = stripe * hl + s->i; /* number of pixels in highres image */ hx = jbg_ceil_half(s->xd, s->d - layer); hy = jbg_ceil_half(s->yd, s->d - layer); /* number of pixels in lowres image */ lx = jbg_ceil_half(hx, 1); ly = jbg_ceil_half(hy, 1); /* bytes per line in highres and lowres image */ hbpl = jbg_ceil_half(hx, 3); lbpl = jbg_ceil_half(lx, 3); /* pointer to highres and lowres image bytes */ hp = s->lhp[ layer & 1][plane] + (stripe * hl + s->i) * hbpl + (s->x >> 3); lp2 = s->lhp[(layer-1) & 1][plane] + (stripe * ll + (s->i >> 1)) * lbpl + (s->x >> 4); lp1 = lp2 + lbpl; /* restore a few local variables */ line_h1 = s->line_h1; line_h2 = s->line_h2; line_h3 = s->line_h3; line_l1 = s->line_l1; line_l2 = s->line_l2; line_l3 = s->line_l3; x = s->x; if (s->x == 0 && s->i == 0 && (stripe == 0 || s->reset[plane][layer - s->dl])) { s->tx[plane][layer - s->dl] = s->ty[plane][layer - s->dl] = 0; if (s->pseudo) s->lntp[plane][layer - s->dl] = 1; }#ifdef DEBUG if (s->x == 0 && s->i == 0 && s->pseudo) fprintf(stderr, "decode_pscd(%p, %p, %ld): s/d/p = %2lu/%2u/%2u\n", (void *) s, (void *) data, (long) len, stripe, layer, plane);#endif if (layer == 0) { /* * Decode lowest resolution layer */ for (; s->i < hl && y < hy; s->i++, y++) { /* adaptive template changes */ if (x == 0) for (n = 0; n < s->at_moves; n++) if (s->at_line[n] == s->i) { s->tx[plane][layer - s->dl] = s->at_tx[n]; s->ty[plane][layer - s->dl] = s->at_ty[n];#ifdef DEBUG fprintf(stderr, "ATMOVE: line=%lu, tx=%d, ty=%d.\n", s->i, s->tx[plane][layer - s->dl], s->ty[plane][layer - s->dl]);#endif } tx = s->tx[plane][layer - s->dl]; assert(tx >= 0); /* i.e., tx can safely be cast to unsigned */ /* typical prediction */ if (s->options & JBG_TPBON && s->pseudo) { slntp = arith_decode(se, (s->options & JBG_LRLTWO) ? TPB2CX : TPB3CX); if (se->result == JBG_MORE || se->result == JBG_MARKER) goto leave; s->lntp[plane][layer - s->dl] = !(slntp ^ s->lntp[plane][layer - s->dl]); if (s->lntp[plane][layer - s->dl]) { /* this line is 'not typical' and has to be coded completely */ s->pseudo = 0; } else { /* this line is 'typical' (i.e. identical to the previous one) */ p1 = hp; if (s->i == 0 && (stripe == 0 || s->reset[plane][layer - s->dl])) while (p1 < hp + hbpl) *p1++ = 0; else { q1 = hp - hbpl; while (q1 < hp) *p1++ = *q1++; } hp += hbpl; continue; } } /* * Layout of the variables line_h1, line_h2, line_h3, which contain * as bits the neighbour pixels of the currently decoded pixel X: * * 76543210 76543210 76543210 76543210 line_h3 * 76543210 76543210 76543210 76543210 line_h2 * 76543210 76543210 76543210 76543210 X line_h1 */ if (x == 0) { line_h1 = line_h2 = line_h3 = 0; if (s->i > 0 || (y > 0 && !s->reset[plane][layer - s->dl])) line_h2 = (long)*(hp - hbpl) << 8; if (s->i > 1 || (y > 1 && !s->reset[plane][layer - s->dl])) line_h3 = (long)*(hp - hbpl - hbpl) << 8; } /* * Another tiny JBIG standard bug: * * While implementing the line_h3 handling here, I discovered * another problem with the ITU-T T.82(1993 E) specification. * This might be a somewhat pathological case, however. The * standard is unclear about how a decoder should behave in the * following situation: * * Assume we are in layer 0 and all stripes are single lines * (L0=1 allowed by table 9). We are now decoding the first (and * only) line of the third stripe. Assume, the first stripe was * terminated by SDRST and the second stripe was terminated by * SDNORM. While decoding the only line of the third stripe with * the three-line template, we need access to pixels from the * previous two stripes. We know that the previous stripe * terminated with SDNROM, so we access the pixel from the * second stripe. But do we have to replace the pixels from the * first stripe by background pixels, because this stripe ended * with SDRST? The standard, especially clause 6.2.5 does never * mention this case, so the behaviour is undefined here. My * current implementation remembers only the marker used to * terminate the previous stripe. In the above example, the * pixels of the first stripe are accessed despite the fact that * this stripe ended with SDRST. An alternative (only slightly * more complicated) implementation would be to remember the end * marker (SDNORM or SDRST) of the previous two stripes in a * plane/layer and to act accordingly when accessing the two * previous lines. What am I supposed to do here? * * As the standard is unclear about the correct behaviour in the * situation of the above example, I strongly suggest to avoid * the following situation while encoding data with JBIG: * * LRLTWO = 0, L0=1 and both SDNORM and SDRST appear in layer 0. * * I guess that only a very few if any encoders will switch * between SDNORM and SDRST, so let us hope that this ambiguity * in the standard will never cause any interoperability * problems. * * Markus Kuhn -- 1995-04-30 */ /* decode line */ while (x < hx) { if ((x & 7) == 0) { if (x < hbpl * 8 - 8 && (s->i > 0 || (y > 0 && !s->reset[plane][layer - s->dl]))) { line_h2 |= *(hp - hbpl + 1);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -