转换为多线程套接字应用程序

标签 c multithreading posix unix

正如我目前所做的那样this project仅在 C 中,直到此时我才将我的网络服务器用作单线程应用程序。但是,我不想那样了!所以我有以下代码来处理我的工作。

void BeginListen()
{
        CreateSocket();

        BindSocket();

        ListenOnSocket();

        while ( 1 )
        {
            ProcessConnections();
        }
}

现在我在 ProcessConnection(); 开始之前添加了 fork(); 这有助于我允许多个连接!但是,当我添加用于守护应用程序的代码时,在 this answer 中找到.我遇到了一个小问题,使用 fork() 会创建我的整个运行应用程序的副本,这就是 fork() 的目的。所以,我想解决这个问题。

我的 ProcessConnection() 看起来像这样

void ProcessConnections()
{
        fork();

        addr_size = sizeof(connector);

        connecting_socket = accept(current_socket, (struct sockaddr *)&connector, &addr_size);

        if ( connecting_socket < 0 )
        {
                perror("Accepting sockets");
                exit(-1);
        }

        HandleCurrentConnection(connecting_socket);


        DisposeCurrentConnection();
}

我该怎么做才能简单地在 connecting=socket = accept... 之上或之后添加几行,以使其同时接受多个连接?我可以使用 fork(); 但是当它归结为 DisposeCurrentConnection(); 我想终止该进程并让父线程运行。

最佳答案

我不是 100% 确定你想做什么,买下我的头顶,我更愿意在接受后做 fork ,然后简单地退出()当你'重做。但请记住,当子进程退出时,您需要对 SIGCHLD 信号作出 react ,否则您将有大量的僵尸进程徘徊,等待将它们的退出状态传递给父进程。 C 伪代码:

for (;;) {
  connecting_socket = accept(server_socket);
  if (connecting_socket < 0)
    {
      if (errno == EINTR)
        continue;
      else
        {
          // handle error
          break;
        }
    }

  if (! (child_pid = fork ()))
    {
       // child process, do work with connecting socket
       exit (0);
    }
  else if (child_pid > 0)
    {
      // parent process, keep track of child_pid if necessary.
    }
  else
    {
      // fork failed, unable to service request, send 503 or equivalent.
    }
}

child_pid 需要(如前所述)来终止子进程,但如果您希望使用 waitpid 来收集退出状态也是如此。

关于僵尸进程,如果你对进程发生的事情不感兴趣,你可以为 SIGCHLD 安装一个信号处理程序,然后用 -1 循环 waitpid 直到它没有更多的子进程,就像这样

while (-1 != waitpid (-1, NULL, WNOHANG))
  /* no loop body */ ;

waitpid 函数将返回退出的子进程的 pid,因此如果您愿意,可以将此与有关连接的其他一些信息相关联(如果您确实跟踪了 pid)。请记住,如果捕获到 SIGCHLD,accept 可能会在 errno 设置为 EINTR 时退出,没有有效连接,因此请记住在 accept 返回时检查这一点。

编辑:
不要忘记检查错误条件,即 fork 返回 -1。

关于转换为多线程套接字应用程序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/433461/

相关文章:

c++ - C++ 中的多线程矩阵乘法

c - 将多个 C 文件解析为单个 AST 的工具/解析器

c - 打印 CString 会打印之前未知的文本

c++ - Flann vs. Brute Force 匹配器

c++ - pthread_create创建的子线程如何调用主线程?

linux - POSIX UDP 套接字 : how is the data splitted to UDP packets?

pthreads - pthreads 的官方标准是什么?

c++ - C/C++ 库从 Internet 广播和 Podcast Feeds 获取播放列表?

c - I/O、写入本地驱动器上的文件或写入套接字,哪个更快?

java - 一个线程可以同时处理多个请求吗?