3

我正在使用 libjpeg 从 OpenCV Mat 转换图像缓冲区并将其写入内存位置

这是代码:

bool mat2jpeg(cv::Mat frame, unsigned char **outbuffer
    , long unsigned int *outlen) {

    unsigned char *outdata = frame.data;

    struct jpeg_compress_struct cinfo = { 0 };
    struct jpeg_error_mgr jerr;
    JSAMPROW row_ptr[1];
    int row_stride;

    *outbuffer = NULL;
    *outlen = 0;

    cinfo.err = jpeg_std_error(&jerr);
    jpeg_create_compress(&cinfo);
    jpeg_mem_dest(&cinfo, outbuffer, outlen);
    jpeg_set_quality(&cinfo, JPEG_QUALITY, TRUE);
    cinfo.image_width = frame.cols;
    cinfo.image_height = frame.rows;
    cinfo.input_components = 1;
    cinfo.in_color_space = JCS_GRAYSCALE;

    jpeg_set_defaults(&cinfo);
    jpeg_start_compress(&cinfo, TRUE);
    row_stride = frame.cols;

    while (cinfo.next_scanline < cinfo.image_height) {
        row_ptr[0] = &outdata[cinfo.next_scanline * row_stride];
        jpeg_write_scanlines(&cinfo, row_ptr, 1);
    }

    jpeg_finish_compress(&cinfo);
    jpeg_destroy_compress(&cinfo);


    return true;

}

问题是我无法在任何地方释放出缓冲区。

这就是我使用该功能的方式:

long unsigned int * __size__ = nullptr;

unsigned char * _buf = nullptr;

mat2jpeg(_img, &_buf, __size__);

free(_buf) 和 free(*_buf) 都失败了,看来我正试图通过这样做来释放堆头。

并且 mat2jpeg 不接受指向 outbuffer 指针的指针。任何想法?

4

3 回答 3

0

我认为您的问题可能与您的__size__变量有关。它没有分配到任何地方。根据我对libjpeg 源代码的阅读,这意味着永远不会分配缓冲区,并且程序会调用致命错误函数。

我认为你需要这样称呼它:

long unsigned int __size__ = 0; // not a pointer

unsigned char * _buf = nullptr;

mat2jpeg(_img, &_buf, &__size__); // send address of __size__

然后你应该能够释放缓冲区:

free(_buf);
于 2015-09-15T13:59:19.863 回答
0

在我的情况下,没有办法释放内存图像指针,唯一的方法是为图像保留足够的内存,这样库就不会为我保留内存,我可以控制内存,内存会成为我自己的应用程序的一部分,而不是库的 dll 或 .lib:

//previous code...
struct jpeg_compress_struct cinfo;

//reserving the enough memory for my image (width * height)
unsigned char* _image = (unsigned char*)malloc(Width * Height);

//putting the reserved size into _imageSize
_imageSize = Width * Height;

//call the function like this:
jpeg_mem_dest(&cinfo, &_image, &_imageSize);
................
//releasing the reserved memory
free(_image);

注意:如果你放_imageSize = 0,库会假设你没有保留内存,而自己的库会这样做..所以你需要输入_imageSize保留的字节数_image

这样您就可以完全控制保留的内存,并且可以随时在软件中释放它。

于 2021-04-06T02:31:07.917 回答
0

我已经验证是导致问题的dll。我试图将 libjpeg 重新编译为静态库,现在一切都像一个魅力。

于 2015-09-17T09:12:21.930 回答