my code is the following
<?php
$semaphore_key = 2112;
$semaphore_max = 1;
$semaphore_permissions = 0666;
$semaphore_autorelease = 1;
$semaphore = sem_get($semaphore_key, $semaphore_max, $semaphore_permissions, $semaphore_autorelease);
if(!$semaphore)
{
echo "Failed to get semaphore - sem_get().\n";
exit();
}else{
echo "ok\n";
}
sem_acquire($semaphore);
sleep(10);
sem_release($semaphore);
?>
In the linux terminal, I run:
php semaphore.php &
and after 1 sec, I run
php semaphore.php
I expect the second call to the php to exit, but both print "ok" and arrive to the sleep(10), and I don't understand because the semaphore is locked by the other script running in background.
Since semaphore_max is set to 1, I expect the second call to the script to print "Failed to get semaphore - sem_get()." and terminate, but it is not happening.
echo $semaphore results in "Resource id #4", so I suppose sysvsem is working fine.
Someone could help?
Thanks
sem_get() just fetches/constructs the semaphore object, it will only return false if perhaps there are no more resources available to create a semaphore, or if your parameters are invalid.
sem_aquire() is where the expected locking behaviour happens, but you have to pass true into the 2nd argument to not block and return false immediately.
So your code should be:
$semaphore = sem_get($semaphore_key, $semaphore_max, $semaphore_permissions, $semaphore_autorelease);
if(sem_aquire($semaphore, true) === false) {
echo "Failed to get semaphore - sem_get().\n";
exit();
}else{
echo "ok\n";
}
sleep(10);
sem_release($semaphore);
Related
I'm creating a button on my web page.I want that when someone presses this button an execution of a process of Linux commands on my first server (like "cd file" "./file_to_execute"..) when these commandes are done and finished i want to connect on another server by ssh and to execute another commands.
the probleme is how can i know that the commands before are already finished to proceed to the second part which is to connect on another server .
to resume :
first step connect on the first server , execute some commands
=> when these commands are done ( the part i dont know how to do it )
second step : to connect on another server and execute some others commands.
I'm searching for a way that will allows me to add some pop up to inform the user of my web page that he finished the first step and he started the second.
<?php
$hostname = '192.177.0.252';
$username = 'pepe';
$password = '*****';
$commande = 'cd file && ./file_one.sh';
if (false === $connection_first = ssh2_connect($hostname, 22)) {
echo 'failed<br />';
exit();
}
else {
echo 'Connected<br />';
}
if (false === ssh2_auth_password($connection_first, $username, $password)) {
echo 'failed<br />';
exit();
}
else {
echo 'done !<br />';
}
if (false === $stream = ssh2_exec($connection_first, $commande)) {
echo "error<br />";
}
?>
Thanks
PS: sorry for my English, I'm from Barcelone
To handle events where an exception occurs i would recommend using a try/catch statement, like the one below:
try {
echo inverse(5) . "\n";
echo inverse(0) . "\n";
} catch (Exception $e) {
echo 'Caught exception: ', $e->getMessage(), "\n";
}
When you're trying to handle events and need to know when they finish, there are a few ways to achieve this. You can either set a boolean to true after the command has been executed (like what you are already doing). OR you can return output from the command by printing the output to a txt file and then echoing out the returns of this file. See code below:
exec ('/usr/bin/flush-cache-mage > /tmp/.tmp-mxadmin');
$out = nl2br(file_get_contents('/tmp/.tmp-mxadmin'));
echo $out;
At this point you can create conditions based off of what is returned in the $out variable.
I've been searching back and forth looking for a solution to this problem I'm having. It appears that socket_select() will always find accepted sockets (resources returned by socket_accept()) as available to read from, even though there are no packets waiting. I'm sure there's a little something I forgot to do, but I can't figure out what that is.
Here's the relevant code:
while(TRUE){
$read_sockets=$this->client_sockets;
$write_sockets=NULL;
$except=NULL;
if(socket_select($read_sockets, $write_sockets, $except, NULL)<1) continue;
foreach($read_sockets as $pending_socket){
echo "Read request received...".PHP_EOL;
if($this->socket==$pending_socket){
$new_client_socket=socket_accept($this->socket);
socket_write($new_client_socket,$this->read_data($new_client_socket),2048);
$this->client_sockets[]=$new_client_socket;
echo "New client...".PHP_EOL;
} else {
$pending_socket_data=$this->read_data($pending_socket);
if($pending_socket_data===false){
unset($this->client_sockets[array_search($pending_socket,$this->client_sockets)]);
continue;
}
socket_write($pending_socket,$pending_socket_data,2048);
echo "Old client...".PHP_EOL;
}
}
}
private function read_data(&$socket){
echo 'Reading data...'.PHP_EOL;
$client_data='';$tmp='';
while(socket_recv($socket,$tmp,$this->max_length,0) > 0){
$client_data .= $tmp;
}
return $client_data;
}
I know I'm not catching some exceptions, as socket_recv === FALSE, but this code is just a proof of concept, that I had to get down to while debugging the main code.
$this->socket is the server socket, and is non-blocking.
Thank's in advance!
private function read_data(&$socket){
echo 'Reading data...'.PHP_EOL;
$client_data='';$tmp='';
while(socket_recv($socket,$tmp,$this->max_length,0) > 0){
$client_data .= $tmp;
}
return $client_data;
}
Method read_data never return false, so the codes below will never run.
if($pending_socket_data===false){
unset($this->client_sockets[array_search($pending_socket,$this->client_sockets)]);
continue;
}
When socket_recv return false ,you should check socket_last_error() and decide if to socket_close($pending_socket) and unset($this->client_sockets[..]).
When socket_recv return 0, may be socket closed and you should call unset($this->client_sockets[..]).
how can I check if a php ping returned succesfull or failed using php exec, I have in mind something with a while loop but I'm not sure if ts the best approach, I tried:
exec('ping www.google.com', $output)
but I would have to do a var_dump($output); to see the results, I want for each line the ping command returns to check it
$i = 2;
while(exec('ping www.google.com', $output)) {
if($output) {
echo 'True';
} else {
echo 'False';
}
}
I know this code is WRONG but its kind of what I need, if any of you could give me a head start on how to do it or suggestions I would really appreciate it....THANKS!!
This should do it:
if(exec('ping http://www.google.com')) {
echo 'True';
} else {
echo 'False';
}
I suggest you could use CUrl See Manual but that all depends upon what you are trying to achieve.
Provide more data if needed.
NOTE
You are to use http:// before google.com as that's needed in order to make the ping.
It's probably faster and more efficient and just do it within PHP, instead of exec'ing a shell
$host = '1.2.3.4';
$port = 80;
$waitTimeoutInSeconds = 1;
if($fp = fsockopen($host,$port,$errCode,$errStr,$waitTimeoutInSeconds)){
// It worked
} else {
// It didn't work
}
fclose($fp);
Also some servers will have EXEC disabled for security reasons, so your method won't work on every server setup.
I don't know how to make this.
There is an XML Api server and I'm getting contents with cURL; it works fine. Now I have to call the creditCardPreprocessors state. It has 'in progress state' too and PHP should wait until the progess is finished. I tried already with sleep and other ways, but I can't make it. This is a simplified example variation of what I tried:
function process_state($xml){
if($result = request($xml)){
// It'll return NULL on bad state for example
return $result;
}
sleep(3);
process_state($xml);
}
I know, this can be an infite loop but I've tried to add counting to exit if it reaches five; it won't exit, the server will hang up and I'll have 500 errors for minutes and Apache goes unreachable for that vhost.
EDIT:
Another example
$i = 0;
$card_state = false;
// We're gona assume now the request() turns back NULL if card state is processing TRUE if it's done
while(!$card_state && $i < 10){
$i++;
if($result = request('XML STUFF')){
$card_state = $result;
break;
}
sleep(2);
}
The recursive method you've defined could cause problems depending on the response timing you get back from the server. I think you'd want to use a while loop here. It keeps the requests serialized.
$returnable_responses = array('code1','code2','code3'); // the array of responses that you want the function to stop after receiving
$max_number_of_calls = 5; // or some number
$iterator = 0;
$result = NULL;
while(!in_array($result,$returnable_responses) && ($iterator < $max_number_of_calls)) {
$result = request($xml);
$iterator++;
}
....
else {
$affiliate->setStatus('D');
echo "Before load";die;
if($affiliate->load())
{
echo $affiliate->getUsername();
die(($affiliate->getUsername())."Success to load affiliate");
}
else
{
$chkaffiliate= new Pap_Api_Affiliate($session);
$chkaffiliate->setUsername($_POST['txt_email']);
if($chkaffiliate->load())
{
echo $chkaffiliate->getUsername();
}
die("Failed to load affiliate");
}
die("Failed to process payment,account request declined. <br><br>Please try again using a different email OR Contact our support team to manually approve your account.".$response->error_message);
}
I get the output Failed to process payment...that is, the last die() in the above code, however I don't get the Before Load in the first echo, while both are in the same block. Any ideas?
This is just not possible.
if (something){
die();
}
else{
die();
}
dies everytime, in any case. Search for other die("Failed to process payment"); function calls
Your problem is with this line:
echo "Before load";die;
You die immediately after the echo statement so no other processing will take place!