在linux中为正在运行的程序设置环境变量

时间:2015-06-23 18:57:40

标签: c linux environment-variables signals

我的程序使用环境变量client.UseDefaultCredentials = false; client.DeliveryMethod = SmtpDeliveryMethod.Network; 值来确定调试消息的级别。 DBG_MSG打印最大调试信息。

但是,只要程序以奇怪的意外方式运行,环境变量就不会设置为打印完整的调试信息。当程序重新运行环境设置时,它不会显示相同的错误。

我正在考虑为DBG_MSG=3实现一个信号处理程序,以便在运行时使用SIGUSR1设置此环境变量。这样我就可以将信号发送到挂起的作业,使其打印更多的调试信息。

这样做时需要采取哪些安全措施?

还有其他方法可以从外部更改正在运行的程序的环境吗?

4 个答案:

答案 0 :(得分:3)

putenv不是async-signal-safe,因此应该从SIGUSR1处理程序调用从不。此外,putenv所做的更改不一定会被另一个帖子中的getenv调用注意到。

您应该做的是在启动时只读取DBG_MSG环境变量一次,并将值存储在类型为volatile sig_atomic_t的全局变量中。您的调试日志记录例程应查看此变量以确定要打印的信息量。然后让信号处理程序调整变量的值。

我还建议SIGUSR1应该增加变量,而SIGUSR2应该减少它。这样,您可以根据需要提高和降低日志级别。

sig_atomic_t可能非常小,并且不保证有符号或无符号:便携式程序只能使用它来存储0到127(包括0和127)范围内的值。因此,请确保您的信号处理程序将值限制在对程序有意义的范围内(即,不要将日志级别增加到超过最大值或将其降低到最小值之外)。

答案 1 :(得分:1)

安全措施是:不要这样做。

putenv(3)不是异步信号安全的(主要是因为它可以调用malloc(3)),所以你不应该从信号处理程序中调用它。

答案 2 :(得分:0)

您需要确保不会在程序中使用env变量。应该从shell中设置一次env变量并单独保留。毕竟,它们是环境变量。他们只是为您的程序设置或定义一个环境。

答案 3 :(得分:0)

还有一种方法...... 你也可以实现ioctl调用..

甚至很多司机也在做同样的事情。