ZLIB распаковка

Я написал небольшое приложение, которое должно распаковывать данные, закодированные в формате gzip/deflate.

Для этого я использую библиотеку ZLIB, используя функцию распаковки.

Проблема в том, что функция не работает! Другими словами, данные не являются несжатыми!

Я выкладываю здесь код:

int (*decompress)(PBYTE,PULONG,PBYTE,ULONG);

void DecodeData(PBYTE data,ULONG dataSize){
  LoadLibrary("C:\\zlib1.dll");

  decompress=(int(*)(PBYTE,PULONG,PBYTE,ULONG))GetProcAddress(
    GetModuleHandle("zlib1.dll"),"uncompress");

  // Yeah I know the size is hardcoded and it's not right, but it's just a test,
  // so nevermind

  PBYTE decompressedData=(PBYTE)VirtualAlloc(NULL,300,MEM_COMMIT|MEM_RESERVE,
    PAGE_EXECUTE_READWRITE);
  ULONG maxSize=250;

  decompress(decompressedData,&maxSize,data,dataSize);

  MessageBox(0,(char*)decompressedData,0,MB_OK);//MessageBox shows no data, it's blank!
}

GetProcAddress успешно получает указатель на функцию, проблема в том, что функция возвращает NULL(и даже не ошибки, перечисленные в документации zlib)

Заранее спасибо =)

2 ответа

uncompress() Функция не будет распаковывать данные gzip, и в зависимости от того, что вы подразумеваете под "deflate", она также не может распаковывать это.

Существует три возможных формата, к которым вы обращаетесь, это фактические сжатые данные, возможно, с некоторыми короткими заголовками и трейлерами для идентификации потока и предоставления некоторых проверочных данных в конце. Есть необработанные данные о дефляте, как описано в RFC 1951. Существуют данные с дефлированием в zlib, определенные в RFC 1950. Есть сжатые gzip данные deflate, определенные RFC 1952.

uncompress() будет распаковывать только zlib-упакованные данные deflate. Он не будет распаковывать данные в формате gzip или необработанные данные.

Вы не предоставили контекст для того, что вы пытаетесь сделать. Однако, когда вы говорите "gzip/deflate", я могу предположить, что по этой комбинации вы ссылаетесь на имена опций кодирования содержимого HTTP. В этом случае из-за неудачного выбора имени кодировка содержимого "deflate" относится к дефлированным данным, заключенным в zlib, а не к необработанным данным. uncompress() будет распаковывать правильно доставленные HTTP-дефлятированные данные в кодированном виде.

Я говорю "правильно доставлено", потому что это не может быть. Опять же, из-за неудачного выбора имени и неспособности программистов Microsoft фактически прочитать спецификацию HTTP, серверы IIS некорректно доставляли необработанные данные с дефляцией вместо данных, упакованных в zlib, когда клиент принимал кодирование контента с дефляцией. Это привело к тому, что клиенты должны либо попытаться декодировать кодирование дефлятированного содержимого в обоих направлениях и посмотреть, работает ли один из них, либо лучший подход, который заключается в том, чтобы просто не принимать кодирование дефлирования в первую очередь. Если клиент принимает только кодировку содержимого gzip, проблем нет.

Ты можешь использовать inflateInit2(), inflate(), а также inflateEnd() функции zlib для декодирования любого из упомянутых форматов, т.е. gzip-wrapped, zlib-wrapped и raw. Пожалуйста, прочитайте документацию в zlib.h чтобы увидеть как.

Кстати, uncompress() Функция возвращает целое число, а не указатель. Поэтому, когда вы говорите, что функция вернулась NULL вместо того, что предполагалось, я могу только предположить, что интерфейс к этой функции zlib не был определен должным образом.

Почему в вашем GetProcAddress используется 'uncompress', но вы пытаетесь распаковать? Вы получаете адрес процедуры 'uncompress'!!!

Другие вопросы по тегам