从多线程程序调用系统()
我们正在研究用C++编写的多线程内存消耗应用程序。 我们必须执行大量的shellscript/linux命令(并获取返回码)。从多线程程序调用系统()
读完article之后,我们清楚地知道在我们的上下文中使用system()是一个坏主意。
解决方法是在程序启动后和创建任何线程之前分叉,但与该进程的通信可能并不容易(套接字,管道?)。
我们考虑过的第二种解决方案可能包含一个专门用python编写的deamon(使用xinetd?),它将能够处理我们的系统调用。
你有过这个问题吗?你是如何解决它的?
注: 这里是解释这个问题更完整的文章:()http://developers.sun.com/solaris/articles/subprocess/subprocess.html 他们建议使用它使用的vfork的posix_spawn而不是fork()的(在系统中使用())。
您将得到关于的问题如何您应该调用一个外部程序(fork/exec/wait,如何),但这只是问题的一部分。真正的问题是这种调度,我假设你不想并行运行太多的外部程序。
不知道线程组织如何进入你的系统,我可以警告你两个问题。
这是一个重要的问题是通过限制外部命令/脚本调用来降低负载。您可以设置一个参数,告诉多少个并行外部命令应该同时运行。在调用外部命令之前,应该增加一个显示活动外部进程数量的变量;如果超过极限参数,请睡觉()一些,然后重试。处理完成后,减少该变量。 (增加和减少必须互斥)
另一个问题是,当你使用外部程序时,管理它的生命周期。你应该为每个外部进程设置一个“超时”,如果它暂停一段时间,就杀了它。应该有一个“超时”线程(或者应该是主线程),它控制着其他线程。
如果您使用fork()并且不立即使用exec *()跟随它,那么您链接的文章主要讨论问题。由于system()通常由fork()和exec()实现,因此大多数问题都不适用。但是,一个适用的问题是关于关闭文件描述符的问题;除非你有特殊的理由否则,默认情况下用O_CLOEXEC打开文件可能是一个很好的经验法则。
大型内存消耗应用程序的fork()+ exec()的一个问题是,如果您的OS配置为不允许内存过量使用,fork()可能会失败。对此的一个解决方案是在开始在主进程中分配大量内存之前,先分叉一个“外部进程处理程序”进程。
最好的解决方案是,如果你需要的功能是作为一个库提供的,不需要首先分叉。尽管如此,这可能不会在短期内增加你的心。
这个怎么样的解决方案:
叉()在程序的一开始,并让孩子专门用于起动和管理外部程序。然后让父节点启动它的所有线程并执行应用程序逻辑,当需要外部进程时通过管道发送请求。
这会在启动它们之前分叉线程的问题。
将外部程序的运行称为“系统调用”可能是个坏主意。在C和C++中,系统调用通常意味着与内核进行交谈,即直接进行OS级调用。 – unwind 2011-12-20 11:39:21
你有没有链接到正确的文章?这是关于'fork()'产生单线程子进程,即使父进程是多线程的,并且没有说'system()'是一个坏主意。 – 2011-12-20 11:53:05
system()执行fork()然后执行exec()cf手册页:( – 2011-12-20 14:25:55