'xoring negative number doesn't return the same value with ^ and xor()

I don't understand why these doesn't return the same values.

150 ^ -91

-205

but

from pwn import *
xor(150,-91)

b'3'

Of course, chr(-205) is invalid and different to '3'



Solution 1:[1]

It looks like the library packs the arguments into unsigned values:

strs = [packing.flat(s, word_size = 8, sign = False, endianness = 'little') for s in args]

The two's complement representation for -91 is 0b10100101 in binary, that's 165 when converted to unsigned integer:

>>> 0b10100101
165
>>> from pwn import *
>>> flat(150, word_size=8, sign=False, endianness='little')
b'\x96'
>>> flat(-91, word_size=8, sign=False, endianness='little')
b'\xa5'
>>> 0x96
150
>>> 0xa5
165
>>> 150 ^ 165
51
>>> chr(51)
'3'

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 HTF