C 字节读取器中的分段错误(内核转储)



我有一个系统操作入门类的作业,它有两个不同的部分,第一个是一个简单的程序,用于逐个字节读取可执行文件,并输出输入的字符串长度至少为 4 个字符。它是可以在 UNIX 中使用的字符串程序(命令)的简单建模。

我遇到了三个单独的示例可执行文件的分段错误(核心转储)错误。我知道这本质上意味着我正在尝试访问一些我无法访问的内存地址(通过超出程序拥有的分配块,或通过其他方式)。不幸的是,我不明白为什么这个程序要这样做。

我认为问题出在我的链表实现上 - 我用它来存储可读的字符,然后在出现不可读字符时检查链表是否有 4 个条目。如果是这样,我打印出来。然后我清除链表并重新开始。

我正在逐个字节遍历文件,我觉得这个程序的逻辑是合理的。但是,我对指针、地址和 malloc 的完全理解并不那么合理。我有一种预感,由于缺乏知识,正在发生分割错误。

有人可以看看下面的代码,找出我做错了什么吗?最重要的是,你能解释一下我滥用了什么概念,为什么?我担心程序以应有的方式运行,是的,但也担心我缺乏理解。代码如下 - 谢谢。

#include <stdio.h>
#include <stdlib.h>
struct node{
    char ANSII;
    struct node *next_node;
};
void clear_list(struct node *first_node);
void print(struct node *first_node);
int counter(struct node *first_node);
void append(char temp, struct node *first_node);

int main(int argc, char **argv){
    FILE *f = NULL;
    struct node header;
    char temp;
    if(argc != 2){ /* argv[0] = name of the program, argv[1] = file to open */
        printf("usage: %s filename:", argv[0]);
    }
    f = fopen(argv[1], "rb");
    if(f == 0){ /* check for successful read */
         printf("Could not open file.n");
    }
    while(!feof(f)){
        fread(&temp, sizeof(1), 1, f);
        if(temp >= 32 && temp <= 128){ /* If it falls between the bounds of printable     characters. */
            append(temp, &header); //Builds the string
        }else{
            if(counter(&header) > 3){
                print(&header);
            }
            clear_list(&header);
        }
    }
    return 0;
}
void clear_list(struct node *first_node){
    struct node *conductor;
    while(first_node != NULL){
        conductor = first_node;
        while(conductor->next_node != NULL){
            conductor = conductor->next_node;
        }
        free(conductor);
    }
}
void print(struct node *first_node){
    struct node *conductor = first_node;
    while(conductor != 0){
        printf("%s", conductor->ANSII);
        conductor = conductor->next_node;
    }
    printf("n");
}
int counter(struct node *first_node){
    struct node *conductor = first_node;
    int counter = 0;
    while(conductor != 0){
        conductor = conductor->next_node;
        counter++;
    }
    return counter;
}
void append(char temp, struct node *first_node){
    struct node *conductor = first_node;
    while(conductor->next_node != 0){
        conductor = conductor->next_node;
    }
    conductor->next_node = malloc(sizeof(conductor->next_node));
    if(conductor->next_node == 0){
        printf("Memory allocation failed!");
        return;
    }
    conductor = conductor->next_node;
    conductor->ANSII = temp;
}
到目前为止,我

尝试实现答案,现在我得到的不是分段错误:

*** glibc detected *** ./mystrings: double free or corruption (fasttop): 0x0000000000601250   ***
======= Backtrace: =========
/lib64/libc.so.6[0x3886a75916]
./mystrings[0x400798]
./mystrings[0x40072f]
/lib64/libc.so.6(__libc_start_main+0xfd)[0x3886a1ecdd]
./mystrings[0x4005b9]
======= Memory map: ========
00400000-00401000 r-xp 00000000 00:1b 1921384528                         /afs/pitt.edu/home/n/a/nap54/private/cs449/project2/mystrings
00600000-00601000 rw-p 00000000 00:1b 1921384528                              /afs/pitt.edu/home/n/a/nap54/private/cs449/project2/mystrings
00601000-00622000 rw-p 00000000 00:00 0                                  [heap]
3886600000-3886620000 r-xp 00000000 fd:00 180                            /lib64/ld-2.12.so
388681f000-3886820000 r--p 0001f000 fd:00 180                            /lib64/ld-2.12.so
3886820000-3886821000 rw-p 00020000 fd:00 180                            /lib64/ld-2.12.so
3886821000-3886822000 rw-p 00000000 00:00 0
3886a00000-3886b89000 r-xp 00000000 fd:00 183                            /lib64/libc-2.12.so
3886b89000-3886d89000 ---p 00189000 fd:00 183                            /lib64/libc-2.12.so
3886d89000-3886d8d000 r--p 00189000 fd:00 183                            /lib64/libc-2.12.so
3886d8d000-3886d8e000 rw-p 0018d000 fd:00 183                            /lib64/libc-   2.12.so
3886d8e000-3886d93000 rw-p 00000000 00:00 0
388d200000-388d216000 r-xp 00000000 fd:00 6639                           /lib64/libgcc_s-4.4.6-20120305.so.1
388d216000-388d415000 ---p 00016000 fd:00 6639                           /lib64/libgcc_s-  4.4.6-20120305.so.1
388d415000-388d416000 rw-p 00015000 fd:00 6639                           /lib64/libgcc_s-    4.4.6-20120305.so.1
7ffff7fd5000-7ffff7fd8000 rw-p 00000000 00:00 0
7ffff7ffb000-7ffff7ffe000 rw-p 00000000 00:00 0
7ffff7ffe000-7ffff7fff000 r-xp 00000000 00:00 0                          [vdso]
7ffffffea000-7ffffffff000 rw-p 00000000 00:00 0                          [stack]
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0                  [vsyscall]
Aborted (core dumped)

现在我完全迷失了。有人能摆脱(更多?)洞察力吗?谢谢你们的帮助伙计们...

当你声明变量header时,你不初始化成员。这意味着这些值将是未定义的和随机的。然后,当您调用append时,next_node成员很可能不是NULL前导,您确实取消引用了未定义的指针并具有未定义的行为。

至少初始化 header 结构的 next_node main 成员。

相关内容

  • 没有找到相关文章

最新更新