You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Ubuntu下C语言读取DNS文件对应IP时出现段错误的问题问询

问题:C程序在Ubuntu下触发Segmentation fault,Windows下运行正常

我在名为DNS.txt的文本文件中存储了若干网站名称及其对应的随机IP地址,用C语言编写了程序查找特定网站的对应IP。程序在Windows下运行正常,但在Ubuntu执行时抛出错误:

Segmentation fault (core dumped)

我的实现逻辑是逐字符检查网站是否存在,找到后将读取指针停在网站最后一个字符处,跳过一个字符后把剩余字符存入ip数组。程序代码如下:

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
int main() {
    // Write C code here
    FILE* ptr = fopen("DNS.txt","r");
    int found=0, i=0;
    char website[20] = "google.com";
    char ip[30];
    char temp;
    while ((temp=fgetc(ptr)) != EOF){
        if (temp == website[i]){
            i++;
            if (i==strlen(website)){
                found = 1;
                break;
            }
        }
        else
            i=0;
    }
    
    if (found){
        i=0;
        temp = fgetc(ptr);
        temp=fgetc(ptr);
        while (temp != '\n'){
            ip[i++]=temp;
            temp=fgetc(ptr);
        }
        ip[i] = '\0';
        printf("%s",ip);
    }
    else{
        printf("Ip address not found");
    }

    return 0;
}

DNS.txt文件内容如下:

google.com-1234.45.6
youtube.com-5738.292.22
github.com-2374.2342.2

文件与程序存放在同一目录下。


问题原因分析

  1. 未检查文件打开状态:fopen在Ubuntu下若无法找到文件(比如权限问题、路径匹配问题)会返回NULL,后续直接用fgetc(ptr)操作空指针会触发段错误。Windows下的文件系统特性可能掩盖了这个问题,但Ubuntu对空指针操作的检查更严格。
  2. EOF处理逻辑缺失:找到网站后,若后续读取直接到文件末尾(比如文件格式异常),while (temp != '\n')会进入无限循环,导致ip数组越界写入,触发段错误。
  3. fgetc返回值类型错误:fgetc返回int类型(包含EOF的-1),用char存储会导致EOF判断失效(无符号char会把-1转为255),进而引发错误的循环逻辑。
  4. 换行符差异:Windows换行是\r\n,Ubuntu是\n,原代码中连续两次调用fgetc跳过字符的逻辑,在Ubuntu下可能跳过了IP的起始字符,甚至直接读到EOF。

修复后的代码

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
int main() {
    FILE* ptr = fopen("DNS.txt","r");
    // 检查文件是否成功打开
    if (!ptr) {
        perror("Failed to open file");
        return EXIT_FAILURE;
    }

    int found = 0, i = 0;
    char website[20] = "google.com";
    char ip[30];
    int website_len = strlen(website);
    int c; // 用int存储fgetc返回值,兼容EOF判断

    while ((c = fgetc(ptr)) != EOF) {
        if ((char)c == website[i]) {
            i++;
            if (i == website_len) {
                found = 1;
                break;
            }
        } else {
            i = 0;
        }
    }

    if (found) {
        i = 0;
        // 跳过分隔符'-',先检查是否到文件末尾
        if ((c = fgetc(ptr)) == EOF) {
            printf("Invalid file format\n");
            fclose(ptr);
            return EXIT_FAILURE;
        }
        // 读取IP直到换行或EOF,同时防止数组越界
        while ((c = fgetc(ptr)) != EOF && (char)c != '\n') {
            if (i < sizeof(ip)-1) {
                ip[i++] = (char)c;
            } else {
                printf("IP exceeds maximum length\n");
                break;
            }
        }
        ip[i] = '\0';
        printf("%s\n", ip);
    } else {
        printf("IP address not found\n");
    }

    fclose(ptr); // 关闭文件,避免资源泄漏
    return EXIT_SUCCESS;
}

关键修复点

  • 添加文件打开校验:判断ptr是否为NULL,用perror输出具体错误原因,避免空指针操作。
  • 正确存储fgetc返回值:用int类型存储返回值,确保EOF判断准确。
  • 处理边界情况:读取IP前检查是否到文件末尾,避免无限循环;写入ip数组时限制索引范围,防止越界。
  • 规范文件操作:程序结束前关闭打开的文件,避免资源泄漏。

内容的提问来源于stack exchange,提问作者Dhanaseelan V

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.18 23:10:56