If using Unix Sockets, and you want to use SO_PEERCRED, you can use the number 17 for the optname (and SOL_SOCKET for the level). The PID of the connecting process will be returned.
(PHP 4 >= 4.3.0, PHP 5, PHP 7, PHP 8)
socket_get_option — ソケットのオプションを取得する
socket_get_option() 関数は、ソケット
socket
のオプション option
の値を取得します。socket_get_option() は、失敗した場合に
false
を返します。
socket
socket_create() あるいは socket_accept() で作成した Socket クラスのインスタンス。
level
level
パラメータは、オプションのプロトコルレベルを指定します。
例えば、オプションをソケットレベルで取得するには
level
パラメータに SOL_SOCKET
を指定します。
TCP
のようなそれ以外のレベルの場合、そのレベルのプロトコル番号を指定します。
プロトコル番号は getprotobyname()
関数を使用して取得可能です。
option
オプション | 説明 | 型 |
---|---|---|
SO_DEBUG |
デバッグ情報を記録するかどうかを報告します。 | int |
SO_BROADCAST |
ブロードキャストメッセージの送信がサポートされているかどうかを報告します。 | int |
SO_REUSEADDR |
ローカルアドレスが再利用可能かどうかを報告します。 | int |
SO_REUSEPORT |
ローカルポートが再利用可能かどうかを報告します。 | int |
SO_KEEPALIVE |
定期的なメッセージの送信によって接続がアクティブになっているかどうかを報告します。 もしソケットがこれらのメッセージに応答できなかった場合、 接続は崩壊し、ソケットへの書き込みを行うと SIGPIPE シグナルを受け取ります。 | int |
SO_LINGER |
データがまだ残っているうちに socket_close()
をコールした場合に、 l_onoff が非ゼロで l_linger がゼロの場合は、 その時点で未送信のデータはすべて破棄されます。 接続ベースのソケットの場合、接続先には RST (リセット) を送信します。 一方 l_onoff が非ゼロで l_linger も非ゼロの場合は、 socket_close() は 全データを送信し終えるか l_linger で指定した時間が経過するまで処理をブロックします。 ソケットが非ブロックモードの場合は、 socket_close() は失敗してエラーを返します。 |
array。配列に含まれるキーは l_onoff および l_linger のふたつ。 |
SO_OOBINLINE |
socket
が帯域外のデータをインラインに残し続けるかを報告します。
|
int |
SO_SNDBUF |
送信バッファのサイズを報告します。 | int |
SO_RCVBUF |
受信バッファのサイズを報告します。 | int |
SO_ERROR |
エラーステータスに関する情報を報告し、それをクリアします。 | int (socket_set_option() で設定することはできません) |
SO_TYPE |
socket の型 (たとえば SOCK_STREAM ) を報告します。
|
int (socket_set_option() で設定することはできません) |
SO_DONTROUTE |
送信メッセージがルータを越えるかどうかを報告します。 | int |
SO_RCVLOWAT |
socket の入力操作を行う際の最小バイト数を報告します。
|
int |
SO_RCVTIMEO |
入力操作のタイムアウト値を報告します。 | array。配列に含まれるキーはふたつ。 sec はタイムアウトの秒単位の部分で、 usec はタイムアウトのマイクロ秒位の部分。 |
SO_SNDTIMEO |
出力関数がフロー制御のためにブロックするタイムアウト値を報告します。 | array。配列に含まれるキーはふたつ。 sec はタイムアウトの秒単位の部分で、 usec はタイムアウトのマイクロ秒位の部分。 |
SO_SNDLOWAT |
socket
の出力操作を行う際の最小バイト数を報告します。
|
int |
TCP_NODELAY |
Nagle TCP アルゴリズムが無効になっているかどうかを報告します。 | int |
MCAST_JOIN_GROUP |
マルチキャストグループに参加します。 |
二つのキー "group" と "interface"
を含む配列。"group" には IPv4 あるいは IPv6
のマルチキャストアドレスを文字列で指定します。
"interface" には、インターフェイス番号 (整数値)
あるいは "eth0" などのインターフェイス名 (文字列) を指定します。
0 を指定すると、ルーティングテーブルを使ってインターフェイスを選択します
(socket_set_option() でのみ利用可能)。
|
MCAST_LEAVE_GROUP |
マルチキャストグループから離れます。 |
配列。詳細は MCAST_JOIN_GROUP を参照ください
(socket_set_option() でのみ利用可能)。
|
MCAST_BLOCK_SOURCE |
特定のソースから、そのマルチキャストグループにやってくるパケットをブロックします。 そのマルチキャストグループに事前に参加しておく必要があります。 |
MCAST_JOIN_GROUP と同じキーを含み、さらに追加でもうひとつのキーを含む配列。
追加のキーは source で、
ブロック対象となるソースの IPv4 アドレスあるいは IPv6 アドレスを文字列で指定します
(socket_set_option() でのみ利用可能)。
|
MCAST_UNBLOCK_SOURCE |
特定のソースから、そのマルチキャストグループにやってくるパケットのブロックを解除 (そして、受信を再開) します。 そのマルチキャストグループに事前に参加しておく必要があります。 |
MCAST_BLOCK_SOURCE と同じ形式の配列
(socket_set_option() でのみ利用可能)。
|
MCAST_JOIN_SOURCE_GROUP |
特定の値にマッチするソースアドレスからそのマルチキャストグループにやってきたパケットを受信します。 |
MCAST_BLOCK_SOURCE と同じ形式の配列
(socket_set_option() でのみ利用可能)。
|
MCAST_LEAVE_SOURCE_GROUP |
特定の値にマッチするソースアドレスからそのマルチキャストグループにやってきたパケットの受信を停止します。 |
MCAST_BLOCK_SOURCE と同じ形式の配列
(socket_set_option() でのみ利用可能)。
|
IP_MULTICAST_IF |
IPv4 マルチキャストパケットの送信インターフェイス。 |
インターフェイス番号を表す整数値か、インターフェイス名を表す
eth0 のような文字列。
0 を指定すると、ルーティングテーブルを使ってインターフェイスを選択します。
socket_get_option() 関数の戻り値は、インターフェイスのインデックスとなります。
注意すべき点は、C の API とは違ってこのオプションには IP アドレスを渡せないということです。
そのため、
IP_MULTICAST_IF と
IPV6_MULTICAST_IF のインターフェイスの相違はなくなります。
|
IPV6_MULTICAST_IF |
IPv6 マルチキャストパケットの送信インターフェイス。 |
IP_MULTICAST_IF と同じ。
|
IP_MULTICAST_LOOP |
IPv4 パケットのマルチキャストループバックポリシー。 これを有効にすると、以前に参加したグループに、 マルチキャストのデータをループバックさせることができます。 このオプションの効果は、unix で有効にするか Windows で有効にするかで異なります。 前者は受信先のパスに影響するのに対し、 後者では送信元のパスに影響します。 |
整数値 (0 あるいは
1 )。socket_set_option()
では任意の値を受け付けますが、通常の PHP のルールに従ってそれを
boolean 値に変換します。
|
IPV6_MULTICAST_LOOP |
IP_MULTICAST_LOOP の IPv6 版。
|
整数値。IP_MULTICAST_LOOP を参照ください。
|
IP_MULTICAST_TTL |
IPv4 送信パケットの有効期間。0 (このインターフェイスから離れない) から 255 までの値を指定しなければなりません。デフォルトは 1 (ローカルネットワークにだけ到達する) です。 | 0 から 255 までの整数値。 |
IPV6_MULTICAST_HOPS |
IP_MULTICAST_TTL の IPv6 版。
値として -1 を指定することもでき、これはデフォルトのルートを使うことを意味します。
|
-1 から 255 までの整数値。 |
SO_MARK |
Linux でパケットフィルタを行う目的で、 ソケットの識別子を設定します。 | int |
SO_ACCEPTFILTER |
listen しているソケットに対し、accept filter を追加します (FreeBSD/NetBSD)。 accept filter カーネルモジュールは、FreeBSD では前もってロードしておく必要があります (e.g. accf_http)。 | フィルタの名前を示す文字列 (最大15文字) |
SO_USER_COOKIE |
FreeBSD でパケットフィルタを行う目的で、 ソケットの識別子を設定します。 | int |
SO_RTABLE |
OpenBSD でパケットフィルタを行う目的で、 ソケットの識別子を設定します。 | int |
SO_DONTTRUNC |
未読のデータを保持します。 | int |
SO_WANTMORE |
さらにデータが読み取れる時にヒントを与えます。 | int |
TCP_DEFER_ACCEPT |
データが利用可能になるまでソケットに通知しません。 | int |
SO_INCOMING_CPU |
ソケットの CPU affinity の情報を取得/設定します。 | int |
SO_MEMINFO |
ソケットの meminfo を全て取得します。 | int |
SO_BPF_EXTENSIONS |
ソケットにアタッチするための、 kernel がサポートしている BPF 拡張を取得します。 | int |
SO_SETFIB |
ソケットの route table (FIB) を設定します(FreeBSD のみ) | int |
SOL_FILTER |
ソケットの属性をフィルタします(Solaris/Illumos のみ) | int |
TCP_KEEPCNT |
接続を切断する前に、TCP が送信すべき keepalive プローブの最大数を設定します | int |
TCP_KEEPIDLE |
接続がアイドル状態である必要がある、時間を設定します | int |
TCP_KEEPINTVL |
個別の keepalive プローブを送信する間隔を設定します | int |
TCP_KEEPALIVE |
接続がアイドル状態である必要がある、時間を設定します(macOS のみ) | int |
TCP_NOTSENT_LOWAT |
ソケットストリームの書き込みキュー中の、未送信のデータ数を制限します(Linuxのみ) | int |
指定したオプションの値を返します。
失敗した場合に false
を返します
バージョン | 説明 |
---|---|
8.0.0 |
socket は、Socket クラスのインスタンスになりました。
これより前のバージョンでは、リソース型でした。
|
例1 socket_get_option() の例
<?php
$socket = socket_create_listen(1223);
$linger = array('l_linger' => 1, 'l_onoff' => 1);
socket_set_option($socket, SOL_SOCKET, SO_LINGER, $linger);
var_dump(socket_get_option($socket, SOL_SOCKET, SO_REUSEADDR));
?>
If using Unix Sockets, and you want to use SO_PEERCRED, you can use the number 17 for the optname (and SOL_SOCKET for the level). The PID of the connecting process will be returned.
Just 2 notes here:
- On UNIX, If SO_DEBUG is set, the php program needs an effective user id of 0.
- activating SO_OOBINLINE on a socket is equivalent to passing MSG_OOB flag to each recieving functions used with that socket (eg: socket_recv, socket_recvfrom).
I was playing around with this option to use multiply socket connections with same hostname and same port (IRC). However the socket function needed for this is SO_REUSEPORT.
Though the majority of linux distro's does not have that yet officially implented in there distro's.
However for debian there is an patch that can be installed to get it working:
https://git.kernel.org/cgit/linux/kernel/git/torvalds/linux.git/commit/?id=c617f398edd4db2b8567a28e899a88f8f574798d
it has some work but I got it working after a while (Noobie in debian) maybe some other people are facing the same problem as I was.
to receive UDP DHCP packets on a dedicated interface, you have to use the undocumented option SO_BINDTODEVICE:
<?php
$socket = socket_create(AF_INET, SOCK_DGRAM, SOL_UDP);
socket_set_option($socket, SOL_SOCKET, SO_BINDTODEVICE, 'eth1');
socket_set_option($socket, SOL_SOCKET, SO_BROADCAST, 1);
socket_set_option($socket, SOL_SOCKET, SO_REUSEADDR, 1);
socket_set_option($socket, SOL_SOCKET, SO_REUSEPORT, 1);
socket_bind($socket, '255.255.255.255', 67);
while (1) {
if ($src = @socket_recv($socket, $data, 9999, 0)) {
echo $data . PHP_EOL;
}
}
?>