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

使用systemd运行C程序时触发Core Dump的问题排查

问题分析与解决方案

首先,咱们先聚焦最致命的SIGFPE算术异常:
从core dump信息看,崩溃发生在interval - (millis % interval)这行,这明显是除零错误——也就是说interval的值为0了。那为什么命令行运行正常,systemd下就会出现这个情况?

根源:配置文件加载失败

你提到程序在systemd下无法读取配置文件,本该触发exit(1)却没正常执行(或者说配置加载失败后变量没正确初始化)。结合你用sudo -H -u midnite-modbusd /usr/local/bin/midnite-modbusd命令行运行正常的情况,最大的可能是systemd的默认工作目录与命令行不同:

  • 命令行运行时,你是在某个目录下执行的(比如程序的配置文件所在目录),程序默认从当前工作目录读取配置文件;
  • 而systemd服务默认的工作目录是/(根目录),程序在根目录下找不到配置文件,导致interval等参数没有被正确初始化,保持了默认值0,进而触发除零错误。

解决配置文件与崩溃问题

你可以通过两种方式修复:

  1. 在systemd单元文件中指定工作目录:
    在[Service]段添加WorkingDirectory,指向程序配置文件所在的目录,比如:
    [Service]
    Type=simple
    User=midnite-modbusd
    WorkingDirectory=/path/to/your/config/directory
    ExecStart=/usr/local/bin/midnite-modbusd
    Restart=on-failure
    
  2. 修改程序,使用绝对路径读取配置文件:
    把程序中读取配置文件的路径改成绝对路径(比如/etc/midnite-modbusd.conf),这样不管工作目录在哪,都能找到配置文件。

日志延迟问题

关于journalctl -f无法实时更新日志的问题,这是因为systemd捕获程序输出时,默认使用全缓冲模式,而命令行运行时终端会触发行缓冲,所以日志实时输出。解决方法有两个:

  • 修改程序,强制刷新输出:
    在每次printf或fprintf(stderr, ...)之后调用fflush(stdout)或fflush(stderr),确保日志立即输出;
  • 在systemd单元中配置输出模式:
    在[Service]段添加相关配置,强制即时输出:
    [Service]
    # 其他配置...
    StandardOutput=journal+console
    StandardError=journal+console
    SyslogIdentifier=midnite-modbusd
    

额外验证步骤

你可以先手动切换到根目录,用指定用户运行程序,复现问题:

cd /
sudo -H -u midnite-modbusd /usr/local/bin/midnite-modbusd

如果此时也出现崩溃和配置文件读取失败,就完全验证了工作目录的问题。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.27 09:35:13