Z_MEM_ERROR Zlib deflateInit2() 嵌入式设备

Z_MEM_ERROR Zlib deflateInit2() embedded device

请注意这段代码:

  #define CHUNK 0x4000
  z_stream strm;
  unsigned char out[CHUNK];
  int ret;

  strm.zalloc = Z_NULL;
  strm.zfree = Z_NULL;
  strm.opaque = Z_NULL;

  int windowsBits = 15;
  int GZIP_ENCODING = 16;

  ret = deflateInit2(&strm, Z_BEST_SPEED, Z_DEFLATED, windowsBits | GZIP_ENCODING, 1, 
                     Z_DEFAULT_STRATEGY);
  if(ret == Z_OK) {
     strm.next_in = (z_const unsigned char *)answer;
     strm.avail_in = strlen(answer);
     do {
        strm.avail_out = CHUNK;
        strm.next_out = out;
        ret = deflate(&strm, Z_FINISH);
     } while (strm.avail_out == 0);
  }

    /* clean up and return */
  (void)deflateEnd(&strm);

answer(200 个元素的无符号字符数组,最后一个是 \0)填充在 4 个声明和其余部分之间。

它在 Z_MEM_ERRORdeflateInit2 中崩溃。

我正在研究 STM32F4(微控制器)。在尝试实施压缩之前,我的 RAM 几乎已满 (~87%)。

当我使用不同的参数时,我使这部分工作了一次,但后来在程序中出现错误(因为我想将 gzip 压缩后的字符串发送到 HTTP 输出,错误是:

unrecognized encoding.

我有:~30 KB 可用 RAM。

zlib 的 deflate 通常需要大约 256K 的 RAM。参见 zlib technical details。 30K 有点限制,但您仍然可以使用 memLevelwindowBits 参数来减少内存占用。来自该页面:

deflate memory usage (bytes) = (1 << (windowBits+2)) + (1 << (memLevel+9))

所以你可以用 5 的 memLevel 和 11 的 windowBits 到达那里,大约需要 24K(加上一些其他结构)。这会稍微降低压缩效果,但至少它会起作用。 (对于 gzip 编码,您仍然可以将 16 添加到 windowBits。)