4

已经有几个关于此的问题,但似乎没有一个有效。我有一个当前已关闭的生产系统,我需要能够快速从守护程序获取 stderr 输出以对其进行调试。

我以为我可以从它被调用的点(在 init.d 脚本中)重定向输出,但事实证明这非常困难。

 start-stop-daemon -d $DDIR -b -m --start --quiet -pidfile $PIDFILE --exec $DAEMON -- \
                $DAEMON_ARGS > /var/log/daemon.log 2>&1 \
                || return 2

这不起作用。我尝试运行一个调用可执行文件并重定向输出的 shell 脚本,但日志文件仍然为空(我知道该进程正在输出信息)。

任何帮助将不胜感激。

4

4 回答 4

3

如果您有 start-stop-daemon >= version 1.16.5,您只需调用它--no-close即可重定向已启动进程的输出。

来自man start-stop-daemon

-C,--不关闭

          Do not close any file descriptor when forcing the daemon into
          the background (since version 1.16.5).  Used for debugging
          purposes to see the process output, or to redirect file
          descriptors to log the process output.  Only relevant when
          using --background.
于 2016-11-24T14:13:53.357 回答
2

据我记得,这是不可能的,通常当我需要从守护进程获取数据时,我要么事先记录它,要么创建一个监控程序,通过网络套接字或命名管道或任何其他进程间通信机制连接到该程序。

于 2012-10-08T19:10:51.097 回答
1

调用start-stop-daemon> /var/log/daemon.log 2>&1重定向start-stop-daemon的输出,而不是启动的守护进程的输出start-stop-daemon将在运行守护程序之前关闭标准输出/输入描述符。

将可执行文件包装在一个简单的 shell 脚本中,如下所示:

#!/bin/bash
STDERR=$1
shift
DAEMON=$1
shift
$DAEMON 2>$STDERR $*

对我有用-也许您应该检查文件权限?

这个简单的解决方案有一个问题——当start-stop-daemon杀死这个包装器时,被包装的守护程序将保持活动状态。这在 bash 中不容易解决,因为在脚本执行期间您无法运行信号处理程序(trap有关详细信息,请参阅文档)。您必须编写一个看起来像这样的 C 包装器:

#include <fcntl.h>
#include <unistd.h>
int main(int argc, char** argv){
    int fd_err;

    fd_err = open(argv[1], O_WRONLY | O_CREAT | O_TRUNC);
    dup2(fd_err, STDERR_FILENO);
    close(fd_err);

    return execvp(argv[2], argv + 2);
}

(为了清楚起见,我省略了错误检查)。

于 2013-11-19T23:13:02.380 回答
0

这是一个可行的解决方案(基于此处给出的解决方案)。

在 init.d 脚本的开头(以及标题之后),添加以下内容:

exec > >(tee --append /var/log/daemon.log)

#You may also choose to log to /var/log/messages using this:
#exec > >(logger -t MY_DAEMON_NAME)

#And redirect errors to the same file with this:
exec 2>&1

这将记录脚本期间调用的所有内容,包括start-stop-daemon输出。

于 2013-03-07T12:23:16.560 回答