blob: 3a5bd3021d386ea23ec20f0467c2423790760b1c [file] [log] [blame]
Guido van Rossum7d9ea502003-02-03 20:45:52 +00001import unittest
Benjamin Petersonee8712c2008-05-20 21:35:26 +00002from test import support
Christian Heimesd5e2b6f2008-03-19 21:50:51 +00003import binascii
Andrew M. Kuchling9a0f98e2001-02-21 02:17:01 +00004import random
Antoine Pitrou4b3fe142010-05-07 17:08:54 +00005from test.support import precisionbigmemtest, _1G
Andrew M. Kuchling9a0f98e2001-02-21 02:17:01 +00006
R. David Murraya21e4ca2009-03-31 23:16:50 +00007zlib = support.import_module('zlib')
8
Andrew M. Kuchling9a0f98e2001-02-21 02:17:01 +00009
Guido van Rossum7d9ea502003-02-03 20:45:52 +000010class ChecksumTestCase(unittest.TestCase):
11 # checksum test cases
12 def test_crc32start(self):
Guido van Rossum776152b2007-05-22 22:44:07 +000013 self.assertEqual(zlib.crc32(b""), zlib.crc32(b"", 0))
Georg Brandlab91fde2009-08-13 08:51:18 +000014 self.assertTrue(zlib.crc32(b"abc", 0xffffffff))
Andrew M. Kuchlingfcfc8d52001-08-10 15:50:11 +000015
Guido van Rossum7d9ea502003-02-03 20:45:52 +000016 def test_crc32empty(self):
Guido van Rossum776152b2007-05-22 22:44:07 +000017 self.assertEqual(zlib.crc32(b"", 0), 0)
18 self.assertEqual(zlib.crc32(b"", 1), 1)
19 self.assertEqual(zlib.crc32(b"", 432), 432)
Andrew M. Kuchling9a0f98e2001-02-21 02:17:01 +000020
Guido van Rossum7d9ea502003-02-03 20:45:52 +000021 def test_adler32start(self):
Guido van Rossum776152b2007-05-22 22:44:07 +000022 self.assertEqual(zlib.adler32(b""), zlib.adler32(b"", 1))
Georg Brandlab91fde2009-08-13 08:51:18 +000023 self.assertTrue(zlib.adler32(b"abc", 0xffffffff))
Jeremy Hylton6eb4b6a1997-08-15 15:59:43 +000024
Guido van Rossum7d9ea502003-02-03 20:45:52 +000025 def test_adler32empty(self):
Guido van Rossum776152b2007-05-22 22:44:07 +000026 self.assertEqual(zlib.adler32(b"", 0), 0)
27 self.assertEqual(zlib.adler32(b"", 1), 1)
28 self.assertEqual(zlib.adler32(b"", 432), 432)
Jeremy Hylton6eb4b6a1997-08-15 15:59:43 +000029
Guido van Rossum7d9ea502003-02-03 20:45:52 +000030 def assertEqual32(self, seen, expected):
31 # 32-bit values masked -- checksums on 32- vs 64- bit machines
32 # This is important if bit 31 (0x08000000L) is set.
Guido van Rossume2a383d2007-01-15 16:59:06 +000033 self.assertEqual(seen & 0x0FFFFFFFF, expected & 0x0FFFFFFFF)
Guido van Rossum7d9ea502003-02-03 20:45:52 +000034
35 def test_penguins(self):
Guido van Rossum776152b2007-05-22 22:44:07 +000036 self.assertEqual32(zlib.crc32(b"penguin", 0), 0x0e5c1a120)
37 self.assertEqual32(zlib.crc32(b"penguin", 1), 0x43b6aa94)
38 self.assertEqual32(zlib.adler32(b"penguin", 0), 0x0bcf02f6)
39 self.assertEqual32(zlib.adler32(b"penguin", 1), 0x0bd602f7)
Guido van Rossum7d9ea502003-02-03 20:45:52 +000040
Guido van Rossum776152b2007-05-22 22:44:07 +000041 self.assertEqual(zlib.crc32(b"penguin"), zlib.crc32(b"penguin", 0))
42 self.assertEqual(zlib.adler32(b"penguin"),zlib.adler32(b"penguin",1))
Guido van Rossum7d9ea502003-02-03 20:45:52 +000043
Gregory P. Smithab0d8a12008-03-17 20:24:09 +000044 def test_crc32_adler32_unsigned(self):
Antoine Pitrouc8428d32009-12-14 18:23:30 +000045 foo = b'abcdefghijklmnop'
Gregory P. Smithab0d8a12008-03-17 20:24:09 +000046 # explicitly test signed behavior
Gregory P. Smith27275032008-03-20 06:20:09 +000047 self.assertEqual(zlib.crc32(foo), 2486878355)
Antoine Pitrouc8428d32009-12-14 18:23:30 +000048 self.assertEqual(zlib.crc32(b'spam'), 1138425661)
Gregory P. Smithab0d8a12008-03-17 20:24:09 +000049 self.assertEqual(zlib.adler32(foo+foo), 3573550353)
Antoine Pitrouc8428d32009-12-14 18:23:30 +000050 self.assertEqual(zlib.adler32(b'spam'), 72286642)
Gregory P. Smithab0d8a12008-03-17 20:24:09 +000051
Christian Heimesd5e2b6f2008-03-19 21:50:51 +000052 def test_same_as_binascii_crc32(self):
Martin v. Löwis15b16a32008-12-02 06:00:15 +000053 foo = b'abcdefghijklmnop'
Gregory P. Smith27275032008-03-20 06:20:09 +000054 crc = 2486878355
Christian Heimesd5e2b6f2008-03-19 21:50:51 +000055 self.assertEqual(binascii.crc32(foo), crc)
56 self.assertEqual(zlib.crc32(foo), crc)
Martin v. Löwis15b16a32008-12-02 06:00:15 +000057 self.assertEqual(binascii.crc32(b'spam'), zlib.crc32(b'spam'))
Guido van Rossum7d9ea502003-02-03 20:45:52 +000058
59
Christian Heimesb186d002008-03-18 15:15:01 +000060
Guido van Rossum7d9ea502003-02-03 20:45:52 +000061class ExceptionTestCase(unittest.TestCase):
62 # make sure we generate some expected errors
Guido van Rossum8ce8a782007-11-01 19:42:39 +000063 def test_badlevel(self):
64 # specifying compression level out of range causes an error
65 # (but -1 is Z_DEFAULT_COMPRESSION and apparently the zlib
66 # accepts 0 too)
Antoine Pitrouc8428d32009-12-14 18:23:30 +000067 self.assertRaises(zlib.error, zlib.compress, b'ERROR', 10)
68
69 def test_badargs(self):
70 self.assertRaises(TypeError, zlib.adler32)
71 self.assertRaises(TypeError, zlib.crc32)
72 self.assertRaises(TypeError, zlib.compress)
73 self.assertRaises(TypeError, zlib.decompress)
74 for arg in (42, None, '', 'abc', (), []):
75 self.assertRaises(TypeError, zlib.adler32, arg)
76 self.assertRaises(TypeError, zlib.crc32, arg)
77 self.assertRaises(TypeError, zlib.compress, arg)
78 self.assertRaises(TypeError, zlib.decompress, arg)
Guido van Rossum7d9ea502003-02-03 20:45:52 +000079
80 def test_badcompressobj(self):
81 # verify failure on building compress object with bad params
Neil Schemenauer94afd3e2004-06-05 19:02:52 +000082 self.assertRaises(ValueError, zlib.compressobj, 1, zlib.DEFLATED, 0)
Guido van Rossum8ce8a782007-11-01 19:42:39 +000083 # specifying total bits too large causes an error
84 self.assertRaises(ValueError,
85 zlib.compressobj, 1, zlib.DEFLATED, zlib.MAX_WBITS + 1)
Guido van Rossum7d9ea502003-02-03 20:45:52 +000086
87 def test_baddecompressobj(self):
88 # verify failure on building decompress object with bad params
Antoine Pitroue96bf092010-04-06 17:25:56 +000089 self.assertRaises(ValueError, zlib.decompressobj, -1)
Guido van Rossum7d9ea502003-02-03 20:45:52 +000090
Christian Heimes5e696852008-04-09 08:37:03 +000091 def test_decompressobj_badflush(self):
92 # verify failure on calling decompressobj.flush with bad params
93 self.assertRaises(ValueError, zlib.decompressobj().flush, 0)
94 self.assertRaises(ValueError, zlib.decompressobj().flush, -1)
95
Guido van Rossum7d9ea502003-02-03 20:45:52 +000096
Antoine Pitrou4b3fe142010-05-07 17:08:54 +000097class BaseCompressTestCase(object):
98 def check_big_compress_buffer(self, size, compress_func):
99 _1M = 1024 * 1024
100 fmt = "%%0%dx" % (2 * _1M)
101 # Generate 10MB worth of random, and expand it by repeating it.
102 # The assumption is that zlib's memory is not big enough to exploit
103 # such spread out redundancy.
Antoine Pitrouadfe27a2010-05-07 18:09:36 +0000104 data = b''.join([binascii.a2b_hex(fmt % random.getrandbits(8 * _1M))
Antoine Pitrou4b3fe142010-05-07 17:08:54 +0000105 for i in range(10)])
106 data = data * (size // len(data) + 1)
107 try:
108 compress_func(data)
109 finally:
110 # Release memory
111 data = None
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000112
Antoine Pitrou4b3fe142010-05-07 17:08:54 +0000113 def check_big_decompress_buffer(self, size, decompress_func):
114 data = b'x' * size
115 try:
116 compressed = zlib.compress(data, 1)
117 finally:
118 # Release memory
119 data = None
120 data = decompress_func(compressed)
121 # Sanity check
122 try:
123 self.assertEqual(len(data), size)
124 self.assertEqual(len(data.strip(b'x')), 0)
125 finally:
126 data = None
127
128
129class CompressTestCase(BaseCompressTestCase, unittest.TestCase):
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000130 # Test compression in one go (whole message compression)
131 def test_speech(self):
Neil Schemenauer6412b122004-06-05 19:34:28 +0000132 x = zlib.compress(HAMLET_SCENE)
133 self.assertEqual(zlib.decompress(x), HAMLET_SCENE)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000134
135 def test_speech128(self):
Neil Schemenauer6412b122004-06-05 19:34:28 +0000136 # compress more data
137 data = HAMLET_SCENE * 128
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000138 x = zlib.compress(data)
Antoine Pitrouc8428d32009-12-14 18:23:30 +0000139 self.assertEqual(zlib.compress(bytearray(data)), x)
140 for ob in x, bytearray(x):
141 self.assertEqual(zlib.decompress(ob), data)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000142
Antoine Pitrou4b3fe142010-05-07 17:08:54 +0000143 # Memory use of the following functions takes into account overallocation
144
145 @precisionbigmemtest(size=_1G + 1024 * 1024, memuse=3)
146 def test_big_compress_buffer(self, size):
147 compress = lambda s: zlib.compress(s, 1)
148 self.check_big_compress_buffer(size, compress)
149
150 @precisionbigmemtest(size=_1G + 1024 * 1024, memuse=2)
151 def test_big_decompress_buffer(self, size):
152 self.check_big_decompress_buffer(size, zlib.decompress)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000153
154
Antoine Pitrou4b3fe142010-05-07 17:08:54 +0000155class CompressObjectTestCase(BaseCompressTestCase, unittest.TestCase):
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000156 # Test compression object
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000157 def test_pair(self):
Neil Schemenauer6412b122004-06-05 19:34:28 +0000158 # straightforward compress/decompress objects
Antoine Pitrouc8428d32009-12-14 18:23:30 +0000159 datasrc = HAMLET_SCENE * 128
160 datazip = zlib.compress(datasrc)
161 # should compress both bytes and bytearray data
162 for data in (datasrc, bytearray(datasrc)):
163 co = zlib.compressobj()
164 x1 = co.compress(data)
165 x2 = co.flush()
166 self.assertRaises(zlib.error, co.flush) # second flush should not work
167 self.assertEqual(x1 + x2, datazip)
168 for v1, v2 in ((x1, x2), (bytearray(x1), bytearray(x2))):
169 dco = zlib.decompressobj()
170 y1 = dco.decompress(v1 + v2)
171 y2 = dco.flush()
172 self.assertEqual(data, y1 + y2)
173 self.assertTrue(isinstance(dco.unconsumed_tail, bytes))
174 self.assertTrue(isinstance(dco.unused_data, bytes))
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000175
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000176 def test_compressoptions(self):
177 # specify lots of options to compressobj()
178 level = 2
179 method = zlib.DEFLATED
180 wbits = -12
181 memlevel = 9
182 strategy = zlib.Z_FILTERED
183 co = zlib.compressobj(level, method, wbits, memlevel, strategy)
Neil Schemenauer6412b122004-06-05 19:34:28 +0000184 x1 = co.compress(HAMLET_SCENE)
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000185 x2 = co.flush()
186 dco = zlib.decompressobj(wbits)
187 y1 = dco.decompress(x1 + x2)
188 y2 = dco.flush()
Neil Schemenauer6412b122004-06-05 19:34:28 +0000189 self.assertEqual(HAMLET_SCENE, y1 + y2)
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000190
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000191 def test_compressincremental(self):
192 # compress object in steps, decompress object as one-shot
Neil Schemenauer6412b122004-06-05 19:34:28 +0000193 data = HAMLET_SCENE * 128
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000194 co = zlib.compressobj()
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000195 bufs = []
196 for i in range(0, len(data), 256):
197 bufs.append(co.compress(data[i:i+256]))
198 bufs.append(co.flush())
Guido van Rossum776152b2007-05-22 22:44:07 +0000199 combuf = b''.join(bufs)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000200
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000201 dco = zlib.decompressobj()
Guido van Rossum776152b2007-05-22 22:44:07 +0000202 y1 = dco.decompress(b''.join(bufs))
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000203 y2 = dco.flush()
204 self.assertEqual(data, y1 + y2)
205
Neil Schemenauer6412b122004-06-05 19:34:28 +0000206 def test_decompinc(self, flush=False, source=None, cx=256, dcx=64):
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000207 # compress object in steps, decompress object in steps
Neil Schemenauer6412b122004-06-05 19:34:28 +0000208 source = source or HAMLET_SCENE
209 data = source * 128
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000210 co = zlib.compressobj()
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000211 bufs = []
Neil Schemenauer6412b122004-06-05 19:34:28 +0000212 for i in range(0, len(data), cx):
213 bufs.append(co.compress(data[i:i+cx]))
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000214 bufs.append(co.flush())
Guido van Rossum776152b2007-05-22 22:44:07 +0000215 combuf = b''.join(bufs)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000216
Gregory P. Smith693fc462008-09-06 20:13:06 +0000217 decombuf = zlib.decompress(combuf)
218 # Test type of return value
Georg Brandlab91fde2009-08-13 08:51:18 +0000219 self.assertTrue(isinstance(decombuf, bytes))
Gregory P. Smith693fc462008-09-06 20:13:06 +0000220
221 self.assertEqual(data, decombuf)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000222
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000223 dco = zlib.decompressobj()
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000224 bufs = []
Neil Schemenauer6412b122004-06-05 19:34:28 +0000225 for i in range(0, len(combuf), dcx):
226 bufs.append(dco.decompress(combuf[i:i+dcx]))
Guido van Rossum776152b2007-05-22 22:44:07 +0000227 self.assertEqual(b'', dco.unconsumed_tail, ########
228 "(A) uct should be b'': not %d long" %
Neil Schemenauer6412b122004-06-05 19:34:28 +0000229 len(dco.unconsumed_tail))
Amaury Forgeot d'Arce43d33a2008-07-02 20:50:16 +0000230 self.assertEqual(b'', dco.unused_data)
Neil Schemenauer6412b122004-06-05 19:34:28 +0000231 if flush:
232 bufs.append(dco.flush())
233 else:
234 while True:
Antoine Pitrouc8428d32009-12-14 18:23:30 +0000235 chunk = dco.decompress(b'')
Neil Schemenauer6412b122004-06-05 19:34:28 +0000236 if chunk:
237 bufs.append(chunk)
238 else:
239 break
Guido van Rossum776152b2007-05-22 22:44:07 +0000240 self.assertEqual(b'', dco.unconsumed_tail, ########
241 "(B) uct should be b'': not %d long" %
Neil Schemenauer6412b122004-06-05 19:34:28 +0000242 len(dco.unconsumed_tail))
Amaury Forgeot d'Arce43d33a2008-07-02 20:50:16 +0000243 self.assertEqual(b'', dco.unused_data)
Guido van Rossum776152b2007-05-22 22:44:07 +0000244 self.assertEqual(data, b''.join(bufs))
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000245 # Failure means: "decompressobj with init options failed"
246
Neil Schemenauer6412b122004-06-05 19:34:28 +0000247 def test_decompincflush(self):
248 self.test_decompinc(flush=True)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000249
Neil Schemenauer6412b122004-06-05 19:34:28 +0000250 def test_decompimax(self, source=None, cx=256, dcx=64):
251 # compress in steps, decompress in length-restricted steps
252 source = source or HAMLET_SCENE
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000253 # Check a decompression object with max_length specified
Neil Schemenauer6412b122004-06-05 19:34:28 +0000254 data = source * 128
255 co = zlib.compressobj()
256 bufs = []
257 for i in range(0, len(data), cx):
258 bufs.append(co.compress(data[i:i+cx]))
259 bufs.append(co.flush())
Guido van Rossum776152b2007-05-22 22:44:07 +0000260 combuf = b''.join(bufs)
Neil Schemenauer6412b122004-06-05 19:34:28 +0000261 self.assertEqual(data, zlib.decompress(combuf),
262 'compressed data failure')
263
264 dco = zlib.decompressobj()
265 bufs = []
266 cb = combuf
267 while cb:
268 #max_length = 1 + len(cb)//10
269 chunk = dco.decompress(cb, dcx)
Georg Brandlab91fde2009-08-13 08:51:18 +0000270 self.assertFalse(len(chunk) > dcx,
Neil Schemenauer6412b122004-06-05 19:34:28 +0000271 'chunk too big (%d>%d)' % (len(chunk), dcx))
272 bufs.append(chunk)
273 cb = dco.unconsumed_tail
274 bufs.append(dco.flush())
Guido van Rossum776152b2007-05-22 22:44:07 +0000275 self.assertEqual(data, b''.join(bufs), 'Wrong data retrieved')
Neil Schemenauer6412b122004-06-05 19:34:28 +0000276
277 def test_decompressmaxlen(self, flush=False):
278 # Check a decompression object with max_length specified
279 data = HAMLET_SCENE * 128
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000280 co = zlib.compressobj()
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000281 bufs = []
282 for i in range(0, len(data), 256):
283 bufs.append(co.compress(data[i:i+256]))
284 bufs.append(co.flush())
Guido van Rossum776152b2007-05-22 22:44:07 +0000285 combuf = b''.join(bufs)
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000286 self.assertEqual(data, zlib.decompress(combuf),
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000287 'compressed data failure')
288
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000289 dco = zlib.decompressobj()
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000290 bufs = []
291 cb = combuf
292 while cb:
Guido van Rossumf3594102003-02-27 18:39:18 +0000293 max_length = 1 + len(cb)//10
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000294 chunk = dco.decompress(cb, max_length)
Georg Brandlab91fde2009-08-13 08:51:18 +0000295 self.assertFalse(len(chunk) > max_length,
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000296 'chunk too big (%d>%d)' % (len(chunk),max_length))
297 bufs.append(chunk)
298 cb = dco.unconsumed_tail
Neil Schemenauer6412b122004-06-05 19:34:28 +0000299 if flush:
300 bufs.append(dco.flush())
301 else:
302 while chunk:
Antoine Pitrouc8428d32009-12-14 18:23:30 +0000303 chunk = dco.decompress(b'', max_length)
Georg Brandlab91fde2009-08-13 08:51:18 +0000304 self.assertFalse(len(chunk) > max_length,
Neil Schemenauer6412b122004-06-05 19:34:28 +0000305 'chunk too big (%d>%d)' % (len(chunk),max_length))
306 bufs.append(chunk)
Guido van Rossum776152b2007-05-22 22:44:07 +0000307 self.assertEqual(data, b''.join(bufs), 'Wrong data retrieved')
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000308
Neil Schemenauer6412b122004-06-05 19:34:28 +0000309 def test_decompressmaxlenflush(self):
310 self.test_decompressmaxlen(flush=True)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000311
312 def test_maxlenmisc(self):
313 # Misc tests of max_length
Neil Schemenauer94afd3e2004-06-05 19:02:52 +0000314 dco = zlib.decompressobj()
Antoine Pitrouc8428d32009-12-14 18:23:30 +0000315 self.assertRaises(ValueError, dco.decompress, b"", -1)
Guido van Rossum776152b2007-05-22 22:44:07 +0000316 self.assertEqual(b'', dco.unconsumed_tail)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000317
318 def test_flushes(self):
319 # Test flush() with the various options, using all the
320 # different levels in order to provide more variations.
321 sync_opt = ['Z_NO_FLUSH', 'Z_SYNC_FLUSH', 'Z_FULL_FLUSH']
322 sync_opt = [getattr(zlib, opt) for opt in sync_opt
323 if hasattr(zlib, opt)]
Neil Schemenauer6412b122004-06-05 19:34:28 +0000324 data = HAMLET_SCENE * 8
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000325
326 for sync in sync_opt:
327 for level in range(10):
328 obj = zlib.compressobj( level )
329 a = obj.compress( data[:3000] )
330 b = obj.flush( sync )
331 c = obj.compress( data[3000:] )
332 d = obj.flush()
Guido van Rossum776152b2007-05-22 22:44:07 +0000333 self.assertEqual(zlib.decompress(b''.join([a,b,c,d])),
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000334 data, ("Decompress failed: flush "
335 "mode=%i, level=%i") % (sync, level))
336 del obj
337
338 def test_odd_flush(self):
339 # Test for odd flushing bugs noted in 2.0, and hopefully fixed in 2.1
340 import random
341
342 if hasattr(zlib, 'Z_SYNC_FLUSH'):
343 # Testing on 17K of "random" data
344
345 # Create compressor and decompressor objects
Neil Schemenauer6412b122004-06-05 19:34:28 +0000346 co = zlib.compressobj(zlib.Z_BEST_COMPRESSION)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000347 dco = zlib.decompressobj()
348
349 # Try 17K of data
350 # generate random data stream
351 try:
352 # In 2.3 and later, WichmannHill is the RNG of the bug report
353 gen = random.WichmannHill()
354 except AttributeError:
355 try:
356 # 2.2 called it Random
357 gen = random.Random()
358 except AttributeError:
359 # others might simply have a single RNG
360 gen = random
361 gen.seed(1)
362 data = genblock(1, 17 * 1024, generator=gen)
363
364 # compress, sync-flush, and decompress
365 first = co.compress(data)
366 second = co.flush(zlib.Z_SYNC_FLUSH)
367 expanded = dco.decompress(first + second)
368
369 # if decompressed data is different from the input data, choke.
370 self.assertEqual(expanded, data, "17K random source doesn't match")
371
Andrew M. Kuchling3b585b32004-12-28 20:10:48 +0000372 def test_empty_flush(self):
373 # Test that calling .flush() on unused objects works.
374 # (Bug #1083110 -- calling .flush() on decompress objects
375 # caused a core dump.)
376
377 co = zlib.compressobj(zlib.Z_BEST_COMPRESSION)
Georg Brandlab91fde2009-08-13 08:51:18 +0000378 self.assertTrue(co.flush()) # Returns a zlib header
Andrew M. Kuchling3b585b32004-12-28 20:10:48 +0000379 dco = zlib.decompressobj()
Guido van Rossum776152b2007-05-22 22:44:07 +0000380 self.assertEqual(dco.flush(), b"") # Returns nothing
Tim Peters5a9fb3c2005-01-07 16:01:32 +0000381
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000382 if hasattr(zlib.compressobj(), "copy"):
383 def test_compresscopy(self):
384 # Test copying a compression object
385 data0 = HAMLET_SCENE
Guido van Rossum776152b2007-05-22 22:44:07 +0000386 data1 = bytes(str(HAMLET_SCENE, "ascii").swapcase(), "ascii")
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000387 c0 = zlib.compressobj(zlib.Z_BEST_COMPRESSION)
388 bufs0 = []
389 bufs0.append(c0.compress(data0))
Thomas Wouters477c8d52006-05-27 19:21:47 +0000390
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000391 c1 = c0.copy()
392 bufs1 = bufs0[:]
Thomas Wouters477c8d52006-05-27 19:21:47 +0000393
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000394 bufs0.append(c0.compress(data0))
395 bufs0.append(c0.flush())
Guido van Rossum776152b2007-05-22 22:44:07 +0000396 s0 = b''.join(bufs0)
Thomas Wouters477c8d52006-05-27 19:21:47 +0000397
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000398 bufs1.append(c1.compress(data1))
399 bufs1.append(c1.flush())
Guido van Rossum776152b2007-05-22 22:44:07 +0000400 s1 = b''.join(bufs1)
Thomas Wouters477c8d52006-05-27 19:21:47 +0000401
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000402 self.assertEqual(zlib.decompress(s0),data0+data0)
403 self.assertEqual(zlib.decompress(s1),data0+data1)
Thomas Wouters477c8d52006-05-27 19:21:47 +0000404
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000405 def test_badcompresscopy(self):
406 # Test copying a compression object in an inconsistent state
407 c = zlib.compressobj()
408 c.compress(HAMLET_SCENE)
409 c.flush()
410 self.assertRaises(ValueError, c.copy)
Thomas Wouters477c8d52006-05-27 19:21:47 +0000411
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000412 if hasattr(zlib.decompressobj(), "copy"):
413 def test_decompresscopy(self):
414 # Test copying a decompression object
415 data = HAMLET_SCENE
416 comp = zlib.compress(data)
Gregory P. Smith693fc462008-09-06 20:13:06 +0000417 # Test type of return value
Georg Brandlab91fde2009-08-13 08:51:18 +0000418 self.assertTrue(isinstance(comp, bytes))
Thomas Wouters477c8d52006-05-27 19:21:47 +0000419
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000420 d0 = zlib.decompressobj()
421 bufs0 = []
422 bufs0.append(d0.decompress(comp[:32]))
Thomas Wouters477c8d52006-05-27 19:21:47 +0000423
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000424 d1 = d0.copy()
425 bufs1 = bufs0[:]
Thomas Wouters477c8d52006-05-27 19:21:47 +0000426
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000427 bufs0.append(d0.decompress(comp[32:]))
Guido van Rossum776152b2007-05-22 22:44:07 +0000428 s0 = b''.join(bufs0)
Thomas Wouters477c8d52006-05-27 19:21:47 +0000429
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000430 bufs1.append(d1.decompress(comp[32:]))
Guido van Rossum776152b2007-05-22 22:44:07 +0000431 s1 = b''.join(bufs1)
Thomas Wouters477c8d52006-05-27 19:21:47 +0000432
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000433 self.assertEqual(s0,s1)
434 self.assertEqual(s0,data)
Thomas Wouters477c8d52006-05-27 19:21:47 +0000435
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000436 def test_baddecompresscopy(self):
437 # Test copying a compression object in an inconsistent state
438 data = zlib.compress(HAMLET_SCENE)
439 d = zlib.decompressobj()
440 d.decompress(data)
441 d.flush()
442 self.assertRaises(ValueError, d.copy)
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000443
Antoine Pitrou4b3fe142010-05-07 17:08:54 +0000444 # Memory use of the following functions takes into account overallocation
445
446 @precisionbigmemtest(size=_1G + 1024 * 1024, memuse=3)
447 def test_big_compress_buffer(self, size):
448 c = zlib.compressobj(1)
449 compress = lambda s: c.compress(s) + c.flush()
450 self.check_big_compress_buffer(size, compress)
451
452 @precisionbigmemtest(size=_1G + 1024 * 1024, memuse=2)
453 def test_big_decompress_buffer(self, size):
454 d = zlib.decompressobj()
455 decompress = lambda s: d.decompress(s) + d.flush()
456 self.check_big_decompress_buffer(size, decompress)
457
458
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000459def genblock(seed, length, step=1024, generator=random):
460 """length-byte stream of random data from a seed (in step-byte blocks)."""
461 if seed is not None:
462 generator.seed(seed)
463 randint = generator.randint
464 if length < step or step < 2:
465 step = length
Guido van Rossum776152b2007-05-22 22:44:07 +0000466 blocks = bytes()
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000467 for i in range(0, length, step):
Guido van Rossum776152b2007-05-22 22:44:07 +0000468 blocks += bytes(randint(0, 255) for x in range(step))
469 return blocks
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000470
471
472
473def choose_lines(source, number, seed=None, generator=random):
474 """Return a list of number lines randomly chosen from the source"""
475 if seed is not None:
476 generator.seed(seed)
477 sources = source.split('\n')
478 return [generator.choice(sources) for n in range(number)]
479
480
481
Guido van Rossum776152b2007-05-22 22:44:07 +0000482HAMLET_SCENE = b"""
Fred Drake004d5e62000-10-23 17:22:08 +0000483LAERTES
Jeremy Hylton6eb4b6a1997-08-15 15:59:43 +0000484
485 O, fear me not.
486 I stay too long: but here my father comes.
487
488 Enter POLONIUS
489
490 A double blessing is a double grace,
491 Occasion smiles upon a second leave.
492
Fred Drake004d5e62000-10-23 17:22:08 +0000493LORD POLONIUS
Jeremy Hylton6eb4b6a1997-08-15 15:59:43 +0000494
495 Yet here, Laertes! aboard, aboard, for shame!
496 The wind sits in the shoulder of your sail,
497 And you are stay'd for. There; my blessing with thee!
498 And these few precepts in thy memory
499 See thou character. Give thy thoughts no tongue,
500 Nor any unproportioned thought his act.
501 Be thou familiar, but by no means vulgar.
502 Those friends thou hast, and their adoption tried,
503 Grapple them to thy soul with hoops of steel;
504 But do not dull thy palm with entertainment
505 Of each new-hatch'd, unfledged comrade. Beware
506 Of entrance to a quarrel, but being in,
507 Bear't that the opposed may beware of thee.
508 Give every man thy ear, but few thy voice;
509 Take each man's censure, but reserve thy judgment.
510 Costly thy habit as thy purse can buy,
511 But not express'd in fancy; rich, not gaudy;
512 For the apparel oft proclaims the man,
513 And they in France of the best rank and station
514 Are of a most select and generous chief in that.
515 Neither a borrower nor a lender be;
516 For loan oft loses both itself and friend,
517 And borrowing dulls the edge of husbandry.
518 This above all: to thine ownself be true,
519 And it must follow, as the night the day,
520 Thou canst not then be false to any man.
521 Farewell: my blessing season this in thee!
522
Fred Drake004d5e62000-10-23 17:22:08 +0000523LAERTES
Jeremy Hylton6eb4b6a1997-08-15 15:59:43 +0000524
525 Most humbly do I take my leave, my lord.
526
Fred Drake004d5e62000-10-23 17:22:08 +0000527LORD POLONIUS
Jeremy Hylton6eb4b6a1997-08-15 15:59:43 +0000528
529 The time invites you; go; your servants tend.
530
Fred Drake004d5e62000-10-23 17:22:08 +0000531LAERTES
Jeremy Hylton6eb4b6a1997-08-15 15:59:43 +0000532
533 Farewell, Ophelia; and remember well
534 What I have said to you.
535
Fred Drake004d5e62000-10-23 17:22:08 +0000536OPHELIA
Jeremy Hylton6eb4b6a1997-08-15 15:59:43 +0000537
538 'Tis in my memory lock'd,
539 And you yourself shall keep the key of it.
540
Fred Drake004d5e62000-10-23 17:22:08 +0000541LAERTES
Jeremy Hylton6eb4b6a1997-08-15 15:59:43 +0000542
543 Farewell.
544"""
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000545
546
547def test_main():
Benjamin Petersonee8712c2008-05-20 21:35:26 +0000548 support.run_unittest(
Walter Dörwald21d3a322003-05-01 17:45:56 +0000549 ChecksumTestCase,
550 ExceptionTestCase,
551 CompressTestCase,
552 CompressObjectTestCase
553 )
Guido van Rossum7d9ea502003-02-03 20:45:52 +0000554
555if __name__ == "__main__":
Guido van Rossum776152b2007-05-22 22:44:07 +0000556 unittest.main() # XXX
557 ###test_main()