Example #1
0
bool inflateZlibInstallShield(byte *dst, uint dstLen, const byte *src, uint srcLen) {
	if (!dst || !dstLen || !src || !srcLen)
		return false;

	// See if we have sync bytes. If so, just use our function for that.
	if (srcLen >= 4 && READ_BE_UINT32(src + srcLen - 4) == 0xFFFF)
		return inflateZlibHeaderless(dst, dstLen, src, srcLen);

	// Otherwise, we have some custom code we get to use here.

	byte *temp = (byte *)malloc(kTempBufSize);

	uint32 bytesRead = 0, bytesProcessed = 0;
	while (bytesRead < srcLen) {
		uint16 chunkSize = READ_LE_UINT16(src + bytesRead);
		bytesRead += 2;

		// Initialize zlib
		z_stream stream;
		stream.next_in = const_cast<byte *>(src + bytesRead);
		stream.avail_in = chunkSize;
		stream.next_out = temp;
		stream.avail_out = kTempBufSize;
		stream.zalloc = Z_NULL;
		stream.zfree = Z_NULL;
		stream.opaque = Z_NULL;

		// Negative MAX_WBITS tells zlib there's no zlib header
		int err = inflateInit2(&stream, -MAX_WBITS);
		if (err != Z_OK)
			return false;

		err = inflate(&stream, Z_FINISH);
		if (err != Z_OK && err != Z_STREAM_END) {
			inflateEnd(&stream);
			free(temp);
			return false;
		}

		memcpy(dst + bytesProcessed, temp, stream.total_out);
		bytesProcessed += stream.total_out;

		inflateEnd(&stream);
		bytesRead += chunkSize;
	}

	free(temp);
	return true;
}
Example #2
0
uint32 CdfArchive::BlockDecode(uint8 *dst, uint32 a_dst_size, const uint8 *a_src, uint32 a_src_size) const
{
	uint32 dst_size = 0;

	uint16 data_type = READ_LE_UINT16(a_src);

	const uint8 *src = a_src + sizeof(uint16);
	uint32 src_size = a_src_size - sizeof(uint16);

	// data uncompressed, just copy contents
	if(data_type == 0)
	{
		memcpy(dst, src, src_size);
		dst_size = src_size;
	}
	// deflate compression used
	else if(data_type == 8)
		dst_size = inflateZlibHeaderless((byte *)dst, a_dst_size, src, src_size);

	return dst_size;
}