0

Now, for a number of reasons I need to ping several hosts on a regular basis for a dashboard display.

I use this PHP function to do it:

function PingHost($strIpAddr) {
        exec(escapeshellcmd('ping -q -W 1 -c 1 '.$strIpAddr), $dataresult, $returnvar);
        if (substr($dataresult[4],0,3) == "rtt") {
                //We got a ping result, lets parse it.
                        $arr = explode("/",$dataresult[4]);
                        return ereg_replace(" ms","",$arr[4]);
        } elseif (substr($dataresult[3],35,16) == "100% packet loss") {
                //Host is down!
                        return "Down";
        } elseif ($returnvar == "2") {
                return "No DNS";
        }
}

The problem is that whenever there is an unknown host, I will get an error logged to my apache error log (/var/log/apache/error.log). How would I go about disabling logs for this particular function ?

Disabling logs in the vhost is not an option since logs for that vhost are relevant, just not the pings.

Thanks,

2 Answers 2

1

you need to change something into your function - basically exec doesn't catch standard error which gets written into the log file - you need to change the function as follow

function PingHost($strIpAddr) {
    exec(escapeshellcmd('ping -q -W 1 -c 1 '.$strIpAddr.' 2>&1'), $dataresult, $returnvar);
    if (substr($dataresult[4],0,3) == "rtt") {
            //We got a ping result, lets parse it.
                    $arr = explode("/",$dataresult[4]);
                    return ereg_replace(" ms","",$arr[4]);
    } elseif (substr($dataresult[3],35,16) == "100% packet loss") {
            //Host is down!
                    return "Down";
    } elseif ($returnvar == "2") {
            return "No DNS";
    }
    if($returnvar == 68)
            return "Unknown host";

}

3
  • Shell commands have 2 types of standard output: stdout and stderr. With that command you redirect stderr to stdout. I think it should work. Another option could have been ' 2>/dev/null'
    – LatinSuD
    Dec 31, 2010 at 13:23
  • Unfortunately, neither adding .' 2>&1', .' 2>/dev/null' or .' > /dev/null 2>&1' work. Nice idea though, I hadn't thought about that. If I add these, what I get is something like "ping: unknown host 2>/dev/null"
    – fooraide
    Dec 31, 2010 at 14:03
  • Ok, I found it - you've pointed me on the right track. Adding .' 2>/dev/null' and removing "escapeshellcmd" worked. Thanks !
    – fooraide
    Dec 31, 2010 at 14:06
1

This is a pretty old post, but seeing as I found it while diving into a similar issue that I was facing, I figured it might help someone else to share.

I have written the following function to handle all calls to command line functions in my application. It behaves in a similar fashion to exec with a few helpful additions:

  • Accepts an associative array of arguments which are escaped by escapeshellarg and later replaced into the command using strtr
  • Escapes the shell command itself using escapeshellcmd
  • Redirects stderr to stdout using 2>&1 as mentioned above by silviud

The function is as follows:

/**
 * @param string   $command Use ':param_key' to escape arguments.
 * @param string[] $output
 * @param int|null $return
 * @param string[] $args    Use format [ 'param_key' => 'param_value' ].
 *
 * @return string
 */
function safe_exec( $command, &$output = null, &$return = null, $args = array() ) {
    // Escape all args
    foreach( $args as $arg_key => $arg_value ) {
        $args[ ':' . $arg_key ] = escapeshellarg( $arg_value );
        unset( $args[ $arg_key ] );
    }

    // Escape command and replace params
    $command = strtr( escapeshellcmd( $command ), $args ) . ' 2>&1';

    // Exec and return
    return exec( $command, $output, $return );
} // safe_exec

For a quick usage example, this is how I use it to retrieve the tray status of our Ricoh printers:

/**
 * These values are entered by the user (which is why we escape them), 
 * but for example:
 * 
 * $address = '10.243.224.42'
 * $tray = 1
 */

$oid = '1.3.6.1.4.1.367.3.2.1.2.20.2.2.1.11.2.' . $tray;

$command = "snmpwalk -v 2c -c public :address :oid";
safe_exec( $command, $output, $return, array(
    'address' => $address,
    'oid' => $oid,
) );

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .