如何将int转换为十六进制并将十六进制写入文件?

时间:2019-01-09 18:25:09

标签: python type-conversion int hex python-2.x

我想在Python 2.7.13中执行以下操作:

  • 将int值转换为十六进制(58829405413336430应该变成d101085402656e
  • 向创建的十六进制添加“有效载荷”(如c1234这样的简单字符串)
  • 十六进制写入文件

我的代码当前如下所示:

mime=58829405413336430
payload="c9999"

fw_file=open('testhex', 'wb')
fw_file.write("%x" % mime)
fw_file.write(str(payload).encode("hex"))
fw_file.close()

然后我得到以下文件(在Debian上使用xxd

xxd HACKEDTOGETHER
00000000: 6431 3031 3038 3534 3032 3635 3665 3633  d101085402656e63
00000010: 3339 3339 3339 3339                      39393939

这不是我需要的不是。我需要一个看起来像这样的文件:

xxd WORKING
00000000: d101 0854 0265 6e63 3939 3939            ...T.enc9999

我的理解如下:

"%x" % mime将我的int转换为十六进制,但它被写为String。 encode正确地做到了,但这不适用于整数。我该如何规避这种行为,并在文件中写入“纯”十六进制?如果在Python 2中无法做到这一点,我也可以使用Python 3。

这是我对StackOverflow的第一个问题,请告诉我是否应该做其他事情。

1 个答案:

答案 0 :(得分:2)

部分问题是"%x" % mime的结果是一对十六进制个字符 的字符串-在这种情况下,"d101085402656e"代表整数的值mime采用这种格式,因此就是要写入文件的内容。但是,需要的是构成整数本身的实际字节值。

在Python 3中,可以轻松地解决此问题,而可以使用该版本的int类型中添加的内置方法to_bytes()来解决,但是在Python 2.x中,它必须另一种方式。

由于您使用str(payload).encode("hex")也会返回十六进制字符串表示形式,因此也存在类似的问题,而不是payload中已经存在的每个字符的实际字节值,这是必需的。幸运的是,在这种情况下,可以使用Python 2.x内置的bytearray类轻松完成所需的操作。

在我写的一个函数的版本下面,该函数作为answer的一部分发布到相关的question上,该函数可以处理mime值问题。

该函数定义之后的代码显示了在这种情况下如何使用它以及bytearray类,以将正确的二进制数据写入文件。

def int_to_bytes(n, minlen=0):
    """ Convert integer to bytearray with optional minimum length. 
    """
    if n > 0:
        arr = []
        while n:
            n, rem = n >> 8, n & 0xff
            arr.append(rem)
        b = bytearray(reversed(arr))
    elif n == 0:
        b = bytearray(b'\x00')
    else:
        raise ValueError('Only non-negative values supported')

    if minlen > 0 and len(b) < minlen: # zero padding needed?
        b = (minlen-len(b)) * '\x00' + b
    return b

mime = 58829405413336430
payload = 'c9999'

with open('testhex', 'wb') as fw_file:
    fw_file.write(int_to_bytes(mime))
    fw_file.write(bytearray(payload))

这是它生成的testhex文件内容的十六进制转储(使用Python 2.7.15):

00000000h: D1 01 08 54 02 65 6E 63 39 39 39 39             ; Ñ..T.enc9999