Current Location: Home> Latest Articles> Why do I get stuck when using socket_accept()? What is the difference between blocking mode and non-blocking mode?

Why do I get stuck when using socket_accept()? What is the difference between blocking mode and non-blocking mode?

M66 2025-05-20

When using PHP for network programming, many developers often encounter a problem when using socket_accept() to create a TCP server: the program is stuck and cannot continue to execute. This phenomenon mostly stems from insufficient understanding of "blocking mode" and "non-blocking mode". This article will explain why socket_accept() "stuck" and explain in detail the difference between blocking and non-blocking modes.

1. What is socket_accept() ?

socket_accept() is a function in the PHP Socket extension that accepts connection requests from clients. After you create a socket with socket_create() and use socket_bind() and socket_listen() to start listening, you need to use socket_accept() to receive the connection:

 $socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
socket_bind($socket, '0.0.0.0', 8080);
socket_listen($socket);

while (true) {
    $client = socket_accept($socket);
    // right $client Perform read and write operations
}

In the above example, socket_accept() will keep blocking while waiting for connection until a client connects in.

2. Why is it "stuck"?

The so-called "stuck" is actually the program is waiting for the connection but not returning. This is not a bug, but a normal behavior in blocking mode.

By default, PHP socket is in blocking mode. This means:

  • If no client is connected to the server, socket_accept() will wait;

  • The CPU will not execute subsequent code until socket_accept() returns the result.

So when you are debugging or running the server, without a client connecting, the program will always be "stuck" in the socket_accept() line.

This is acceptable in production environments, because the server just needs to wait for the connection. But in environments where debugging or multiple tasks need to be handled, this blocking behavior may become a problem.

3. Solutions for non-blocking mode

If you want the program to continue to execute without a connection, such as performing certain operations on a regular basis or detecting other events, you need to use non-blocking mode .

Set non-blocking mode:

 socket_set_nonblock($socket);

At this time, socket_accept() will no longer wait, but instead:

  • Return to the client socket when there is a connection;

  • Return false immediately when there is no connection and set the error code to SOCKET_EAGAIN or SOCKET_EWOULDBLOCK .

Sample code:

 $socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
socket_bind($socket, '0.0.0.0', 8080);
socket_listen($socket);
socket_set_nonblock($socket);

while (true) {
    $client = @socket_accept($socket);
    if ($client === false) {
        // No connection,Keep doing other things
        echo "Waiting for connection...\n";
        sleep(1);
    } else {
        // Received the connection successfully
        socket_write($client, "Hello from m66.net\n");
        socket_close($client);
    }
}

4. Use socket_select() to manage blocking more gracefully

Another common practice is to use socket_select() to detect whether there are sockets that can be read and written, which can avoid blind loop checking:

 $read = [$socket];
$write = $except = null;

if (socket_select($read, $write, $except, 5) > 0) {
    $client = socket_accept($socket);
    // Handle client connections
}

This method does not block indefinitely because you can set the timeout time. It is also suitable for scenes where multiple sockets are listened to at the same time and is a common technique in high-performance network programming.

5. Summary

  • socket_accept() is blocking by default, and if there is no connection request, it will wait;

  • Blocking behavior is not a bug, but it will cause the program to "stagnate" while waiting for connection;

  • You can set socket_set_nonblock() to non-blocking mode to avoid program stagnation;

  • A more advanced solution is to use socket_select() to manage the state of multiple sockets.