【发布时间】:2014-07-03 14:56:47
【问题描述】:
我在练习 17 中使用 Learn C the Hard Way 在线书籍学习 C,但遇到了一个令人困惑的错误。在练习中,我被告知使用 malloc(sizeof(struct xxxx)) 为连接和数据库分配内存,如下所示:
struct Connection *conn = malloc(sizeof(struct Connection));
if(!conn) die("Memory error");
conn->db = malloc(sizeof(struct Database));
if(!conn->db) die("Memory error");
当我运行程序时,我得到一个分段错误,然后在 valgrind 下运行它后,我得到这个错误:
==5770== Command: ./ex17 db.dat c
==5770==
==5770== Invalid read of size 1
==5770== at 0x40C4130: _IO_file_fopen@@GLIBC_2.1 (fileops.c:267)
==5770== by 0x40B88CA: __fopen_internal (iofopen.c:90)
==5770== by 0x40B893A: fopen@@GLIBC_2.1 (iofopen.c:103)
==5770== by 0x8048861: Database_open (ex17.c:58)
==5770== by 0x8048C4C: main (ex17.c:156)
==5770== Address 0x77 is not stack'd, malloc'd or (recently) free'd
main 中的第 156 行只是通过函数 struct Connection *conn = Database_open(filename, action); 创建一个新的连接结构,这似乎不是问题。一直到 Database_open 中的第 58 行是 conn->file = fopen(filename, 'w'); 从错误的未堆叠、malloc 部分,我认为上面的 malloc 是问题所在。有人可以确认/帮我解决这个问题吗?
【问题讨论】:
-
考虑到如果
mallocs 失败,程序应该死掉并显示错误消息,可以肯定地说这段代码不是问题。 -
fopen的第二个参数应该是双引号中的字符串,而不是字符常量:fopen(filename, "w")。 -
@MicroVirus 是正确的:
malloc调用不是问题。回溯表明您正在尝试使用值0x77作为地址。0x77恰好是字符'w'的ASCII值;这会响铃吗?请更新您的问题以包含足够的代码来诊断问题;如有必要,请将您的程序缩小到足以发布但仍然存在问题的内容。 -
换句话说:您的问题是一个简单的错字,因此偏离主题。将来,您可能希望将练习中的代码复制粘贴到另一个文件中,并在您输入的版本和复制粘贴的版本之间运行差异。
-
@FlorinStingaciu 该链接显示错字:)
标签: c memory-management struct