我正在读贾斯汀·塞茨( Justin )的一本书,书名为“黑帽子”( Black ),为黑客和受虐者编写Python程序。
这是书中的代码:
import socket
import os
import struct
from ctypes import *
# host to listen
host = "10.0.2.15"
# our IP header
class IP(Structure):
_fields_ = [
("ihl", c_ubyte, 4),
("version", c_ubyte,4),
("tos", c_ubyte),
("len", c_ushort),
("id", c_ushort),
("offset", c_ubyte),
("ttl", c_ubyte),
("protocol_num", c_ubyte),
("sum", c_ubyte),
("src", c_ulong),
("dst", c_ulong)
]
def __new__(cls,socket_buffer=None):
return cls.from_buffer_copy(socket_buffer)
在这段代码中,函数new中有一个名为from_buffer_copy()
的函数。它是ctypes
Python库中的一个函数。
我想知道它能做什么,使用它的语法是什么?
Python文档说语法是from_buffer_copy(source[, offset])
。我已经找到了使用这种语法的例子,但是文档提供的用法定义对我来说是模糊的。
Python:副本()
在这本书中,我看到这个函数只有一个参数,那么它是如何实现的呢?
任何帮助都将不胜感激。
发布于 2022-06-18 08:27:25
在文档from_buffer_copy(source[, offset])
中,方括号表示第二个参数是可选的。在代码中,它如下所示,其中给出了可选的第二个参数的默认值:
def from_buffer_copy(self, source, offset=0): ...
下面是.from_buffer_copy
和.from_buffer
之间区别的一个工作示例,并给出了解释。这些函数用于根据作为字节数据接收的内存结构创建Python类:
import ctypes as ct
# A simple ctypes structure with two 4-byte fields.
# It will need at least 8 bytes of data to build this structure.
class Demo(ct.Structure):
_fields_ = (('first', ct.c_uint32),
('second', ct.c_uint32))
# defines the print representation to easily look at the fields
def __repr__(self):
return f'Demo(first=0x{self.first:08x}. second=0x{self.second:08x})'
# A 10-byte read-only bytes buffer.
# Extra bytes to demonstrate the offset parameter.
buf = bytes([1,2,3,4,5,6,7,8,9,10])
try:
# This syntax constructs a Demo object that refers to the *same*
# memory that buffer occupies, starting from the default offset of 0,
# but to do so requires a writeable buffer
demo1 = Demo.from_buffer(buf)
except TypeError as e:
print(e) # This error will print
# This builds the Demo object from a copy of the memory,
# so a read-only buffer can be used, starting from default offset 0.
demo2 = Demo.from_buffer_copy(buf)
print(demo2)
# This builds the object from offset 2, so the values of "first" and
# "second" will be different.
demo3 = Demo.from_buffer_copy(buf,2)
print(demo3)
# This is a writable buffer, so from_buffer will work
buf2 = bytearray([1,2,3,4,5,6,7,8])
demo4 = Demo.from_buffer(buf2)
print(demo4)
# Since demo4 references the *same* memory, changing writable buf2
# also changes demo4
buf2[1] = 0xff
print(demo4)
输出:
underlying buffer is not writable # error message from demo1 attempt
Demo(first=0x04030201. second=0x08070605) # demo2 copied from offset 0
Demo(first=0x06050403. second=0x0a090807) # demo3 copied from offset 2
Demo(first=0x04030201. second=0x08070605) # demo4
Demo(first=0x0403ff01. second=0x08070605) # demo4 after write to buf2
https://stackoverflow.com/questions/72667653
复制相似问题