这个zlib字符串解压缩有什么问题?

时间:2011-07-05 12:35:55

标签: iphone ios zlib

我正在尝试为我的应用创建一个简单的字符串压缩算法。

/*
 Decompresses the source buffer into the destination buffer.  sourceLen is
 the byte length of the source buffer.  Upon entry, destLen is the total size
 of the destination buffer, which must be large enough to hold the entire
 uncompressed data.  (The size of the uncompressed data must have been saved
 previously by the compressor and transmitted to the decompressor by some
 mechanism outside the scope of this compression library.) Upon exit, destLen
 is the actual size of the uncompressed buffer.

 uncompress returns Z_OK if success, Z_MEM_ERROR if there was not
 enough memory, Z_BUF_ERROR if there was not enough room in the output
 buffer, or Z_DATA_ERROR if the input data was corrupted or incomplete.
 */

[Base64 initialize];
NSData * data = [Base64 decode:@"MDAwMDAwNTB42vPMVkhKzVNIBeLsnNTMPB0IpVCWWZyVqpAJkalKTVUoS8xTSMpJLC0HALWrEYi="];

NSString * deBase64 = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];

int lengteOP = [[deBase64 substringWithRange:NSMakeRange(0,8)] intValue];
NSUInteger lengteIP = [deBase64 length];

const unsigned char *input = (const unsigned char *) [[deBase64 substringFromIndex:8]  cStringUsingEncoding:NSASCIIStringEncoding];
unsigned char * dest; 

uncompress(dest, lengteOP, input, lengteIP);

尝试此操作时出现EXC_BADD_ACCESS错误。 使用ZLib在delphi中使用代码构建字符串,与iPhone sdk中的库相同

它是一个base64编码字符串,前8个字符表示字符串的长度,后跟zlib-ed字符串。

2 个答案:

答案 0 :(得分:0)

我没有运行代码,但您的问题可能是dest。这是文档中的一个片段。

  

进入后,destLen是总大小   必须的目标缓冲区   足够大以容纳整个   未压缩的数据。

目标需要在调用函数之前分配内存,否则会尝试将数据写入无效内存,从而导致EXC_BAD_ACCESS。

尝试以下方法:

unsigned char * dest = malloc(sizeof(unsigned char) * lengteOP);

uncompress(dest, lengteOP, input, lengteIP);

//Use dest (create NSString with proper encoding for example)

free(dest);

答案 1 :(得分:0)

- 已完成代码

/*
 Decompresses the source buffer into the destination buffer.  sourceLen is
 the byte length of the source buffer.  Upon entry, destLen is the total size
 of the destination buffer, which must be large enough to hold the entire
 uncompressed data.  (The size of the uncompressed data must have been saved
 previously by the compressor and transmitted to the decompressor by some
 mechanism outside the scope of this compression library.) Upon exit, destLen
 is the actual size of the uncompressed buffer.

 uncompress returns Z_OK if success, Z_MEM_ERROR if there was not
 enough memory, Z_BUF_ERROR if there was not enough room in the output
 buffer, or Z_DATA_ERROR if the input data was corrupted or incomplete.

 ZEXTERN int ZEXPORT uncompress OF((Bytef *dest,   uLongf *destLen,
 const Bytef *source, uLong sourceLen));

 */

[Base64 initialize];
NSData * data = [Base64 decode:@"MDAwMDAwNTB42vPMVkhKzVNIBeLsnNTMPB0IpVCWWZyVqpAJkalKTVUoS8xTSMpJLC0HALWrEYi="];

NSString * deBase64 = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];

uLongf lengthOriginal = [[deBase64 substringWithRange:NSMakeRange(0,8)] floatValue]; 
uLongf * lengteOP = malloc(sizeof(uLongf));

lengteOP = &lengthOriginal;

NSUInteger lengteIP = [deBase64 length];

NSString * codedString = [deBase64 substringFromIndex:8];

const unsigned char *input = (const unsigned char *) [codedString cStringUsingEncoding:NSISOLatin1StringEncoding];

unsigned char * dest = malloc((sizeof(unsigned char) * lengthOriginal));

uncompress(dest, lengteOP, input, lengteIP);

NSString *  bla = @"Decoded string :";  
NSLog([bla stringByAppendingString:[NSString stringWithCString:dest encoding:NSASCIIStringEncoding]]);



free(dest);
free(lengteOP);