php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #73307 Stream Socket Server unable to create IPv4/IPv6 Sockets
Submitted: 2016-10-12 16:45 UTC Modified: 2016-10-19 10:43 UTC
From: lucius at luciusgaitan dot com Assigned:
Status: Not a bug Package: Unknown/Other Function
PHP Version: 7.0.11 OS: CentOS 7.2.1511 x64
Private report: No CVE-ID: None
View Add Comment Developer Edit
Welcome! If you don't have a Git account, you can't do anything here.
You can add a comment by following this link or if you reported this bug, you can edit this bug over here.
(description)
Block user comment
Status: Assign to:
Package:
Bug Type:
Summary:
From: lucius at luciusgaitan dot com
New email:
PHP Version: OS:

 

 [2016-10-12 16:45 UTC] lucius at luciusgaitan dot com
Description:
------------
Having a dual stack server, php is unable to create two sockets in the same port for different addresses ipv4 and ipv6.
Only the first attempt to create the socket succeeds, the second returns "PHP Warning:  stream_socket_server(): unable to connect to ... (Address already in use)".

Using the defaults 0.0.0.0 and [::]. If the real ip addresses are defined everything works well.

Also, $errno equals to 0 and returned value is FALSE as described in /manual/en/function.stream-socket-server.php.


./configure --with-config-file-path=/etc --disable-short-tags --enable-bcmath --enable-calendar --enable-gd-native-ttf --enable-mbstring --enable-pdo=shared --enable-sockets --enable-zip --with-curl=/opt/curlssl/ --with-freetype-dir=/usr --with-gd --with-jpeg-dir=/usr --with-mysqli --with-openssl --with-pcre-regex --with-pdo-mysql=shared --with-pdo-sqlite=shared --with-pic --with-png-dir=/usr --with-zlib --with-zlib-dir=/usr --enable-pcntl --with-bz2 -enable-opcache --enable-fpm --with-fpm-systemd



Thank you.



Test script:
---------------
$errno = null; $error = null;
$bindto = ['0.0.0.0', '[::]'];
$socket = [];

for ($x = 0; $x < 2; ++$x) {
    $ctx = stream_context_create(['socket' => ['bindto' => $bindto[$x] . ':3672']]);
    $socket[] = stream_socket_server('tls://' . $bindto[$x] . ':3672', $errno, $error, STREAM_SERVER_BIND | STREAM_SERVER_LISTEN, $ctx);
}


Patches

Add a Patch

Pull Requests

Add a Pull Request

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2016-10-19 10:43 UTC] bwoebi@php.net
-Status: Open +Status: Not a bug
 [2016-10-19 10:43 UTC] bwoebi@php.net
This is behavior of the underlying syscalls; some OS choose to map IPv4 into the IPv6 space in general. (And thus [::] is a superset of 0.0.0.0 there, leading to address already in use.)

Under Linux you may find your default behavior under /proc/sys/net/ipv6/bindv6only (1 if separated, 0 if overlapping).

Additionally, to explicitly control it from the script, PHP 7.0.1+ expose a "ipv6_v6only" socket stream context option.

Try: $ctx = stream_context_create(['socket' => ['ipv6_v6only' => true]]);
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Wed Apr 24 23:01:34 2024 UTC