Joshua Faust
Joshua Faust

Reputation: 306

Complex Binary Analysis - Bit flipping and writing to Binary file (Python)

I have a .bin file that needs to be read in, bit flipped, and written back to a binary file. For example:

RAW INPUT:    \xdd\x00 = 1101110100000000
FINAL OUTPUT: \x00\xbb = 0000000010111011

RAW INPUT:    \x33\x00 = 0011001100000000
FINAL OUTPUT: \x00\xcc = 0000000011001100

I'm having difficulties during this translation where some of the bytes will be translated and others will not. In the example above, I can easily flip the binary bits and get \x00\xbb from \xdd\x00, but the translation does not work for the \x33\00 to \x00\xcc

What I am currently doing is reading 1 byte in at a time, translating it into an integer, getting a binary value, flipping the bits, and then storing that to a new binary file.

data = binary_file.read(1)
while data:
    bits = ord(data)                        # Integer Value
    binary = ("{0:b}".format(bits))         # Binary value of Integer
    flipped = 0
    while bits:
        flipped <<=1
        flipped += bits & 1
        bits >>= 1
    data = binary_file.read(1)
    tmp = bytes([flipped])
    output_file.write(tmp)

Once I have the new file completed, I then open it back up, read two bytes in at a time, and flip them like so:

with open('H:/gitKraken/test.bin', 'rb') as tmp_file:
    print('Flipping Bytes')
    data = tmp_file.read(2)
    final_output = open('final.bin', 'wb')
    while data:
        flip = (data[0], data[1])
        final_output.write(bytes([flip[1]]))
        final_output.write(bytes([flip[0]]))
        data = tmp_file.read(2)

The values that I am getting are not what I was expecting:

This method works on the following bytes:
Raw Data: \x00\x00\xdd\x00
Expected (Wanted) Value: \x00\x00\x00\xbb
Final Data: \x00\x00\x00\xbb

However, the method does not work on the following bytes:
Raw Data: \x00\x00\x33\x00
Expected (Wanted) Value:: \x00\x00\x00\xcc
Final Data: \x00\x00\x003

Any ideas on how I can improve this process and make it actually work?


EDIT1:

Here is the effective process flow of how exactly I need to treat each byte and the end product:

Hex Bytes (Raw Data)      44           88          22          0
Binary Representation   01000100    10001000    00100010    00000000
Reverse Binary Order    00100010    00010001    01000100    00000000
New Hex Bytes              22          11          44          00
Flip Hex bytes(Final Data) 11          22          00          44

Here is another example using the bytes \x00\x00\xdd\x00

Hex Bytes (Raw Data)       00          00          dd          00
Binary Representation   00000000    00000000    11011101    00000000
Reverse Binary Order    00000000    00000000    10111011    00000000
New Hex Bytes              00          00          bb          00
Flip Hex bytes(Final Data) 00          00          00          bb

Upvotes: 1

Views: 1216

Answers (1)

Thierry Lathuille
Thierry Lathuille

Reputation: 24233

You could do it like this:

with open('test.bin', 'rb') as f:
    data = f.read()

def reverse(b):
    return int('{:08b}'.format(b)[::-1], 2)

out = bytearray()   
for i in range(0, len(data), 2):
    out.extend((reverse(data[i+1]), reverse(data[i])))

with open('out.bin', 'wb') as f:
    f.write(out)

The reverse part is from nneonneo's answer to Reversing bits of Python integer

Upvotes: 1

Related Questions