在python中写入内存中的特定地址

Posted

技术标签:

【中文标题】在python中写入内存中的特定地址【英文标题】:Writing to particular address in memory in python 【发布时间】:2016-08-01 10:30:34 【问题描述】:

我知道 python 是一种高级语言,它可以自行管理内存分配等,用户/开发人员不需要像 c、c++ 等其他语言那样担心。

但是有没有办法让我们可以在 python 中的特定内存地址中写入一些值

我知道 id() ,如果转换为十六进制类型可以给出十六进制位置,但我们如何在一个位置写入。

【问题讨论】:

即使在 C 语言中,您也无法在硬代码内存位置上进行写入,除非您在某些可以绝对访问内存的系统上工作。 ***.com/questions/11207783/… 不是重复的,但请参阅此处的讨论:***.com/questions/8250625/… 【参考方案1】:

首先,正如 cmets 中所指出的,这是一个相当大的问题,为什么您会想要做这样的事情。您应该仔细考虑是否有其他选择。

话虽如此,但通过扩展很容易做到这一点。 Python 本身的构建使得extend it via C or C++ 很容易。通过Cython 更容易做到这一点。

以下概述了如何构建一个 Python 可调用函数,该函数采用整数 pv。它将值v 写入数字地址为p 的内存地址。

注意再次请注意,这只是一个技术答案。整个操作以及其中的部分操作都值得商榷,您应该考虑您想要实现的目标。

创建一个文件modify.h,内容为:

void modify(int p, int v);

创建一个文件modify.c,内容为:

#include "modify.h"

void modify(int p, int v)

    *(int *)(p) = v;

创建一个文件modify.pyx,内容为:

cdef extern from "modify.h"
     void modify(int p, int v)

def py_modify(p, v):
    modify(p, v)

最后,创建setup.py,内容为:

from distutils.core import setup
from distutils.extension import Extension
from Cython.Distutils import build_ext

ext_modules = [Extension(
    name="modify",
    sources=["modify.pyx", "modify.c"])]

setup(
    name = 'modify',
    cmdclass = 'build_ext': build_ext,
    ext_modules = ext_modules,
    # ext_modules = cythonize(ext_modules)  ? not in 0.14.1
    # version=
    # description=
    # author=
    # author_email=
)

我希望您将此答案仅用于学习目的。

【讨论】:

此解决方案是否适用于以下用途:我想编写一个带有一些按钮作用于数据的 GUI,创建一个 .exe 程序并允许人们将其安装在他们的计算机上。所以我需要能够在启动时让程序调用以前保存在“某处”的数据并在每次启动时重用它【参考方案2】:

在给定内存地址的情况下,您可以使用 ctypes 修改任何用户空间内存位置。

例如 numpy 数组公开了数组缓冲区的原始地址,因此您可以像这样访问/修改值:

import numpy as np
import ctypes

a=np.random.rand(2,3)
addr=a.__array_interface__['data'][0]
p=ctypes.c_void_p(addr)
pf=ctypes.cast(p, ctypes.POINTER(ctypes.c_double))
assert pf[0] == a[0,0]
assert pf[1] == a[0,1]
assert pf[3] == a[1,0]

但是你不能轻易地将这个技巧应用到像 int 这样的普通 python 变量,因为 id() 返回 python 对象的起始地址,而不是存储值的确切位置,请检查:

from ctypes import *
a=123456
p=cast(c_void_p(id(a)), POINTER(c_int))
print(p[:10])

从结果中我们可以看到该值实际上在偏移量 6*4=24

[1, 0, -1792371528, 127, 1, 0, 123456, 1, 1, 0]

【讨论】:

【参考方案3】:

Python 本身不包含任何允许程序员直接访问内存的工具。这意味着遗憾(或高兴,取决于您的观点)您的问题的答案是“否”。

【讨论】:

AFAIK,“Python 本身”不允许 GPU 操作或套接字消息传递。它只允许通过扩展和库来这样做。所以答案可能是严格正确的,但您可以将其基本原理应用于实际使用 Python 的其他几个问题。【参考方案4】:

我不知道怎么做,但我知道(一)为什么。直接写入寄存器允许设置特定的微控制器。例如,配置端口或外围设备。这通常在 C 中完成(更接近硬件),但如果您出于其他原因想使用 Python,这将是一个不错的功能。

【讨论】:

以上是关于在python中写入内存中的特定地址的主要内容,如果未能解决你的问题,请参考以下文章

显式地向内存中的特定地址/位置分配或访问值?

内存管理

python 如何将数据写入某个csv文件的特定位置?

如何在java中的文件中循环写入或附加字符串?

从python内存中的MPEG(.ts)文件中提取音频,而不将MPEG写入文件

Python如何查看变量在内存中的地址