from chrysacase import ChrysalideTestCase from pychrysalide.common import pack_uleb128, unpack_uleb128, pack_leb128, unpack_leb128 from pychrysalide.common import PackedBuffer class TestLEB128Values(ChrysalideTestCase): """TestCase for common LEB128 features*""" def testUnsignedLeb128Encoding(self): """Pack and unpack unsigned LEB128 values.""" cases = { 624485: b'\xe5\x8e\x26', 127: b'\x7f', 128: b'\x80\x01', } for value, encoding in cases.items(): pbuf = PackedBuffer() status = pack_uleb128(value, pbuf) self.assertTrue(status) self.assertEqual(pbuf.payload_length, len(encoding)) pbuf.rewind() got = pbuf.extract(len(encoding)) self.assertEqual(got, encoding) self.assertFalse(pbuf.more_data) for value, encoding in cases.items(): pbuf = PackedBuffer() pbuf.extend(encoding, False) pbuf.rewind() got = unpack_uleb128(pbuf) self.assertIsNotNone(got) self.assertEqual(got, value) def testSignedLeb128Encoding(self): """Pack and unpack signed LEB128 values.""" cases = { -123456: b'\xc0\xbb\x78', -42: b'\x56', -9001: b'\xd7\xb9\x7f', } for value, encoding in cases.items(): pbuf = PackedBuffer() status = pack_leb128(value, pbuf) self.assertTrue(status) self.assertEqual(pbuf.payload_length, len(encoding)) pbuf.rewind() got = pbuf.extract(len(encoding)) self.assertEqual(got, encoding) self.assertFalse(pbuf.more_data) for value, encoding in cases.items(): pbuf = PackedBuffer() pbuf.extend(encoding, False) pbuf.rewind() got = unpack_leb128(pbuf) self.assertIsNotNone(got) self.assertEqual(got, value) def testTooBigLeb128Encodings(self): """Prevent overflow for LEB128 values.""" pbuf = PackedBuffer() pbuf.extend(b'\x80' * 10 + b'\x7f', False) pbuf.rewind() got = unpack_uleb128(pbuf) self.assertIsNone(got) pbuf = PackedBuffer() pbuf.extend(b'\x80' * 10 + b'\x7f', False) pbuf.rewind() got = unpack_leb128(pbuf) self.assertIsNone(got)