| #!/usr/bin/env python |
| |
| import unittest |
| import sys |
| sys.path.insert(0, '..') |
| import bitstring |
| import copy |
| import os |
| import collections |
| from bitstring import BitStream, ConstBitStream, pack |
| from bitstring import ByteStore, offsetcopy |
| |
| |
| class FlexibleInitialisation(unittest.TestCase): |
| def testFlexibleInitialisation(self): |
| a = BitStream('uint:8=12') |
| c = BitStream(' uint : 8 = 12') |
| self.assertTrue(a == c == BitStream(uint=12, length=8)) |
| self.assertEqual(a.uint, 12) |
| a = BitStream(' int:2= -1') |
| b = BitStream('int :2 = -1') |
| c = BitStream(' int: 2 =-1 ') |
| self.assertTrue(a == b == c == BitStream(int=-1, length=2)) |
| |
| def testFlexibleInitialisation2(self): |
| h = BitStream('hex=12') |
| o = BitStream('oct=33') |
| b = BitStream('bin=10') |
| self.assertEqual(h, '0x12') |
| self.assertEqual(o, '0o33') |
| self.assertEqual(b, '0b10') |
| |
| def testFlexibleInitialisation3(self): |
| for s in ['se=-1', ' se = -1 ', 'se = -1']: |
| a = BitStream(s) |
| self.assertEqual(a.se, -1) |
| for s in ['ue=23', 'ue =23', 'ue = 23']: |
| a = BitStream(s) |
| self.assertEqual(a.ue, 23) |
| |
| def testMultipleStringInitialisation(self): |
| a = BitStream('0b1 , 0x1') |
| self.assertEqual(a, '0b10001') |
| a = BitStream('ue=5, ue=1, se=-2') |
| self.assertEqual(a.read('ue'), 5) |
| self.assertEqual(a.read('ue'), 1) |
| self.assertEqual(a.read('se'), -2) |
| b = BitStream('uint:32 = 12, 0b11') + 'int:100=-100, 0o44' |
| self.assertEqual(b.read(32).uint, 12) |
| self.assertEqual(b.read(2).bin, '11') |
| self.assertEqual(b.read(100).int, -100) |
| |
| |
| class Reading(unittest.TestCase): |
| def testReadBits(self): |
| s = BitStream(bytes=b'\x4d\x55') |
| self.assertEqual(s.read(4).hex, '4') |
| self.assertEqual(s.read(8).hex, 'd5') |
| self.assertEqual(s.read(1), [0]) |
| self.assertEqual(s.read(3).bin, '101') |
| self.assertFalse(s.read(0)) |
| |
| def testReadByte(self): |
| s = BitStream(hex='4d55') |
| self.assertEqual(s.read(8).hex, '4d') |
| self.assertEqual(s.read(8).hex, '55') |
| |
| def testReadBytes(self): |
| s = BitStream(hex='0x112233448811') |
| self.assertEqual(s.read(3 * 8).hex, '112233') |
| self.assertRaises(ValueError, s.read, -2 * 8) |
| s.bitpos += 1 |
| self.assertEqual(s.read(2 * 8).bin, '1000100100010000') |
| |
| def testReadUE(self): |
| self.assertRaises(bitstring.InterpretError, BitStream('')._getue) |
| # The numbers 0 to 8 as unsigned Exponential-Golomb codes |
| s = BitStream(bin='1 010 011 00100 00101 00110 00111 0001000 0001001') |
| self.assertEqual(s.pos, 0) |
| for i in range(9): |
| self.assertEqual(s.read('ue'), i) |
| self.assertRaises(bitstring.ReadError, s.read, 'ue') |
| |
| def testReadSE(self): |
| s = BitStream(bin='010 00110 0001010 0001000 00111') |
| self.assertEqual(s.read('se'), 1) |
| self.assertEqual(s.read('se'), 3) |
| self.assertEqual(s.readlist(3 * ['se']), [5, 4, -3]) |
| |
| |
| class Find(unittest.TestCase): |
| def testFind1(self): |
| s = ConstBitStream(bin='0b0000110110000') |
| self.assertTrue(s.find(BitStream(bin='11011'), False)) |
| self.assertEqual(s.bitpos, 4) |
| self.assertEqual(s.read(5).bin, '11011') |
| s.bitpos = 0 |
| self.assertFalse(s.find('0b11001', False)) |
| |
| def testFind2(self): |
| s = BitStream(bin='0') |
| self.assertTrue(s.find(s, False)) |
| self.assertEqual(s.pos, 0) |
| self.assertFalse(s.find('0b00', False)) |
| self.assertRaises(ValueError, s.find, BitStream(), False) |
| |
| def testFindWithOffset(self): |
| s = BitStream(hex='0x112233')[4:] |
| self.assertTrue(s.find('0x23', False)) |
| self.assertEqual(s.pos, 8) |
| |
| def testFindCornerCases(self): |
| s = BitStream(bin='000111000111') |
| self.assertTrue(s.find('0b000')) |
| self.assertEqual(s.pos, 0) |
| self.assertTrue(s.find('0b000')) |
| self.assertEqual(s.pos, 0) |
| self.assertTrue(s.find('0b0111000111')) |
| self.assertEqual(s.pos, 2) |
| self.assertTrue(s.find('0b000', start=2)) |
| self.assertEqual(s.pos, 6) |
| self.assertTrue(s.find('0b111', start=6)) |
| self.assertEqual(s.pos, 9) |
| s.pos += 2 |
| self.assertTrue(s.find('0b1', start=s.pos)) |
| |
| def testFindBytes(self): |
| s = BitStream('0x010203040102ff') |
| self.assertFalse(s.find('0x05', bytealigned=True)) |
| self.assertTrue(s.find('0x02', bytealigned=True)) |
| self.assertEqual(s.read(16).hex, '0203') |
| self.assertTrue(s.find('0x02', start=s.bitpos, bytealigned=True)) |
| s.read(1) |
| self.assertFalse(s.find('0x02', start=s.bitpos, bytealigned=True)) |
| |
| def testFindBytesAlignedCornerCases(self): |
| s = BitStream('0xff') |
| self.assertTrue(s.find(s)) |
| self.assertFalse(s.find(BitStream(hex='0x12'))) |
| self.assertFalse(s.find(BitStream(hex='0xffff'))) |
| |
| def testFindBytesBitpos(self): |
| s = BitStream(hex='0x1122334455') |
| s.pos = 2 |
| s.find('0x66', bytealigned=True) |
| self.assertEqual(s.pos, 2) |
| s.pos = 38 |
| s.find('0x66', bytealigned=True) |
| self.assertEqual(s.pos, 38) |
| |
| def testFindByteAligned(self): |
| s = BitStream(hex='0x12345678') |
| self.assertTrue(s.find(BitStream(hex='0x56'), bytealigned=True)) |
| self.assertEqual(s.bytepos, 2) |
| s.pos = 0 |
| self.assertFalse(s.find(BitStream(hex='0x45'), bytealigned=True)) |
| s = BitStream('0x1234') |
| s.find('0x1234') |
| self.assertTrue(s.find('0x1234')) |
| s += '0b111' |
| s.pos = 3 |
| s.find('0b1', start=17, bytealigned=True) |
| self.assertFalse(s.find('0b1', start=17, bytealigned=True)) |
| self.assertEqual(s.pos, 3) |
| |
| def testFindByteAlignedWithOffset(self): |
| s = BitStream(hex='0x112233')[4:] |
| self.assertTrue(s.find(BitStream(hex='0x23'))) |
| |
| def testFindByteAlignedErrors(self): |
| s = BitStream(hex='0xffff') |
| self.assertRaises(ValueError, s.find, '') |
| self.assertRaises(ValueError, s.find, BitStream()) |
| |
| |
| class Rfind(unittest.TestCase): |
| def testRfind(self): |
| a = BitStream('0b001001001') |
| b = a.rfind('0b001') |
| self.assertEqual(b, (6,)) |
| self.assertEqual(a.pos, 6) |
| big = BitStream(length=100000) + '0x12' + BitStream(length=10000) |
| found = big.rfind('0x12', bytealigned=True) |
| self.assertEqual(found, (100000,)) |
| self.assertEqual(big.pos, 100000) |
| |
| def testRfindByteAligned(self): |
| a = BitStream('0x8888') |
| b = a.rfind('0b1', bytealigned=True) |
| self.assertEqual(b, (8,)) |
| self.assertEqual(a.pos, 8) |
| |
| def testRfindStartbit(self): |
| a = BitStream('0x0000ffffff') |
| b = a.rfind('0x0000', start=1, bytealigned=True) |
| self.assertEqual(b, ()) |
| self.assertEqual(a.pos, 0) |
| b = a.rfind('0x00', start=1, bytealigned=True) |
| self.assertEqual(b, (8,)) |
| self.assertEqual(a.pos, 8) |
| |
| def testRfindEndbit(self): |
| a = BitStream('0x000fff') |
| b = a.rfind('0b011', bytealigned=False, start=0, end=14) |
| self.assertEqual(bool(b), True) |
| b = a.rfind('0b011', False, 0, 13) |
| self.assertEqual(b, ()) |
| |
| def testRfindErrors(self): |
| a = BitStream('0x43234234') |
| self.assertRaises(ValueError, a.rfind, '', bytealigned=True) |
| self.assertRaises(ValueError, a.rfind, '0b1', start=-99, bytealigned=True) |
| self.assertRaises(ValueError, a.rfind, '0b1', end=33, bytealigned=True) |
| self.assertRaises(ValueError, a.rfind, '0b1', start=10, end=9, bytealigned=True) |
| |
| |
| class Shift(unittest.TestCase): |
| def testShiftLeft(self): |
| s = BitStream('0b1010') |
| t = s << 1 |
| self.assertEqual(s.bin, '1010') |
| self.assertEqual(t.bin, '0100') |
| t = t << 0 |
| self.assertEqual(t, '0b0100') |
| t = t << 100 |
| self.assertEqual(t.bin, '0000') |
| |
| def testShiftLeftErrors(self): |
| s = BitStream() |
| self.assertRaises(ValueError, s.__lshift__, 1) |
| s = BitStream('0xf') |
| self.assertRaises(ValueError, s.__lshift__, -1) |
| |
| def testShiftRight(self): |
| s = BitStream('0b1010') |
| t = s >> 1 |
| self.assertEqual(s.bin, '1010') |
| self.assertEqual(t.bin, '0101') |
| q = s >> 0 |
| self.assertEqual(q, '0b1010') |
| q.replace('0b1010', '') |
| s = s >> 100 |
| self.assertEqual(s.bin, '0000') |
| |
| def testShiftRightErrors(self): |
| s = BitStream() |
| self.assertRaises(ValueError, s.__rshift__, 1) |
| s = BitStream('0xf') |
| self.assertRaises(ValueError, s.__rshift__, -1) |
| |
| def testShiftRightInPlace(self): |
| s = BitStream('0xffff')[4:12] |
| s >>= 1 |
| self.assertEqual(s, '0b01111111') |
| s = BitStream('0b11011') |
| s >>= 2 |
| self.assertEqual(s.bin, '00110') |
| s >>= 100000000000000 |
| self.assertEqual(s.bin, '00000') |
| s = BitStream('0xff') |
| s >>= 1 |
| self.assertEqual(s, '0x7f') |
| s >>= 0 |
| self.assertEqual(s, '0x7f') |
| |
| def testShiftRightInPlaceErrors(self): |
| s = BitStream() |
| self.assertRaises(ValueError, s.__irshift__, 1) |
| s += '0b11' |
| self.assertRaises(ValueError, s.__irshift__, -1) |
| |
| def testShiftLeftInPlace(self): |
| s = BitStream('0xffff') |
| t = s[4:12] |
| t <<= 2 |
| self.assertEqual(t, '0b11111100') |
| s = BitStream('0b11011') |
| s <<= 2 |
| self.assertEqual(s.bin, '01100') |
| s <<= 100000000000000000000 |
| self.assertEqual(s.bin, '00000') |
| s = BitStream('0xff') |
| s <<= 1 |
| self.assertEqual(s, '0xfe') |
| s <<= 0 |
| self.assertEqual(s, '0xfe') |
| |
| def testShiftLeftInPlaceErrors(self): |
| s = BitStream() |
| self.assertRaises(ValueError, s.__ilshift__, 1) |
| s += '0b11' |
| self.assertRaises(ValueError, s.__ilshift__, -1) |
| |
| |
| class Replace(unittest.TestCase): |
| def testReplace1(self): |
| a = BitStream('0b1') |
| n = a.replace('0b1', '0b0', bytealigned=True) |
| self.assertEqual(a.bin, '0') |
| self.assertEqual(n, 1) |
| n = a.replace('0b1', '0b0', bytealigned=True) |
| self.assertEqual(n, 0) |
| |
| def testReplace2(self): |
| a = BitStream('0b00001111111') |
| n = a.replace('0b1', '0b0', bytealigned=True) |
| self.assertEqual(a.bin, '00001111011') |
| self.assertEqual(n, 1) |
| n = a.replace('0b1', '0b0', bytealigned=False) |
| self.assertEqual(a.bin, '00000000000') |
| self.assertEqual(n, 6) |
| |
| def testReplace3(self): |
| a = BitStream('0b0') |
| n = a.replace('0b0', '0b110011111', bytealigned=True) |
| self.assertEqual(n, 1) |
| self.assertEqual(a.bin, '110011111') |
| n = a.replace('0b11', '', bytealigned=False) |
| self.assertEqual(n, 3) |
| self.assertEqual(a.bin, '001') |
| |
| def testReplace4(self): |
| a = BitStream('0x00114723ef4732344700') |
| n = a.replace('0x47', '0x00', bytealigned=True) |
| self.assertEqual(n, 3) |
| self.assertEqual(a.hex, '00110023ef0032340000') |
| a.replace('0x00', '', bytealigned=True) |
| self.assertEqual(a.hex, '1123ef3234') |
| a.replace('0x11', '', start=1, bytealigned=True) |
| self.assertEqual(a.hex, '1123ef3234') |
| a.replace('0x11', '0xfff', end=7, bytealigned=True) |
| self.assertEqual(a.hex, '1123ef3234') |
| a.replace('0x11', '0xfff', end=8, bytealigned=True) |
| self.assertEqual(a.hex, 'fff23ef3234') |
| |
| def testReplace5(self): |
| a = BitStream('0xab') |
| b = BitStream('0xcd') |
| c = BitStream('0xabef') |
| c.replace(a, b) |
| self.assertEqual(c, '0xcdef') |
| self.assertEqual(a, '0xab') |
| self.assertEqual(b, '0xcd') |
| a = BitStream('0x0011223344') |
| a.pos = 12 |
| a.replace('0x11', '0xfff', bytealigned=True) |
| self.assertEqual(a.pos, 8) |
| self.assertEqual(a, '0x00fff223344') |
| |
| def testReplaceWithSelf(self): |
| a = BitStream('0b11') |
| a.replace('0b1', a) |
| self.assertEqual(a, '0xf') |
| a.replace(a, a) |
| self.assertEqual(a, '0xf') |
| |
| def testReplaceCount(self): |
| a = BitStream('0x223344223344223344') |
| n = a.replace('0x2', '0x0', count=0, bytealigned=True) |
| self.assertEqual(n, 0) |
| self.assertEqual(a.hex, '223344223344223344') |
| n = a.replace('0x2', '0x0', count=1, bytealigned=True) |
| self.assertEqual(n, 1) |
| self.assertEqual(a.hex, '023344223344223344') |
| n = a.replace('0x33', '', count=2, bytealigned=True) |
| self.assertEqual(n, 2) |
| self.assertEqual(a.hex, '02442244223344') |
| n = a.replace('0x44', '0x4444', count=1435, bytealigned=True) |
| self.assertEqual(n, 3) |
| self.assertEqual(a.hex, '02444422444422334444') |
| |
| def testReplaceBitpos(self): |
| a = BitStream('0xff') |
| a.bitpos = 8 |
| a.replace('0xff', '', bytealigned=True) |
| self.assertEqual(a.bitpos, 0) |
| a = BitStream('0b0011110001') |
| a.bitpos = 4 |
| a.replace('0b1', '0b000') |
| self.assertEqual(a.bitpos, 8) |
| a = BitStream('0b1') |
| a.bitpos = 1 |
| a.replace('0b1', '0b11111', bytealigned=True) |
| self.assertEqual(a.bitpos, 5) |
| a.replace('0b11', '0b0', False) |
| self.assertEqual(a.bitpos, 3) |
| a.append('0b00') |
| a.replace('0b00', '0xffff') |
| self.assertEqual(a.bitpos, 17) |
| |
| def testReplaceErrors(self): |
| a = BitStream('0o123415') |
| self.assertRaises(ValueError, a.replace, '', '0o7', bytealigned=True) |
| self.assertRaises(ValueError, a.replace, '0b1', '0b1', start=-100, bytealigned=True) |
| self.assertRaises(ValueError, a.replace, '0b1', '0b1', end=19, bytealigned=True) |
| |
| |
| class SliceAssignment(unittest.TestCase): |
| |
| # TODO: Move this to another class |
| def testSetSlice(self): |
| a = BitStream() |
| a[0:0] = '0xabcdef' |
| self.assertEqual(a.bytepos, 3) |
| a[4:16] = '' |
| self.assertEqual(a, '0xaef') |
| self.assertEqual(a.bitpos, 4) |
| a[8:] = '0x00' |
| self.assertEqual(a, '0xae00') |
| self.assertEqual(a.bytepos, 2) |
| a += '0xf' |
| a[8:] = '0xe' |
| self.assertEqual(a, '0xaee') |
| self.assertEqual(a.bitpos, 12) |
| b = BitStream() |
| b[0:800] = '0xffee' |
| self.assertEqual(b, '0xffee') |
| b[4:48] = '0xeed123' |
| self.assertEqual(b, '0xfeed123') |
| b[-800:8] = '0x0000' |
| self.assertEqual(b, '0x0000ed123') |
| a = BitStream('0xabcde') |
| self.assertEqual(a[-100:-90], '') |
| self.assertEqual(a[-100:-16], '0xa') |
| a[-100:-16] = '0x0' |
| self.assertEqual(a, '0x0bcde') |
| |
| def testInsertingUsingSetItem(self): |
| a = BitStream() |
| a[0:0] = '0xdeadbeef' |
| self.assertEqual(a, '0xdeadbeef') |
| self.assertEqual(a.bytepos, 4) |
| a[16:16] = '0xfeed' |
| self.assertEqual(a, '0xdeadfeedbeef') |
| self.assertEqual(a.bytepos, 4) |
| a[0:0] = '0xa' |
| self.assertEqual(a, '0xadeadfeedbeef') |
| self.assertEqual(a.bitpos, 4) |
| a.bytepos = 6 |
| a[0:0] = '0xff' |
| self.assertEqual(a.bytepos, 1) |
| a[8:0] = '0x00000' |
| self.assertTrue(a.startswith('0xff00000adead')) |
| |
| def testSliceAssignmentBitPos(self): |
| a = BitStream('int:64=-1') |
| a.pos = 64 |
| a[0:8] = '' |
| self.assertEqual(a.pos, 0) |
| a.pos = 52 |
| a[48:56] = '0x0000' |
| self.assertEqual(a.pos, 64) |
| a[10:10] = '0x0' |
| self.assertEqual(a.pos, 14) |
| a[56:68] = '0x000' |
| self.assertEqual(a.pos, 14) |
| |
| |
| class Pack(unittest.TestCase): |
| def testPack1(self): |
| s = bitstring.pack('uint:6, bin, hex, int:6, se, ue, oct', 10, '0b110', 'ff', -1, -6, 6, '54') |
| t = BitStream('uint:6=10, 0b110, 0xff, int:6=-1, se=-6, ue=6, oct=54') |
| self.assertEqual(s, t) |
| self.assertRaises(bitstring.CreationError, pack, 'tomato', '0') |
| self.assertRaises(bitstring.CreationError, pack, 'uint', 12) |
| self.assertRaises(bitstring.CreationError, pack, 'hex', 'penguin') |
| self.assertRaises(bitstring.CreationError, pack, 'hex12', '0x12') |
| |
| def testPackWithLiterals(self): |
| s = bitstring.pack('0xf') |
| self.assertEqual(s, '0xf') |
| self.assertTrue(type(s), BitStream) |
| s = pack('0b1') |
| self.assertEqual(s, '0b1') |
| s = pack('0o7') |
| self.assertEqual(s, '0o7') |
| s = pack('int:10=-1') |
| self.assertEqual(s, '0b1111111111') |
| s = pack('uint:10=1') |
| self.assertEqual(s, '0b0000000001') |
| s = pack('ue=12') |
| self.assertEqual(s.ue, 12) |
| s = pack('se=-12') |
| self.assertEqual(s.se, -12) |
| s = pack('bin=01') |
| self.assertEqual(s.bin, '01') |
| s = pack('hex=01') |
| self.assertEqual(s.hex, '01') |
| s = pack('oct=01') |
| self.assertEqual(s.oct, '01') |
| |
| def testPackWithDict(self): |
| a = pack('uint:6=width, se=height', height=100, width=12) |
| w, h = a.unpack('uint:6, se') |
| self.assertEqual(w, 12) |
| self.assertEqual(h, 100) |
| d = {} |
| d['w'] = '0xf' |
| d['300'] = 423 |
| d['e'] = '0b1101' |
| a = pack('int:100=300, bin=e, uint:12=300', **d) |
| x, y, z = a.unpack('int:100, bin, uint:12') |
| self.assertEqual(x, 423) |
| self.assertEqual(y, '1101') |
| self.assertEqual(z, 423) |
| |
| def testPackWithDict2(self): |
| a = pack('int:5, bin:3=b, 0x3, bin=c, se=12', 10, b='0b111', c='0b1') |
| b = BitStream('int:5=10, 0b111, 0x3, 0b1, se=12') |
| self.assertEqual(a, b) |
| a = pack('bits:3=b', b=BitStream('0b101')) |
| self.assertEqual(a, '0b101') |
| a = pack('bits:24=b', b=BitStream('0x001122')) |
| self.assertEqual(a, '0x001122') |
| |
| def testPackWithDict3(self): |
| s = pack('hex:4=e, hex:4=0xe, hex:4=e', e='f') |
| self.assertEqual(s, '0xfef') |
| s = pack('sep', sep='0b00') |
| self.assertEqual(s, '0b00') |
| |
| def testPackWithDict4(self): |
| s = pack('hello', hello='0xf') |
| self.assertEqual(s, '0xf') |
| s = pack('x, y, x, y, x', x='0b10', y='uint:12=100') |
| t = BitStream('0b10, uint:12=100, 0b10, uint:12=100, 0b10') |
| self.assertEqual(s, t) |
| a = [1, 2, 3, 4, 5] |
| s = pack('int:8, div,' * 5, *a, **{'div': '0b1'}) |
| t = BitStream('int:8=1, 0b1, int:8=2, 0b1, int:8=3, 0b1, int:8=4, 0b1, int:8=5, 0b1') |
| self.assertEqual(s, t) |
| |
| def testPackWithLocals(self): |
| width = 352 |
| height = 288 |
| s = pack('uint:12=width, uint:12=height', **locals()) |
| self.assertEqual(s, '0x160120') |
| |
| def testPackWithLengthRestriction(self): |
| s = pack('bin:3', '0b000') |
| self.assertRaises(bitstring.CreationError, pack, 'bin:3', '0b0011') |
| self.assertRaises(bitstring.CreationError, pack, 'bin:3', '0b11') |
| self.assertRaises(bitstring.CreationError, pack, 'bin:3=0b0011') |
| self.assertRaises(bitstring.CreationError, pack, 'bin:3=0b11') |
| |
| s = pack('hex:4', '0xf') |
| self.assertRaises(bitstring.CreationError, pack, 'hex:4', '0b111') |
| self.assertRaises(bitstring.CreationError, pack, 'hex:4', '0b11111') |
| self.assertRaises(bitstring.CreationError, pack, 'hex:8=0xf') |
| |
| s = pack('oct:6', '0o77') |
| self.assertRaises(bitstring.CreationError, pack, 'oct:6', '0o1') |
| self.assertRaises(bitstring.CreationError, pack, 'oct:6', '0o111') |
| self.assertRaises(bitstring.CreationError, pack, 'oct:3', '0b1') |
| self.assertRaises(bitstring.CreationError, pack, 'oct:3=hello', hello='0o12') |
| |
| s = pack('bits:3', BitStream('0b111')) |
| self.assertRaises(bitstring.CreationError, pack, 'bits:3', BitStream('0b11')) |
| self.assertRaises(bitstring.CreationError, pack, 'bits:3', BitStream('0b1111')) |
| self.assertRaises(bitstring.CreationError, pack, 'bits:12=b', b=BitStream('0b11')) |
| |
| def testPackNull(self): |
| s = pack('') |
| self.assertFalse(s) |
| s = pack(',') |
| self.assertFalse(s) |
| s = pack(',,,,,0b1,,,,,,,,,,,,,0b1,,,,,,,,,,') |
| self.assertEqual(s, '0b11') |
| s = pack(',,uint:12,,bin:3,', 100, '100') |
| a, b = s.unpack(',,,uint:12,,,,bin:3,,,') |
| self.assertEqual(a, 100) |
| self.assertEqual(b, '100') |
| |
| def testPackDefaultUint(self): |
| s = pack('10, 5', 1, 2) |
| a, b = s.unpack('10, 5') |
| self.assertEqual((a, b), (1, 2)) |
| s = pack('10=150, 12=qee', qee=3) |
| self.assertEqual(s, 'uint:10=150, uint:12=3') |
| t = BitStream('100=5') |
| self.assertEqual(t, 'uint:100=5') |
| |
| def testPackDefualtUintErrors(self): |
| self.assertRaises(bitstring.CreationError, BitStream, '5=-1') |
| |
| def testPackingLongKeywordBitstring(self): |
| s = pack('bits=b', b=BitStream(128000)) |
| self.assertEqual(s, BitStream(128000)) |
| |
| def testPackingWithListFormat(self): |
| f = ['bin', 'hex', 'uint:10'] |
| a = pack(','.join(f), '00', '234', 100) |
| b = pack(f, '00', '234', 100) |
| self.assertEqual(a, b) |
| |
| |
| class Unpack(unittest.TestCase): |
| def testUnpack1(self): |
| s = BitStream('uint:13=23, hex=e, bin=010, int:41=-554, 0o44332, se=-12, ue=4') |
| s.pos = 11 |
| a, b, c, d, e, f, g = s.unpack('uint:13, hex:4, bin:3, int:41, oct:15, se, ue') |
| self.assertEqual(a, 23) |
| self.assertEqual(b, 'e') |
| self.assertEqual(c, '010') |
| self.assertEqual(d, -554) |
| self.assertEqual(e, '44332') |
| self.assertEqual(f, -12) |
| self.assertEqual(g, 4) |
| self.assertEqual(s.pos, 11) |
| |
| def testUnpack2(self): |
| s = BitStream('0xff, 0b000, uint:12=100') |
| a, b, c = s.unpack('bits:8, bits, uint:12') |
| self.assertEqual(type(s), BitStream) |
| self.assertEqual(a, '0xff') |
| self.assertEqual(type(s), BitStream) |
| self.assertEqual(b, '0b000') |
| self.assertEqual(c, 100) |
| a, b = s.unpack(['bits:11', 'uint']) |
| self.assertEqual(a, '0xff, 0b000') |
| self.assertEqual(b, 100) |
| |
| def testUnpackNull(self): |
| s = pack('0b1, , , 0xf,') |
| a, b = s.unpack('bin:1,,,hex:4,') |
| self.assertEqual(a, '1') |
| self.assertEqual(b, 'f') |
| |
| |
| class FromFile(unittest.TestCase): |
| def testCreationFromFileOperations(self): |
| s = BitStream(filename='smalltestfile') |
| s.append('0xff') |
| self.assertEqual(s.hex, '0123456789abcdefff') |
| |
| s = ConstBitStream(filename='smalltestfile') |
| t = BitStream('0xff') + s |
| self.assertEqual(t.hex, 'ff0123456789abcdef') |
| |
| s = BitStream(filename='smalltestfile') |
| del s[:1] |
| self.assertEqual((BitStream('0b0') + s).hex, '0123456789abcdef') |
| |
| s = BitStream(filename='smalltestfile') |
| del s[:7 * 8] |
| self.assertEqual(s.hex, 'ef') |
| |
| s = BitStream(filename='smalltestfile') |
| s.insert('0xc', 4) |
| self.assertEqual(s.hex, '0c123456789abcdef') |
| |
| s = BitStream(filename='smalltestfile') |
| s.prepend('0xf') |
| self.assertEqual(s.hex, 'f0123456789abcdef') |
| |
| s = BitStream(filename='smalltestfile') |
| s.overwrite('0xaaa', 12) |
| self.assertEqual(s.hex, '012aaa6789abcdef') |
| |
| s = BitStream(filename='smalltestfile') |
| s.reverse() |
| self.assertEqual(s.hex, 'f7b3d591e6a2c480') |
| |
| s = BitStream(filename='smalltestfile') |
| del s[-60:] |
| self.assertEqual(s.hex, '0') |
| |
| s = BitStream(filename='smalltestfile') |
| del s[:60] |
| self.assertEqual(s.hex, 'f') |
| |
| def testFileProperties(self): |
| s = ConstBitStream(filename='smalltestfile') |
| self.assertEqual(s.hex, '0123456789abcdef') |
| self.assertEqual(s.uint, 81985529216486895) |
| self.assertEqual(s.int, 81985529216486895) |
| self.assertEqual(s.bin, '0000000100100011010001010110011110001001101010111100110111101111') |
| self.assertEqual(s[:-1].oct, '002215053170465363367') |
| s.bitpos = 0 |
| self.assertEqual(s.read('se'), -72) |
| s.bitpos = 0 |
| self.assertEqual(s.read('ue'), 144) |
| self.assertEqual(s.bytes, b'\x01\x23\x45\x67\x89\xab\xcd\xef') |
| self.assertEqual(s.tobytes(), b'\x01\x23\x45\x67\x89\xab\xcd\xef') |
| |
| def testCreationFromFileWithLength(self): |
| s = ConstBitStream(filename='test.m1v', length=32) |
| self.assertEqual(s.length, 32) |
| self.assertEqual(s.hex, '000001b3') |
| s = ConstBitStream(filename='test.m1v', length=0) |
| self.assertFalse(s) |
| self.assertRaises(bitstring.CreationError, BitStream, filename='smalltestfile', length=65) |
| self.assertRaises(bitstring.CreationError, ConstBitStream, filename='smalltestfile', length=64, offset=1) |
| # self.assertRaises(bitstring.CreationError, ConstBitStream, filename='smalltestfile', offset=65) |
| f = open('smalltestfile', 'rb') |
| # self.assertRaises(bitstring.CreationError, ConstBitStream, auto=f, offset=65) |
| self.assertRaises(bitstring.CreationError, ConstBitStream, auto=f, length=65) |
| self.assertRaises(bitstring.CreationError, ConstBitStream, auto=f, offset=60, length=5) |
| |
| def testCreationFromFileWithOffset(self): |
| a = BitStream(filename='test.m1v', offset=4) |
| self.assertEqual(a.peek(4 * 8).hex, '00001b31') |
| b = BitStream(filename='test.m1v', offset=28) |
| self.assertEqual(b.peek(8).hex, '31') |
| |
| def testFileSlices(self): |
| s = BitStream(filename='smalltestfile') |
| self.assertEqual(s[-16:].hex, 'cdef') |
| |
| def testCreataionFromFileErrors(self): |
| self.assertRaises(IOError, BitStream, filename='Idonotexist') |
| |
| def testFindInFile(self): |
| s = BitStream(filename='test.m1v') |
| self.assertTrue(s.find('0x160120')) |
| self.assertEqual(s.bytepos, 4) |
| s3 = s.read(3 * 8) |
| self.assertEqual(s3.hex, '160120') |
| s.bytepos = 0 |
| self.assertTrue(s._pos == 0) |
| self.assertTrue(s.find('0x0001b2')) |
| self.assertEqual(s.bytepos, 13) |
| |
| def testHexFromFile(self): |
| s = BitStream(filename='test.m1v') |
| self.assertEqual(s[0:32].hex, '000001b3') |
| self.assertEqual(s[-32:].hex, '000001b7') |
| s.hex = '0x11' |
| self.assertEqual(s.hex, '11') |
| |
| def testFileOperations(self): |
| s1 = BitStream(filename='test.m1v') |
| s2 = BitStream(filename='test.m1v') |
| self.assertEqual(s1.read(32).hex, '000001b3') |
| self.assertEqual(s2.read(32).hex, '000001b3') |
| s1.bytepos += 4 |
| self.assertEqual(s1.read(8).hex, '02') |
| self.assertEqual(s2.read(5 * 8).hex, '1601208302') |
| s1.pos = s1.len |
| try: |
| s1.pos += 1 |
| self.assertTrue(False) |
| except ValueError: |
| pass |
| |
| def testFileBitGetting(self): |
| s = ConstBitStream(filename='smalltestfile', offset=16, length=8) # 0x45 |
| b = s[1] |
| self.assertTrue(b) |
| b = s.any(0, [-1, -2, -3]) |
| self.assertTrue(b) |
| b = s.all(0, [0, 1, 2]) |
| self.assertFalse(b) |
| |
| def testVeryLargeFiles(self): |
| # This uses an 11GB file which isn't distributed for obvious reasons |
| # and so this test won't work for anyone except me! |
| try: |
| s = ConstBitStream(filename='11GB.mkv') |
| except IOError: |
| return |
| self.assertEqual(s.len, 11743020505 * 8) |
| self.assertEqual(s[1000000000:1000000100].hex, 'bdef7335d4545f680d669ce24') |
| self.assertEqual(s[-4::8].hex, 'bbebf7a1') |
| |
| |
| class CreationErrors(unittest.TestCase): |
| def testIncorrectBinAssignment(self): |
| s = BitStream() |
| self.assertRaises(bitstring.CreationError, s._setbin_safe, '0010020') |
| |
| def testIncorrectHexAssignment(self): |
| s = BitStream() |
| self.assertRaises(bitstring.CreationError, s._sethex, '0xabcdefg') |
| |
| |
| class Length(unittest.TestCase): |
| def testLengthZero(self): |
| self.assertEqual(BitStream('').len, 0) |
| |
| def testLength(self): |
| self.assertEqual(BitStream('0x80').len, 8) |
| |
| def testLengthErrors(self): |
| #TODO: Lots of new checks, for various inits which now disallow length and offset |
| pass |
| #self.assertRaises(ValueError, BitStream, bin='111', length=-1) |
| #self.assertRaises(ValueError, BitStream, bin='111', length=4) |
| |
| def testOffsetLengthError(self): |
| self.assertRaises(bitstring.CreationError, BitStream, hex='0xffff', offset=-1) |
| |
| |
| class SimpleConversions(unittest.TestCase): |
| def testConvertToUint(self): |
| self.assertEqual(BitStream('0x10').uint, 16) |
| self.assertEqual(BitStream('0b000111').uint, 7) |
| |
| def testConvertToInt(self): |
| self.assertEqual(BitStream('0x10').int, 16) |
| self.assertEqual(BitStream('0b11110').int, -2) |
| |
| def testConvertToHex(self): |
| self.assertEqual(BitStream(bytes=b'\x00\x12\x23\xff').hex, '001223ff') |
| s = BitStream('0b11111') |
| self.assertRaises(bitstring.InterpretError, s._gethex) |
| |
| |
| class Empty(unittest.TestCase): |
| def testEmptyBitstring(self): |
| s = BitStream() |
| self.assertRaises(bitstring.ReadError, s.read, 1) |
| self.assertEqual(s.bin, '') |
| self.assertEqual(s.hex, '') |
| self.assertRaises(bitstring.InterpretError, s._getint) |
| self.assertRaises(bitstring.InterpretError, s._getuint) |
| self.assertFalse(s) |
| |
| def testNonEmptyBitStream(self): |
| s = BitStream(bin='0') |
| self.assertFalse(not s.len) |
| |
| |
| class Position(unittest.TestCase): |
| def testBitPosition(self): |
| s = BitStream(bytes=b'\x00\x00\x00') |
| self.assertEqual(s.bitpos, 0) |
| s.read(5) |
| self.assertEqual(s.pos, 5) |
| s.pos = s.len |
| self.assertRaises(bitstring.ReadError, s.read, 1) |
| |
| def testBytePosition(self): |
| s = BitStream(bytes=b'\x00\x00\x00') |
| self.assertEqual(s.bytepos, 0) |
| s.read(10) |
| self.assertRaises(bitstring.ByteAlignError, s._getbytepos) |
| s.read(6) |
| self.assertEqual(s.bytepos, 2) |
| |
| def testSeekToBit(self): |
| s = BitStream(bytes=b'\x00\x00\x00\x00\x00\x00') |
| s.bitpos = 0 |
| self.assertEqual(s.bitpos, 0) |
| self.assertRaises(ValueError, s._setbitpos, -1) |
| self.assertRaises(ValueError, s._setbitpos, 6 * 8 + 1) |
| s.bitpos = 6 * 8 |
| self.assertEqual(s.bitpos, 6 * 8) |
| |
| def testSeekToByte(self): |
| s = BitStream(bytes=b'\x00\x00\x00\x00\x00\xab') |
| s.bytepos = 5 |
| self.assertEqual(s.read(8).hex, 'ab') |
| |
| def testAdvanceBitsAndBytes(self): |
| s = BitStream(bytes=b'\x00\x00\x00\x00\x00\x00\x00\x00') |
| s.pos += 5 |
| self.assertEqual(s.pos, 5) |
| s.bitpos += 16 |
| self.assertEqual(s.pos, 2 * 8 + 5) |
| s.pos -= 8 |
| self.assertEqual(s.pos, 8 + 5) |
| |
| def testRetreatBitsAndBytes(self): |
| a = BitStream(length=100) |
| a.pos = 80 |
| a.bytepos -= 5 |
| self.assertEqual(a.bytepos, 5) |
| a.pos -= 5 |
| self.assertEqual(a.pos, 35) |
| |
| |
| class Offset(unittest.TestCase): |
| def testOffset1(self): |
| s = BitStream(bytes=b'\x00\x1b\x3f', offset=4) |
| self.assertEqual(s.read(8).bin, '00000001') |
| self.assertEqual(s.length, 20) |
| |
| def testOffset2(self): |
| s1 = BitStream(bytes=b'\xf1\x02\x04') |
| s2 = BitStream(bytes=b'\xf1\x02\x04', length=23) |
| for i in [1, 2, 3, 4, 5, 6, 7, 6, 5, 4, 3, 2, 1, 0, 7, 3, 5, 1, 4]: |
| s1._datastore = offsetcopy(s1._datastore, i) |
| self.assertEqual(s1.hex, 'f10204') |
| s2._datastore = offsetcopy(s2._datastore, i) |
| self.assertEqual(s2.bin, '11110001000000100000010') |
| |
| |
| class Append(unittest.TestCase): |
| def testAppend(self): |
| s1 = BitStream('0b00000') |
| s1.append(BitStream(bool=True)) |
| self.assertEqual(s1.bin, '000001') |
| self.assertEqual((BitStream('0x0102') + BitStream('0x0304')).hex, '01020304') |
| |
| def testAppendSameBitstring(self): |
| s1 = BitStream('0xf0')[:6] |
| s1.append(s1) |
| self.assertEqual(s1.bin, '111100111100') |
| |
| def testAppendWithOffset(self): |
| s = BitStream(bytes=b'\x28\x28', offset=1) |
| s.append('0b0') |
| self.assertEqual(s.hex, '5050') |
| |
| |
| class ByteAlign(unittest.TestCase): |
| def testByteAlign(self): |
| s = BitStream(hex='0001ff23') |
| s.bytealign() |
| self.assertEqual(s.bytepos, 0) |
| s.pos += 11 |
| s.bytealign() |
| self.assertEqual(s.bytepos, 2) |
| s.pos -= 10 |
| s.bytealign() |
| self.assertEqual(s.bytepos, 1) |
| |
| def testByteAlignWithOffset(self): |
| s = BitStream(hex='0112233') |
| s._datastore = offsetcopy(s._datastore, 3) |
| bitstoalign = s.bytealign() |
| self.assertEqual(bitstoalign, 0) |
| self.assertEqual(s.read(5).bin, '00001') |
| |
| def testInsertByteAligned(self): |
| s = BitStream('0x0011') |
| s.insert(BitStream('0x22'), 8) |
| self.assertEqual(s.hex, '002211') |
| s = BitStream(0) |
| s.insert(BitStream(bin='101'), 0) |
| self.assertEqual(s.bin, '101') |
| |
| |
| class Truncate(unittest.TestCase): |
| def testTruncateStart(self): |
| s = BitStream('0b1') |
| del s[:1] |
| self.assertFalse(s) |
| s = BitStream(hex='1234') |
| self.assertEqual(s.hex, '1234') |
| del s[:4] |
| self.assertEqual(s.hex, '234') |
| del s[:9] |
| self.assertEqual(s.bin, '100') |
| del s[:2] |
| self.assertEqual(s.bin, '0') |
| self.assertEqual(s.len, 1) |
| del s[:1] |
| self.assertFalse(s) |
| |
| def testTruncateEnd(self): |
| s = BitStream('0b1') |
| del s[-1:] |
| self.assertFalse(s) |
| s = BitStream(bytes=b'\x12\x34') |
| self.assertEqual(s.hex, '1234') |
| del s[-4:] |
| self.assertEqual(s.hex, '123') |
| del s[-9:] |
| self.assertEqual(s.bin, '000') |
| del s[-3:] |
| self.assertFalse(s) |
| s = BitStream('0b001') |
| del s[:2] |
| del s[-1:] |
| self.assertFalse(s) |
| |
| |
| class Slice(unittest.TestCase): |
| def testByteAlignedSlice(self): |
| s = BitStream(hex='0x123456') |
| self.assertEqual(s[8:16].hex, '34') |
| s = s[8:24] |
| self.assertEqual(s.len, 16) |
| self.assertEqual(s.hex, '3456') |
| s = s[0:8] |
| self.assertEqual(s.hex, '34') |
| s.hex = '0x123456' |
| self.assertEqual(s[8:24][0:8].hex, '34') |
| |
| def testSlice(self): |
| s = BitStream(bin='000001111100000') |
| s1 = s[0:5] |
| s2 = s[5:10] |
| s3 = s[10:15] |
| self.assertEqual(s1.bin, '00000') |
| self.assertEqual(s2.bin, '11111') |
| self.assertEqual(s3.bin, '00000') |
| |
| |
| class Insert(unittest.TestCase): |
| def testInsert(self): |
| s1 = BitStream(hex='0x123456') |
| s2 = BitStream(hex='0xff') |
| s1.bytepos = 1 |
| s1.insert(s2) |
| self.assertEqual(s1.bytepos, 2) |
| self.assertEqual(s1.hex, '12ff3456') |
| s1.insert('0xee', 24) |
| self.assertEqual(s1.hex, '12ff34ee56') |
| self.assertEqual(s1.bitpos, 32) |
| self.assertRaises(ValueError, s1.insert, '0b1', -1000) |
| self.assertRaises(ValueError, s1.insert, '0b1', 1000) |
| |
| def testInsertNull(self): |
| s = BitStream(hex='0x123').insert(BitStream(), 3) |
| self.assertEqual(s.hex, '123') |
| |
| def testInsertBits(self): |
| one = BitStream(bin='1') |
| zero = BitStream(bin='0') |
| s = BitStream(bin='00') |
| s.insert(one, 0) |
| self.assertEqual(s.bin, '100') |
| s.insert(zero, 0) |
| self.assertEqual(s.bin, '0100') |
| s.insert(one, s.len) |
| self.assertEqual(s.bin, '01001') |
| s.insert(s, 2) |
| self.assertEqual(s.bin, '0101001001') |
| |
| |
| class Resetting(unittest.TestCase): |
| def testSetHex(self): |
| s = BitStream() |
| s.hex = '0' |
| self.assertEqual(s.hex, '0') |
| s.hex = '0x010203045' |
| self.assertEqual(s.hex, '010203045') |
| self.assertRaises(bitstring.CreationError, s._sethex, '0x002g') |
| |
| def testSetBin(self): |
| s = BitStream(bin="000101101") |
| self.assertEqual(s.bin, '000101101') |
| self.assertEqual(s.len, 9) |
| s.bin = '0' |
| self.assertEqual(s.bin, '0') |
| self.assertEqual(s.len, 1) |
| |
| def testSetEmptyBin(self): |
| s = BitStream(hex='0x000001b3') |
| s.bin = '' |
| self.assertEqual(s.len, 0) |
| self.assertEqual(s.bin, '') |
| |
| def testSetInvalidBin(self): |
| s = BitStream() |
| self.assertRaises(bitstring.CreationError, s._setbin_safe, '00102') |
| |
| |
| class Overwriting(unittest.TestCase): |
| def testOverwriteBit(self): |
| s = BitStream(bin='0') |
| s.overwrite(BitStream(bin='1'), 0) |
| self.assertEqual(s.bin, '1') |
| |
| def testOverwriteLimits(self): |
| s = BitStream(bin='0b11111') |
| s.overwrite(BitStream(bin='000'), 0) |
| self.assertEqual(s.bin, '00011') |
| s.overwrite('0b000', 2) |
| self.assertEqual(s.bin, '00000') |
| |
| def testOverwriteNull(self): |
| s = BitStream(hex='342563fedec') |
| s2 = BitStream(s) |
| s.overwrite(BitStream(bin=''), 23) |
| self.assertEqual(s.bin, s2.bin) |
| |
| def testOverwritePosition(self): |
| s1 = BitStream(hex='0123456') |
| s2 = BitStream(hex='ff') |
| s1.bytepos = 1 |
| s1.overwrite(s2) |
| self.assertEqual((s1.hex, s1.bytepos), ('01ff456', 2)) |
| s1.overwrite('0xff', 0) |
| self.assertEqual((s1.hex, s1.bytepos), ('ffff456', 1)) |
| |
| def testOverwriteWithSelf(self): |
| s = BitStream('0x123') |
| s.overwrite(s) |
| self.assertEqual(s, '0x123') |
| |
| |
| class Split(unittest.TestCase): |
| def testSplitByteAlignedCornerCases(self): |
| s = BitStream() |
| bsl = s.split(BitStream(hex='0xff')) |
| self.assertEqual(next(bsl).hex, '') |
| self.assertRaises(StopIteration, next, bsl) |
| s = BitStream(hex='aabbcceeddff') |
| delimiter = BitStream() |
| bsl = s.split(delimiter) |
| self.assertRaises(ValueError, next, bsl) |
| delimiter = BitStream(hex='11') |
| bsl = s.split(delimiter) |
| self.assertEqual(next(bsl).hex, s.hex) |
| |
| def testSplitByteAligned(self): |
| s = BitStream(hex='0x1234aa1234bbcc1234ffff') |
| delimiter = BitStream(hex='1234') |
| bsl = s.split(delimiter) |
| self.assertEqual([b.hex for b in bsl], ['', '1234aa', '1234bbcc', '1234ffff']) |
| self.assertEqual(s.pos, 0) |
| |
| def testSplitByteAlignedWithIntialBytes(self): |
| s = BitStream(hex='aa471234fedc43 47112233 47 4723 472314') |
| delimiter = BitStream(hex='47') |
| s.find(delimiter) |
| self.assertEqual(s.bytepos, 1) |
| bsl = s.split(delimiter, start=0) |
| self.assertEqual([b.hex for b in bsl], ['aa', '471234fedc43', '47112233', |
| '47', '4723', '472314']) |
| self.assertEqual(s.bytepos, 1) |
| |
| def testSplitByteAlignedWithOverlappingDelimiter(self): |
| s = BitStream(hex='aaffaaffaaffaaffaaff') |
| bsl = s.split(BitStream(hex='aaffaa')) |
| self.assertEqual([b.hex for b in bsl], ['', 'aaffaaff', 'aaffaaffaaff']) |
| |
| |
| class Adding(unittest.TestCase): |
| def testAdding(self): |
| s1 = BitStream(hex='0x0102') |
| s2 = BitStream(hex='0x0304') |
| s3 = s1 + s2 |
| self.assertEqual(s1.hex, '0102') |
| self.assertEqual(s2.hex, '0304') |
| self.assertEqual(s3.hex, '01020304') |
| s3 += s1 |
| self.assertEqual(s3.hex, '010203040102') |
| self.assertEqual(s2[9:16].bin, '0000100') |
| self.assertEqual(s1[0:9].bin, '000000010') |
| s4 = BitStream(bin='000000010') +\ |
| BitStream(bin='0000100') |
| self.assertEqual(s4.bin, '0000000100000100') |
| s2p = s2[9:16] |
| s1p = s1[0:9] |
| s5p = s1p + s2p |
| s5 = s1[0:9] + s2[9:16] |
| self.assertEqual(s5.bin, '0000000100000100') |
| |
| def testMoreAdding(self): |
| s = BitStream(bin='00') + BitStream(bin='') + BitStream(bin='11') |
| self.assertEqual(s.bin, '0011') |
| s = '0b01' |
| s += BitStream('0b11') |
| self.assertEqual(s.bin, '0111') |
| s = BitStream('0x00') |
| t = BitStream('0x11') |
| s += t |
| self.assertEqual(s.hex, '0011') |
| self.assertEqual(t.hex, '11') |
| s += s |
| self.assertEqual(s.hex, '00110011') |
| |
| def testRadd(self): |
| s = '0xff' + BitStream('0xee') |
| self.assertEqual(s.hex, 'ffee') |
| |
| |
| def testTruncateAsserts(self): |
| s = BitStream('0x001122') |
| s.bytepos = 2 |
| del s[-s.len:] |
| self.assertEqual(s.bytepos, 0) |
| s.append('0x00') |
| s.append('0x1122') |
| s.bytepos = 2 |
| del s[:s.len] |
| self.assertEqual(s.bytepos, 0) |
| s.append('0x00') |
| |
| def testOverwriteErrors(self): |
| s = BitStream(bin='11111') |
| self.assertRaises(ValueError, s.overwrite, BitStream(bin='1'), -10) |
| self.assertRaises(ValueError, s.overwrite, BitStream(bin='1'), 6) |
| self.assertRaises(ValueError, s.overwrite, BitStream(bin='11111'), 1) |
| |
| def testDeleteBits(self): |
| s = BitStream(bin='000111100000') |
| s.bitpos = 4 |
| del s[4:8] |
| self.assertEqual(s.bin, '00010000') |
| del s[4:1004] |
| self.assertTrue(s.bin, '0001') |
| |
| def testDeleteBitsWithPosition(self): |
| s = BitStream(bin='000111100000') |
| del s[4:8] |
| self.assertEqual(s.bin, '00010000') |
| |
| def testDeleteBytes(self): |
| s = BitStream('0x00112233') |
| del s[8:8] |
| self.assertEqual(s.hex, '00112233') |
| self.assertEqual(s.pos, 0) |
| del s[8:16] |
| self.assertEqual(s.hex, '002233') |
| self.assertEqual(s.bytepos, 0) |
| del s[:24] |
| self.assertFalse(s) |
| self.assertEqual(s.pos, 0) |
| |
| def testGetItemWithPositivePosition(self): |
| s = BitStream(bin='0b1011') |
| self.assertEqual(s[0], True) |
| self.assertEqual(s[1], False) |
| self.assertEqual(s[2], True) |
| self.assertEqual(s[3], True) |
| self.assertRaises(IndexError, s.__getitem__, 4) |
| |
| def testGetItemWithNegativePosition(self): |
| s = BitStream(bin='1011') |
| self.assertEqual(s[-1], True) |
| self.assertEqual(s[-2], True) |
| self.assertEqual(s[-3], False) |
| self.assertEqual(s[-4], True) |
| self.assertRaises(IndexError, s.__getitem__, -5) |
| |
| def testSlicing(self): |
| s = ConstBitStream(hex='0123456789') |
| self.assertEqual(s[0:8].hex, '01') |
| self.assertFalse(s[0:0]) |
| self.assertFalse(s[23:20]) |
| self.assertEqual(s[8:12].bin, '0010') |
| self.assertEqual(s[32:80], '0x89') |
| |
| def testNegativeSlicing(self): |
| s = ConstBitStream(hex='012345678') |
| self.assertEqual(s[:-8].hex, '0123456') |
| self.assertEqual(s[-16:-8].hex, '56') |
| self.assertEqual(s[-24:].hex, '345678') |
| self.assertEqual(s[-1000:-24], '0x012') |
| |
| def testLen(self): |
| s = BitStream() |
| self.assertEqual(len(s), 0) |
| s.append(BitStream(bin='001')) |
| self.assertEqual(len(s), 3) |
| |
| def testJoin(self): |
| s1 = BitStream(bin='0') |
| s2 = BitStream(bin='1') |
| s3 = BitStream(bin='000') |
| s4 = BitStream(bin='111') |
| strings = [s1, s2, s1, s3, s4] |
| s = BitStream().join(strings) |
| self.assertEqual(s.bin, '010000111') |
| |
| def testJoin2(self): |
| s1 = BitStream(hex='00112233445566778899aabbccddeeff') |
| s2 = BitStream(bin='0b000011') |
| bsl = [s1[0:32], s1[4:12], s2, s2, s2, s2] |
| s = ConstBitStream().join(bsl) |
| self.assertEqual(s.hex, '00112233010c30c3') |
| |
| bsl = [BitStream(uint=j, length=12) for j in range(10) for i in range(10)] |
| s = BitStream().join(bsl) |
| self.assertEqual(s.length, 1200) |
| |
| |
| def testPos(self): |
| s = BitStream(bin='1') |
| self.assertEqual(s.bitpos, 0) |
| s.read(1) |
| self.assertEqual(s.bitpos, 1) |
| |
| def testWritingData(self): |
| strings = [BitStream(bin=x) for x in ['0', '001', '0011010010', '010010', '1011']] |
| s = BitStream().join(strings) |
| s2 = BitStream(bytes=s.bytes) |
| self.assertEqual(s2.bin, '000100110100100100101011') |
| s2.append(BitStream(bin='1')) |
| s3 = BitStream(bytes=s2.tobytes()) |
| self.assertEqual(s3.bin, '00010011010010010010101110000000') |
| |
| def testWritingDataWithOffsets(self): |
| s1 = BitStream(bytes=b'\x10') |
| s2 = BitStream(bytes=b'\x08\x00', length=8, offset=1) |
| s3 = BitStream(bytes=b'\x04\x00', length=8, offset=2) |
| self.assertTrue(s1 == s2) |
| self.assertTrue(s2 == s3) |
| self.assertTrue(s1.bytes == s2.bytes) |
| self.assertTrue(s2.bytes == s3.bytes) |
| |
| def testVariousThings1(self): |
| hexes = ['12345678', '87654321', 'ffffffffff', 'ed', '12ec'] |
| bins = ['001010', '1101011', '0010000100101110110110', '11', '011'] |
| bsl = [] |
| for (hex, bin) in list(zip(hexes, bins)) * 5: |
| bsl.append(BitStream(hex=hex)) |
| bsl.append(BitStream(bin=bin)) |
| s = BitStream().join(bsl) |
| for (hex, bin) in list(zip(hexes, bins)) * 5: |
| h = s.read(4 * len(hex)) |
| b = s.read(len(bin)) |
| self.assertEqual(h.hex, hex) |
| self.assertEqual(b.bin, bin) |
| |
| def testVariousThings2(self): |
| s1 = BitStream(hex="0x1f08")[:13] |
| self.assertEqual(s1.bin, '0001111100001') |
| s2 = BitStream(bin='0101') |
| self.assertEqual(s2.bin, '0101') |
| s1.append(s2) |
| self.assertEqual(s1.length, 17) |
| self.assertEqual(s1.bin, '00011111000010101') |
| s1 = s1[3:8] |
| self.assertEqual(s1.bin, '11111') |
| |
| def testVariousThings3(self): |
| s1 = BitStream(hex='0x012480ff')[2:27] |
| s2 = s1 + s1 |
| self.assertEqual(s2.length, 50) |
| s3 = s2[0:25] |
| s4 = s2[25:50] |
| self.assertEqual(s3.bin, s4.bin) |
| |
| def testPeekBit(self): |
| s = BitStream(bin='01') |
| self.assertEqual(s.peek(1), [0]) |
| self.assertEqual(s.peek(1), [0]) |
| self.assertEqual(s.read(1), [0]) |
| self.assertEqual(s.peek(1), [1]) |
| self.assertEqual(s.peek(1), [1]) |
| |
| s = BitStream(bytes=b'\x1f', offset=3) |
| self.assertEqual(s.len, 5) |
| self.assertEqual(s.peek(5).bin, '11111') |
| self.assertEqual(s.peek(5).bin, '11111') |
| s.pos += 1 |
| self.assertRaises(bitstring.ReadError, s.peek, 5) |
| |
| s = BitStream(hex='001122334455') |
| self.assertEqual(s.peek(8).hex, '00') |
| self.assertEqual(s.read(8).hex, '00') |
| s.pos += 33 |
| self.assertRaises(bitstring.ReadError, s.peek, 8) |
| |
| s = BitStream(hex='001122334455') |
| self.assertEqual(s.peek(8 * 2).hex, '0011') |
| self.assertEqual(s.read(8 * 3).hex, '001122') |
| self.assertEqual(s.peek(8 * 3).hex, '334455') |
| self.assertRaises(bitstring.ReadError, s.peek, 25) |
| |
| def testAdvanceBit(self): |
| s = BitStream(hex='0xff') |
| s.bitpos = 6 |
| s.pos += 1 |
| self.assertEqual(s.bitpos, 7) |
| s.bitpos += 1 |
| try: |
| s.pos += 1 |
| self.assertTrue(False) |
| except ValueError: |
| pass |
| |
| def testAdvanceByte(self): |
| s = BitStream(hex='0x010203') |
| s.bytepos += 1 |
| self.assertEqual(s.bytepos, 1) |
| s.bytepos += 1 |
| self.assertEqual(s.bytepos, 2) |
| s.bytepos += 1 |
| try: |
| s.bytepos += 1 |
| self.assertTrue(False) |
| except ValueError: |
| pass |
| |
| def testRetreatBit(self): |
| s = BitStream(hex='0xff') |
| try: |
| s.pos -= 1 |
| self.assertTrue(False) |
| except ValueError: |
| pass |
| s.pos = 5 |
| s.pos -= 1 |
| self.assertEqual(s.pos, 4) |
| |
| def testRetreatByte(self): |
| s = BitStream(hex='0x010203') |
| try: |
| s.bytepos -= 1 |
| self.assertTrue(False) |
| except ValueError: |
| pass |
| s.bytepos = 3 |
| s.bytepos -= 1 |
| self.assertEqual(s.bytepos, 2) |
| self.assertEqual(s.read(8).hex, '03') |
| |
| def testCreationByAuto(self): |
| s = BitStream('0xff') |
| self.assertEqual(s.hex, 'ff') |
| s = BitStream('0b00011') |
| self.assertEqual(s.bin, '00011') |
| self.assertRaises(bitstring.CreationError, BitStream, 'hello') |
| s1 = BitStream(bytes=b'\xf5', length=3, offset=5) |
| s2 = BitStream(s1, length=1, offset=1) |
| self.assertEqual(s2, '0b0') |
| s = BitStream(bytes=b'\xff', offset=2) |
| t = BitStream(s, offset=2) |
| self.assertEqual(t, '0b1111') |
| self.assertRaises(TypeError, BitStream, auto=1.2) |
| |
| def testCreationByAuto2(self): |
| s = BitStream('bin=001') |
| self.assertEqual(s.bin, '001') |
| s = BitStream('oct=0o007') |
| self.assertEqual(s.oct, '007') |
| s = BitStream('hex=123abc') |
| self.assertEqual(s, '0x123abc') |
| |
| s = BitStream('bin:2=01') |
| self.assertEqual(s, '0b01') |
| for s in ['bin:1=01', 'bits:4=0b1', 'oct:3=000', 'hex:4=0x1234']: |
| self.assertRaises(bitstring.CreationError, BitStream, s) |
| |
| def testInsertUsingAuto(self): |
| s = BitStream('0xff') |
| s.insert('0x00', 4) |
| self.assertEqual(s.hex, 'f00f') |
| self.assertRaises(ValueError, s.insert, 'ff') |
| |
| def testOverwriteUsingAuto(self): |
| s = BitStream('0x0110') |
| s.overwrite('0b1') |
| self.assertEqual(s.hex, '8110') |
| s.overwrite('') |
| self.assertEqual(s.hex, '8110') |
| self.assertRaises(ValueError, s.overwrite, '0bf') |
| |
| def testFindUsingAuto(self): |
| s = BitStream('0b000000010100011000') |
| self.assertTrue(s.find('0b101')) |
| self.assertEqual(s.pos, 7) |
| |
| def testFindbytealignedUsingAuto(self): |
| s = BitStream('0x00004700') |
| self.assertTrue(s.find('0b01000111', bytealigned=True)) |
| self.assertEqual(s.bytepos, 2) |
| |
| def testAppendUsingAuto(self): |
| s = BitStream('0b000') |
| s.append('0b111') |
| self.assertEqual(s.bin, '000111') |
| s.append('0b0') |
| self.assertEqual(s.bin, '0001110') |
| |
| def testSplitByteAlignedUsingAuto(self): |
| s = BitStream('0x000143563200015533000123') |
| sections = s.split('0x0001') |
| self.assertEqual(next(sections).hex, '') |
| self.assertEqual(next(sections).hex, '0001435632') |
| self.assertEqual(next(sections).hex, '00015533') |
| self.assertEqual(next(sections).hex, '000123') |
| self.assertRaises(StopIteration, next, sections) |
| |
| def testSplitByteAlignedWithSelf(self): |
| s = BitStream('0x1234') |
| sections = s.split(s) |
| self.assertEqual(next(sections).hex, '') |
| self.assertEqual(next(sections).hex, '1234') |
| self.assertRaises(StopIteration, next, sections) |
| |
| def testPrepend(self): |
| s = BitStream('0b000') |
| s.prepend('0b11') |
| self.assertEqual(s.bin, '11000') |
| s.prepend(s) |
| self.assertEqual(s.bin, '1100011000') |
| s.prepend('') |
| self.assertEqual(s.bin, '1100011000') |
| |
| def testNullSlice(self): |
| s = BitStream('0x111') |
| t = s[1:1] |
| self.assertEqual(t._datastore.bytelength, 0) |
| |
| def testMultipleAutos(self): |
| s = BitStream('0xa') |
| s.prepend('0xf') |
| s.append('0xb') |
| self.assertEqual(s, '0xfab') |
| s.prepend(s) |
| s.append('0x100') |
| s.overwrite('0x5', 4) |
| self.assertEqual(s, '0xf5bfab100') |
| |
| def testReverse(self): |
| s = BitStream('0b0011') |
| s.reverse() |
| self.assertEqual(s.bin, '1100') |
| s = BitStream('0b10') |
| s.reverse() |
| self.assertEqual(s.bin, '01') |
| s = BitStream() |
| s.reverse() |
| self.assertEqual(s.bin, '') |
| |
| def testInitWithConcatenatedStrings(self): |
| s = BitStream('0xff 0Xee 0xd 0xcc') |
| self.assertEqual(s.hex, 'ffeedcc') |
| s = BitStream('0b0 0B111 0b001') |
| self.assertEqual(s.bin, '0111001') |
| s += '0b1' + '0B1' |
| self.assertEqual(s.bin, '011100111') |
| s = BitStream(hex='ff0xee') |
| self.assertEqual(s.hex, 'ffee') |
| s = BitStream(bin='000b0b11') |
| self.assertEqual(s.bin, '0011') |
| s = BitStream(' 0o123 0O 7 0 o1') |
| self.assertEqual(s.oct, '12371') |
| s += ' 0 o 332' |
| self.assertEqual(s.oct, '12371332') |
| |
| def testEquals(self): |
| s1 = BitStream('0b01010101') |
| s2 = BitStream('0b01010101') |
| self.assertTrue(s1 == s2) |
| s3 = BitStream() |
| s4 = BitStream() |
| self.assertTrue(s3 == s4) |
| self.assertFalse(s3 != s4) |
| s5 = BitStream(bytes=b'\xff', offset=2, length=3) |
| s6 = BitStream('0b111') |
| self.assertTrue(s5 == s6) |
| class A(object): |
| pass |
| self.assertFalse(s5 == A()) |
| |
| def testLargeEquals(self): |
| s1 = BitStream(1000000) |
| s2 = BitStream(1000000) |
| s1.set(True, [-1, 55, 53214, 534211, 999999]) |
| s2.set(True, [-1, 55, 53214, 534211, 999999]) |
| self.assertEqual(s1, s2) |
| s1.set(True, 800000) |
| self.assertNotEqual(s1, s2) |
| |
| def testNotEquals(self): |
| s1 = BitStream('0b0') |
| s2 = BitStream('0b1') |
| self.assertTrue(s1 != s2) |
| self.assertFalse(s1 != BitStream('0b0')) |
| |
| def testEqualityWithAutoInitialised(self): |
| a = BitStream('0b00110111') |
| self.assertTrue(a == '0b00110111') |
| self.assertTrue(a == '0x37') |
| self.assertTrue('0b0011 0111' == a) |
| self.assertTrue('0x3 0x7' == a) |
| self.assertFalse(a == '0b11001000') |
| self.assertFalse('0x3737' == a) |
| |
| def testInvertSpecialMethod(self): |
| s = BitStream('0b00011001') |
| self.assertEqual((~s).bin, '11100110') |
| self.assertEqual((~BitStream('0b0')).bin, '1') |
| self.assertEqual((~BitStream('0b1')).bin, '0') |
| self.assertTrue(~~s == s) |
| |
| def testInvertBitPosition(self): |
| s = ConstBitStream('0xefef') |
| s.pos = 8 |
| t = ~s |
| self.assertEqual(s.pos, 8) |
| self.assertEqual(t.pos, 0) |
| |
| def testInvertSpecialMethodErrors(self): |
| s = BitStream() |
| self.assertRaises(bitstring.Error, s.__invert__) |
| |
| def testJoinWithAuto(self): |
| s = BitStream().join(['0xf', '0b00', BitStream(bin='11')]) |
| self.assertEqual(s, '0b11110011') |
| |
| def testAutoBitStringCopy(self): |
| s = BitStream('0xabcdef') |
| t = BitStream(s) |
| self.assertEqual(t.hex, 'abcdef') |
| del s[-8:] |
| self.assertEqual(t.hex, 'abcdef') |
| |
| class Multiplication(unittest.TestCase): |
| |
| def testMultiplication(self): |
| a = BitStream('0xff') |
| b = a * 8 |
| self.assertEqual(b, '0xffffffffffffffff') |
| b = 4 * a |
| self.assertEqual(b, '0xffffffff') |
| self.assertTrue(1 * a == a * 1 == a) |
| c = a * 0 |
| self.assertFalse(c) |
| a *= 3 |
| self.assertEqual(a, '0xffffff') |
| a *= 0 |
| self.assertFalse(a) |
| one = BitStream('0b1') |
| zero = BitStream('0b0') |
| mix = one * 2 + 3 * zero + 2 * one * 2 |
| self.assertEqual(mix, '0b110001111') |
| q = BitStream() |
| q *= 143 |
| self.assertFalse(q) |
| q += [True, True, False] |
| q.pos += 2 |
| q *= 0 |
| self.assertFalse(q) |
| self.assertEqual(q.bitpos, 0) |
| |
| def testMultiplicationWithFiles(self): |
| a = BitStream(filename='test.m1v') |
| b = a.len |
| a *= 3 |
| self.assertEqual(a.len, 3 * b) |
| |
| def testMultiplicationErrors(self): |
| a = BitStream('0b1') |
| b = BitStream('0b0') |
| self.assertRaises(ValueError, a.__mul__, -1) |
| self.assertRaises(ValueError, a.__imul__, -1) |
| self.assertRaises(ValueError, a.__rmul__, -1) |
| self.assertRaises(TypeError, a.__mul__, 1.2) |
| self.assertRaises(TypeError, a.__rmul__, b) |
| self.assertRaises(TypeError, a.__imul__, b) |
| |
| def testFileAndMemEquivalence(self): |
| a = ConstBitStream(filename='smalltestfile') |
| b = BitStream(filename='smalltestfile') |
| self.assertTrue(isinstance(a._datastore._rawarray, bitstring.MmapByteArray)) |
| self.assertTrue(isinstance(b._datastore._rawarray, bytearray)) |
| self.assertEqual(a._datastore.getbyte(0), b._datastore.getbyte(0)) |
| self.assertEqual(a._datastore.getbyteslice(1, 5), bytearray(b._datastore.getbyteslice(1, 5))) |
| |
| |
| class BitWise(unittest.TestCase): |
| |
| def testBitwiseAnd(self): |
| a = BitStream('0b01101') |
| b = BitStream('0b00110') |
| self.assertEqual((a & b).bin, '00100') |
| self.assertEqual((a & '0b11111'), a) |
| self.assertRaises(ValueError, a.__and__, '0b1') |
| self.assertRaises(ValueError, b.__and__, '0b110111111') |
| c = BitStream('0b0011011') |
| c.pos = 4 |
| d = c & '0b1111000' |
| self.assertEqual(d.pos, 0) |
| self.assertEqual(d.bin, '0011000') |
| d = '0b1111000' & c |
| self.assertEqual(d.bin, '0011000') |
| |
| def testBitwiseOr(self): |
| a = BitStream('0b111001001') |
| b = BitStream('0b011100011') |
| self.assertEqual((a | b).bin, '111101011') |
| self.assertEqual((a | '0b000000000'), a) |
| self.assertRaises(ValueError, a.__or__, '0b0000') |
| self.assertRaises(ValueError, b.__or__, a + '0b1') |
| a = '0xff00' | BitStream('0x00f0') |
| self.assertEqual(a.hex, 'fff0') |
| |
| def testBitwiseXor(self): |
| a = BitStream('0b111001001') |
| b = BitStream('0b011100011') |
| self.assertEqual((a ^ b).bin, '100101010') |
| self.assertEqual((a ^ '0b111100000').bin, '000101001') |
| self.assertRaises(ValueError, a.__xor__, '0b0000') |
| self.assertRaises(ValueError, b.__xor__, a + '0b1') |
| a = '0o707' ^ BitStream('0o777') |
| self.assertEqual(a.oct, '070') |
| |
| class Split(unittest.TestCase): |
| |
| def testSplit(self): |
| a = BitStream('0b0 010100111 010100 0101 010') |
| a.pos = 20 |
| subs = [i.bin for i in a.split('0b010')] |
| self.assertEqual(subs, ['0', '010100111', '010100', '0101', '010']) |
| self.assertEqual(a.pos, 20) |
| |
| def testSplitCornerCases(self): |
| a = BitStream('0b000000') |
| bsl = a.split('0b1', False) |
| self.assertEqual(next(bsl), a) |
| self.assertRaises(StopIteration, next, bsl) |
| b = BitStream() |
| bsl = b.split('0b001', False) |
| self.assertFalse(next(bsl)) |
| self.assertRaises(StopIteration, next, bsl) |
| |
| def testSplitErrors(self): |
| a = BitStream('0b0') |
| b = a.split('', False) |
| self.assertRaises(ValueError, next, b) |
| |
| def testSliceWithOffset(self): |
| a = BitStream(bytes=b'\x00\xff\x00', offset=7) |
| b = a[7:12] |
| self.assertEqual(b.bin, '11000') |
| |
| def testSplitWithMaxsplit(self): |
| a = BitStream('0xaabbccbbccddbbccddee') |
| self.assertEqual(len(list(a.split('0xbb', bytealigned=True))), 4) |
| bsl = list(a.split('0xbb', count=1, bytealigned=True)) |
| self.assertEqual((len(bsl), bsl[0]), (1, '0xaa')) |
| bsl = list(a.split('0xbb', count=2, bytealigned=True)) |
| self.assertEqual(len(bsl), 2) |
| self.assertEqual(bsl[0], '0xaa') |
| self.assertEqual(bsl[1], '0xbbcc') |
| |
| def testSplitMore(self): |
| s = BitStream('0b1100011001110110') |
| for i in range(10): |
| a = list(s.split('0b11', False, count=i)) |
| b = list(s.split('0b11', False))[:i] |
| self.assertEqual(a, b) |
| b = s.split('0b11', count=-1) |
| self.assertRaises(ValueError, next, b) |
| |
| def testSplitStartbit(self): |
| a = BitStream('0b0010101001000000001111') |
| bsl = a.split('0b001', bytealigned=False, start=1) |
| self.assertEqual([x.bin for x in bsl], ['010101', '001000000', '001111']) |
| b = a.split('0b001', start=-100) |
| self.assertRaises(ValueError, next, b) |
| b = a.split('0b001', start=23) |
| self.assertRaises(ValueError, next, b) |
| b = a.split('0b1', start=10, end=9) |
| self.assertRaises(ValueError, next, b) |
| |
| def testSplitStartbitByteAligned(self): |
| a = BitStream('0x00ffffee') |
| bsl = list(a.split('0b111', start=9, bytealigned=True)) |
| self.assertEqual([x.bin for x in bsl], ['1111111', '11111111', '11101110']) |
| |
| def testSplitEndbit(self): |
| a = BitStream('0b000010001001011') |
| bsl = list(a.split('0b1', bytealigned=False, end=14)) |
| self.assertEqual([x.bin for x in bsl], ['0000', '1000', '100', '10', '1']) |
| self.assertEqual(list(a[4:12].split('0b0', False)), list(a.split('0b0', start=4, end=12))) |
| # Shouldn't raise ValueError |
| bsl = list(a.split('0xffee', end=15)) |
| # Whereas this one will when we call next() |
| bsl = a.split('0xffee', end=16) |
| self.assertRaises(ValueError, next, bsl) |
| |
| def testSplitEndbitByteAligned(self): |
| a = BitStream('0xff00ff')[:22] |
| bsl = list(a.split('0b 0000 0000 111', end=19)) |
| self.assertEqual([x.bin for x in bsl], ['11111111', '00000000111']) |
| bsl = list(a.split('0b 0000 0000 111', end=18)) |
| self.assertEqual([x.bin for x in bsl], ['111111110000000011']) |
| |
| def testSplitMaxSplit(self): |
| a = BitStream('0b1' * 20) |
| for i in range(10): |
| bsl = list(a.split('0b1', count=i)) |
| self.assertEqual(len(bsl), i) |
| |
| ####################### |
| |
| def testPositionInSlice(self): |
| a = BitStream('0x00ffff00') |
| a.bytepos = 2 |
| b = a[8:24] |
| self.assertEqual(b.bytepos, 0) |
| |
| def testFindByteAlignedWithBits(self): |
| a = BitStream('0x00112233445566778899') |
| a.find('0b0001', bytealigned=True) |
| self.assertEqual(a.bitpos, 8) |
| |
| def testFindStartbitNotByteAligned(self): |
| a = BitStream('0b0010000100') |
| found = a.find('0b1', start=4) |
| self.assertEqual((found, a.bitpos), ((7,), 7)) |
| found = a.find('0b1', start=2) |
| self.assertEqual((found, a.bitpos), ((2,), 2)) |
| found = a.find('0b1', bytealigned=False, start=8) |
| self.assertEqual((found, a.bitpos), ((), 2)) |
| |
| def testFindEndbitNotByteAligned(self): |
| a = BitStream('0b0010010000') |
| found = a.find('0b1', bytealigned=False, end=2) |
| self.assertEqual((found, a.bitpos), ((), 0)) |
| found = a.find('0b1', end=3) |
| self.assertEqual((found, a.bitpos), ((2,), 2)) |
| found = a.find('0b1', bytealigned=False, start=3, end=5) |
| self.assertEqual((found, a.bitpos), ((), 2)) |
| found = a.find('0b1', start=3, end=6) |
| self.assertEqual((found[0], a.bitpos), (5, 5)) |
| |
| def testFindStartbitByteAligned(self): |
| a = BitStream('0xff001122ff0011ff') |
| a.pos = 40 |
| found = a.find('0x22', start=23, bytealigned=True) |
| self.assertEqual((found, a.bytepos), ((24,), 3)) |
| a.bytepos = 4 |
| found = a.find('0x22', start=24, bytealigned=True) |
| self.assertEqual((found, a.bytepos), ((24,), 3)) |
| found = a.find('0x22', start=25, bytealigned=True) |
| self.assertEqual((found, a.pos), ((), 24)) |
| found = a.find('0b111', start=40, bytealigned=True) |
| self.assertEqual((found, a.pos), ((56,), 56)) |
| |
| def testFindEndbitByteAligned(self): |
| a = BitStream('0xff001122ff0011ff') |
| found = a.find('0x22', end=31, bytealigned=True) |
| self.assertFalse(found) |
| self.assertEqual(a.pos, 0) |
| found = a.find('0x22', end=32, bytealigned=True) |
| self.assertTrue(found) |
| self.assertEqual(a.pos, 24) |
| self.assertEqual(found[0], 24) |
| |
| def testFindStartEndbitErrors(self): |
| a = BitStream('0b00100') |
| self.assertRaises(ValueError, a.find, '0b1', bytealigned=False, start=-100) |
| self.assertRaises(ValueError, a.find, '0b1', end=6) |
| self.assertRaises(ValueError, a.find, '0b1', start=4, end=3) |
| b = BitStream('0x0011223344') |
| self.assertRaises(ValueError, a.find, '0x22', bytealigned=True, start=-100) |
| self.assertRaises(ValueError, a.find, '0x22', end=41, bytealigned=True) |
| |
| def testPrependAndAppendAgain(self): |
| c = BitStream('0x1122334455667788') |
| c.bitpos = 40 |
| c.prepend('0b1') |
| self.assertEqual(c.bitpos, 41) |
| c = BitStream() |
| c.prepend('0x1234') |
| self.assertEqual(c.bytepos, 2) |
| c = BitStream() |
| c.append('0x1234') |
| self.assertEqual(c.bytepos, 0) |
| s = BitStream(bytes=b'\xff\xff', offset=2) |
| self.assertEqual(s.length, 14) |
| t = BitStream(bytes=b'\x80', offset=1, length=2) |
| s.prepend(t) |
| self.assertEqual(s, '0x3fff') |
| |
| def testFindAll(self): |
| a = BitStream('0b11111') |
| p = a.findall('0b1') |
| self.assertEqual(list(p), [0, 1, 2, 3, 4]) |
| p = a.findall('0b11') |
| self.assertEqual(list(p), [0, 1, 2, 3]) |
| p = a.findall('0b10') |
| self.assertEqual(list(p), []) |
| a = BitStream('0x4733eeff66554747335832434547') |
| p = a.findall('0x47', bytealigned=True) |
| self.assertEqual(list(p), [0, 6 * 8, 7 * 8, 13 * 8]) |
| p = a.findall('0x4733', bytealigned=True) |
| self.assertEqual(list(p), [0, 7 * 8]) |
| a = BitStream('0b1001001001001001001') |
| p = a.findall('0b1001', bytealigned=False) |
| self.assertEqual(list(p), [0, 3, 6, 9, 12, 15]) |
| self.assertEqual(a.pos, 15) |
| |
| def testFindAllGenerator(self): |
| a = BitStream('0xff1234512345ff1234ff12ff') |
| p = a.findall('0xff', bytealigned=True) |
| self.assertEqual(next(p), 0) |
| self.assertEqual(next(p), 6 * 8) |
| self.assertEqual(next(p), 9 * 8) |
| self.assertEqual(next(p), 11 * 8) |
| self.assertRaises(StopIteration, next, p) |
| |
| def testFindAllCount(self): |
| s = BitStream('0b1') * 100 |
| for i in [0, 1, 23]: |
| self.assertEqual(len(list(s.findall('0b1', count=i))), i) |
| b = s.findall('0b1', bytealigned=True, count=-1) |
| self.assertRaises(ValueError, next, b) |
| |
| def testContains(self): |
| a = BitStream('0b1') + '0x0001dead0001' |
| self.assertTrue('0xdead' in a) |
| self.assertEqual(a.pos, 0) |
| self.assertFalse('0xfeed' in a) |
| |
| def testRepr(self): |
| max = bitstring.MAX_CHARS |
| bls = ['', '0b1', '0o5', '0x43412424f41', '0b00101001010101'] |
| for bs in bls: |
| a = BitStream(bs) |
| b = eval(a.__repr__()) |
| self.assertTrue(a == b) |
| for f in [ConstBitStream(filename='test.m1v'), |
| ConstBitStream(filename='test.m1v', length=17), |
| ConstBitStream(filename='test.m1v', length=23, offset=23102)]: |
| f2 = eval(f.__repr__()) |
| self.assertEqual(f._datastore._rawarray.source.name, f2._datastore._rawarray.source.name) |
| self.assertTrue(f2.tobytes() == f.tobytes()) |
| a = BitStream('0b1') |
| self.assertEqual(repr(a), "BitStream('0b1')") |
| a += '0b11' |
| self.assertEqual(repr(a), "BitStream('0b111')") |
| a += '0b1' |
| self.assertEqual(repr(a), "BitStream('0xf')") |
| a *= max |
| self.assertEqual(repr(a), "BitStream('0x" + "f" * max + "')") |
| a += '0xf' |
| self.assertEqual(repr(a), "BitStream('0x" + "f" * max + "...') # length=%d" % (max * 4 + 4)) |
| |
| def testPrint(self): |
| s = BitStream(hex='0x00') |
| self.assertEqual('0x' + s.hex, s.__str__()) |
| s = BitStream(filename='test.m1v') |
| self.assertEqual('0x' + s[0:bitstring.MAX_CHARS * 4].hex + '...', s.__str__()) |
| self.assertEqual(BitStream().__str__(), '') |
| s = BitStream('0b11010') |
| self.assertEqual('0b' + s.bin, s.__str__()) |
| s = BitStream('0x12345678901234567890,0b1') |
| self.assertEqual('0x12345678901234567890, 0b1', s.__str__()) |
| |
| def testIter(self): |
| a = BitStream('0b001010') |
| b = BitStream() |
| for bit in a: |
| b.append(ConstBitStream(bool=bit)) |
| self.assertEqual(a, b) |
| |
| def testDelitem(self): |
| a = BitStream('0xffee') |
| del a[0:8] |
| self.assertEqual(a.hex, 'ee') |
| del a[0:8] |
| self.assertFalse(a) |
| del a[10:12] |
| self.assertFalse(a) |
| |
| def testNonZeroBitsAtStart(self): |
| a = BitStream(bytes=b'\xff', offset=2) |
| b = BitStream('0b00') |
| b += a |
| self.assertTrue(b == '0b0011 1111') |
| #self.assertEqual(a._datastore.rawbytes, b'\xff') |
| self.assertEqual(a.tobytes(), b'\xfc') |
| |
| def testNonZeroBitsAtEnd(self): |
| a = BitStream(bytes=b'\xff', length=5) |
| #self.assertEqual(a._datastore.rawbytes, b'\xff') |
| b = BitStream('0b00') |
| a += b |
| self.assertTrue(a == '0b1111100') |
| self.assertEqual(a.tobytes(), b'\xf8') |
| self.assertRaises(ValueError, a._getbytes) |
| |
| def testNewOffsetErrors(self): |
| self.assertRaises(bitstring.CreationError, BitStream, hex='ff', offset=-1) |
| self.assertRaises(bitstring.CreationError, BitStream, '0xffffffff', offset=33) |
| |
| def testSliceStep(self): |
| a = BitStream('0x3') |
| b = a[::1] |
| self.assertEqual(a, b) |
| self.assertEqual(a[2:4:1], '0b11') |
| self.assertEqual(a[0:2:1], '0b00') |
| self.assertEqual(a[:3], '0o1') |
| |
| a = BitStream('0x0011223344556677') |
| self.assertEqual(a[-8:], '0x77') |
| self.assertEqual(a[:-24], '0x0011223344') |
| self.assertEqual(a[-1000:-24], '0x0011223344') |
| |
| def testInterestingSliceStep(self): |
| a = BitStream('0b0011000111') |
| self.assertEqual(a[7:3:-1], '0b1000') |
| self.assertEqual(a[9:2:-1], '0b1110001') |
| self.assertEqual(a[8:2:-2], '0b100') |
| self.assertEqual(a[100:-20:-3], '0b1010') |
| self.assertEqual(a[100:-20:-1], '0b1110001100') |
| self.assertEqual(a[10:2:-1], '0b1110001') |
| self.assertEqual(a[100:2:-1], '0b1110001') |
| |
| def testInsertionOrderAndBitpos(self): |
| b = BitStream() |
| b[0:0] = '0b0' |
| b[0:0] = '0b1' |
| self.assertEqual(b, '0b10') |
| self.assertEqual(b.bitpos, 1) |
| a = BitStream() |
| a.insert('0b0') |
| a.insert('0b1') |
| self.assertEqual(a, '0b01') |
| self.assertEqual(a.bitpos, 2) |
| |
| def testOverwriteOrderAndBitpos(self): |
| a = BitStream('0xff') |
| a.overwrite('0xa') |
| self.assertEqual(a, '0xaf') |
| self.assertEqual(a.bitpos, 4) |
| a.overwrite('0xb') |
| self.assertEqual(a, '0xab') |
| self.assertEqual(a.bitpos, 8) |
| self.assertRaises(ValueError, a.overwrite, '0b1') |
| a.overwrite('0xa', 4) |
| self.assertEqual(a, '0xaa') |
| self.assertEqual(a.bitpos, 8) |
| a.overwrite(a, 0) |
| self.assertEqual(a, '0xaa') |
| |
| def testInitSliceWithInt(self): |
| a = BitStream(length=8) |
| a[:] = 100 |
| self.assertEqual(a.uint, 100) |
| a[0] = 1 |
| self.assertEqual(a.bin, '11100100') |
| a[1] = 0 |
| self.assertEqual(a.bin, '10100100') |
| a[-1] = -1 |
| self.assertEqual(a.bin, '10100101') |
| a[-3:] = -2 |
| self.assertEqual(a.bin, '10100110') |
| |
| def testInitSliceWithIntErrors(self): |
| a = BitStream('0b0000') |
| self.assertRaises(ValueError, a.__setitem__, slice(0, 4), 16) |
| self.assertRaises(ValueError, a.__setitem__, slice(0, 4), -9) |
| self.assertRaises(ValueError, a.__setitem__, 0, 2) |
| self.assertRaises(ValueError, a.__setitem__, 0, -2) |
| |
| def testReverseWithSlice(self): |
| a = BitStream('0x0012ff') |
| a.reverse() |
| self.assertEqual(a, '0xff4800') |
| a.reverse(8, 16) |
| self.assertEqual(a, '0xff1200') |
| b = a[8:16] |
| b.reverse() |
| a[8:16] = b |
| self.assertEqual(a, '0xff4800') |
| |
| def testReverseWithSliceErrors(self): |
| a = BitStream('0x123') |
| self.assertRaises(ValueError, a.reverse, -1, 4) |
| self.assertRaises(ValueError, a.reverse, 10, 9) |
| self.assertRaises(ValueError, a.reverse, 1, 10000) |
| |
| def testInitialiseFromList(self): |
| a = BitStream([]) |
| self.assertFalse(a) |
| a = BitStream([True, False, [], [0], 'hello']) |
| self.assertEqual(a, '0b10011') |
| a += [] |
| self.assertEqual(a, '0b10011') |
| a += [True, False, True] |
| self.assertEqual(a, '0b10011101') |
| a.find([12, 23]) |
| self.assertEqual(a.pos, 3) |
| self.assertEqual([1, 0, False, True], BitStream('0b1001')) |
| a = [True] + BitStream('0b1') |
| self.assertEqual(a, '0b11') |
| |
| def testInitialiseFromTuple(self): |
| a = BitStream(()) |
| self.assertFalse(a) |
| a = BitStream((0, 1, '0', '1')) |
| self.assertEqual('0b0111', a) |
| a.replace((True, True), []) |
| self.assertEqual(a, (False, True)) |
| |
| def testCut(self): |
| a = BitStream('0x00112233445') |
| b = list(a.cut(8)) |
| self.assertEqual(b, ['0x00', '0x11', '0x22', '0x33', '0x44']) |
| b = list(a.cut(4, 8, 16)) |
| self.assertEqual(b, ['0x1', '0x1']) |
| b = list(a.cut(4, 0, 44, 4)) |
| self.assertEqual(b, ['0x0', '0x0', '0x1', '0x1']) |
| a = BitStream() |
| b = list(a.cut(10)) |
| self.assertTrue(not b) |
| |
| def testCutErrors(self): |
| a = BitStream('0b1') |
| b = a.cut(1, 1, 2) |
| self.assertRaises(ValueError, next, b) |
| b = a.cut(1, -2, 1) |
| self.assertRaises(ValueError, next, b) |
| b = a.cut(0) |
| self.assertRaises(ValueError, next, b) |
| b = a.cut(1, count=-1) |
| self.assertRaises(ValueError, next, b) |
| |
| def testCutProblem(self): |
| s = BitStream('0x1234') |
| for n in list(s.cut(4)): |
| s.prepend(n) |
| self.assertEqual(s, '0x43211234') |
| |
| def testJoinFunctions(self): |
| a = BitStream().join(['0xa', '0xb', '0b1111']) |
| self.assertEqual(a, '0xabf') |
| a = BitStream('0b1').join(['0b0' for i in range(10)]) |
| self.assertEqual(a, '0b0101010101010101010') |
| a = BitStream('0xff').join([]) |
| self.assertFalse(a) |
| |
| def testAddingBitpos(self): |
| a = BitStream('0xff') |
| b = BitStream('0x00') |
| a.bitpos = b.bitpos = 8 |
| c = a + b |
| self.assertEqual(c.bitpos, 0) |
| |
| def testIntelligentRead1(self): |
| a = BitStream(uint=123, length=23) |
| u = a.read('uint:23') |
| self.assertEqual(u, 123) |
| self.assertEqual(a.pos, a.len) |
| b = BitStream(int=-12, length=44) |
| i = b.read('int:44') |
| self.assertEqual(i, -12) |
| self.assertEqual(b.pos, b.len) |
| u2, i2 = (a + b).readlist('uint:23, int:44') |
| self.assertEqual((u2, i2), (123, -12)) |
| |
| def testIntelligentRead2(self): |
| a = BitStream(ue=822) |
| u = a.read('ue') |
| self.assertEqual(u, 822) |
| self.assertEqual(a.pos, a.len) |
| b = BitStream(se=-1001) |
| s = b.read('se') |
| self.assertEqual(s, -1001) |
| self.assertEqual(b.pos, b.len) |
| s, u1, u2 = (b + 2 * a).readlist('se, ue, ue') |
| self.assertEqual((s, u1, u2), (-1001, 822, 822)) |
| |
| def testIntelligentRead3(self): |
| a = BitStream('0x123') + '0b11101' |
| h = a.read('hex:12') |
| self.assertEqual(h, '123') |
| b = a.read('bin: 5') |
| self.assertEqual(b, '11101') |
| c = '0b' + b + a |
| b, h = c.readlist('bin:5, hex:12') |
| self.assertEqual((b, h), ('11101', '123')) |
| |
| def testIntelligentRead4(self): |
| a = BitStream('0o007') |
| o = a.read('oct:9') |
| self.assertEqual(o, '007') |
| self.assertEqual(a.pos, a.len) |
| |
| def testIntelligentRead5(self): |
| a = BitStream('0x00112233') |
| c0, c1, c2 = a.readlist('bits:8, bits:8, bits:16') |
| self.assertEqual((c0, c1, c2), (BitStream('0x00'), BitStream('0x11'), BitStream('0x2233'))) |
| a.pos = 0 |
| c = a.read('bits:16') |
| self.assertEqual(c, BitStream('0x0011')) |
| |
| def testIntelligentRead6(self): |
| a = BitStream('0b000111000') |
| b1, b2, b3 = a.readlist('bin :3, int: 3, int:3') |
| self.assertEqual(b1, '000') |
| self.assertEqual(b2, -1) |
| self.assertEqual(b3, 0) |
| |
| def testIntelligentRead7(self): |
| a = BitStream('0x1234') |
| a1, a2, a3, a4 = a.readlist('bin:0, oct:0, hex:0, bits:0') |
| self.assertTrue(a1 == a2 == a3 == '') |
| self.assertFalse(a4) |
| self.assertRaises(ValueError, a.read, 'int:0') |
| self.assertRaises(ValueError, a.read, 'uint:0') |
| self.assertEqual(a.pos, 0) |
| |
| def testIntelligentRead8(self): |
| a = BitStream('0x123456') |
| for t in ['hex:1', 'oct:1', 'hex4', '-5', 'fred', 'bin:-2', |
| 'uint:p', 'uint:-2', 'int:u', 'int:-3', 'ses', 'uee', '-14']: |
| self.assertRaises(ValueError, a.read, t) |
| |
| def testIntelligentRead9(self): |
| a = BitStream('0xff') |
| self.assertEqual(a.read('intle'), -1) |
| |
| def testFillerReads1(self): |
| s = BitStream('0x012345') |
| t = s.read('bits') |
| self.assertEqual(s, t) |
| s.pos = 0 |
| a, b = s.readlist('hex:8, hex') |
| self.assertEqual(a, '01') |
| self.assertEqual(b, '2345') |
| self.assertTrue(isinstance(b, str)) |
| s.bytepos = 0 |
| a, b = s.readlist('bin, hex:20') |
| self.assertEqual(a, '0000') |
| self.assertEqual(b, '12345') |
| self.assertTrue(isinstance(a, str)) |
| |
| def testFillerReads2(self): |
| s = BitStream('0xabcdef') |
| self.assertRaises(bitstring.Error, s.readlist, 'bits, se') |
| self.assertRaises(bitstring.Error, s.readlist, 'hex:4, bits, ue, bin:4') |
| s.pos = 0 |
| self.assertRaises(bitstring.Error, s.readlist, 'bin, bin') |
| |
| def testIntelligentPeek(self): |
| a = BitStream('0b01, 0x43, 0o4, uint:23=2, se=5, ue=3') |
| b, c, e = a.peeklist('bin:2, hex:8, oct:3') |
| self.assertEqual((b, c, e), ('01', '43', '4')) |
| self.assertEqual(a.pos, 0) |
| a.pos = 13 |
| f, g, h = a.peeklist('uint:23, se, ue') |
| self.assertEqual((f, g, h), (2, 5, 3)) |
| self.assertEqual(a.pos, 13) |
| |
| def testReadMultipleBits(self): |
| s = BitStream('0x123456789abcdef') |
| a, b = s.readlist([4, 4]) |
| self.assertEqual(a, '0x1') |
| self.assertEqual(b, '0x2') |
| c, d, e = s.readlist([8, 16, 8]) |
| self.assertEqual(c, '0x34') |
| self.assertEqual(d, '0x5678') |
| self.assertEqual(e, '0x9a') |
| |
| def testPeekMultipleBits(self): |
| s = BitStream('0b1101, 0o721, 0x2234567') |
| a, b, c, d = s.peeklist([2, 1, 1, 9]) |
| self.assertEqual(a, '0b11') |
| self.assertEqual(bool(b), False) |
| self.assertEqual(bool(c), True) |
| self.assertEqual(d, '0o721') |
| self.assertEqual(s.pos, 0) |
| a, b = s.peeklist([4, 9]) |
| self.assertEqual(a, '0b1101') |
| self.assertEqual(b, '0o721') |
| s.pos = 13 |
| a, b = s.peeklist([16, 8]) |
| self.assertEqual(a, '0x2234') |
| self.assertEqual(b, '0x56') |
| self.assertEqual(s.pos, 13) |
| |
| def testDifficultPrepends(self): |
| a = BitStream('0b1101011') |
| b = BitStream() |
| for i in range(10): |
| b.prepend(a) |
| self.assertEqual(b, a * 10) |
| |
| def testPackingWrongNumberOfThings(self): |
| self.assertRaises(bitstring.CreationError, pack, 'bin:1') |
| self.assertRaises(bitstring.CreationError, pack, '', 100) |
| |
| def testPackWithVariousKeys(self): |
| a = pack('uint10', uint10='0b1') |
| self.assertEqual(a, '0b1') |
| b = pack('0b110', **{'0b110': '0xfff'}) |
| self.assertEqual(b, '0xfff') |
| |
| def testPackWithVariableLength(self): |
| for i in range(1, 11): |
| a = pack('uint:n', 0, n=i) |
| self.assertEqual(a.bin, '0' * i) |
| |
| def testToBytes(self): |
| a = BitStream(bytes=b'\xab\x00') |
| b = a.tobytes() |
| self.assertEqual(a.bytes, b) |
| for i in range(7): |
| del a[-1:] |
| self.assertEqual(a.tobytes(), b'\xab\x00') |
| del a[-1:] |
| self.assertEqual(a.tobytes(), b'\xab') |
| |
| def testToFile(self): |
| a = BitStream('0x0000ff')[:17] |
| f = open('temp_bitstring_unit_testing_file', 'wb') |
| a.tofile(f) |
| f.close() |
| b = BitStream(filename='temp_bitstring_unit_testing_file') |
| self.assertEqual(b, '0x000080') |
| |
| a = BitStream('0x911111') |
| del a[:1] |
| self.assertEqual(a + '0b0', '0x222222') |
| f = open('temp_bitstring_unit_testing_file', 'wb') |
| a.tofile(f) |
| f.close() |
| b = BitStream(filename='temp_bitstring_unit_testing_file') |
| self.assertEqual(b, '0x222222') |
| os.remove('temp_bitstring_unit_testing_file') |
| |
| #def testToFileWithLargerFile(self): |
| # a = BitStream(length=16000000) |
| # a[1] = '0b1' |
| # a[-2] = '0b1' |
| # f = open('temp_bitstring_unit_testing_file' ,'wb') |
| # a.tofile(f) |
| # f.close() |
| # b = BitStream(filename='temp_bitstring_unit_testing_file') |
| # self.assertEqual(b.len, 16000000) |
| # self.assertEqual(b[1], True) |
| # |
| # f = open('temp_bitstring_unit_testing_file' ,'wb') |
| # a[1:].tofile(f) |
| # f.close() |
| # b = BitStream(filename='temp_bitstring_unit_testing_file') |
| # self.assertEqual(b.len, 16000000) |
| # self.assertEqual(b[0], True) |
| # os.remove('temp_bitstring_unit_testing_file') |
| |
| def testTokenParser(self): |
| tp = bitstring.tokenparser |
| self.assertEqual(tp('hex'), (True, [('hex', None, None)])) |
| self.assertEqual(tp('hex=14'), (True, [('hex', None, '14')])) |
| self.assertEqual(tp('se'), (False, [('se', None, None)])) |
| self.assertEqual(tp('ue=12'), (False, [('ue', None, '12')])) |
| self.assertEqual(tp('0xef'), (False, [('0x', None, 'ef')])) |
| self.assertEqual(tp('uint:12'), (False, [('uint', 12, None)])) |
| self.assertEqual(tp('int:30=-1'), (False, [('int', 30, '-1')])) |
| self.assertEqual(tp('bits:10'), (False, [('bits', 10, None)])) |
| self.assertEqual(tp('bits:10'), (False, [('bits', 10, None)])) |
| self.assertEqual(tp('123'), (False, [('uint', 123, None)])) |
| self.assertEqual(tp('123'), (False, [('uint', 123, None)])) |
| self.assertRaises(ValueError, tp, 'hex12') |
| self.assertEqual(tp('hex12', ('hex12',)), (False, [('hex12', None, None)])) |
| self.assertEqual(tp('2*bits:6'), (False, [('bits', 6, None), ('bits', 6, None)])) |
| |
| def testAutoFromFileObject(self): |
| with open('test.m1v', 'rb') as f: |
| s = ConstBitStream(f, offset=32, length=12) |
| self.assertEqual(s.uint, 352) |
| t = ConstBitStream('0xf') + f |
| self.assertTrue(t.startswith('0xf000001b3160')) |
| s2 = ConstBitStream(f) |
| t2 = BitStream('0xc') |
| t2.prepend(s2) |
| self.assertTrue(t2.startswith('0x000001b3')) |
| self.assertTrue(t2.endswith('0xc')) |
| with open('test.m1v', 'rb') as b: |
| u = BitStream(bytes=b.read()) |
| # TODO: u == s2 is much slower than u.bytes == s2.bytes |
| self.assertEqual(u.bytes, s2.bytes) |
| |
| def testFileBasedCopy(self): |
| with open('smalltestfile', 'rb') as f: |
| s = BitStream(f) |
| t = BitStream(s) |
| s.prepend('0b1') |
| self.assertEqual(s[1:], t) |
| s = BitStream(f) |
| t = copy.copy(s) |
| t.append('0b1') |
| self.assertEqual(s, t[:-1]) |
| |
| def testBigEndianSynonyms(self): |
| s = BitStream('0x12318276ef') |
| self.assertEqual(s.int, s.intbe) |
| self.assertEqual(s.uint, s.uintbe) |
| s = BitStream(intbe=-100, length=16) |
| self.assertEqual(s, 'int:16=-100') |
| s = BitStream(uintbe=13, length=24) |
| self.assertEqual(s, 'int:24=13') |
| s = BitStream('uintbe:32=1000') |
| self.assertEqual(s, 'uint:32=1000') |
| s = BitStream('intbe:8=2') |
| self.assertEqual(s, 'int:8=2') |
| self.assertEqual(s.read('intbe'), 2) |
| s.pos = 0 |
| self.assertEqual(s.read('uintbe'), 2) |
| |
| def testBigEndianSynonymErrors(self): |
| self.assertRaises(bitstring.CreationError, BitStream, uintbe=100, length=15) |
| self.assertRaises(bitstring.CreationError, BitStream, intbe=100, length=15) |
| self.assertRaises(bitstring.CreationError, BitStream, 'uintbe:17=100') |
| self.assertRaises(bitstring.CreationError, BitStream, 'intbe:7=2') |
| s = BitStream('0b1') |
| self.assertRaises(bitstring.InterpretError, s._getintbe) |
| self.assertRaises(bitstring.InterpretError, s._getuintbe) |
| self.assertRaises(ValueError, s.read, 'uintbe') |
| self.assertRaises(ValueError, s.read, 'intbe') |
| |
| def testLittleEndianUint(self): |
| s = BitStream(uint=100, length=16) |
| self.assertEqual(s.uintle, 25600) |
| s = BitStream(uintle=100, length=16) |
| self.assertEqual(s.uint, 25600) |
| self.assertEqual(s.uintle, 100) |
| s.uintle += 5 |
| self.assertEqual(s.uintle, 105) |
| s = BitStream('uintle:32=999') |
| self.assertEqual(s.uintle, 999) |
| s.byteswap() |
| self.assertEqual(s.uint, 999) |
| s = pack('uintle:24', 1001) |
| self.assertEqual(s.uintle, 1001) |
| self.assertEqual(s.length, 24) |
| self.assertEqual(s.read('uintle'), 1001) |
| |
| def testLittleEndianInt(self): |
| s = BitStream(int=100, length=16) |
| self.assertEqual(s.intle, 25600) |
| s = BitStream(intle=100, length=16) |
| self.assertEqual(s.int, 25600) |
| self.assertEqual(s.intle, 100) |
| s.intle += 5 |
| self.assertEqual(s.intle, 105) |
| s = BitStream('intle:32=999') |
| self.assertEqual(s.intle, 999) |
| s.byteswap() |
| self.assertEqual(s.int, 999) |
| s = pack('intle:24', 1001) |
| self.assertEqual(s.intle, 1001) |
| self.assertEqual(s.length, 24) |
| self.assertEqual(s.read('intle'), 1001) |
| |
| def testLittleEndianErrors(self): |
| self.assertRaises(bitstring.CreationError, BitStream, 'uintle:15=10') |
| self.assertRaises(bitstring.CreationError, BitStream, 'intle:31=-999') |
| self.assertRaises(bitstring.CreationError, BitStream, uintle=100, length=15) |
| self.assertRaises(bitstring.CreationError, BitStream, intle=100, length=15) |
| s = BitStream('0xfff') |
| self.assertRaises(bitstring.InterpretError, s._getintle) |
| self.assertRaises(bitstring.InterpretError, s._getuintle) |
| self.assertRaises(ValueError, s.read, 'uintle') |
| self.assertRaises(ValueError, s.read, 'intle') |
| |
| def testStructTokens1(self): |
| self.assertEqual(pack('<b', 23), BitStream('intle:8=23')) |
| self.assertEqual(pack('<B', 23), BitStream('uintle:8=23')) |
| self.assertEqual(pack('<h', 23), BitStream('intle:16=23')) |
| self.assertEqual(pack('<H', 23), BitStream('uintle:16=23')) |
| self.assertEqual(pack('<l', 23), BitStream('intle:32=23')) |
| self.assertEqual(pack('<L', 23), BitStream('uintle:32=23')) |
| self.assertEqual(pack('<q', 23), BitStream('intle:64=23')) |
| self.assertEqual(pack('<Q', 23), BitStream('uintle:64=23')) |
| self.assertEqual(pack('>b', 23), BitStream('intbe:8=23')) |
| self.assertEqual(pack('>B', 23), BitStream('uintbe:8=23')) |
| self.assertEqual(pack('>h', 23), BitStream('intbe:16=23')) |
| self.assertEqual(pack('>H', 23), BitStream('uintbe:16=23')) |
| self.assertEqual(pack('>l', 23), BitStream('intbe:32=23')) |
| self.assertEqual(pack('>L', 23), BitStream('uintbe:32=23')) |
| self.assertEqual(pack('>q', 23), BitStream('intbe:64=23')) |
| self.assertEqual(pack('>Q', 23), BitStream('uintbe:64=23')) |
| self.assertRaises(bitstring.CreationError, pack, '<B', -1) |
| self.assertRaises(bitstring.CreationError, pack, '<H', -1) |
| self.assertRaises(bitstring.CreationError, pack, '<L', -1) |
| self.assertRaises(bitstring.CreationError, pack, '<Q', -1) |
| |
| def testStructTokens2(self): |
| endianness = sys.byteorder |
| sys.byteorder = 'little' |
| self.assertEqual(pack('@b', 23), BitStream('intle:8=23')) |
| self.assertEqual(pack('@B', 23), BitStream('uintle:8=23')) |
| self.assertEqual(pack('@h', 23), BitStream('intle:16=23')) |
| self.assertEqual(pack('@H', 23), BitStream('uintle:16=23')) |
| self.assertEqual(pack('@l', 23), BitStream('intle:32=23')) |
| self.assertEqual(pack('@L', 23), BitStream('uintle:32=23')) |
| self.assertEqual(pack('@q', 23), BitStream('intle:64=23')) |
| self.assertEqual(pack('@Q', 23), BitStream('uintle:64=23')) |
| sys.byteorder = 'big' |
| self.assertEqual(pack('@b', 23), BitStream('intbe:8=23')) |
| self.assertEqual(pack('@B', 23), BitStream('uintbe:8=23')) |
| self.assertEqual(pack('@h', 23), BitStream('intbe:16=23')) |
| self.assertEqual(pack('@H', 23), BitStream('uintbe:16=23')) |
| self.assertEqual(pack('@l', 23), BitStream('intbe:32=23')) |
| self.assertEqual(pack('@L', 23), BitStream('uintbe:32=23')) |
| self.assertEqual(pack('@q', 23), BitStream('intbe:64=23')) |
| self.assertEqual(pack('@Q', 23), BitStream('uintbe:64=23')) |
| sys.byteorder = endianness |
| |
| def testNativeEndianness(self): |
| s = pack('@2L', 40, 40) |
| if sys.byteorder == 'little': |
| self.assertEqual(s, pack('<2L', 40, 40)) |
| else: |
| self.assertEqual(sys.byteorder, 'big') |
| self.assertEqual(s, pack('>2L', 40, 40)) |
| |
| def testStructTokens2(self): |
| s = pack('>hhl', 1, 2, 3) |
| a, b, c = s.unpack('>hhl') |
| self.assertEqual((a, b, c), (1, 2, 3)) |
| s = pack('<QL, >Q \tL', 1001, 43, 21, 9999) |
| self.assertEqual(s.unpack('<QL, >QL'), [1001, 43, 21, 9999]) |
| |
| def testStructTokensMultiplicativeFactors(self): |
| s = pack('<2h', 1, 2) |
| a, b = s.unpack('<2h') |
| self.assertEqual((a, b), (1, 2)) |
| s = pack('<100q', *range(100)) |
| self.assertEqual(s.len, 100 * 64) |
| self.assertEqual(s[44*64:45*64].uintle, 44) |
| s = pack('@L0B2h', 5, 5, 5) |
| self.assertEqual(s.unpack('@Lhh'), [5, 5, 5]) |
| |
| def testStructTokensErrors(self): |
| for f in ['>>q', '<>q', 'q>', '2q', 'q', '>-2q', '@a', '>int:8', '>q2']: |
| self.assertRaises(bitstring.CreationError, pack, f, 100) |
| |
| def testImmutableBitStreams(self): |
| a = ConstBitStream('0x012345') |
| self.assertEqual(a, '0x012345') |
| b = BitStream('0xf') + a |
| self.assertEqual(b, '0xf012345') |
| try: |
| a.append(b) |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.prepend(b) |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a[0] = '0b1' |
| self.assertTrue(False) |
| except TypeError: |
| pass |
| try: |
| del a[5] |
| self.assertTrue(False) |
| except TypeError: |
| pass |
| try: |
| a.replace('0b1', '0b0') |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.insert('0b11', 4) |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.reverse() |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.reversebytes() |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| self.assertEqual(a, '0x012345') |
| self.assertTrue(isinstance(a, ConstBitStream)) |
| |
| def testReverseBytes(self): |
| a = BitStream('0x123456') |
| a.byteswap() |
| self.assertEqual(a, '0x563412') |
| b = a + '0b1' |
| b.byteswap() |
| self.assertEqual('0x123456, 0b1', b) |
| a = BitStream('0x54') |
| a.byteswap() |
| self.assertEqual(a, '0x54') |
| a = BitStream() |
| a.byteswap() |
| self.assertFalse(a) |
| |
| def testReverseBytes2(self): |
| a = BitStream() |
| a.byteswap() |
| self.assertFalse(a) |
| a = BitStream('0x00112233') |
| a.byteswap(0, 0, 16) |
| self.assertEqual(a, '0x11002233') |
| a.byteswap(0, 4, 28) |
| self.assertEqual(a, '0x12302103') |
| a.byteswap(start=0, end=18) |
| self.assertEqual(a, '0x30122103') |
| self.assertRaises(ValueError, a.byteswap, 0, 10, 2) |
| self.assertRaises(ValueError, a.byteswap, 0, -4, 4) |
| self.assertRaises(ValueError, a.byteswap, 0, 24, 48) |
| a.byteswap(0, 24) |
| self.assertEqual(a, '0x30122103') |
| a.byteswap(0, 11, 11) |
| self.assertEqual(a, '0x30122103') |
| |
| def testCapitalsInPack(self): |
| a = pack('A', A='0b1') |
| self.assertEqual(a, '0b1') |
| format = 'bits:4=BL_OFFT, uint:12=width, uint:12=height' |
| d = {'BL_OFFT': '0b1011', 'width': 352, 'height': 288} |
| s = bitstring.pack(format, **d) |
| self.assertEqual(s, '0b1011, uint:12=352, uint:12=288') |
| a = pack('0X0, uint:8, hex', 45, '0XABcD') |
| self.assertEqual(a, '0x0, uint:8=45, 0xabCD') |
| |
| def testOtherCapitals(self): |
| a = ConstBitStream('0XABC, 0O0, 0B11') |
| self.assertEqual(a, 'hex=0Xabc, oct=0, bin=0B11') |
| |
| def testEfficientOverwrite(self): |
| a = BitStream(1000000000) |
| a.overwrite([1], 123456) |
| self.assertEqual(a[123456], True) |
| a.overwrite('0xff', 1) |
| self.assertEqual(a[0:32:1], '0x7f800000') |
| b = BitStream('0xffff') |
| b.overwrite('0x0000') |
| self.assertEqual(b, '0x0000') |
| self.assertEqual(b.pos, 16) |
| c = BitStream(length=1000) |
| c.overwrite('0xaaaaaaaaaaaa', 81) |
| self.assertEqual(c[81:81 + 6 * 8], '0xaaaaaaaaaaaa') |
| self.assertEqual(len(list(c.findall('0b1'))), 24) |
| s = BitStream(length=1000) |
| s = s[5:] |
| s.overwrite('0xffffff', 500) |
| s.pos = 500 |
| self.assertEqual(s.read(4 * 8), '0xffffff00') |
| s.overwrite('0xff', 502) |
| self.assertEqual(s[502:518], '0xffff') |
| |
| def testPeekAndReadListErrors(self): |
| a = BitStream('0x123456') |
| self.assertRaises(ValueError, a.read, 'hex:8, hex:8') |
| self.assertRaises(ValueError, a.peek, 'hex:8, hex:8') |
| self.assertRaises(TypeError, a.read, 10, 12) |
| self.assertRaises(TypeError, a.peek, 12, 14) |
| self.assertRaises(TypeError, a.read, 8, 8) |
| self.assertRaises(TypeError, a.peek, 80, 80) |
| |
| def testStartswith(self): |
| a = BitStream() |
| self.assertTrue(a.startswith(BitStream())) |
| self.assertFalse(a.startswith('0b0')) |
| a = BitStream('0x12ff') |
| self.assertTrue(a.startswith('0x1')) |
| self.assertTrue(a.startswith('0b0001001')) |
| self.assertTrue(a.startswith('0x12ff')) |
| self.assertFalse(a.startswith('0x12ff, 0b1')) |
| self.assertFalse(a.startswith('0x2')) |
| |
| def testStartswithStartEnd(self): |
| s = BitStream('0x123456') |
| self.assertTrue(s.startswith('0x234', 4)) |
| self.assertFalse(s.startswith('0x123', end=11)) |
| self.assertTrue(s.startswith('0x123', end=12)) |
| self.assertTrue(s.startswith('0x34', 8, 16)) |
| self.assertFalse(s.startswith('0x34', 7, 16)) |
| self.assertFalse(s.startswith('0x34', 9, 16)) |
| self.assertFalse(s.startswith('0x34', 8, 15)) |
| |
| def testEndswith(self): |
| a = BitStream() |
| self.assertTrue(a.endswith('')) |
| self.assertFalse(a.endswith(BitStream('0b1'))) |
| a = BitStream('0xf2341') |
| self.assertTrue(a.endswith('0x41')) |
| self.assertTrue(a.endswith('0b001')) |
| self.assertTrue(a.endswith('0xf2341')) |
| self.assertFalse(a.endswith('0x1f2341')) |
| self.assertFalse(a.endswith('0o34')) |
| |
| def testEndswithStartEnd(self): |
| s = BitStream('0x123456') |
| self.assertTrue(s.endswith('0x234', end=16)) |
| self.assertFalse(s.endswith('0x456', start=13)) |
| self.assertTrue(s.endswith('0x456', start=12)) |
| self.assertTrue(s.endswith('0x34', 8, 16)) |
| self.assertTrue(s.endswith('0x34', 7, 16)) |
| self.assertFalse(s.endswith('0x34', 9, 16)) |
| self.assertFalse(s.endswith('0x34', 8, 15)) |
| |
| def testUnhashability(self): |
| s = BitStream('0xf') |
| self.assertRaises(TypeError, set, [s]) |
| self.assertRaises(TypeError, hash, [s]) |
| |
| def testConstBitStreamSetCreation(self): |
| sl = [ConstBitStream(uint=i, length=7) for i in range(15)] |
| s = set(sl) |
| self.assertEqual(len(s), 15) |
| s.add(ConstBitStream('0b0000011')) |
| self.assertEqual(len(s), 15) |
| self.assertRaises(TypeError, s.add, BitStream('0b0000011')) |
| |
| def testConstBitStreamFunctions(self): |
| s = ConstBitStream('0xf, 0b1') |
| self.assertEqual(type(s), ConstBitStream) |
| t = copy.copy(s) |
| self.assertEqual(type(t), ConstBitStream) |
| a = s + '0o3' |
| self.assertEqual(type(a), ConstBitStream) |
| b = a[0:4] |
| self.assertEqual(type(b), ConstBitStream) |
| b = a[4:3] |
| self.assertEqual(type(b), ConstBitStream) |
| b = a[5:2:-1] |
| self.assertEqual(type(b), ConstBitStream) |
| b = ~a |
| self.assertEqual(type(b), ConstBitStream) |
| b = a << 2 |
| self.assertEqual(type(b), ConstBitStream) |
| b = a >> 2 |
| self.assertEqual(type(b), ConstBitStream) |
| b = a * 2 |
| self.assertEqual(type(b), ConstBitStream) |
| b = a * 0 |
| self.assertEqual(type(b), ConstBitStream) |
| b = a & ~a |
| self.assertEqual(type(b), ConstBitStream) |
| b = a | ~a |
| self.assertEqual(type(b), ConstBitStream) |
| b = a ^ ~a |
| self.assertEqual(type(b), ConstBitStream) |
| b = a._slice(4, 4) |
| self.assertEqual(type(b), ConstBitStream) |
| b = a.read(4) |
| self.assertEqual(type(b), ConstBitStream) |
| |
| def testConstBitStreamProperties(self): |
| a = ConstBitStream('0x123123') |
| try: |
| a.hex = '0x234' |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.oct = '0o234' |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.bin = '0b101' |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.ue = 3453 |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.se = -123 |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.int = 432 |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.uint = 4412 |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.intle = 123 |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.uintle = 4412 |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.intbe = 123 |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.uintbe = 4412 |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.intne = 123 |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.uintne = 4412 |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| try: |
| a.bytes = b'hello' |
| self.assertTrue(False) |
| except AttributeError: |
| pass |
| |
| def testConstBitStreamMisc(self): |
| a = ConstBitStream('0xf') |
| b = a |
| a += '0xe' |
| self.assertEqual(b, '0xf') |
| self.assertEqual(a, '0xfe') |
| c = BitStream(a) |
| self.assertEqual(a, c) |
| a = ConstBitStream('0b1') |
| a._append(a) |
| self.assertEqual(a, '0b11') |
| self.assertEqual(type(a), ConstBitStream) |
| a._prepend(a) |
| self.assertEqual(a, '0b1111') |
| self.assertEqual(type(a), ConstBitStream) |
| |
| def testConstBitStreamHashibility(self): |
| a = ConstBitStream('0x1') |
| b = ConstBitStream('0x2') |
| c = ConstBitStream('0x1') |
| c.pos = 3 |
| s = set((a, b, c)) |
| self.assertEqual(len(s), 2) |
| self.assertEqual(hash(a), hash(c)) |
| |
| def testConstBitStreamCopy(self): |
| a = ConstBitStream('0xabc') |
| a.pos = 11 |
| b = copy.copy(a) |
| b.pos = 4 |
| self.assertEqual(id(a._datastore), id(b._datastore)) |
| self.assertEqual(a.pos, 11) |
| self.assertEqual(b.pos, 4) |
| |
| def testPython26stuff(self): |
| s = BitStream('0xff') |
| self.assertTrue(isinstance(s.tobytes(), bytes)) |
| self.assertTrue(isinstance(s.bytes, bytes)) |
| |
| def testReadFromBits(self): |
| a = ConstBitStream('0xaabbccdd') |
| b = a.read(8) |
| self.assertEqual(b, '0xaa') |
| self.assertEqual(a[0:8], '0xaa') |
| self.assertEqual(a[-1], True) |
| a.pos = 0 |
| self.assertEqual(a.read(4).uint, 10) |
| |
| |
| class Set(unittest.TestCase): |
| def testSet(self): |
| a = BitStream(length=16) |
| a.set(True, 0) |
| self.assertEqual(a, '0b10000000 00000000') |
| a.set(1, 15) |
| self.assertEqual(a, '0b10000000 00000001') |
| b = a[4:12] |
| b.set(True, 1) |
| self.assertEqual(b, '0b01000000') |
| b.set(True, -1) |
| self.assertEqual(b, '0b01000001') |
| b.set(1, -8) |
| self.assertEqual(b, '0b11000001') |
| self.assertRaises(IndexError, b.set, True, -9) |
| self.assertRaises(IndexError, b.set, True, 8) |
| |
| def testSetNegativeIndex(self): |
| a = BitStream(10) |
| a.set(1, -1) |
| self.assertEqual(a.bin, '0000000001') |
| a.set(1, [-1, -10]) |
| self.assertEqual(a.bin, '1000000001') |
| self.assertRaises(IndexError, a.set, 1, [-11]) |
| |
| def testFileBasedSetUnset(self): |
| a = BitStream(filename='test.m1v') |
| a.set(True, (0, 1, 2, 3, 4)) |
| self.assertEqual(a[0:32], '0xf80001b3') |
| a = BitStream(filename='test.m1v') |
| a.set(False, (28, 29, 30, 31)) |
| self.assertTrue(a.startswith('0x000001b0')) |
| |
| def testSetList(self): |
| a = BitStream(length=18) |
| a.set(True, range(18)) |
| self.assertEqual(a.int, -1) |
| a.set(False, range(18)) |
| self.assertEqual(a.int, 0) |
| |
| def testUnset(self): |
| a = BitStream(length=16, int=-1) |
| a.set(False, 0) |
| self.assertEqual(~a, '0b10000000 00000000') |
| a.set(0, 15) |
| self.assertEqual(~a, '0b10000000 00000001') |
| b = a[4:12] |
| b.set(False, 1) |
| self.assertEqual(~b, '0b01000000') |
| b.set(False, -1) |
| self.assertEqual(~b, '0b01000001') |
| b.set(False, -8) |
| self.assertEqual(~b, '0b11000001') |
| self.assertRaises(IndexError, b.set, False, -9) |
| self.assertRaises(IndexError, b.set, False, 8) |
| |
| def testSetWholeBitStream(self): |
| a = BitStream(14) |
| a.set(1) |
| self.assertTrue(a.all(1)) |
| a.set(0) |
| self.assertTrue(a.all(0)) |
| |
| |
| class Invert(unittest.TestCase): |
| def testInvertBits(self): |
| a = BitStream('0b111000') |
| a.invert(range(a.len)) |
| self.assertEqual(a, '0b000111') |
| a.invert([0, 1, -1]) |
| self.assertEqual(a, '0b110110') |
| |
| def testInvertWholeBitStream(self): |
| a = BitStream('0b11011') |
| a.invert() |
| self.assertEqual(a, '0b00100') |
| |
| def testInvertSingleBit(self): |
| a = BitStream('0b000001') |
| a.invert(0) |
| self.assertEqual(a.bin, '100001') |
| a.invert(-1) |
| self.assertEqual(a.bin, '100000') |
| |
| def testInvertErrors(self): |
| a = BitStream(10) |
| self.assertRaises(IndexError, a.invert, 10) |
| self.assertRaises(IndexError, a.invert, -11) |
| self.assertRaises(IndexError, a.invert, [1, 2, 10]) |
| |
| |
| ####################### |
| |
| def testIor(self): |
| a = BitStream('0b1101001') |
| a |= '0b1110000' |
| self.assertEqual(a, '0b1111001') |
| b = a[2:] |
| c = a[1:-1] |
| b |= c |
| self.assertEqual(c, '0b11100') |
| self.assertEqual(b, '0b11101') |
| |
| def testIand(self): |
| a = BitStream('0b0101010101000') |
| a &= '0b1111110000000' |
| self.assertEqual(a, '0b0101010000000') |
| s = BitStream(filename='test.m1v', offset=26, length=24) |
| s &= '0xff00ff' |
| self.assertEqual(s, '0xcc0004') |
| |
| def testIxor(self): |
| a = BitStream('0b11001100110011') |
| a ^= '0b11111100000010' |
| self.assertEqual(a, '0b00110000110001') |
| |
| def testLogicalInplaceErrors(self): |
| a = BitStream(4) |
| self.assertRaises(ValueError, a.__ior__, '0b111') |
| self.assertRaises(ValueError, a.__iand__, '0b111') |
| self.assertRaises(ValueError, a.__ixor__, '0b111') |
| |
| |
| class AllAndAny(unittest.TestCase): |
| def testAll(self): |
| a = BitStream('0b0111') |
| self.assertTrue(a.all(True, (1, 3))) |
| self.assertFalse(a.all(True, (0, 1, 2))) |
| self.assertTrue(a.all(True, [-1])) |
| self.assertFalse(a.all(True, [0])) |
| |
| def testFileBasedAll(self): |
| a = BitStream(filename='test.m1v') |
| self.assertTrue(a.all(True, [31])) |
| a = BitStream(filename='test.m1v') |
| self.assertTrue(a.all(False, (0, 1, 2, 3, 4))) |
| |
| def testFileBasedAny(self): |
| a = BitStream(filename='test.m1v') |
| self.assertTrue(a.any(True, (31, 12))) |
| a = BitStream(filename='test.m1v') |
| self.assertTrue(a.any(False, (0, 1, 2, 3, 4))) |
| |
| def testAny(self): |
| a = BitStream('0b10011011') |
| self.assertTrue(a.any(True, (1, 2, 3, 5))) |
| self.assertFalse(a.any(True, (1, 2, 5))) |
| self.assertTrue(a.any(True, (-1,))) |
| self.assertFalse(a.any(True, (1,))) |
| |
| def testAllFalse(self): |
| a = BitStream('0b0010011101') |
| self.assertTrue(a.all(False, (0, 1, 3, 4))) |
| self.assertFalse(a.all(False, (0, 1, 2, 3, 4))) |
| |
| def testAnyFalse(self): |
| a = BitStream('0b01001110110111111111111111111') |
| self.assertTrue(a.any(False, (4, 5, 6, 2))) |
| self.assertFalse(a.any(False, (1, 15, 20))) |
| |
| def testAnyEmptyBitstring(self): |
| a = ConstBitStream() |
| self.assertFalse(a.any(True)) |
| self.assertFalse(a.any(False)) |
| |
| def testAllEmptyBitStream(self): |
| a = ConstBitStream() |
| self.assertTrue(a.all(True)) |
| self.assertTrue(a.all(False)) |
| |
| def testAnyWholeBitstring(self): |
| a = ConstBitStream('0xfff') |
| self.assertTrue(a.any(True)) |
| self.assertFalse(a.any(False)) |
| |
| def testAllWholeBitstring(self): |
| a = ConstBitStream('0xfff') |
| self.assertTrue(a.all(True)) |
| self.assertFalse(a.all(False)) |
| |
| def testErrors(self): |
| a = BitStream('0xf') |
| self.assertRaises(IndexError, a.all, True, [5]) |
| self.assertRaises(IndexError, a.all, True, [-5]) |
| self.assertRaises(IndexError, a.any, True, [5]) |
| self.assertRaises(IndexError, a.any, True, [-5]) |
| |
| ################### |
| |
| def testFloatInitialisation(self): |
| for f in (0.0000001, -1.0, 1.0, 0.2, -3.1415265, 1.331e32): |
| a = BitStream(float=f, length=64) |
| a.pos = 6 |
| self.assertEqual(a.float, f) |
| a = BitStream('float:64=%s' % str(f)) |
| a.pos = 6 |
| self.assertEqual(a.float, f) |
| a = BitStream('floatbe:64=%s' % str(f)) |
| a.pos = 6 |
| self.assertEqual(a.floatbe, f) |
| a = BitStream('floatle:64=%s' % str(f)) |
| a.pos = 6 |
| self.assertEqual(a.floatle, f) |
| a = BitStream('floatne:64=%s' % str(f)) |
| a.pos = 6 |
| self.assertEqual(a.floatne, f) |
| b = BitStream(float=f, length=32) |
| b.pos = 6 |
| self.assertAlmostEqual(b.float / f, 1.0) |
| b = BitStream('float:32=%s' % str(f)) |
| b.pos = 6 |
| self.assertAlmostEqual(b.float / f, 1.0) |
| b = BitStream('floatbe:32=%s' % str(f)) |
| b.pos = 6 |
| self.assertAlmostEqual(b.floatbe / f, 1.0) |
| b = BitStream('floatle:32=%s' % str(f)) |
| b.pos = 6 |
| self.assertAlmostEqual(b.floatle / f, 1.0) |
| b = BitStream('floatne:32=%s' % str(f)) |
| b.pos = 6 |
| self.assertAlmostEqual(b.floatne / f, 1.0) |
| a = BitStream('0x12345678') |
| a.pos = 6 |
| a.float = 23 |
| self.assertEqual(a.float, 23.0) |
| |
| def testFloatInitStrings(self): |
| for s in ('5', '+0.0001', '-1e101', '4.', '.2', '-.65', '43.21E+32'): |
| a = BitStream('float:64=%s' % s) |
| self.assertEqual(a.float, float(s)) |
| |
| def testFloatPacking(self): |
| a = pack('>d', 0.01) |
| self.assertEqual(a.float, 0.01) |
| self.assertEqual(a.floatbe, 0.01) |
| a.byteswap() |
| self.assertEqual(a.floatle, 0.01) |
| b = pack('>f', 1e10) |
| self.assertAlmostEqual(b.float / 1e10, 1.0) |
| c = pack('<f', 10.3) |
| self.assertAlmostEqual(c.floatle / 10.3, 1.0) |
| d = pack('>5d', 10.0, 5.0, 2.5, 1.25, 0.1) |
| self.assertEqual(d.unpack('>5d'), [10.0, 5.0, 2.5, 1.25, 0.1]) |
| |
| def testFloatReading(self): |
| a = BitStream('floatle:64=12, floatbe:64=-0.01, floatne:64=3e33') |
| x, y, z = a.readlist('floatle:64, floatbe:64, floatne:64') |
| self.assertEqual(x, 12.0) |
| self.assertEqual(y, -0.01) |
| self.assertEqual(z, 3e33) |
| a = BitStream('floatle:32=12, floatbe:32=-0.01, floatne:32=3e33') |
| x, y, z = a.readlist('floatle:32, floatbe:32, floatne:32') |
| self.assertAlmostEqual(x / 12.0, 1.0) |
| self.assertAlmostEqual(y / -0.01, 1.0) |
| self.assertAlmostEqual(z / 3e33, 1.0) |
| a = BitStream('0b11, floatle:64=12, 0xfffff') |
| a.pos = 2 |
| self.assertEqual(a.read('floatle:64'), 12.0) |
| b = BitStream(floatle=20, length=32) |
| b.floatle = 10.0 |
| b = [0] + b |
| self.assertEqual(b[1:].floatle, 10.0) |
| |
| def testNonAlignedFloatReading(self): |
| s = BitStream('0b1, float:32 = 10.0') |
| x, y = s.readlist('1, float:32') |
| self.assertEqual(y, 10.0) |
| s[1:] = 'floatle:32=20.0' |
| x, y = s.unpack('1, floatle:32') |
| self.assertEqual(y, 20.0) |
| |
| def testFloatErrors(self): |
| a = BitStream('0x3') |
| self.assertRaises(bitstring.InterpretError, a._getfloat) |
| self.assertRaises(bitstring.CreationError, a._setfloat, -0.2) |
| for l in (8, 10, 12, 16, 30, 128, 200): |
| self.assertRaises(ValueError, BitStream, float=1.0, length=l) |
| self.assertRaises(bitstring.CreationError, BitStream, floatle=0.3, length=0) |
| self.assertRaises(bitstring.CreationError, BitStream, floatle=0.3, length=1) |
| self.assertRaises(bitstring.CreationError, BitStream, float=2) |
| self.assertRaises(bitstring.InterpretError, a.read, 'floatle:2') |
| |
| def testReadErrorChangesPos(self): |
| a = BitStream('0x123123') |
| try: |
| a.read('10, 5') |
| except ValueError: |
| pass |
| self.assertEqual(a.pos, 0) |
| |
| def testRor(self): |
| a = BitStream('0b11001') |
| a.ror(0) |
| self.assertEqual(a, '0b11001') |
| a.ror(1) |
| self.assertEqual(a, '0b11100') |
| a.ror(5) |
| self.assertEqual(a, '0b11100') |
| a.ror(101) |
| self.assertEqual(a, '0b01110') |
| a = BitStream('0b1') |
| a.ror(1000000) |
| self.assertEqual(a, '0b1') |
| |
| def testRorErrors(self): |
| a = BitStream() |
| self.assertRaises(bitstring.Error, a.ror, 0) |
| a += '0b001' |
| self.assertRaises(ValueError, a.ror, -1) |
| |
| def testRol(self): |
| a = BitStream('0b11001') |
| a.rol(0) |
| self.assertEqual(a, '0b11001') |
| a.rol(1) |
| self.assertEqual(a, '0b10011') |
| a.rol(5) |
| self.assertEqual(a, '0b10011') |
| a.rol(101) |
| self.assertEqual(a, '0b00111') |
| a = BitStream('0b1') |
| a.rol(1000000) |
| self.assertEqual(a, '0b1') |
| |
| def testRolFromFile(self): |
| a = BitStream(filename='test.m1v') |
| l = a.len |
| a.rol(1) |
| self.assertTrue(a.startswith('0x000003')) |
| self.assertEqual(a.len, l) |
| self.assertTrue(a.endswith('0x0036e')) |
| |
| def testRorFromFile(self): |
| a = BitStream(filename='test.m1v') |
| l = a.len |
| a.ror(1) |
| self.assertTrue(a.startswith('0x800000')) |
| self.assertEqual(a.len, l) |
| self.assertTrue(a.endswith('0x000db')) |
| |
| def testRolErrors(self): |
| a = BitStream() |
| self.assertRaises(bitstring.Error, a.rol, 0) |
| a += '0b001' |
| self.assertRaises(ValueError, a.rol, -1) |
| |
| def testBytesToken(self): |
| a = BitStream('0x010203') |
| b = a.read('bytes:1') |
| self.assertTrue(isinstance(b, bytes)) |
| self.assertEqual(b, b'\x01') |
| x, y, z = a.unpack('4, bytes:2, uint') |
| self.assertEqual(x, 0) |
| self.assertEqual(y, b'\x10\x20') |
| self.assertEqual(z, 3) |
| s = pack('bytes:4', b'abcd') |
| self.assertEqual(s.bytes, b'abcd') |
| |
| def testBytesTokenMoreThoroughly(self): |
| a = BitStream('0x0123456789abcdef') |
| a.pos += 16 |
| self.assertEqual(a.read('bytes:1'), b'\x45') |
| self.assertEqual(a.read('bytes:3'), b'\x67\x89\xab') |
| x, y, z = a.unpack('bits:28, bytes, bits:12') |
| self.assertEqual(y, b'\x78\x9a\xbc') |
| |
| def testDedicatedReadFunctions(self): |
| a = BitStream('0b11, uint:43=98798798172, 0b11111') |
| x = a._readuint(43, 2) |
| self.assertEqual(x, 98798798172) |
| self.assertEqual(a.pos, 0) |
| x = a._readint(43, 2) |
| self.assertEqual(x, 98798798172) |
| self.assertEqual(a.pos, 0) |
| |
| a = BitStream('0b11, uintbe:48=98798798172, 0b11111') |
| x = a._readuintbe(48, 2) |
| self.assertEqual(x, 98798798172) |
| self.assertEqual(a.pos, 0) |
| x = a._readintbe(48, 2) |
| self.assertEqual(x, 98798798172) |
| self.assertEqual(a.pos, 0) |
| |
| a = BitStream('0b111, uintle:40=123516, 0b111') |
| self.assertEqual(a._readuintle(40, 3), 123516) |
| b = BitStream('0xff, uintle:800=999, 0xffff') |
| self.assertEqual(b._readuintle(800, 8), 999) |
| |
| a = BitStream('0b111, intle:48=999999999, 0b111111111111') |
| self.assertEqual(a._readintle(48, 3), 999999999) |
| b = BitStream('0xff, intle:200=918019283740918263512351235, 0xfffffff') |
| self.assertEqual(b._readintle(200, 8), 918019283740918263512351235) |
| |
| a = BitStream('0b111, floatbe:64=-5.32, 0xffffffff') |
| self.assertEqual(a._readfloat(64, 3), -5.32) |
| |
| a = BitStream('0b111, floatle:64=9.9998, 0b111') |
| self.assertEqual(a._readfloatle(64, 3), 9.9998) |
| |
| def testAutoInitWithInt(self): |
| a = BitStream(0) |
| self.assertFalse(a) |
| a = BitStream(1) |
| self.assertEqual(a, '0b0') |
| a = BitStream(1007) |
| self.assertEqual(a, BitStream(length=1007)) |
| self.assertRaises(bitstring.CreationError, BitStream, -1) |
| |
| a = 6 + ConstBitStream('0b1') + 3 |
| self.assertEqual(a, '0b0000001000') |
| a += 1 |
| self.assertEqual(a, '0b00000010000') |
| self.assertEqual(ConstBitStream(13), 13) |
| |
| def testReadingProblems(self): |
| a = BitStream('0x000001') |
| b = a.read('uint:24') |
| self.assertEqual(b, 1) |
| a.pos = 0 |
| self.assertRaises(bitstring.ReadError, a.read, 'bytes:4') |
| |
| def testAddVersesInPlaceAdd(self): |
| a1 = ConstBitStream('0xabc') |
| b1 = a1 |
| a1 += '0xdef' |
| self.assertEqual(a1, '0xabcdef') |
| self.assertEqual(b1, '0xabc') |
| |
| a2 = BitStream('0xabc') |
| b2 = a2 |
| c2 = a2 + '0x0' |
| a2 += '0xdef' |
| self.assertEqual(a2, '0xabcdef') |
| self.assertEqual(b2, '0xabcdef') |
| self.assertEqual(c2, '0xabc0') |
| |
| def testAndVersesInPlaceAnd(self): |
| a1 = ConstBitStream('0xabc') |
| b1 = a1 |
| a1 &= '0xf0f' |
| self.assertEqual(a1, '0xa0c') |
| self.assertEqual(b1, '0xabc') |
| |
| a2 = BitStream('0xabc') |
| b2 = a2 |
| c2 = a2 & '0x00f' |
| a2 &= '0xf0f' |
| self.assertEqual(a2, '0xa0c') |
| self.assertEqual(b2, '0xa0c') |
| self.assertEqual(c2, '0x00c') |
| |
| def testOrVersesInPlaceOr(self): |
| a1 = ConstBitStream('0xabc') |
| b1 = a1 |
| a1 |= '0xf0f' |
| self.assertEqual(a1, '0xfbf') |
| self.assertEqual(b1, '0xabc') |
| |
| a2 = BitStream('0xabc') |
| b2 = a2 |
| c2 = a2 | '0x00f' |
| a2 |= '0xf0f' |
| self.assertEqual(a2, '0xfbf') |
| self.assertEqual(b2, '0xfbf') |
| self.assertEqual(c2, '0xabf') |
| |
| def testXorVersesInPlaceXor(self): |
| a1 = ConstBitStream('0xabc') |
| b1 = a1 |
| a1 ^= '0xf0f' |
| self.assertEqual(a1, '0x5b3') |
| self.assertEqual(b1, '0xabc') |
| |
| a2 = BitStream('0xabc') |
| b2 = a2 |
| c2 = a2 ^ '0x00f' |
| a2 ^= '0xf0f' |
| self.assertEqual(a2, '0x5b3') |
| self.assertEqual(b2, '0x5b3') |
| self.assertEqual(c2, '0xab3') |
| |
| def testMulVersesInPlaceMul(self): |
| a1 = ConstBitStream('0xabc') |
| b1 = a1 |
| a1 *= 3 |
| self.assertEqual(a1, '0xabcabcabc') |
| self.assertEqual(b1, '0xabc') |
| |
| a2 = BitStream('0xabc') |
| b2 = a2 |
| c2 = a2 * 2 |
| a2 *= 3 |
| self.assertEqual(a2, '0xabcabcabc') |
| self.assertEqual(b2, '0xabcabcabc') |
| self.assertEqual(c2, '0xabcabc') |
| |
| def testLshiftVersesInPlaceLshift(self): |
| a1 = ConstBitStream('0xabc') |
| b1 = a1 |
| a1 <<= 4 |
| self.assertEqual(a1, '0xbc0') |
| self.assertEqual(b1, '0xabc') |
| |
| a2 = BitStream('0xabc') |
| b2 = a2 |
| c2 = a2 << 8 |
| a2 <<= 4 |
| self.assertEqual(a2, '0xbc0') |
| self.assertEqual(b2, '0xbc0') |
| self.assertEqual(c2, '0xc00') |
| |
| def testRshiftVersesInPlaceRshift(self): |
| a1 = ConstBitStream('0xabc') |
| b1 = a1 |
| a1 >>= 4 |
| self.assertEqual(a1, '0x0ab') |
| self.assertEqual(b1, '0xabc') |
| |
| a2 = BitStream('0xabc') |
| b2 = a2 |
| c2 = a2 >> 8 |
| a2 >>= 4 |
| self.assertEqual(a2, '0x0ab') |
| self.assertEqual(b2, '0x0ab') |
| self.assertEqual(c2, '0x00a') |
| |
| def testAutoFromBool(self): |
| a = ConstBitStream() + True + False + True |
| self.assertEqual(a, '0b00') |
| # self.assertEqual(a, '0b101') |
| # b = ConstBitStream(False) |
| # self.assertEqual(b, '0b0') |
| # c = ConstBitStream(True) |
| # self.assertEqual(c, '0b1') |
| # self.assertEqual(b, False) |
| # self.assertEqual(c, True) |
| # self.assertEqual(b & True, False) |
| |
| |
| class Bugs(unittest.TestCase): |
| def testBugInReplace(self): |
| s = BitStream('0x00112233') |
| l = list(s.split('0x22', start=8, bytealigned=True)) |
| self.assertEqual(l, ['0x11', '0x2233']) |
| s = BitStream('0x00112233') |
| s.replace('0x22', '0xffff', start=8, bytealigned=True) |
| self.assertEqual(s, '0x0011ffff33') |
| s = BitStream('0x0123412341234') |
| s.replace('0x23', '0xf', start=9, bytealigned=True) |
| self.assertEqual(s, '0x012341f41f4') |
| |
| def testTruncateStartBug(self): |
| a = BitStream('0b000000111')[2:] |
| a._truncatestart(6) |
| self.assertEqual(a, '0b1') |
| |
| def testNullBits(self): |
| s = ConstBitStream(bin='') |
| t = ConstBitStream(oct='') |
| u = ConstBitStream(hex='') |
| v = ConstBitStream(bytes=b'') |
| self.assertFalse(s) |
| self.assertFalse(t) |
| self.assertFalse(u) |
| self.assertFalse(v) |
| |
| def testMultiplicativeFactorsCreation(self): |
| s = BitStream('1*0b1') |
| self.assertEqual(s, '0b1') |
| s = BitStream('4*0xc') |
| self.assertEqual(s, '0xcccc') |
| s = BitStream('0b1, 0*0b0') |
| self.assertEqual(s, '0b1') |
| s = BitStream('0b1, 3*uint:8=34, 2*0o755') |
| self.assertEqual(s, '0b1, uint:8=34, uint:8=34, uint:8=34, 0o755755') |
| s = BitStream('0*0b1001010') |
| self.assertFalse(s) |
| |
| def testMultiplicativeFactorsReading(self): |
| s = BitStream('0xc') * 5 |
| a, b, c, d, e = s.readlist('5*4') |
| self.assertTrue(a == b == c == d == e == 12) |
| s = ConstBitStream('2*0b101, 4*uint:7=3') |
| a, b, c, d, e = s.readlist('2*bin:3, 3*uint:7') |
| self.assertTrue(a == b == '101') |
| self.assertTrue(c == d == e == 3) |
| |
| def testMultiplicativeFactorsPacking(self): |
| s = pack('3*bin', '1', '001', '101') |
| self.assertEqual(s, '0b1001101') |
| s = pack('hex, 2*se=-56, 3*uint:37', '34', 1, 2, 3) |
| a, b, c, d, e, f = s.unpack('hex:8, 2*se, 3*uint:37') |
| self.assertEqual(a, '34') |
| self.assertEqual(b, -56) |
| self.assertEqual(c, -56) |
| self.assertEqual((d, e, f), (1, 2, 3)) |
| # This isn't allowed yet. See comment in tokenparser. |
| #s = pack('fluffy*uint:8', *range(3), fluffy=3) |
| #a, b, c = s.readlist('2*uint:8, 1*uint:8, 0*uint:8') |
| #self.assertEqual((a, b, c), (0, 1, 2)) |
| |
| def testMultiplicativeFactorsUnpacking(self): |
| s = ConstBitStream('0b10111') |
| a, b, c, d = s.unpack('3*bool, bin') |
| self.assertEqual((a, b, c), (True, False, True)) |
| self.assertEqual(d, '11') |
| |
| |
| def testPackingDefaultIntWithKeyword(self): |
| s = pack('12', 100) |
| self.assertEqual(s.unpack('12')[0], 100) |
| s = pack('oh_no_not_the_eyes=33', oh_no_not_the_eyes=17) |
| self.assertEqual(s.uint, 33) |
| self.assertEqual(s.len, 17) |
| |
| def testInitFromIterable(self): |
| self.assertTrue(isinstance(range(10), collections.Iterable)) |
| s = ConstBitStream(range(12)) |
| self.assertEqual(s, '0x7ff') |
| |
| def testFunctionNegativeIndices(self): |
| # insert |
| s = BitStream('0b0111') |
| s.insert('0b0', -1) |
| self.assertEqual(s, '0b01101') |
| self.assertRaises(ValueError, s.insert, '0b0', -1000) |
| |
| # reverse |
| s.reverse(-2) |
| self.assertEqual(s, '0b01110') |
| t = BitStream('0x778899abcdef') |
| t.reverse(-12, -4) |
| self.assertEqual(t, '0x778899abc7bf') |
| |
| # reversebytes |
| t.byteswap(0, -40, -16) |
| self.assertEqual(t, '0x77ab9988c7bf') |
| |
| # overwrite |
| t.overwrite('0x666', -20) |
| self.assertEqual(t, '0x77ab998666bf') |
| |
| # find |
| found = t.find('0x998', bytealigned=True, start=-31) |
| self.assertFalse(found) |
| found = t.find('0x998', bytealigned=True, start=-32) |
| self.assertTrue(found) |
| self.assertEqual(t.pos, 16) |
| t.pos = 0 |
| found = t.find('0x988', bytealigned=True, end=-21) |
| self.assertFalse(found) |
| found = t.find('0x998', bytealigned=True, end=-20) |
| self.assertTrue(found) |
| self.assertEqual(t.pos, 16) |
| |
| #findall |
| s = BitStream('0x1234151f') |
| l = list(s.findall('0x1', bytealigned=True, start=-15)) |
| self.assertEqual(l, [24]) |
| l = list(s.findall('0x1', bytealigned=True, start=-16)) |
| self.assertEqual(l, [16, 24]) |
| l = list(s.findall('0x1', bytealigned=True, end=-5)) |
| self.assertEqual(l, [0, 16]) |
| l = list(s.findall('0x1', bytealigned=True, end=-4)) |
| self.assertEqual(l, [0, 16, 24]) |
| |
| # rfind |
| found = s.rfind('0x1f', end=-1) |
| self.assertFalse(found) |
| found = s.rfind('0x12', start=-31) |
| self.assertFalse(found) |
| |
| # cut |
| s = BitStream('0x12345') |
| l = list(s.cut(4, start=-12, end=-4)) |
| self.assertEqual(l, ['0x3', '0x4']) |
| |
| # split |
| s = BitStream('0xfe0012fe1200fe') |
| l = list(s.split('0xfe', bytealigned=True, end=-1)) |
| self.assertEqual(l, ['', '0xfe0012', '0xfe1200f, 0b111']) |
| l = list(s.split('0xfe', bytealigned=True, start=-8)) |
| self.assertEqual(l, ['', '0xfe']) |
| |
| # startswith |
| self.assertTrue(s.startswith('0x00f', start=-16)) |
| self.assertTrue(s.startswith('0xfe00', end=-40)) |
| self.assertFalse(s.startswith('0xfe00', end=-41)) |
| |
| # endswith |
| self.assertTrue(s.endswith('0x00fe', start=-16)) |
| self.assertFalse(s.endswith('0x00fe', start=-15)) |
| self.assertFalse(s.endswith('0x00fe', end=-1)) |
| self.assertTrue(s.endswith('0x00f', end=-4)) |
| |
| # replace |
| s.replace('0xfe', '', end=-1) |
| self.assertEqual(s, '0x00121200fe') |
| s.replace('0x00', '', start=-24) |
| self.assertEqual(s, '0x001212fe') |
| |
| def testRotateStartAndEnd(self): |
| a = BitStream('0b110100001') |
| a.rol(1, 3, 6) |
| self.assertEqual(a, '0b110001001') |
| a.ror(1, start=-4) |
| self.assertEqual(a, '0b110001100') |
| a.rol(202, end=-5) |
| self.assertEqual(a, '0b001101100') |
| a.ror(3, end=4) |
| self.assertEqual(a, '0b011001100') |
| self.assertRaises(ValueError, a.rol, 5, start=-4, end=-6) |
| |
| def testByteSwapInt(self): |
| s = pack('5*uintle:16', *range(10, 15)) |
| self.assertEqual(list(range(10, 15)), s.unpack('5*uintle:16')) |
| swaps = s.byteswap(2) |
| self.assertEqual(list(range(10, 15)), s.unpack('5*uintbe:16')) |
| self.assertEqual(swaps, 5) |
| s = BitStream('0xf234567f') |
| swaps = s.byteswap(1, start=4) |
| self.assertEqual(swaps, 3) |
| self.assertEqual(s, '0xf234567f') |
| s.byteswap(2, start=4) |
| self.assertEqual(s, '0xf452367f') |
| s.byteswap(2, start=4, end=-4) |
| self.assertEqual(s, '0xf234567f') |
| s.byteswap(3) |
| self.assertEqual(s, '0x5634f27f') |
| s.byteswap(2, repeat=False) |
| self.assertEqual(s, '0x3456f27f') |
| swaps = s.byteswap(5) |
| self.assertEqual(swaps, 0) |
| swaps = s.byteswap(4, repeat=False) |
| self.assertEqual(swaps, 1) |
| self.assertEqual(s, '0x7ff25634') |
| |
| def testByteSwapPackCode(self): |
| s = BitStream('0x0011223344556677') |
| swaps = s.byteswap('b') |
| self.assertEqual(s, '0x0011223344556677') |
| self.assertEqual(swaps, 8) |
| swaps = s.byteswap('>3h', repeat=False) |
| self.assertEqual(s, '0x1100332255446677') |
| self.assertEqual(swaps, 1) |
| |
| def testByteSwapIterable(self): |
| s = BitStream('0x0011223344556677') |
| swaps = s.byteswap(range(1, 4), repeat=False) |
| self.assertEqual(swaps, 1) |
| self.assertEqual(s, '0x0022115544336677') |
| swaps = s.byteswap([2], start=8) |
| self.assertEqual(s, '0x0011224455663377') |
| self.assertEqual(3, swaps) |
| swaps = s.byteswap([2, 3], start=4) |
| self.assertEqual(swaps, 1) |
| self.assertEqual(s, '0x0120156452463377') |
| |
| def testByteSwapErrors(self): |
| s = BitStream('0x0011223344556677') |
| self.assertRaises(ValueError, s.byteswap, 'z') |
| self.assertRaises(ValueError, s.byteswap, -1) |
| self.assertRaises(ValueError, s.byteswap, [-1]) |
| self.assertRaises(ValueError, s.byteswap, [1, 'e']) |
| self.assertRaises(ValueError, s.byteswap, '!h') |
| self.assertRaises(ValueError, s.byteswap, 2, start=-1000) |
| self.assertRaises(TypeError, s.byteswap, 5.4) |
| |
| def testByteSwapFromFile(self): |
| s = BitStream(filename='smalltestfile') |
| swaps = s.byteswap('2bh') |
| self.assertEqual(s, '0x0123674589abefcd') |
| self.assertEqual(swaps, 2) |
| |
| def testBracketExpander(self): |
| be = bitstring.expand_brackets |
| self.assertEqual(be('hello'), 'hello') |
| self.assertEqual(be('(hello)'), 'hello') |
| self.assertEqual(be('1*(hello)'), 'hello') |
| self.assertEqual(be('2*(hello)'), 'hello,hello') |
| self.assertEqual(be('1*(a, b)'), 'a,b') |
| self.assertEqual(be('2*(a, b)'), 'a,b,a,b') |
| self.assertEqual(be('2*(a), 3*(b)'), 'a,a,b,b,b') |
| self.assertEqual(be('2*(a, b, 3*(c, d), e)'), 'a,b,c,d,c,d,c,d,e,a,b,c,d,c,d,c,d,e') |
| |
| def testBracketTokens(self): |
| s = BitStream('3*(0x0, 0b1)') |
| self.assertEqual(s, '0x0, 0b1, 0x0, 0b1, 0x0, 0b1') |
| s = pack('2*(uint:12, 3*(7, 6))', *range(3, 17)) |
| a = s.unpack('12, 7, 6, 7, 6, 7, 6, 12, 7, 6, 7, 6, 7, 6') |
| self.assertEqual(a, list(range(3, 17))) |
| b = s.unpack('2*(12,3*(7,6))') |
| self.assertEqual(a, b) |
| |
| def testPackCodeDicts(self): |
| self.assertEqual(sorted(bitstring.REPLACEMENTS_BE.keys()), |
| sorted(bitstring.REPLACEMENTS_LE.keys())) |
| self.assertEqual(sorted(bitstring.REPLACEMENTS_BE.keys()), |
| sorted(bitstring.PACK_CODE_SIZE.keys())) |
| for key in bitstring.PACK_CODE_SIZE: |
| be = pack(bitstring.REPLACEMENTS_BE[key], 0) |
| le = pack(bitstring.REPLACEMENTS_LE[key], 0) |
| self.assertEqual(be.len, bitstring.PACK_CODE_SIZE[key] * 8) |
| self.assertEqual(le.len, be.len) |
| |
| # These tests don't compile for Python 3, so they're commented out to save me stress. |
| #def testUnicode(self): |
| #a = ConstBitStream(u'uint:12=34') |
| #self.assertEqual(a.uint, 34) |
| #a += u'0xfe' |
| #self.assertEqual(a[12:], '0xfe') |
| #a = BitStream('0x1122') |
| #c = a.byteswap(u'h') |
| #self.assertEqual(c, 1) |
| #self.assertEqual(a, u'0x2211') |
| |
| #def testLongInt(self): |
| #a = BitStream(4L) |
| #self.assertEqual(a, '0b0000') |
| #a[1:3] = -1L |
| #self.assertEqual(a, '0b0110') |
| #a[0] = 1L |
| #self.assertEqual(a, '0b1110') |
| #a *= 4L |
| #self.assertEqual(a, '0xeeee') |
| #c = a.byteswap(2L) |
| #self.assertEqual(c, 1) |
| #a = BitStream('0x11223344') |
| #a.byteswap([1, 2L]) |
| #self.assertEqual(a, '0x11332244') |
| #b = a*2L |
| #self.assertEqual(b, '0x1133224411332244') |
| #s = pack('uint:12', 46L) |
| #self.assertEqual(s.uint, 46) |
| |
| |
| class UnpackWithDict(unittest.TestCase): |
| def testLengthKeywords(self): |
| a = ConstBitStream('2*13=100, 0b111') |
| x, y, z = a.unpack('n, uint:m, bin:q', n=13, m=13, q=3) |
| self.assertEqual(x, 100) |
| self.assertEqual(y, 100) |
| self.assertEqual(z, '111') |
| |
| def testLengthKeywordsWithStretch(self): |
| a = ConstBitStream('0xff, 0b000, 0xf') |
| x, y, z = a.unpack('hex:a, bin, hex:b', a=8, b=4) |
| self.assertEqual(y, '000') |
| |
| def testUnusedKeyword(self): |
| a = ConstBitStream('0b110') |
| x, = a.unpack('bin:3', notused=33) |
| self.assertEqual(x, '110') |
| |
| def testLengthKeywordErrors(self): |
| a = pack('uint:p=33', p=12) |
| self.assertRaises(ValueError, a.unpack, 'uint:p') |
| self.assertRaises(ValueError, a.unpack, 'uint:p', p='a_string') |
| |
| |
| class ReadWithDict(unittest.TestCase): |
| def testLengthKeywords(self): |
| s = BitStream('0x0102') |
| x, y = s.readlist('a, hex:b', a=8, b=4) |
| self.assertEqual((x, y), (1, '0')) |
| self.assertEqual(s.pos, 12) |
| |
| def testBytesKeywordProblem(self): |
| s = BitStream('0x01') |
| x, = s.unpack('bytes:a', a=1) |
| self.assertEqual(x, b'\x01') |
| |
| s = BitStream('0x000ff00a') |
| x, y, z = s.unpack('12, bytes:x, bits', x=2) |
| self.assertEqual((x, y, z), (0, b'\xff\x00', '0xa')) |
| |
| |
| |
| class PeekWithDict(unittest.TestCase): |
| def testLengthKeywords(self): |
| s = BitStream('0x0102') |
| x, y = s.peeklist('a, hex:b', a=8, b=4) |
| self.assertEqual((x, y), (1, '0')) |
| self.assertEqual(s.pos, 0) |
| |
| ##class Miscellany(unittest.TestCase): |
| ## |
| ## def testNumpyInt(self): |
| ## try: |
| ## import numpy |
| ## a = ConstBitStream(uint=numpy.uint8(5), length=3) |
| ## self.assertEqual(a.uint, 5) |
| ## except ImportError: |
| ## # Not to worry |
| ## pass |
| |
| class BoolToken(unittest.TestCase): |
| def testInterpretation(self): |
| a = ConstBitStream('0b1') |
| self.assertEqual(a.bool, True) |
| self.assertEqual(a.read('bool'), True) |
| self.assertEqual(a.unpack('bool')[0], True) |
| b = ConstBitStream('0b0') |
| self.assertEqual(b.bool, False) |
| self.assertEqual(b.peek('bool'), False) |
| self.assertEqual(b.unpack('bool')[0], False) |
| |
| def testPack(self): |
| a = pack('bool=True') |
| b = pack('bool=False') |
| self.assertEqual(a.bool, True) |
| self.assertEqual(b.bool, False) |
| c = pack('4*bool', False, True, 'False', 'True') |
| self.assertEqual(c, '0b0101') |
| |
| def testAssignment(self): |
| a = BitStream() |
| a.bool = True |
| self.assertEqual(a.bool, True) |
| a.hex = 'ee' |
| a.bool = False |
| self.assertEqual(a.bool, False) |
| a.bool = 'False' |
| self.assertEqual(a.bool, False) |
| a.bool = 'True' |
| self.assertEqual(a.bool, True) |
| a.bool = 0 |
| self.assertEqual(a.bool, False) |
| a.bool = 1 |
| self.assertEqual(a.bool, True) |
| |
| def testErrors(self): |
| self.assertRaises(bitstring.CreationError, pack, 'bool', 'hello') |
| self.assertRaises(bitstring.CreationError, pack, 'bool=true') |
| self.assertRaises(bitstring.CreationError, pack, 'True') |
| self.assertRaises(bitstring.CreationError, pack, 'bool', 2) |
| a = BitStream('0b11') |
| self.assertRaises(bitstring.InterpretError, a._getbool) |
| b = BitStream() |
| self.assertRaises(bitstring.InterpretError, a._getbool) |
| self.assertRaises(bitstring.CreationError, a._setbool, 'false') |
| |
| def testLengthWithBoolRead(self): |
| a = ConstBitStream('0xf') |
| self.assertRaises(ValueError, a.read, 'bool:0') |
| self.assertRaises(ValueError, a.read, 'bool:1') |
| self.assertRaises(ValueError, a.read, 'bool:2') |
| |
| |
| class ReadWithIntegers(unittest.TestCase): |
| def testReadInt(self): |
| a = ConstBitStream('0xffeedd') |
| b = a.read(8) |
| self.assertEqual(b.hex, 'ff') |
| self.assertEqual(a.pos, 8) |
| b = a.peek(8) |
| self.assertEqual(b.hex, 'ee') |
| self.assertEqual(a.pos, 8) |
| b = a.peek(1) |
| self.assertEqual(b, '0b1') |
| b = a.read(1) |
| self.assertEqual(b, '0b1') |
| |
| def testReadIntList(self): |
| a = ConstBitStream('0xab, 0b110') |
| b, c = a.readlist([8, 3]) |
| self.assertEqual(b.hex, 'ab') |
| self.assertEqual(c.bin, '110') |
| |
| |
| class FileReadingStrategy(unittest.TestCase): |
| def testBitStreamIsAlwaysRead(self): |
| a = BitStream(filename='smalltestfile') |
| self.assertTrue(isinstance(a._datastore, bitstring.ByteStore)) |
| f = open('smalltestfile', 'rb') |
| b = BitStream(f) |
| self.assertTrue(isinstance(b._datastore, bitstring.ByteStore)) |
| |
| def testBitsIsNeverRead(self): |
| a = ConstBitStream(filename='smalltestfile') |
| self.assertTrue(isinstance(a._datastore._rawarray, bitstring.MmapByteArray)) |
| f = open('smalltestfile', 'rb') |
| b = ConstBitStream(f) |
| self.assertTrue(isinstance(b._datastore._rawarray, bitstring.MmapByteArray)) |
| |
| |
| class Count(unittest.TestCase): |
| def testCount(self): |
| a = ConstBitStream('0xf0f') |
| self.assertEqual(a.count(True), 8) |
| self.assertEqual(a.count(False), 4) |
| |
| b = BitStream() |
| self.assertEqual(b.count(True), 0) |
| self.assertEqual(b.count(False), 0) |
| |
| def testCountWithOffsetData(self): |
| a = ConstBitStream('0xff0120ff') |
| b = a[1:-1] |
| self.assertEqual(b.count(1), 16) |
| self.assertEqual(b.count(0), 14) |
| |
| |
| class ZeroBitReads(unittest.TestCase): |
| def testInteger(self): |
| a = ConstBitStream('0x123456') |
| self.assertRaises(bitstring.InterpretError, a.read, 'uint:0') |
| self.assertRaises(bitstring.InterpretError, a.read, 'float:0') |
| |
| #class EfficientBitsCopies(unittest.TestCase): |
| # |
| # def testBitsCopy(self): |
| # a = ConstBitStream('0xff') |
| # b = ConstBitStream(a) |
| # c = a[:] |
| # d = copy.copy(a) |
| # self.assertTrue(a._datastore is b._datastore) |
| # self.assertTrue(a._datastore is c._datastore) |
| # self.assertTrue(a._datastore is d._datastore) |
| |
| class InitialiseFromBytes(unittest.TestCase): |
| def testBytesBehaviour(self): |
| a = ConstBitStream(b'uint:5=2') |
| b = ConstBitStream(b'') |
| c = ConstBitStream(bytes=b'uint:5=2') |
| if b'' == '': |
| # Python 2 |
| self.assertEqual(a, 'uint:5=2') |
| self.assertFalse(b) |
| self.assertEqual(c.bytes, b'uint:5=2') |
| else: |
| self.assertEqual(a.bytes, b'uint:5=2') |
| self.assertFalse(b) |
| self.assertEqual(c, b'uint:5=2') |
| |
| def testBytearrayBehaviour(self): |
| a = ConstBitStream(bytearray(b'uint:5=2')) |
| b = ConstBitStream(bytearray(4)) |
| c = ConstBitStream(bytes=bytearray(b'uint:5=2')) |
| self.assertEqual(a.bytes, b'uint:5=2') |
| self.assertEqual(b, '0x00000000') |
| self.assertEqual(c.bytes, b'uint:5=2') |
| |
| |
| class CoverageCompletionTests(unittest.TestCase): |
| def testUeReadError(self): |
| s = ConstBitStream('0b000000001') |
| self.assertRaises(bitstring.ReadError, s.read, 'ue') |
| |
| def testOverwriteWithSelf(self): |
| s = BitStream('0b1101') |
| s.overwrite(s) |
| self.assertEqual(s, '0b1101') |
| |
| |
| class Subclassing(unittest.TestCase): |
| |
| def testIsInstance(self): |
| class SubBits(BitStream): pass |
| a = SubBits() |
| self.assertTrue(isinstance(a, SubBits)) |
| |
| def testClassType(self): |
| class SubBits(BitStream): pass |
| self.assertEqual(SubBits().__class__, SubBits) |
| |
| |
| class BytesProblems(unittest.TestCase): |
| |
| def testOffsetButNoLength(self): |
| b = BitStream(bytes=b'\x00\xaa', offset=8) |
| self.assertEqual(b.hex, 'aa') |
| b = BitStream(bytes=b'\x00\xaa', offset=4) |
| self.assertEqual(b.hex, '0aa') |
| |
| def testInvert(self): |
| b = BitStream(bytes=b'\x00\xaa', offset=8, length=8) |
| self.assertEqual(b.hex, 'aa') |
| b.invert() |
| self.assertEqual(b.hex, '55') |
| |
| def testPrepend(self): |
| b = BitStream(bytes=b'\xaa\xbb', offset=8, length=4) |
| self.assertEqual(b.hex, 'b') |
| b.prepend('0xe') |
| self.assertEqual(b.hex, 'eb') |
| b = BitStream(bytes=b'\x00\xaa', offset=8, length=8) |
| b.prepend('0xee') |
| self.assertEqual(b.hex, 'eeaa') |
| |
| def testByteSwap(self): |
| b = BitStream(bytes=b'\x01\x02\x03\x04', offset=8) |
| b.byteswap() |
| self.assertEqual(b, '0x040302') |
| |
| def testBinProperty(self): |
| b = BitStream(bytes=b'\x00\xaa', offset=8, length=4) |
| self.assertEqual(b.bin, '1010') |