ref: 6c52ccfe9970dc5b709c378d49187ebb2874aa81
parent: 91c71a44412a052616c45f6e50a0431a103514a8
author: raph <raph@ded80894-8fb9-0310-811b-c03f3676ab4d>
date: Mon Jul 1 15:34:31 EDT 2002
Text region decoding now seems to decode 042_10.jb2 correctly. Added IAID decoding procedure. Changed jbig2_decode_text_region to use IAID procedure. Fixed off-by-one errors in corner alignment calculations. Added for (;;) loop for 3c, corresponding to looping over all symbol instances in a strip (outer while loop corresponds to looping over all strips in the region). Fixed predicates in CURS updating logic. git-svn-id: http://svn.ghostscript.com/jbig2dec/trunk@94 ded80894-8fb9-0310-811b-c03f3676ab4d
--- a/Makefile.am
+++ b/Makefile.am
@@ -1,10 +1,10 @@
-# $Id: Makefile.am,v 1.4 2002/06/20 15:42:47 giles Exp $
+# $Id: Makefile.am,v 1.5 2002/07/01 19:34:30 raph Exp $
## process this file with automake to generate Makefile.in
lib_LIBRARIES = libjbig2dec.a
libjbig2dec_a_SOURCES = jbig2.c \
- jbig2_arith.c jbig2_arith_int.c jbig2_huffman.c \
+ jbig2_arith.c jbig2_arith_int.c jbig2_arith_iaid.c jbig2_huffman.c \
jbig2_segment.c jbig2_page.c \
jbig2_symbol_dict.c jbig2_text.c \
jbig2_generic.c jbig2_mmr.c \
--- /dev/null
+++ b/jbig2_arith_iaid.c
@@ -1,0 +1,67 @@
+/* Annex A.3 */
+
+#ifdef VERBOSE
+#include <stdio.h> /* for debug printing only */
+#endif
+
+#include <stddef.h>
+#include <stdint.h>
+#include "jbig2.h"
+#include "jbig2_priv.h"
+#include "jbig2_arith.h"
+#include "jbig2_arith_iaid.h"
+
+struct _Jbig2ArithIaidCtx {
+ int SBSYMCODELEN;
+ Jbig2ArithCx *IAIDx;
+};
+
+Jbig2ArithIaidCtx *
+jbig2_arith_iaid_ctx_new(Jbig2Ctx *ctx, int SBSYMCODELEN)
+{
+ Jbig2ArithIaidCtx *result = jbig2_new(ctx, Jbig2ArithIaidCtx, 1);
+ int ctx_size = 1 << SBSYMCODELEN;
+
+ result->SBSYMCODELEN = SBSYMCODELEN;
+ result->IAIDx = jbig2_alloc(ctx->allocator, ctx_size);
+ memset(result->IAIDx, 0, ctx_size);
+
+ return result;
+}
+
+/* A.3 */
+/* Return value: -1 on error, 0 on normal value */
+int
+jbig2_arith_iaid_decode(Jbig2ArithIaidCtx *ctx, Jbig2ArithState *as,
+ int32_t *p_result)
+{
+ Jbig2ArithCx *IAIDx = ctx->IAIDx;
+ int SBSYMCODELEN = ctx->SBSYMCODELEN;
+ int PREV = 1;
+ int D;
+ int i;
+
+ /* A.3 (2) */
+ for (i = 0; i < SBSYMCODELEN; i++)
+ {
+ D = jbig2_arith_decode(as, &IAIDx[PREV]);
+#ifdef VERBOSE
+ fprintf(stderr, "IAID%x: D = %d\n", PREV, D);
+#endif
+ PREV = (PREV << 1) | D;
+ }
+ /* A.3 (3) */
+ PREV -= 1 << SBSYMCODELEN;
+#ifdef VERBOSE
+ fprintf(stderr, "IAID result: %d\n", PREV);
+#endif
+ *p_result = PREV;
+ return 0;
+}
+
+void
+jbig2_arith_iaid_ctx_free(Jbig2Ctx *ctx, Jbig2ArithIaidCtx *iax)
+{
+ jbig2_free(ctx->allocator, iax->IAIDx);
+ jbig2_free(ctx->allocator, iax);
+}
--- /dev/null
+++ b/jbig2_arith_iaid.h
@@ -1,0 +1,11 @@
+typedef struct _Jbig2ArithIaidCtx Jbig2ArithIaidCtx;
+
+Jbig2ArithIaidCtx *
+jbig2_arith_iaid_ctx_new(Jbig2Ctx *ctx, int SBSYMCODELEN);
+
+int
+jbig2_arith_iaid_decode(Jbig2ArithIaidCtx *ctx, Jbig2ArithState *as,
+ int32_t *p_result);
+
+void
+jbig2_arith_iaid_ctx_free(Jbig2Ctx *ctx, Jbig2ArithIaidCtx *iax);
--- a/jbig2_text.c
+++ b/jbig2_text.c
@@ -8,7 +8,7 @@
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
- $Id: jbig2_text.c,v 1.6 2002/06/27 14:02:08 giles Exp $
+ $Id: jbig2_text.c,v 1.7 2002/07/01 19:34:31 raph Exp $
*/
#include <stddef.h>
@@ -24,6 +24,7 @@
#include "jbig2_priv.h"
#include "jbig2_arith.h"
#include "jbig2_arith_int.h"
+#include "jbig2_arith_iaid.h"
#include "jbig2_generic.h"
#include "jbig2_symbol_dict.h"
@@ -97,7 +98,7 @@
int32_t CURT;
int S,T;
int x,y;
- bool first_symbol = TRUE;
+ bool first_symbol;
uint32_t index, max_id;
Jbig2Image *IB;
Jbig2ArithState *as;
@@ -105,7 +106,7 @@
Jbig2ArithIntCtx *IAFS = NULL;
Jbig2ArithIntCtx *IADS = NULL;
Jbig2ArithIntCtx *IAIT = NULL;
- Jbig2ArithIntCtx *IAID = NULL;
+ Jbig2ArithIaidCtx *IAID = NULL;
int code;
max_id = 0;
@@ -121,6 +122,8 @@
}
if (!params->SBHUFF) {
+ int SBSYMCODELEN;
+
Jbig2WordStream *ws = jbig2_word_stream_buf_new(ctx, data, size);
as = jbig2_arith_new(ctx, ws);
IADT = jbig2_arith_int_ctx_new(ctx);
@@ -127,7 +130,9 @@
IAFS = jbig2_arith_int_ctx_new(ctx);
IADS = jbig2_arith_int_ctx_new(ctx);
IAIT = jbig2_arith_int_ctx_new(ctx);
- IAID = jbig2_arith_int_ctx_new(ctx);
+ /* Table 31 */
+ for (SBSYMCODELEN = 0; (1 << SBSYMCODELEN) < max_id; SBSYMCODELEN++);
+ IAID = jbig2_arith_iaid_ctx_new(ctx, SBSYMCODELEN);
}
/* 6.4.5 (1) */
@@ -157,109 +162,113 @@
STRIPT += DT;
fprintf(stderr, "decoded DT = %d, STRIPT = %d\n", DT, STRIPT);
- /* (3c) */
- if (first_symbol) {
- /* 6.4.7 */
- if (params->SBHUFF) {
- /* todo */
- } else {
- code = jbig2_arith_int_decode(IAFS, as, &DFS);
- }
- FIRSTS += DFS;
- CURS = FIRSTS;
- first_symbol = FALSE;
+ first_symbol = TRUE;
+ /* (3c) */
+ for (;;) {
+ /* (3c.i) */
+ if (first_symbol) {
+ /* 6.4.7 */
+ if (params->SBHUFF) {
+ /* todo */
+ } else {
+ code = jbig2_arith_int_decode(IAFS, as, &DFS);
+ }
+ FIRSTS += DFS;
+ CURS = FIRSTS;
+ first_symbol = FALSE;
fprintf(stderr, "decoded DFS = %d (first symbol) CURS = %d\n", DFS, CURS);
- } else {
- /* 6.4.8 */
- if (params->SBHUFF) {
- /* todo */
- } else {
- code = jbig2_arith_int_decode(IADS, as, &IDS);
- }
- if (code) {
- fprintf(stderr, "Symbol instance S coordinate OOB: End of Strip\n");
- continue;
- }
- CURS += IDS + params->SBDSOFFSET;
- fprintf(stderr, "decoded IDS = %d, CURS = %d\n", IDS, CURS);
- }
+ } else {
+ /* (3c.ii), 6.4.8 */
+ if (params->SBHUFF) {
+ /* todo */
+ } else {
+ code = jbig2_arith_int_decode(IADS, as, &IDS);
+ }
+ if (code) {
+ fprintf(stderr, "Symbol instance S coordinate OOB: End of Strip\n");
+ break;
+ }
+ CURS += IDS + params->SBDSOFFSET;
+ fprintf(stderr, "decoded IDS = %d, CURS = %d\n", IDS, CURS);
+ }
- /* 6.4.9 */
- if (params->SBSTRIPS == 1) {
- CURT = 0;
- } else if (params->SBHUFF) {
- /* todo */
- } else {
- code = jbig2_arith_int_decode(IAIT, as, &CURT);
- }
- T = STRIPT + CURT;
- fprintf(stderr, "decoded CURT = %d, STRIPT = %d, T = %d\n", CURT, STRIPT, T);
-
- /* (3b.iv) / 6.4.10 decode the symbol id */
- if (params->SBHUFF) {
- /* todo */
- } else {
- code = jbig2_arith_int_decode(IAID, as, &ID);
- }
- if (ID < 0 || ID >= max_id) {
- return jbig2_error(ctx, JBIG2_SEVERITY_FATAL, segment->number,
- "symbol id out of range! (%d/%d)", ID, max_id);
- }
- fprintf(stderr, "decoded symbol id = %d (code = %d)\n", ID, code);
+ /* (3c.iii), 6.4.9 */
+ if (params->SBSTRIPS == 1) {
+ CURT = 0;
+ } else if (params->SBHUFF) {
+ /* todo */
+ } else {
+ code = jbig2_arith_int_decode(IAIT, as, &CURT);
+ }
+ T = STRIPT + CURT;
+ fprintf(stderr, "decoded CURT = %d, STRIPT = %d, T = %d\n", CURT, STRIPT, T);
- /* (3b.v) look up the symbol bitmap IB */
- {
- int id = ID;
-
- index = 0;
- while (id >= dicts[index]->n_symbols)
- id -= dicts[index++]->n_symbols;
- IB = dicts[index]->glyphs[id];
- }
+ /* (3b.iv) / 6.4.10 decode the symbol id */
+ if (params->SBHUFF) {
+ /* todo */
+ } else {
+ code = jbig2_arith_iaid_decode(IAID, as, &ID);
+ }
+ if (ID < 0 || ID >= max_id) {
+ return jbig2_error(ctx, JBIG2_SEVERITY_FATAL, segment->number,
+ "symbol id out of range! (%d/%d)", ID, max_id);
+ }
+ fprintf(stderr, "decoded symbol id = %d (code = %d)\n", ID, code);
+
+ /* (3c.v) look up the symbol bitmap IB */
+ {
+ int id = ID;
+
+ index = 0;
+ while (id >= dicts[index]->n_symbols)
+ id -= dicts[index++]->n_symbols;
+ IB = dicts[index]->glyphs[id];
+ }
- /* (3b.vi) */
- if ((!params->TRANSPOSED) && (params->REFCORNER > 1)) {
- CURS += IB->width - 1;
- } else if ((params->TRANSPOSED) && (params->REFCORNER < 2)) {
- CURS += IB->height - 1;
- }
+ /* (3c.vi) */
+ if ((!params->TRANSPOSED) && (params->REFCORNER > 1)) {
+ CURS += IB->width - 1;
+ } else if ((params->TRANSPOSED) && !(params->REFCORNER & 1)) {
+ CURS += IB->height - 1;
+ }
- /* (3b.vii) */
- S = CURS;
+ /* (3c.vii) */
+ S = CURS;
- /* (3b.vii) */
- if (!params->TRANSPOSED) {
- switch (params->REFCORNER) { // FIXME: double check offsets
- case JBIG2_CORNER_TOPLEFT: x = S; y = T; break;
- case JBIG2_CORNER_TOPRIGHT: x = S - IB->width; y = T; break;
- case JBIG2_CORNER_BOTTOMLEFT: x = S; y = T - IB->height; break;
- case JBIG2_CORNER_BOTTOMRIGHT: x = S - IB->width; y = T - IB->height; break;
- }
- } else { /* TRANSPOSED */
- switch (params->REFCORNER) {
- case JBIG2_CORNER_TOPLEFT: x = S; y = T; break;
- case JBIG2_CORNER_TOPRIGHT: x = S - IB->width; y = T; break;
- case JBIG2_CORNER_BOTTOMLEFT: x = S; y = T - IB->height; break;
- case JBIG2_CORNER_BOTTOMRIGHT: x = S - IB->width; y = T - IB->height; break;
- }
- }
+ /* (3c.viii) */
+ if (!params->TRANSPOSED) {
+ switch (params->REFCORNER) { // FIXME: double check offsets
+ case JBIG2_CORNER_TOPLEFT: x = S; y = T; break;
+ case JBIG2_CORNER_TOPRIGHT: x = S - IB->width + 1; y = T; break;
+ case JBIG2_CORNER_BOTTOMLEFT: x = S; y = T - IB->height + 1; break;
+ case JBIG2_CORNER_BOTTOMRIGHT: x = S - IB->width + 1; y = T - IB->height + 1; break;
+ }
+ } else { /* TRANSPOSED */
+ switch (params->REFCORNER) {
+ case JBIG2_CORNER_TOPLEFT: x = S; y = T; break;
+ case JBIG2_CORNER_TOPRIGHT: x = S - IB->width + 1; y = T; break;
+ case JBIG2_CORNER_BOTTOMLEFT: x = S; y = T - IB->height + 1; break;
+ case JBIG2_CORNER_BOTTOMRIGHT: x = S - IB->width + 1; y = T - IB->height + 1; break;
+ }
+ }
- /* (3b.ix) */
- jbig2_error(ctx, JBIG2_SEVERITY_DEBUG, segment->number,
- "composing glyph id %d: %dx%d @ (%d,%d) symbol %d/%d",
- ID, IB->width, IB->height, x, y, NINSTANCES + 1,
- params->SBNUMINSTANCES);
- jbig2_image_compose(ctx, image, IB, x, y, params->SBCOMBOP);
+ /* (3c.ix) */
+ jbig2_error(ctx, JBIG2_SEVERITY_DEBUG, segment->number,
+ "composing glyph id %d: %dx%d @ (%d,%d) symbol %d/%d",
+ ID, IB->width, IB->height, x, y, NINSTANCES + 1,
+ params->SBNUMINSTANCES);
+ jbig2_image_compose(ctx, image, IB, x, y, params->SBCOMBOP);
- /* (3b.x) */
- if ((!params->TRANSPOSED) && (params->REFCORNER < 2)) {
- CURS += IB->width -1 ;
- } else if ((params->TRANSPOSED) && (params->REFCORNER > 1)) {
- CURS += IB->height - 1;
- }
+ /* (3c.x) */
+ if ((!params->TRANSPOSED) && (params->REFCORNER < 2)) {
+ CURS += IB->width -1 ;
+ } else if ((params->TRANSPOSED) && (params->REFCORNER & 1)) {
+ CURS += IB->height - 1;
+ }
- /* (3b.xi) */
- NINSTANCES++;
+ /* (3c.xi) */
+ NINSTANCES++;
+ }
}
return 0;
@@ -393,4 +402,4 @@
too_short:
return jbig2_error(ctx, JBIG2_SEVERITY_FATAL, segment->number,
"Segment too short");
-}
\ No newline at end of file
+}