简体   繁体   English

如何在Unix中设置O_NONBLOCKING标志

[英]How to set O_NONBLOCKING flag in Unix

I am writing a sender/reader IPC C program for class, and I am having trouble setting the O_NONBLOCK flag to 0 so that my reader will block when the buffer it is attempting to read from is empty. 我正在为类编写一个发送者/阅读者IPC C程序,但我无法将O_NONBLOCK标志设置为0,这样我的阅读器将在尝试读取的缓冲区为空时阻塞。 Here are the functions I am using: 这是我正在使用的功能:

int set_nonblock_flag(int desc, int value)
{
        int oldflags = fcntl(desc, F_GETFL, 0);
        if (oldflags == -1)
                return -1;
        if (value != 0)
                oldflags |= O_NONBLOCK;
        else
                oldflags &= ~O_NONBLOCK;
        return fcntl(desc, F_SETFL, oldflags);
}

main() 主要()

main ()
{
        int fd[2], nbytes;
        char readbuff[26];
        int r_pid = 0;
        int s_pid = 0;

        /* THIS IS ALL UPDATED!*/
        fd[0] = open("fd.txt",O_RDONLY);
        fd[1] = open("fd.txt",O_WRONLY);
        set_nonblock_flag(fd[0], 0);
        set_nonblock_flag(fd[1], 0);
        /* END UPDATES */

        pipe(fd);

        r_pid = fork();
        if (r_pid < 0) /* error */
        {
                fprintf( stderr, "Failed to fork receiver\n" );
                exit( -1 );
        }
        else if (r_pid == 0) /* this is the receiver */
        {
                fprintf( stdout, "I, %d am the receiver!\n", getpid() );

                close( fd[1] ); /* close write end */
                nbytes = read( fd[0], readbuff, 1 );
                printf ("nonblocking flag = %d\n", fcntl(fd, F_GETFL, 0));
                printf ("Nbytes read: %d\n", nbytes );
        }

... /* rest of function removed */

The line printf ("nonblocking flag = %d\\n", fcntl(fd, F_GETFL, 0)); printf ("nonblocking flag = %d\\n", fcntl(fd, F_GETFL, 0)); is just returning -1 as the flag status. 只是返回-1作为标志状态。 Shouldn't it be 0 if it is cleared? 如果清除,不应该是0吗?

You are calling set_nonblock_flag with first argument as an array of ints. 您正在将带有第一个参数的int数组调用set_nonblock_flag。 Here's a snippet from fcntl manpage. 这是fcntl联机帮助页的摘录。 The first argument should be a file descriptor. 第一个参数应该是文件描述符。

SYNOPSIS 概要

  #include <fcntl.h> int fcntl(int fildes, int cmd, ...); 

DESCRIPTION 描述

The fcntl() function shall perform the operations described below on open files. fcntl()函数应在打开的文件上执行以下描述的操作。 The fildes argument is a file descriptor. fildes参数是文件描述符。

I think you want to first call pipe and then call set_nonblock_flag. 我认为您想先调用管道,然后再调用set_nonblock_flag。 So, I think what you really want is the following: 因此,我认为您真正想要的是:

int fd[2];
...
pipe(fd);
set_nonblock_flag(fd[0], 0);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM