c语言 - 内存免费抛出 segFault



>我正在使用链接列表实现符号表,代码工作正常,但代码中存在内存泄漏,

我有以下结构

struct node
{
char* pcKey;
void* pvValue;
struct node *next;
};
struct _Sym
{
int totalBindings;
struct node *node;
};

添加我有sym_new为符号实例分配内存的方法

sym Sym_new (void)
{
_Sym *m_SymTable_t = (_Sym*) malloc (sizeof(_Sym));
if(m_SymTable_t == NULL)
{
return NULL;
}
else
{
m_SymTable_t->totalBindings = 0;
m_SymTable_t->node = NULL;
return m_SymTable_t;
}//endif
}

我正在根据字符串长度为其他函数中的键和值分配内存。

免费方法是

typedef struct _Sym *Sym;
void Sym_free (Sym m_SymTable_t)
{
assert(m_SymTable_t != NULL);
struct node* temp = m_SymTable_t->node;
struct node *currentBinding = NULL;
while(temp != NULL)
{
currentBinding = temp;
temp = temp -> next;
//Removing comment for the below line throws segfault
//free(currentBinding -> pcKey);
//free(currentBinding -> pvValue);
free(currentBinding);
}
free(m_SymTable_t);
}

完全释放符号的正确方法是什么?

我已经在链接上传了我的symTable_Link.cpp文件

变量pcKeypvValue可能应该初始化为Sym_new()函数中的null。否则,它们可能包含任何旧值。这是因为malloc不一定将分配的内存归零:它只是分配了一大块内存,因此内存可能会被垃圾填满。

因此,如果由于某种原因没有为新创建的对象调用sym_put()这些指针可能会指向无效内存,并在您调用free()段错误时。如果您将它们初始化为nullfree()只会忽略它们,并且不会尝试释放内存。

您可以使用一种"hacky">调试技术来检查pcKeypvValue变量是否肯定是由sym_put调用分配的,方法是使用虚拟值sym_new初始化它们,例如0xCDCDCDCD(请注意这里的指针宽度...这就是为什么我称之为黑客技术)。然后在sym_free在释放pcKeypvValue之前检查这个魔术常数。如果你找到它,那就是问题所在...

同样有趣的可能是线程我是否投射了 malloc 的结果?

编辑:

查看链接的代码,您似乎正在丢弃 const

函数 ID 定义为:

int SymTable_put (SymTable_t m_SymTable_t, const char *pcKey, const void *pvValue)

但是这个演员表...

temp->pcKey = (char*)pcKey;
temp->pvValue = (char*)pvValue;

这是个坏主意。您正在"愚弄"编译器,使其使您的 const 承诺无效。

错误:好的,所以你分配如下

temp->pcKey = (char*) malloc (sizeof(char) * strlen (pcKey));

但随后你使用

temp->pcKey = (char*)pcKey;

所以你 a) 有内存泄漏和 b) 刚刚藏了错误的指针,这可能是你得到段错误的原因。你可能打算做的是(strdup在这里很有用)......

temp->pcKey = strdup(pcKey);

这将为pcKey中的字符串分配新内存,并将字符串复制到新内存中。

我猜你这样称呼这个函数......

SymTable_put (xxx, "KEY string", "VALUE string");

然后你的代码这样做了

temp->pcKey = (char*)malloc (sizeof(char) * strlen (pcKey));
...
temp->pcKey = (char*)pcKey;

所以现在temp->pcKey指向"KEY 字符串"本身,而不是它的副本。因此,当您尝试释放字符串常量时,您的程序会抱怨。您要做的是将字符串从pcKey复制到temp->pcKey,而不是覆盖指针。

编辑: 根据注释,malloc需要空格 + 1 才能包含空终止符。此外,sizeof(char)始终为 1,因此是多余的。尝试strdup内在。

相关内容

  • 没有找到相关文章

最新更新