英文:
Getting "pointer being freed was not allocated" error with using a go shared lib in python
问题
这里发生了什么情况?
这个错误是由于在运行PyCharm中的共享库时出现的。错误信息表明指针被释放,但并没有分配内存给它。这可能是由于在C代码中的FreeCString
函数中出现了问题。
根据你提供的代码,我看到你在Go代码中使用了C.free
函数来释放内存,但是在C代码中并没有看到相应的内存分配操作。这可能导致了指针被释放但未分配的错误。
你可以检查一下在Go代码中是否有其他地方分配了内存给这个指针,或者在FreeCString
函数中确保只有在指针被分配内存后才进行释放操作。
另外,你的Python代码中也有一个问题。在调用FreeCString
函数之后,你打印了指针b
的值,但是在释放内存后,指针已经无效,所以打印的结果可能是不可预测的。你可以尝试将打印语句放在释放内存之前。
希望这些信息对你有帮助!如果你有任何其他问题,请随时提问。
英文:
I keep on getting this error whenever I run the shared lib in pycharm:
Python(20566,0x116d67dc0) malloc: *** error for object 0x5b6222f0: pointer being freed was not allocated
Python(20566,0x116d67dc0) malloc: *** set a breakpoint in malloc_error_break to debug
Abort trap: 6
Here is my go code turned into a share lib:
package main
// #include <stdio.h>
// #include <stdlib.h>
// #include <errno.h>
import "C"
//export FreeCString
func FreeCString(ptr *C.char) {
C.free(unsafe.Pointer(ptr))
}
//export TestString
func TestString() *C.char {
return C.CString("Hello World")
}
Here is my py code:
from ctypes import *
from ctypes import cdll
lib = cdll.LoadLibrary('./test.so')
b = lib.TestString()
lib.FreeCString(b)
print(b)
What is happening here?
答案1
得分: 2
首先,你在释放之后调用了print(b)
,这显然是一个坏主意。
更重要的是,你没有告诉Python关于lib.TestString
的返回类型,所以Python会做出假设。特别是:
> b = lib.TestString()
由于你没有设置lib.TestString.restype
,Python认为返回类型是普通的int
。所以b
被设置为一个32位的int
,它是从一个64位的c_void_p
中丢弃了32位而得到的。(要修复这个问题,将restype
设置为c_void_p
。对于你调用的所有函数,你也应该设置argtypes
,尽管在你可能使用的机器上,这可能不重要。)
> lib.FreeCString(b)
这将间接调用free((void *)(int)malloc(some_size))
。由于指针值经过int
的传递而受损,free
调用立即失败,程序在到达应该存储在b
中的值的错误使用之前停止。
英文:
For one thing, you're calling print(b)
after freeing it, which is clearly a bad idea.
Probably more important, you never told Python about lib.TestString
's return type, so Python will make assumptions. In particular:
> b = lib.TestString()
Since you never set lib.TestString.restype
, Python believes the return type is plain int
. So b
is set to a 32-bit int
that results from throwing away 32 of the 64 bits of a 64-bit c_void_p
. (To fix this, set the restype
to c_void_p
. You should set the argtypes
as well for all functions you call, although on the machine you're probably using, this probably won't matter.)
> lib.FreeCString(b)
This then calls, indirectly, free((void *)(int)malloc(some_size))
. As the pointer value has been damaged by the passage through int
, the free
call fails right then, stopping the program before you get to the bad use-after-free of the value that should have been stored in b
.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论