Mercurial > hgrepos > Python2 > PyMuPDF
comparison mupdf-source/source/fitz/load-jbig2.c @ 2:b50eed0cc0ef upstream
ADD: MuPDF v1.26.7: the MuPDF source as downloaded by a default build of PyMuPDF 1.26.4.
The directory name has changed: no version number in the expanded directory now.
| author | Franz Glasner <fzglas.hg@dom66.de> |
|---|---|
| date | Mon, 15 Sep 2025 11:43:07 +0200 |
| parents | |
| children |
comparison
equal
deleted
inserted
replaced
| 1:1d09e1dec1d9 | 2:b50eed0cc0ef |
|---|---|
| 1 // Copyright (C) 2004-2021 Artifex Software, Inc. | |
| 2 // | |
| 3 // This file is part of MuPDF. | |
| 4 // | |
| 5 // MuPDF is free software: you can redistribute it and/or modify it under the | |
| 6 // terms of the GNU Affero General Public License as published by the Free | |
| 7 // Software Foundation, either version 3 of the License, or (at your option) | |
| 8 // any later version. | |
| 9 // | |
| 10 // MuPDF is distributed in the hope that it will be useful, but WITHOUT ANY | |
| 11 // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS | |
| 12 // FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more | |
| 13 // details. | |
| 14 // | |
| 15 // You should have received a copy of the GNU Affero General Public License | |
| 16 // along with MuPDF. If not, see <https://www.gnu.org/licenses/agpl-3.0.en.html> | |
| 17 // | |
| 18 // Alternative licensing terms are available from the licensor. | |
| 19 // For commercial licensing, see <https://www.artifex.com/> or contact | |
| 20 // Artifex Software, Inc., 39 Mesa Street, Suite 108A, San Francisco, | |
| 21 // CA 94129, USA, for further information. | |
| 22 | |
| 23 #include "mupdf/fitz.h" | |
| 24 | |
| 25 #include "pixmap-imp.h" | |
| 26 | |
| 27 #include <jbig2.h> | |
| 28 | |
| 29 struct info | |
| 30 { | |
| 31 int width, height; | |
| 32 int xres, yres; | |
| 33 int pages; | |
| 34 fz_colorspace *cspace; | |
| 35 }; | |
| 36 | |
| 37 struct fz_jbig2_allocator | |
| 38 { | |
| 39 Jbig2Allocator super; | |
| 40 fz_context *ctx; | |
| 41 }; | |
| 42 | |
| 43 static void | |
| 44 error_callback(void *data, const char *msg, Jbig2Severity severity, uint32_t seg_idx) | |
| 45 { | |
| 46 fz_context *ctx = data; | |
| 47 if (severity == JBIG2_SEVERITY_FATAL) | |
| 48 fz_warn(ctx, "jbig2dec error: %s (segment %u)", msg, seg_idx); | |
| 49 else if (severity == JBIG2_SEVERITY_WARNING) | |
| 50 fz_warn(ctx, "jbig2dec warning: %s (segment %u)", msg, seg_idx); | |
| 51 #ifdef JBIG2_DEBUG | |
| 52 else if (severity == JBIG2_SEVERITY_INFO) | |
| 53 fz_warn(ctx, "jbig2dec info: %s (segment %u)", msg, seg_idx); | |
| 54 else if (severity == JBIG2_SEVERITY_DEBUG) | |
| 55 fz_warn(ctx, "jbig2dec debug: %s (segment %u)", msg, seg_idx); | |
| 56 #endif | |
| 57 } | |
| 58 | |
| 59 static void *fz_jbig2_alloc(Jbig2Allocator *allocator, size_t size) | |
| 60 { | |
| 61 fz_context *ctx = ((struct fz_jbig2_allocator *) allocator)->ctx; | |
| 62 return fz_malloc_no_throw(ctx, size); | |
| 63 } | |
| 64 | |
| 65 static void fz_jbig2_free(Jbig2Allocator *allocator, void *p) | |
| 66 { | |
| 67 fz_context *ctx = ((struct fz_jbig2_allocator *) allocator)->ctx; | |
| 68 fz_free(ctx, p); | |
| 69 } | |
| 70 | |
| 71 static void *fz_jbig2_realloc(Jbig2Allocator *allocator, void *p, size_t size) | |
| 72 { | |
| 73 fz_context *ctx = ((struct fz_jbig2_allocator *) allocator)->ctx; | |
| 74 if (size == 0) | |
| 75 { | |
| 76 fz_free(ctx, p); | |
| 77 return NULL; | |
| 78 } | |
| 79 if (p == NULL) | |
| 80 return Memento_label(fz_malloc(ctx, size), "jbig2_realloc"); | |
| 81 return Memento_label(fz_realloc_no_throw(ctx, p, size), "jbig2_realloc"); | |
| 82 } | |
| 83 | |
| 84 static fz_pixmap * | |
| 85 jbig2_read_image(fz_context *ctx, struct info *jbig2, const unsigned char *buf, size_t len, int only_metadata, int subimage) | |
| 86 { | |
| 87 Jbig2Ctx *jctx = NULL; | |
| 88 Jbig2Image *page = NULL; | |
| 89 struct fz_jbig2_allocator allocator; | |
| 90 fz_pixmap *pix = NULL; | |
| 91 | |
| 92 allocator.super.alloc = fz_jbig2_alloc; | |
| 93 allocator.super.free = fz_jbig2_free; | |
| 94 allocator.super.realloc = fz_jbig2_realloc; | |
| 95 allocator.ctx = ctx; | |
| 96 | |
| 97 fz_var(jctx); | |
| 98 fz_var(page); | |
| 99 fz_var(pix); | |
| 100 | |
| 101 fz_try(ctx) | |
| 102 { | |
| 103 jctx = jbig2_ctx_new((Jbig2Allocator *) &allocator, 0, NULL, error_callback, ctx); | |
| 104 if (jctx == NULL) | |
| 105 fz_throw(ctx, FZ_ERROR_LIBRARY, "cannot create jbig2 context"); | |
| 106 if (jbig2_data_in(jctx, buf, len) < 0) | |
| 107 fz_throw(ctx, FZ_ERROR_LIBRARY, "cannot decode jbig2 image"); | |
| 108 if (jbig2_complete_page(jctx) < 0) | |
| 109 fz_throw(ctx, FZ_ERROR_LIBRARY, "cannot complete jbig2 image"); | |
| 110 | |
| 111 if (only_metadata && subimage < 0) | |
| 112 { | |
| 113 while ((page = jbig2_page_out(jctx)) != NULL) | |
| 114 { | |
| 115 jbig2_release_page(jctx, page); | |
| 116 jbig2->pages++; | |
| 117 } | |
| 118 } | |
| 119 else if (only_metadata && subimage >= 0) | |
| 120 { | |
| 121 while ((page = jbig2_page_out(jctx)) != NULL && subimage > 0) | |
| 122 { | |
| 123 jbig2_release_page(jctx, page); | |
| 124 subimage--; | |
| 125 } | |
| 126 | |
| 127 if (page == NULL) | |
| 128 fz_throw(ctx, FZ_ERROR_LIBRARY, "no jbig2 image decoded"); | |
| 129 | |
| 130 jbig2->cspace = fz_device_gray(ctx); | |
| 131 jbig2->width = page->width; | |
| 132 jbig2->height = page->height; | |
| 133 jbig2->xres = 72; | |
| 134 jbig2->yres = 72; | |
| 135 } | |
| 136 else if (subimage >= 0) | |
| 137 { | |
| 138 while ((page = jbig2_page_out(jctx)) != NULL && subimage > 0) | |
| 139 { | |
| 140 jbig2_release_page(jctx, page); | |
| 141 subimage--; | |
| 142 } | |
| 143 | |
| 144 if (page == NULL) | |
| 145 fz_throw(ctx, FZ_ERROR_LIBRARY, "no jbig2 image decoded"); | |
| 146 | |
| 147 jbig2->cspace = fz_device_gray(ctx); | |
| 148 jbig2->width = page->width; | |
| 149 jbig2->height = page->height; | |
| 150 jbig2->xres = 72; | |
| 151 jbig2->yres = 72; | |
| 152 | |
| 153 pix = fz_new_pixmap(ctx, jbig2->cspace, jbig2->width, jbig2->height, NULL, 0); | |
| 154 fz_unpack_tile(ctx, pix, page->data, 1, 1, page->stride, 0); | |
| 155 fz_invert_pixmap(ctx, pix); | |
| 156 } | |
| 157 } | |
| 158 fz_always(ctx) | |
| 159 { | |
| 160 jbig2_release_page(jctx, page); | |
| 161 jbig2_ctx_free(jctx); | |
| 162 } | |
| 163 fz_catch(ctx) | |
| 164 { | |
| 165 fz_drop_pixmap(ctx, pix); | |
| 166 fz_rethrow(ctx); | |
| 167 } | |
| 168 | |
| 169 return pix; | |
| 170 } | |
| 171 | |
| 172 int | |
| 173 fz_load_jbig2_subimage_count(fz_context *ctx, const unsigned char *buf, size_t len) | |
| 174 { | |
| 175 struct info jbig2 = { 0 }; | |
| 176 int subimage_count = 0; | |
| 177 | |
| 178 fz_try(ctx) | |
| 179 { | |
| 180 jbig2_read_image(ctx, &jbig2, buf, len, 1, -1); | |
| 181 subimage_count = jbig2.pages; | |
| 182 } | |
| 183 fz_catch(ctx) | |
| 184 fz_rethrow(ctx); | |
| 185 | |
| 186 return subimage_count; | |
| 187 } | |
| 188 | |
| 189 void | |
| 190 fz_load_jbig2_info_subimage(fz_context *ctx, const unsigned char *buf, size_t len, int *wp, int *hp, int *xresp, int *yresp, fz_colorspace **cspacep, int subimage) | |
| 191 { | |
| 192 struct info jbig2 = { 0 }; | |
| 193 | |
| 194 jbig2_read_image(ctx, &jbig2, buf, len, 1, subimage); | |
| 195 *cspacep = fz_keep_colorspace(ctx, jbig2.cspace); | |
| 196 *wp = jbig2.width; | |
| 197 *hp = jbig2.height; | |
| 198 *xresp = jbig2.xres; | |
| 199 *yresp = jbig2.yres; | |
| 200 } | |
| 201 | |
| 202 fz_pixmap * | |
| 203 fz_load_jbig2_subimage(fz_context *ctx, const unsigned char *buf, size_t len, int subimage) | |
| 204 { | |
| 205 struct info jbig2 = { 0 }; | |
| 206 return jbig2_read_image(ctx, &jbig2, buf, len, 0, subimage); | |
| 207 } | |
| 208 | |
| 209 fz_pixmap * | |
| 210 fz_load_jbig2(fz_context *ctx, const unsigned char *buf, size_t len) | |
| 211 { | |
| 212 return fz_load_jbig2_subimage(ctx, buf, len, 0); | |
| 213 } | |
| 214 | |
| 215 void | |
| 216 fz_load_jbig2_info(fz_context *ctx, const unsigned char *buf, size_t len, int *wp, int *hp, int *xresp, int *yresp, fz_colorspace **cspacep) | |
| 217 { | |
| 218 fz_load_jbig2_info_subimage(ctx, buf, len, wp, hp, xresp, yresp, cspacep, 0); | |
| 219 } |
