从C中的文件描述符读取

时间:2014-07-23 16:54:21

标签: c file-descriptor

(纠正我,如果我的条款错误)所以我需要从文件描述符读取,但读取方法接受一个字节大小的int读取那么多或我可以使用O_NONBLOCK,但我仍然需要设置一个未知大小的缓冲区大小。让它变得困难。继续我到目前为止所拥有的

这是我处理所有轮询和mkfifo的方法。并且N已在主

中预定义
struct pollfd pfd[N];
int i;
for(i = 0; i < N; i++)
{
    char fileName[32];
    snprintf (fileName, sizeof(fileName), "%d_%di", pid, i);
    mkfifo(fileName, 0666);
    pfd[i].fd = open(fileName, O_RDONLY | O_NDELAY);
    pfd[i].events = POLLIN;
    pfd[i].revents = 0;

    snprintf (fileName, sizeof(fileName), "%d_%do", pid, i);
    mkfifo(fileName, 0666);
    i++;
    pfd[i].fd = open(fileName, O_WRONLY | O_NDELAY);
    pfd[i].events = POLLOUT;
    pfd[i].revents = 0;
    i--;
}
while(1)
{
    int len, n;
    n = poll(pfd, N, 2000);
    if( n < 0 )
    {   
        printf("ERROR on poll");
        continue;
    }
    if(n == 0)
    {
        printf("waiting....\n");
        continue;
    }
    for(i = 0; i < N; i++)
    {
        char buff[1024]; <---i dont want to do this

        if (pfd[i].revents & POLLIN)
        {
            printf("Processing input....\n");
            read(pfd[i].fd, buff, O_NONBLOCK);
            readBattlefield(buff);
            print_battleField_stats();
            pfd[i].fd = 0;
        }
    }
}

我还读过一些地方,一旦read()读取所有来的数据,它就会清空管道,这意味着我可以再次使用相同的数据传输另一个数据。但它不会清空管道,因为我不能再使用相同的管道。我问过我的教授,但他说的只是使用像scanf这样的东西,但是如果scanf采用FILE流,那么如何使用scanf,而poll.fd是一个int?基本上我的最终问题是,如何使用扫描或其他类型通过文件描述符读取传入的数据?使用扫描将有助于我处理数据。

编辑: 在另一个终端我必须把cat文件&gt; (named_file) 我的主程序将读取输入数据。下面是输入数据的样子

3 3

1 2 0

0 2 0

3 0 0

前两个数字是网格信息和玩家编号,之后是网格,但这是一个简化版本,不适用于超过100个玩家的尺寸和超过1000的网格

1 个答案:

答案 0 :(得分:2)

  

char buff [1024]; &lt; ---我不想这样做

那你想做什么?这是它的工作原理。这它是如何工作的:

read(pfd[i].fd, buff, O_NONBLOCK);

这将编译,因为O_NONBLOCK是一个整数#define,但绝对且毫不含糊不正确。 read()的第三个参数是要读取的字节数。不是旗帜。期。它可能为零,但你在这里所做的就是传递一个任意数字 - 无论O_NONBLOCK的值是多少,这可能很容易超过1024,即缓冲区的大小。此未设置读取非块recv()read()类似,并且将这些标记作为第四个参数,但您不能将其与文件描述符一起使用。如果要在文件描述符上设置非阻止,则必须使用open()fcntl()

  

如何使用扫描或其他类型通过文件描述符读取传入数据?

您可以使用FILE*从开放描述符创建fdopen()流。

  

我还读过一些地方,一旦read()读取所有来的数据,它就会清空管道,这意味着我可以再次使用相同的数据传输另一个数据。但它不会清空管道,因为我不能再使用相同的管道了。

一旦达到EOF(因为作者关闭了连接),read()将返回0,并立即继续返回0,直到有人再次打开管道。

如果您设置描述符非阻止,read()将始终立即返回;如果有人连接且无需阅读,则会返回-1,但errno== EAGAIN。见man 2 read

man fifo绝对是你应该读的东西;如果您有任何不确定的地方,请根据该问题提出具体问题。

不要忘记:修复read()来电。这是错误的。 W R O N G.你的教授/ TA /谁也不会错过。