java.io.IOException:错误= 11

我遇到了Java ProcessBuilder一个奇怪的问题。 代码如下所示(略为简化)

 public class Whatever implements Runnable { public void run(){ //someIdentifier is a randomly generated string String in = someIdentifier + "input.txt"; String out = someIdentifier + "output.txt"; ProcessBuilder builder = new ProcessBuilder("./whateveer.sh", in, out); try { Process process = builder.start(); process.waitFor(); } catch (IOException e) { log.error("Could not launch process. Command: " + builder.command(), e); } catch (InterruptedException ex) { log.error(ex); } } } 

whatever.sh写道:

 R --slave --args $1 $2 <whatever1.R >> r.log 

Whatever提交给一个具有固定大小的ExecutorService (35)的实例的负载。 应用程序的其余部分等待所有这些完成 – 用CountdownLatch实现。 在抛出以下exception之前,一切都运行良好几个小时(Scientific Linux 5.0,Java版本“1.6.0_24”):

 java.io.IOException: Cannot run program "./whatever.sh": java.io.IOException: error=11, Resource temporarily unavailable at java.lang.ProcessBuilder.start(Unknown Source) ... rest of stack trace omitted... 

有没有人有一个想法这是什么意思? 基于java.io.IOException: error=11的google / bingsearch结果java.io.IOException: error=11 ,它不是最常见的exception,我完全被困惑。

我疯狂的,没有受过教育的猜测是,我有太多的线程试图同时启动相同的文件。 但是,重现该问题需要花费数小时的CPU时间,所以我没有尝试使用较小的数字。

任何build议,非常感谢。

Solutions Collecting From Web of "java.io.IOException:错误= 11"

error=11几乎肯定是EAGAIN错误代码:

 $ grep EAGAIN asm-generic/errno-base.h #define EAGAIN 11 /* Try again */ 

clone(2)系统调用文档EAGAIN错误返回:

  EAGAIN Too many processes are already running. 

fork(2)系统调用文件两个EAGAIN错误返回:

  EAGAIN fork() cannot allocate sufficient memory to copy the parent's page tables and allocate a task structure for the child. EAGAIN It was not possible to create a new process because the caller's RLIMIT_NPROC resource limit was encountered. To exceed this limit, the process must have either the CAP_SYS_ADMIN or the CAP_SYS_RESOURCE capability. 

如果你的内存真的很低,几乎肯定会显示在系统日志中。 检查dmesg(1)输出或/var/log/syslog以查找有关系统内存不足的任何潜在消息。 (其他的东西会被打破,这似乎不太合理)

遇到每个用户对进程的限制或系统最大进程数量的可能性更大。 也许你的进程之一是不适当收割僵尸? 通过检查ps(1)输出随着时间的推移,这很容易被发现:

 while true ; do ps auxw >> ~/processes ; sleep 10 ; done 

(也许每分钟或每十分钟检查一次,如果确实需要几个小时才能解决问题。)

如果你没有收获僵尸,那么请阅读你必须做的任何事情,让ProcessBuilder使用waitpid(2)收获你的孩子。

如果你合法地运行比rlimits允许的更多的进程,你将需要在你的bash(1)脚本中使用ulimit (如果以root身份运行),或者在/etc/security/limits.confnproc属性设置更高的限制。

如果您正在运行到系统范围的进程限制,则可能需要在/proc/sys/kernel/pid_max写入更大的值。 请参阅proc(5)了解一些(简短)细节。

errno 11的意思是“资源暂时不可用”这通常是一个内存问题,可以防止创建一个线程或套接字。

errno 12的意思是“不能分配内存”。 这是获取内存失败是直接调用内存(而不是需要内存的资源)

我会尝试增加你的系统的交换空间,应该避免这个问题。