打开/关闭文件时出现分段错误?

发布于 2025-01-06 19:33:28 字数 494 浏览 0 评论 0原文

我正在开发一个多线程程序。它能够正确关闭所有线程,但是,它最后会出现段错误。通过注释掉代码的某些部分,我发现它在处理打开/关闭文件的代码区域内:

char *pid_fname;
FILE *file;

sprintf(pid_fname, "%s%d%s", "/proc/", pid, "/stat");
file = fopen(pid_fname, "r");

/* code */

fclose(file);

我尝试在 gdb 中进行调试,但是只有在段错误后打印出“where”后才得到此信息:

#0  0x2f312f63 in ?? ()
#1  0x74617473 in ?? ()
#2  0xbfaee700 in ?? ()
#3  0xbfaee77c in ?? ()
#4  0x006a7810 in ?? ()
#5  0x00000000 in ?? ()

谁能给我一些关于从这里去哪里的指示?

I am working on a multithreaded program. It's able to close all the threads properly, however, it segfaults at the end. Through commenting out certain parts of my code, I found that it is within this area of the code that deals with opening/closing a file:

char *pid_fname;
FILE *file;

sprintf(pid_fname, "%s%d%s", "/proc/", pid, "/stat");
file = fopen(pid_fname, "r");

/* code */

fclose(file);

I tried debugging in gdb, however I only get this after printing out 'where' after the segfault:

#0  0x2f312f63 in ?? ()
#1  0x74617473 in ?? ()
#2  0xbfaee700 in ?? ()
#3  0xbfaee77c in ?? ()
#4  0x006a7810 in ?? ()
#5  0x00000000 in ?? ()

Can anyone give me some pointers on where to go from here?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

赤濁 2025-01-13 19:33:28

您没有文件名的后备存储。您已经创建了一个指针,但没有分配任何空间。这意味着它几乎肯定指向您不想写入的某个地方:-)

假设您知道进程 ID 的最大范围(例如 5 位数字),最简单的修复方法类似于(并稍微更改参数,因为/proc//stat 是固定字符串):

char pid_fname[sizeof("/proc/99999/stat")];
sprintf(pid_fname, "/proc/%d/stat", pid);

否则,您需要根据实际的 pid 值动态分配足够的空间,如果内存不足,则进行防御性编码。

由于系统往往具有固定的进程 ID 范围,因此我会选择固定大小的缓冲区。如果你真的想防止错误,同时又不担心动态分配,你可以使用类似的东西:

char pid_fname[sizeof("/proc/99999/stat")];
if ((pid < 0) || (pid > 99999)) {
    fprintf (stderr, "WTH? What sort of PID was that (%d)?\n", pid);
    exit (1);
}
sprintf(pid_fname, "/proc/%d/stat", pid);

You have no backing storage for the file name. You've created a pointer but have allocated no space. That means it's almost certainly pointing somewhere where you don't want to write to :-)

Assuming you know the maximum range of a process ID (say 5 digits for example), the simplest fix is something like (and changing the arguments slightly since /proc/ and /stat are fixed strings):

char pid_fname[sizeof("/proc/99999/stat")];
sprintf(pid_fname, "/proc/%d/stat", pid);

Otherwise, you'll need to dynamically allocate enough space based on the actual pid value, and code defensively if you run out of memory.

Since systems tend to have a fixed range for process IDs, I'd opt for the fixed size buffer. If you really want to protect from bugs whilst still not worrying about dynamic allocation, you could use something like:

char pid_fname[sizeof("/proc/99999/stat")];
if ((pid < 0) || (pid > 99999)) {
    fprintf (stderr, "WTH? What sort of PID was that (%d)?\n", pid);
    exit (1);
}
sprintf(pid_fname, "/proc/%d/stat", pid);
伴我心暖 2025-01-13 19:33:28

sprintf 要求其第一个参数是指向调用者分配的缓冲区的指针。您甚至没有初始化pid_fname

sprintf requires that its first argument be a pointer to a caller-allocated buffer. You're not even initializing pid_fname.

嘴硬脾气大 2025-01-13 19:33:28
char *pid_fname;
sprintf(pid_fname, "%s%d%s", "/proc/", pid, "/stat");

pid_frame 是一个未初始化的指针。在这种情况下,无法将提供的参数复制到缓冲区。

char *pid_fname;
sprintf(pid_fname, "%s%d%s", "/proc/", pid, "/stat");

pid_frame is an uninitialized pointer. The arguments supplied cannot be copied to the buffer in this case.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文