0

クライアント/サーバーがeventfdを介して通信しています。クライアントまたはサーバーのいずれかが呼び出された場合close(fd)、もう一方の端に見つけてもらいたいです(ファイル記述子が現在閉じられているように)。ゼロ以外のタイムアウトで使用しようとしましたがselect、常にタイムアウトである 0 を返します。私は人々がそれを使用することを提案しているのを見ましfcntlたが、どちらも機能していないようです。助言がありますか?

追加の詳細(重要でない部分のコードは省略します。ファイル記述子の詳細コードを交換する方法については、こちらを参照してください。マルチプロセスアプリケーションです。サーバープロセスは、呼び出しによってeventfdを作成しました

 struct msghdr control_message;
 int fd = eventfd(0,0);
 *CMSG_DATA(control_message) = fd;
 message.msg_control = &control_message;
 sendmsg(socket_fd, & message,0); //send this to client

クライアント側から:

 recvmsg(socket_fd, & message,0);
 //loop using CMSG_NXTHDR(&message, control_message)
 int fd = *(int *) CMSG_DATA(contro_message);

次に、サーバー側で:

 close(fd);

クライアント側: int rc; rc = dup2(fd,fd);

rc が無効になることはありません。

4

1 に答える 1

0

閉じたファイル記述子をチェックしていますか? これはどう?

#include <errno.h>
#include <stdio.h>
#include <string.h>

static void checkit ()
{
    int     rc;

    rc = dup2(2, 2);

    if ( rc == -1 )
            printf("error %d on dup2(2, 2): %s\n", errno, strerror(errno));
    else
            printf("dup2 successful\n");

    write(2, "still working\n", 14);
}

int main (int argc, char **argv)
{
    int     rc;

    checkit();

    close(2);

    checkit();

    return  0;
}

実行すると、次の出力が生成されます。

dup2 successful
still working
error 9 on dup2(2, 2): Bad file descriptor

これが poll を使用するマルチスレッド アプリケーションであり、ファイル記述子が別のスレッドによって閉じられたときに poll が返されるようにする場合は、POLLERR、POLLHUP、または POLLNVAL が役立つ可能性があります。

ポーリングを使用したマルチスレッド バージョン

マルチスレッド プログラムで、閉じられた fd をポーリング (POLLNVAL がイベント) で検出する方法を示すサンプルを次に示します。

#include <errno.h>
#include <poll.h>
#include <pthread.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>

static void *run_poll (void *arg)
{
    struct pollfd   fds[1];
    int             rc;

    fds[0].fd = 2;
    fds[0].events = POLLERR | POLLHUP | POLLNVAL;

            //
            // Poll indefinitely
            //

    printf("starting poll\n");
    fflush(stdout);
    rc = poll((struct pollfd *) &fds, 1, -1);

    if ( rc == -1 )
    {
            printf("POLL returned error %d: %s\n", errno, strerror(errno));
    }
    else
    {
            printf("POLL returned %d (revents = 0x%08x): %s %s %s\n",
                   rc,
                   fds[0].revents,
                   ( ( fds[0].revents & POLLERR  ) ? "pollerr" : "noerr" ),
                   ( ( fds[0].revents & POLLHUP  ) ? "pollhup" : "nohup" ),
                   ( ( fds[0].revents & POLLNVAL ) ? "pollnval" : "nonval" ));
    }

    return  NULL;
}

int main (int argc, char **argv)
{
    pthread_t       thread;
    int             rc;

    rc = pthread_create(&thread, NULL, run_poll, NULL);

    usleep(100);
    printf("closing stderr\n");
    close(2);
    usleep(100);

    return  0;
}

これにより、出力が生成されます

starting poll
closing stderr
POLL returned 1 (revents = 0x00000020): noerr nohup pollnval
于 2013-08-21T17:01:27.140 に答える