2011-12-29 3 views
0

Я пытаюсь выполнить проверку CRC в сетевом протоколе. Расчет CRC осуществляется через PyCRC lib.Python network convert byte

PyCRC генерирует контрольную сумму для данного пакета и возвращает результат: CB3D9FD1

Когда я пытаюсь отправить его на проволоке, как-то Python изменить свою строку и преобразовать его в ASCII в Hex, например, :

Crc = "CB3D9FD1" 
... 
buffer = "\x41\x42\x43\x44"+crc 
... 
s.send(buffer) 

на проводе я буду видеть, что:

\x41\x42\x43\x44***\x43\x42\x33\x44\x39\x46\x44\x31*** 

Вместо:

\x41\x42\x43\x44***\xCB\x3D\x9F\xD1*** 

Любые способы решения этой проблемы легко?

Спасибо!

+0

Вам нужно будет указать дополнительную информацию о том, что вы делаете. Код помогает. Наименьший код, демонстрирующий проблему, идеален. Не стесняйтесь создавать короткий демонстрационный скрипт, который терпит неудачу, и ** обновите ** свой вопрос с ним. Python ничего плохого не делает; ваш скрипт имеет небольшую ошибку. –

+2

Почему вы идете по этому маршруту? Посмотрите на этот ответ для альтернативы: http: // stackoverflow.com/questions/1742866/compute-crc-of-file-in-python – Joe

ответ

2

На самом деле, не конвертируйте CRC в ASCII. Держите его в шестнадцатеричном, а затем упаковать его в строку байт с использованием struct.pack ::

buffer += struct.pack("L", crc) 
+0

Yup Я пробовал это раньше, только проблема - это struct return this: *** struct.error: невозможно преобразовать аргумент в integer *** – n00bz0r

+1

Я бы также рекомендуется использовать восклицательный знак (''! L'') для обеспечения порядка байтов сети (возможно, необходимо). – jcollado

+0

@ n00bz0r убедитесь, что ваш crc является целым числом, возможно, сначала проанализируйте его: int (crc, 16). – Bashwork

0

Если вы превратили CRC в строку, содержащей «CB3D9FD1», то правильной последовательность байт 0x43 0x42 0x33 0x44 0x39 0x46 0x44 0x31. Не преобразовывайте крик в строку или не разбирайте строку как шестнадцатеричный (по два символа для каждого байта).

0

Назначив его так: crc = "CB3D9FD1", вы говорите make var crc и 8-байтовую строку. Поскольку @Bashwork говорит, что вам нужно преобразовать его из шестнадцатеричной строки в числовую или сохранить ее числовой. Назначьте его 0x следующим образом, чтобы получить числовое значение: crc=0xCB3D9FD1.

пакет («L», х) означает, что я даю вам что х (должно быть) в целое, и я хочу, чтобы вы упаковать его как неподписанных долгое.
Вы получаете «struct.error: невозможно преобразовать аргумент в целое число», потому что вы передаете пакет («L», ...) строку «CB3D9FD1».

RTFM, что "L" и "I" и другие аргументы означают: https://docs.python.org/2/library/struct.html

Упакуйте CRC, как длинное целое работает, и вы получите 0s отступы к 64bits (на моем компьютере YMMV).

>>> from struct import pack 
>>> crc=0xcb3d9fd1 
>>> repr(crc) 
'3409813457' 
>>> pack("L", crc) 
'\xd1\x9f=\xcb\x00\x00\x00\x00' 
>>> print crc 
3409813457 

Может быть, вы хотите использовать пакет ("I", ...): чтобы получить 32бит

>>> pack("I",crc) 
'\xd1\x9f=\xcb' 

потерпеть неудачу, если попытаться собрать строку CRC с колодой ("L", ...):

>>> crc = "CB3D9FD1" 
>>> repr(crc) 
"'CB3D9FD1'" 
>>> pack("L", crc) 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
struct.error: cannot convert argument to integer