diff options
author | Tom Sepez <tsepez@chromium.org> | 2017-05-31 15:18:28 -0700 |
---|---|---|
committer | Chromium commit bot <commit-bot@chromium.org> | 2017-05-31 22:49:33 +0000 |
commit | fc04f41200e4ba4f47f52f188708547e8a1bee6d (patch) | |
tree | 93e09a89b3dac5a3801be2e0820bc77adecd8f60 /core/fxcodec/codec/ccodec_bmpmodule.cpp | |
parent | d9dc962586d17ab113f1ad3abefc0fa2758c9d26 (diff) | |
download | pdfium-fc04f41200e4ba4f47f52f188708547e8a1bee6d.tar.xz |
Move all of ccodec_bmpmodule state to its context
This avoids a stale delegate pointer issue in the module. In theory,
it should also allow for multiple decodes at the same time from
different contexts within the same module, but this isn't used.
Rename associated context, and use |new| to create it. Along the
way, resolve a subtle FX_Alloc() vs. user-supplied callback
free() issue, and remove supporting code.
Bug: 728323
Change-Id: I7bb66bb5d5b4fa173bec2b445a8e71ab691fdf5c
Reviewed-on: https://pdfium-review.googlesource.com/6133
Reviewed-by: Lei Zhang <thestig@chromium.org>
Commit-Queue: Tom Sepez <tsepez@chromium.org>
Diffstat (limited to 'core/fxcodec/codec/ccodec_bmpmodule.cpp')
-rw-r--r-- | core/fxcodec/codec/ccodec_bmpmodule.cpp | 137 |
1 files changed, 67 insertions, 70 deletions
diff --git a/core/fxcodec/codec/ccodec_bmpmodule.cpp b/core/fxcodec/codec/ccodec_bmpmodule.cpp index 003f5d3d49..ae0a30c4b4 100644 --- a/core/fxcodec/codec/ccodec_bmpmodule.cpp +++ b/core/fxcodec/codec/ccodec_bmpmodule.cpp @@ -9,81 +9,78 @@ #include "core/fxcodec/codec/codec_int.h" #include "core/fxcodec/fx_codec.h" #include "core/fxcodec/lbmp/fx_bmp.h" +#include "core/fxcrt/cfx_unowned_ptr.h" #include "core/fxge/fx_dib.h" -struct FXBMP_Context { - bmp_decompress_struct_p bmp_ptr; - void* parent_ptr; +class CCodec_BmpModule::Context { + public: + Context(bmp_decompress_struct_p pBmp, + CCodec_BmpModule* pModule, + CCodec_BmpModule::Delegate* pDelegate); + ~Context(); - void* (*m_AllocFunc)(unsigned int); - void (*m_FreeFunc)(void*); + bmp_decompress_struct_p m_pBmp; + CFX_UnownedPtr<CCodec_BmpModule> const m_pModule; + CFX_UnownedPtr<CCodec_BmpModule::Delegate> const m_pDelegate; + char m_szLastError[256]; }; + extern "C" { -static void* bmp_alloc_func(unsigned int size) { - return FX_Alloc(char, size); -} -static void bmp_free_func(void* p) { - FX_Free(p); -} -}; -static void bmp_error_data(bmp_decompress_struct_p bmp_ptr, - const char* err_msg) { - strncpy((char*)bmp_ptr->err_ptr, err_msg, BMP_MAX_ERROR_SIZE - 1); - longjmp(bmp_ptr->jmpbuf, 1); + +static void bmp_error_data(bmp_decompress_struct_p pBmp, const char* err_msg) { + strncpy(pBmp->err_ptr, err_msg, BMP_MAX_ERROR_SIZE - 1); + longjmp(pBmp->jmpbuf, 1); } -static void bmp_read_scanline(bmp_decompress_struct_p bmp_ptr, + +static void bmp_read_scanline(bmp_decompress_struct_p pBmp, int32_t row_num, uint8_t* row_buf) { - FXBMP_Context* p = (FXBMP_Context*)bmp_ptr->context_ptr; - CCodec_BmpModule* pModule = (CCodec_BmpModule*)p->parent_ptr; - pModule->GetDelegate()->BmpReadScanline(row_num, row_buf); + auto* p = reinterpret_cast<CCodec_BmpModule::Context*>(pBmp->context_ptr); + p->m_pDelegate->BmpReadScanline(row_num, row_buf); } -static bool bmp_get_data_position(bmp_decompress_struct_p bmp_ptr, + +static bool bmp_get_data_position(bmp_decompress_struct_p pBmp, uint32_t rcd_pos) { - FXBMP_Context* p = (FXBMP_Context*)bmp_ptr->context_ptr; - CCodec_BmpModule* pModule = (CCodec_BmpModule*)p->parent_ptr; - return pModule->GetDelegate()->BmpInputImagePositionBuf(rcd_pos); + auto* p = reinterpret_cast<CCodec_BmpModule::Context*>(pBmp->context_ptr); + return p->m_pDelegate->BmpInputImagePositionBuf(rcd_pos); } -CCodec_BmpModule::CCodec_BmpModule() { +} // extern "C" + +CCodec_BmpModule::Context::Context(bmp_decompress_struct_p pBmp, + CCodec_BmpModule* pModule, + CCodec_BmpModule::Delegate* pDelegate) + : m_pBmp(pBmp), m_pModule(pModule), m_pDelegate(pDelegate) { memset(m_szLastError, 0, sizeof(m_szLastError)); } -CCodec_BmpModule::~CCodec_BmpModule() {} +CCodec_BmpModule::Context::~Context() { + bmp_destroy_decompress(&m_pBmp); +} -FXBMP_Context* CCodec_BmpModule::Start() { - FXBMP_Context* p = FX_Alloc(FXBMP_Context, 1); - if (!p) - return nullptr; +CCodec_BmpModule::CCodec_BmpModule() {} - memset(p, 0, sizeof(FXBMP_Context)); - if (!p) - return nullptr; +CCodec_BmpModule::~CCodec_BmpModule() {} - p->m_AllocFunc = bmp_alloc_func; - p->m_FreeFunc = bmp_free_func; - p->bmp_ptr = nullptr; - p->parent_ptr = this; - p->bmp_ptr = bmp_create_decompress(); - if (!p->bmp_ptr) { - FX_Free(p); +CCodec_BmpModule::Context* CCodec_BmpModule::Start(Delegate* pDelegate) { + bmp_decompress_struct_p pBmp = bmp_create_decompress(); + if (!pBmp) return nullptr; - } - p->bmp_ptr->context_ptr = p; - p->bmp_ptr->err_ptr = m_szLastError; - p->bmp_ptr->bmp_error_fn = bmp_error_data; - p->bmp_ptr->bmp_get_row_fn = bmp_read_scanline; - p->bmp_ptr->bmp_get_data_position_fn = bmp_get_data_position; + + auto* p = new Context(pBmp, this, pDelegate); + p->m_pBmp->context_ptr = p; + p->m_pBmp->err_ptr = p->m_szLastError; + p->m_pBmp->bmp_error_fn = bmp_error_data; + p->m_pBmp->bmp_get_row_fn = bmp_read_scanline; + p->m_pBmp->bmp_get_data_position_fn = bmp_get_data_position; return p; } -void CCodec_BmpModule::Finish(FXBMP_Context* ctx) { - if (ctx) { - bmp_destroy_decompress(&ctx->bmp_ptr); - ctx->m_FreeFunc(ctx); - } +void CCodec_BmpModule::Finish(Context* ctx) { + delete ctx; } -int32_t CCodec_BmpModule::ReadHeader(FXBMP_Context* ctx, + +int32_t CCodec_BmpModule::ReadHeader(Context* ctx, int32_t* width, int32_t* height, bool* tb_flag, @@ -91,41 +88,41 @@ int32_t CCodec_BmpModule::ReadHeader(FXBMP_Context* ctx, int32_t* pal_num, uint32_t** pal_pp, CFX_DIBAttribute* pAttribute) { - if (setjmp(ctx->bmp_ptr->jmpbuf)) { + if (setjmp(ctx->m_pBmp->jmpbuf)) { return 0; } - int32_t ret = bmp_read_header(ctx->bmp_ptr); + int32_t ret = bmp_read_header(ctx->m_pBmp); if (ret != 1) { return ret; } - *width = ctx->bmp_ptr->width; - *height = ctx->bmp_ptr->height; - *tb_flag = ctx->bmp_ptr->imgTB_flag; - *components = ctx->bmp_ptr->components; - *pal_num = ctx->bmp_ptr->pal_num; - *pal_pp = ctx->bmp_ptr->pal_ptr; + *width = ctx->m_pBmp->width; + *height = ctx->m_pBmp->height; + *tb_flag = ctx->m_pBmp->imgTB_flag; + *components = ctx->m_pBmp->components; + *pal_num = ctx->m_pBmp->pal_num; + *pal_pp = ctx->m_pBmp->pal_ptr; if (pAttribute) { pAttribute->m_wDPIUnit = FXCODEC_RESUNIT_METER; - pAttribute->m_nXDPI = ctx->bmp_ptr->dpi_x; - pAttribute->m_nYDPI = ctx->bmp_ptr->dpi_y; - pAttribute->m_nBmpCompressType = ctx->bmp_ptr->compress_flag; + pAttribute->m_nXDPI = ctx->m_pBmp->dpi_x; + pAttribute->m_nYDPI = ctx->m_pBmp->dpi_y; + pAttribute->m_nBmpCompressType = ctx->m_pBmp->compress_flag; } return 1; } -int32_t CCodec_BmpModule::LoadImage(FXBMP_Context* ctx) { - if (setjmp(ctx->bmp_ptr->jmpbuf)) +int32_t CCodec_BmpModule::LoadImage(Context* ctx) { + if (setjmp(ctx->m_pBmp->jmpbuf)) return 0; - return bmp_decode_image(ctx->bmp_ptr); + return bmp_decode_image(ctx->m_pBmp); } -uint32_t CCodec_BmpModule::GetAvailInput(FXBMP_Context* ctx, +uint32_t CCodec_BmpModule::GetAvailInput(Context* ctx, uint8_t** avail_buf_ptr) { - return bmp_get_avail_input(ctx->bmp_ptr, avail_buf_ptr); + return bmp_get_avail_input(ctx->m_pBmp, avail_buf_ptr); } -void CCodec_BmpModule::Input(FXBMP_Context* ctx, +void CCodec_BmpModule::Input(Context* ctx, const uint8_t* src_buf, uint32_t src_size) { - bmp_input_buffer(ctx->bmp_ptr, (uint8_t*)src_buf, src_size); + bmp_input_buffer(ctx->m_pBmp, (uint8_t*)src_buf, src_size); } |