0

I'm trying to convert an Integer into a 4 byte array with struct.pack(). I'm getting some really odd results though.

import struct
# Using Big Endian Order

struct.pack('>I', 5000) # works fine
>>>'\x00\x00\x13\x88'

struct.pack('>I', 50000) # has a weird "P" variable which the documentation says shouldn't occur with Endian order.
>>>'\x00\x00\xc3P'

Could someone explain what is happening with the 2nd result? I'm expecting an output of 0x0000C350.

Specifically, I'm trying to send this byte array through a socket. e.g.

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(IP, PORT)
s.send(Message) # I need this message to be Big Endian, Byte array representation of the number.

I'm assigning the result of struct.pack() to Message. The Message is meant to be a 4 byte unsigned integer.

3 Answers 3

2

The 'P' you're seeing is just the ascii representation of that particular byte. The ascii code value of 'P' is 80, which is 0x50 in hex:

>>> ord('P')
80
>>> hex(80)
'0x50'
>>> 

Python just displays the bytes in a format that makes it look like an ascii string. It really is a valid-byte array, though:

>>> bytearray((0x00, 0x00, 0xc3, 0x50)) == struct.pack(">I", 50000)
True

That's why you get the expected value when you convert to the byte string to hex. So in short, you're getting the right value back, and you should be ok to send it as-is over the network.

Sign up to request clarification or add additional context in comments.

2 Comments

Oh wow, I would have never seen that! I just assumed it was a format character. Well that makes sense, thanks.
On a releated note, there's a (very) long thread on python-ideas right now that proposes not displaying byte strings as ASCII to help avoid this sort of confusion: mail.python.org/pipermail/python-ideas/2014-September/….
1
>>> bary = struct.pack('>I', 50000)
>>> print(len(bary),type(bary))
(4, <type 'str'>)
>>> "\x00\x00\xc3\x50" == bary
True

bary is binary string,you can use this on the socket.

Comments

0

You can use his.

struct.pack('>I', 50000).encode("hex") '0000c350'

3 Comments

Well that definitely returns the correct hex value. However I'm using this sending this through a socket, so I need the actual byte values. Any way to get the correct byte array representation?
You could elaborate a little in the body of your answer.
Alright, I added a little more code of why I need a byte array

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.