C孩子读到“资源暂时不可用”
所以我有一个从父进程到子进程的文件流 - 大多数时候它工作正常。然而,当快速多次读取时,使用 fgets() 将返回 NULL,并且错误被设置为“资源暂时不可用”。该问题是间歇性的 - 运行执行读取的脚本有时会使 fgets 返回 NULL,有时则不会。
谁能帮我阻止这个错误的发生?谢谢!
编辑:这是一些代码..我不确定还有哪些其他代码会有帮助? 根据要求,有很多
// this is the bit that gets a line from the child
if( fgets( line, MAX_LINE_LENGTH, fpin ) == NULL ) {
if( ferror(fpin) ) {
perror("error on stream fpin");
}
free( line );
return FAIL;
}
打开管道并处理子进程的代码。
// set up pipes
int readPipe[2]; // child -> parent communication
int writePipe[2]; // parent -> child communication
int errorPipe[2]; // child -> parent, to check for errors in exec
/* create pipe */
pipe( readPipe ); // error if return val < 1 for any
pipe( writePipe );
pipe( errorPipe );
pid_t pid; /* process id when we fork */
pid = fork(); /* create new child */
if( pid == 0 ) { /* pid == 0 indicates child process */
// close unused fds
close( PARENT_READ );
close( PARENT_WRITE );
close( errorPipe[0] );
dup2( CHILD_READ, 0 ); // replace stdin with pipe in
dup2( CHILD_WRITE, 1 ); // replace stdout with pipe out
/* replace child process with program to run */
execvp(args[0], args);
// if we get here, exec failed so inform the parent
char *error_message = "exec failed";
write( errorPipe[1], error_message, strlen(error_message)+1 );
exit(-1);
}
So I have a file stream from a parent process to a child - and most of the time it works fine. However, when reading from it multiple times quickly, using fgets() will return NULL and the error is set to "resource temporarily unavailable". The problem is intermittent - and running the script that does the reads will sometimes have fgets return NULL and sometimes wont.
Could anyone help me stop this error from happening? Thanks!
Edit: here is some code.. I'm not sure what other code would be helpful? there's quite a bit
// this is the bit that gets a line from the child
if( fgets( line, MAX_LINE_LENGTH, fpin ) == NULL ) {
if( ferror(fpin) ) {
perror("error on stream fpin");
}
free( line );
return FAIL;
}
As requested, code that opens pipe and deals with child process..
// set up pipes
int readPipe[2]; // child -> parent communication
int writePipe[2]; // parent -> child communication
int errorPipe[2]; // child -> parent, to check for errors in exec
/* create pipe */
pipe( readPipe ); // error if return val < 1 for any
pipe( writePipe );
pipe( errorPipe );
pid_t pid; /* process id when we fork */
pid = fork(); /* create new child */
if( pid == 0 ) { /* pid == 0 indicates child process */
// close unused fds
close( PARENT_READ );
close( PARENT_WRITE );
close( errorPipe[0] );
dup2( CHILD_READ, 0 ); // replace stdin with pipe in
dup2( CHILD_WRITE, 1 ); // replace stdout with pipe out
/* replace child process with program to run */
execvp(args[0], args);
// if we get here, exec failed so inform the parent
char *error_message = "exec failed";
write( errorPipe[1], error_message, strlen(error_message)+1 );
exit(-1);
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
这意味着有人已将标准输入文件描述符设置为非阻塞。
(资源暂时不可用是
EAGAIN
/EWOULDBLOCK
对应的错误消息,仅由read()
返回当选择非阻塞 IO 并且没有数据可读取时)。请注意,父进程可能在执行子进程之前将文件描述符设置为非阻塞。
进一步调查的一些想法:
如果您
strace()
子进程,哪个系统调用返回EAGAIN
?在哪个文件描述符编号上?在失败的
fgets()
之前,printf("%d\n", fcntl(fileno(fpin), F_GETFL));
的输出是什么?< /p>That means that someone has set the standard input file descriptor as non-blocking.
(Resource temporarily unavailable is the error message corresponding to
EAGAIN
/EWOULDBLOCK
, which is returned byread()
only when non-blocking IO has been selected and there is no data to read).Note that it's possible that the parent process set the file descriptor nonblocking before exec-ing your child process.
Some ideas for further investigation:
If you
strace()
the child process, which system call is returningEAGAIN
? On which file descriptor number?What's the output of
printf("%d\n", fcntl(fileno(fpin), F_GETFL));
right before the failingfgets()
?