All this code is run on my local machine
Hi.
I am trying to learn how to properly use sockets.
I created two scripts, the following:
socket.php :
<?php
$address = "10.0.1.13";
$port = 19132;
$socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
if($socket === false){
console("Failed to create socket.");
exit(1);
}
if(socket_bind($socket, $address, $port) === false){
console("CANNOT BIND SOCKET -BYE!");
exit(1);
}
$stop = false;
$start = microtime(true);
console("Socket started ($address) : $port");
while(!$stop){
}
socket_close($socket);
console("Script stopped.");
function console($message){
echo $message . "\n";
}
?>
reader.php :
<?php
$address = "10.0.1.13";
$port = 19132;
/* Allow the script to hang around waiting for connections. */
set_time_limit(0);
/* Turn on implicit output flushing so we see what we're getting
* as it comes in. */
ob_implicit_flush();
if (($socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP)) === false) {
echo "socket_create() failed: reason: " . socket_strerror(socket_last_error()) . "\n";
}
if(socket_connect($socket, $address, $portph) === false){
console("CANNOT CONNECT SOCKET -BYE!");
exit(1);
}
//socket_set_nonblock($socket);
console("success!");
function console($message){
echo $message . "\n";
}
?>
The goal is too run socket.php, and have reader.php connect to the socket. Though, I am always getting Can't assign requested address when trying to connect to socket with reader.php. I don't understand what am I doing wrong.
How can I fix this?
As per PHP.net
Note:
This function must be used on the socket before socket_connect().
you can refer to - [http://php.net/manual/en/function.socket-bind.php][1]
Related
I have a server up online, and I made a simple TCP/IP Server using PHP to handle a certain port. The code I use is found below:
<?php
error_reporting(E_ALL);
/* Allow the script to wait for connections. */
set_time_limit(0);
/* Activate the implicit exit dump, so we'll see what we're getting
* while messages come. */
ob_implicit_flush();
$address = '123.456.789.123';
$port = 1234;
if (($sock = socket_create(AF_INET, SOCK_STREAM, SOL_TCP)) === false) {
echo "socket_create() failed: reason: " . socket_strerror(socket_last_error()) . "\n";
}
if (socket_bind($sock, $address, $port) === false) {
echo "socket_bind() failed: reason: " . socket_strerror(socket_last_error($sock)) . "\n";
}
if (socket_listen($sock, 5) === false) {
echo "socket_listen() failed: reason: " . socket_strerror(socket_last_error($sock)) . "\n";
}
//clients array
$clients = array();
do {
$read = array();
$read[] = $sock;
$read = array_merge($read,$clients);
$write = NULL;
$except = NULL;
$tv_sec = 5;
// Set up a blocking call to socket_select
if(socket_select($read, $write, $except, $tv_sec) < 1)
{
// SocketServer::debug("Problem blocking socket_select?");
echo "socket continuing";
continue;
}
// Handle new Connections
if (in_array($sock, $read)) {
if (($msgsock = socket_accept($sock)) === false) {
echo "socket_accept() failed: reason: " . socket_strerror(socket_last_error($sock)) . "\n";
break;
}
$clients[] = $msgsock;
$key = array_keys($clients, $msgsock);
$msg = "\Welcome to the PHP Test Server. \n" .
"You are the customer number: {$key[0]}\n" .
"To exit, type 'quit'. To close the server type 'shutdown'.\n";
socket_write($msgsock, $msg, strlen($msg));
}
// Handle Input
foreach ($clients as $key => $client) { // for each client
if (in_array($client, $read)) {
if (false === ($buf = socket_read($client, 2048, PHP_NORMAL_READ))) {
echo "socket_read() failed: reason: " . socket_strerror(socket_last_error($client)) . "\n";
break 2;
}
if (!$buf = trim($buf)) {
continue;
}
if ($buf == 'quit') {
unset($clients[$key]);
socket_close($client);
break;
}
if ($buf == 'shutdown') {
socket_close($client);
break 2;
}
$talkback = "Client {$key}: You said '$buf'.\n";
socket_write($client, $talkback, strlen($talkback));
echo "$buf\n";
}
}
} while (true);
socket_close($sock);
?>
The script just basically runs and allows for more than one connection to run. After uploading the code to the server, I connected to the server, got to the directory where the file is, and then ran php filename.php. It does not show any warning or errors.
However, I need to further configure this TCP/IP Server and do things based on the input it receives. Right now, when I run php filename.php, it doesn't show anything (I'm guessing because all the outputs are written to the socket, and not echoed).
How do I test this TCP/IP Server that I made? telnet is out of the question since it's not secure. Right now I'm looking for nothing too complicated, so the Terminal or another simple PHP File would be a good choice.
I would try to use react/socket for your testing purposes. It allows to create clients and servers pretty fast. Try this client code just to get started:
<?php
require_once __DIR__ . "/vendor/autoload.php";
$loop = React\EventLoop\Factory::create();
$connector = new React\Socket\Connector($loop);
$connector->connect('127.0.0.1:1234')->then(function (React\Socket\ConnectionInterface $conn) use ($loop) {
$conn->on('data', function ($data) use ($conn) {
echo $data;
$conn->close();
});
});
$loop->run();
The documentation is here.
I am working on Client Server Socket Program for chat like application, but it is giving following error message
Warning: socket_bind(): unable to bind address [98]: Address already in use.... Could not bind to address on line 15
I have seen various tutorials, but i want Server to listen to client request continuously. I have seen port number it is open also but still the same message. I am stuck at this point for several days could not get proper solutions. Please help to solve it thanks.....
Server.php:
<?php
error_reporting(E_ALL);
/* Allow the script to hang around waiting for connections. */
set_time_limit(0);
/* Turn on implicit output flushing so we see what we're getting
* as it comes in. */
ob_implicit_flush();
$address = 'XXX.XX.XX.XXX';
$port = 15213;
if (($sock = socket_create(AF_INET, SOCK_STREAM, SOL_TCP)) === false) {
echo "socket_create() failed: reason: " . socket_strerror(socket_last_error()) . "\n";
}
if (socket_bind($sock, $address, $port) === false) {
echo "socket_bind() failed: reason: " . socket_strerror(socket_last_error($sock)) . "\n";
}
if (socket_listen($sock, 5) === false) {
echo "socket_listen() failed: reason: " . socket_strerror(socket_last_error($sock)) . "\n";
}
do {
if (($msgsock = socket_accept($sock)) === false) {
echo "socket_accept() failed: reason: " . socket_strerror(socket_last_error($sock)) . "\n";
break;
}
/* Send instructions. */
$msg = "\nWelcome to the PHP Test Server. \n" .
"To quit, type 'quit'. To shut down the server type 'shutdown'.\n";
socket_write($msgsock, $msg, strlen($msg));
do {
if (false === ($buf = socket_read($msgsock, 2048, PHP_NORMAL_READ))) {
echo "socket_read() failed: reason: " . socket_strerror(socket_last_error($msgsock)) . "\n";
break 2;
}
if (!$buf = trim($buf)) {
continue;
}
if ($buf == 'quit') {
break;
}
if ($buf == 'shutdown') {
socket_close($msgsock);
break 2;
}
$talkback = "PHP: You said '$buf'.\n";
socket_write($msgsock, $talkback, strlen($talkback));
echo "$buf\n";
} while (true);
socket_close($msgsock);
} while (true);
socket_close($sock);
?>
Client.php
<?php
error_reporting(E_ALL);
echo "<h2>TCP/IP Connection</h2>\n";
/* Get the port for the WWW service. */
$service_port = getservbyname('www', 'tcp');
/* Get the IP address for the target host. */
$address = gethostbyname('www.example.com');
/* Create a TCP/IP socket. */
$socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
if ($socket === false) {
echo "socket_create() failed: reason: " . socket_strerror(socket_last_error()) . "\n";
} else {
echo "OK.\n";
}
echo "Attempting to connect to '$address' on port '$service_port'...";
$result = socket_connect($socket, $address, $service_port);
if ($result === false) {
echo "socket_connect() failed.\nReason: ($result) " . socket_strerror(socket_last_error($socket)) . "\n";
} else {
echo "OK.\n";
}
$in = "HEAD / HTTP/1.1\r\n";
$in .= "Host: www.example.com\r\n";
$in .= "Connection: Close\r\n\r\n";
$out = '';
echo "Sending HTTP HEAD request...";
socket_write($socket, $in, strlen($in));
echo "OK.\n";
echo "Reading response:\n\n";
while ($out = socket_read($socket, 2048)) {
echo $out;
}
echo "Closing socket...";
socket_close($socket);
echo "OK.\n\n";
?>
In both php files you create a Socket on the same port. That is the problem.
The Server has to create the Socket while the client has to use the Socket (not creating it, too)
Two applications can not create the same socket and listen on the same port.
EDIT:
I have tested your script with xampp at localhost. so IP was 127.0.0.1. The Server listened properly on port 15213 and the client connected properly on this port.
That the port was open i saw with the xampp controll panel.
If you use your scripts like you posted here, then you have to replace in Server.php
$address = 'XXX.XX.XX.XXX';
with
$address = '127.0.0.1';
and in Client.php
$address = gethostbyname('www.example.com');
with
$address = gethostbyname('localhost');
or
$address = '127.0.0.1';
I am new to sockets . I have taken reference from code from google but it doesn't seem to work .
I am posting server and client php files. Please identify the issue .
Server.php
<?php
$host = "xxx.xxx.xxx.xxx/myfolder/server.php"; //host
$port = 9000; //port
$socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP) ;
$result = socket_bind($socket, $host, $port);
$result = socket_listen($socket,5);
$spawn = socket_accept($socket);
$input = socket_read($spawn , 1024);
$output = strrev($input)."n";
socket_write($spawn, $output , strlen($output));
socket_close($spawn);
socket_close($socket);
?>
And here's the Client.php
<?
$host = "xxx.xxx.xxx.xxx/myfolder/server.php";
$port = 9000;
$socket = socket_create(AF_INET, SOCK_STREAM, 0) ;
$result = socket_connect($socket, $host, $port) ;
socket_write($socket, $message, strlen($message)) ;
$result = socket_read ($socket, 1024) ;
echo "Reply From Server :".$result;
socket_close($socket);
?>
after having both the above files on my public directory on my hosting.
I first run the command : php -q /var/www/html/myfolder/server.php
but i get this on my cmd shell :
$ php -q /var/www/html/myfolder/server.php
PHP Warning: socket_bind(): Host lookup failed [-10001]: Unknown host in /var/www/html/myfolder/server.php on line 13
Unable to bind socket at server
(and yes port 9000 is open )
When you create a socket server, you don't specify the host as the full URL to your script; that's why the bind is failing.
Take a look at this sample: http://www.php.net/manual/en/sockets.examples.php
#!/usr/local/bin/php -q
<?php
error_reporting(E_ALL);
/* Allow the script to hang around waiting for connections. */
set_time_limit(0);
/* Turn on implicit output flushing so we see what we're getting
* as it comes in. */
ob_implicit_flush();
$address = '192.168.1.53';
$port = 10000;
if (($sock = socket_create(AF_INET, SOCK_STREAM, SOL_TCP)) === false) {
echo "socket_create() failed: reason: " . socket_strerror(socket_last_error()) . "\n";
}
if (socket_bind($sock, $address, $port) === false) {
echo "socket_bind() failed: reason: " . socket_strerror(socket_last_error($sock)) . "\n";
}
if (socket_listen($sock, 5) === false) {
echo "socket_listen() failed: reason: " . socket_strerror(socket_last_error($sock)) . "\n";
}
do {
if (($msgsock = socket_accept($sock)) === false) {
echo "socket_accept() failed: reason: " . socket_strerror(socket_last_error($sock)) . "\n";
break;
}
/* Send instructions. */
$msg = "\nWelcome to the PHP Test Server. \n" .
"To quit, type 'quit'. To shut down the server type 'shutdown'.\n";
socket_write($msgsock, $msg, strlen($msg));
do {
if (false === ($buf = socket_read($msgsock, 2048, PHP_NORMAL_READ))) {
echo "socket_read() failed: reason: " . socket_strerror(socket_last_error($msgsock)) . "\n";
break 2;
}
if (!$buf = trim($buf)) {
continue;
}
if ($buf == 'quit') {
break;
}
if ($buf == 'shutdown') {
socket_close($msgsock);
break 2;
}
$talkback = "PHP: You said '$buf'.\n";
socket_write($msgsock, $talkback, strlen($talkback));
echo "$buf\n";
} while (true);
socket_close($msgsock);
} while (true);
socket_close($sock);
?>
I want to do something like this article:
broadcast to detect Server IP address
and transfer to PHP, does it possible?
The reason is I want to send broadcast socket to server, and the server will return message then I can determine the message is what I want or not to detect the true IP of the message sender.
The code is like:
<?php
error_reporting(E_ALL);
$address = "255.255.255.255";
$port = 10000;
/* Create a udp socket. */
$socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
if ($socket === false) {
echo "socket_create() failed: reason: " . socket_strerror(socket_last_error()) . "<br/>";
} else {
echo "socket successfully created.<br/>";
}
echo "Attempting to connect to '$address' on port '$port'..."."<br/>";
$result = socket_connect($socket, $address, $port);
if ($result === false) {
echo "socket_connect() failed.\nReason: ($result) " . socket_strerror(socket_last_error($socket)) . "<br/>";
} else {
echo "successfully connected to $address."."<br/>";
}
$i="theMessage";
echo "Sending $i to server."."<br/>";
socket_write($socket, $i, strlen($i));
$input = socket_read($socket, 512);
echo "Response from server is: $input"."<br/>";
$ip="";
if($input=="I want")
$ip=socket_send_from_the_IP; // just psuedocode
echo "Closing socket...";
socket_close($socket);
?>
Or is the direction of my question wrong?
I also think that I should use httprequest?
Any answer appreciated.
Hi there's problem with the socket_read function below, it does not return empty string '' after it has finished reading the data. On second call to socket_read() it just hang there, the page keep loading in browser with no return.
It works if the server close the connection, is it a must for server to close the client socket ? Thanks
$json = $_GET['json'];
/* Get the port for the WWW service. */
// $service_port = getservbyname('www', 'tcp');
$service_port = "1111";
/* Get the IP address for the target host. */
$address = "192.168.3.5";
/* Create a TCP/IP socket. */
$socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
if ($socket === false) {
echo "socket_create() failed: reason: " . socket_strerror(socket_last_error()) . "\n";
die();
} else {
//echo "OK.\n";
}
//echo "Attempting to connect to '$address' on port '$service_port'...";
$result = socket_connect($socket, $address, $service_port);
if ($result === false) {
echo "socket_connect() failed.\nReason: ($result) " . socket_strerror(socket_last_error($socket)) . "\n";
die();
} else {
//echo "OK.\n";
}
$out = '';
//echo "Sending HTTP HEAD request...";
$result = socket_write($socket, $json, strlen($json));
if ($result === false) {
echo "socket_connect() failed.\nReason: ($result) " . socket_strerror(socket_last_error($socket)) . "\n";
die();
} else {
//echo "OK.\n";
}
echo socket_read($socket, 2048);
echo socket_read($socket, 2048);
//
// while (socket_read($socket, 2048) !== '') {
// echo $out;
//
// }
//
socket_close($socket);
Yes, that's exactly what I'd expect it to do - socket_read() will never return an empty string unless you open it a binary and the server responds with '\0'.
You seem to be trying to write an HTTP client. If you are, STOP NOW, throw away your code and go read up on the Curl extension. HTTP is not a simple protocol, and you've still got a lot to learn about how the simple stuff works. You are curently relying on the socket state and the format of the data to determine the data flow - but HTTP uses neither.
If you want to learn how HTTP works, then there's lots of documentation on the internet - the RFC's are a must, but are not a gentle introduction. If your objective is to develop an application, then use curl (or even the HTTP stream wrappers).