一个硬件往服务器端口上发送数据(抓包软得到的是正确的16进制),通过抓包软件抓取的数据是正常的(16进制),然而通过php的socket接受到的数据(通过转换后也是16进制,未转换是乱码),下面贴上代码,请高手帮忙看下哪里错了。为什么php的socket获取的数据和抓包软件获取的不一样通过抓包软件获取的正确代码是(16进制的):FA 01 01 FF AA 03 00 01 00 0B 00 00 00 A3
通过php socket获得的数据(通过dechex(),ord()转换后的,和软件抓取的不一样,是错误的):fa 7 25 2 fa 2 0 9 f6 4 2c 88 fa 1下面贴上php的socket代码:<?php
error_reporting(E_ALL);
set_time_limit(0);
ini_set("allow_call_time_pass_reference",true);//监听端口
$PORT = 8888;
//最大连接池
$MAX_USERS = 50000;
//创建监听端口
//$sock = socket_create_listen($PORT);
$commonProtocol = getprotobyname("tcp");
$sock = socket_create(AF_INET, SOCK_STREAM, $commonProtocol);
@socket_bind($sock, '192.168.1.101', 8888);
@socket_listen($sock);
if (!$sock)
{
    exit(1);
}
//不阻塞
socket_set_nonblock($sock);$connections = array();
$input = array();
$close = array();while (true)
{
//sleep(3);
    $readfds = array_merge($connections, array($sock));
    $writefds = array();    //选择一个连接,获取读、写连接通道
    if (socket_select($readfds, $writefds, $e = null, $t=60))
    {
        foreach ($readfds as $rfd)
        {
            //如果是当前服务端的监听连接
            if ($rfd == $sock)
            {
                //接受客户端连接
                $newconn = socket_accept($sock);
                $i = (int)$newconn;
                $reject = '';
                if (count($connections) >= $MAX_USERS)
                {
                    $reject = "Server full. Try again later.\n";                   
                }                
                //将当前客户端连接放如socket_select选择
                $connections[$i] = $newconn;
                //输入的连接资源缓存容器
                $writefds[$i] = $newconn;               
                //连接不正常
                if ($reject)
                {                  
                    $close[$i] = true;
                }
                else
                {
                    echo "Welcome to the PHP Chat Server!\n";                  
                }               
                //初始化当前连接读取内容的缓存容器
                $input[$i] = "";
                continue;
            }
            //客户端连接
            $i = (int)$rfd;
            //读取
            $tmp = @socket_read($rfd, 14, PHP_NORMAL_READ);
            if (!$tmp)
            {
                //读取不到内容              
                print "connection closed on socket $i\n";
                close($i);
                continue;
            }
            $input[$i] .= $tmp;
            $tmp = substr($input[$i], -1);
            /*if ($tmp != "\r" && $tmp != "\n")
            {
                // no end of line, more data coming
                continue;
            }*/
            $line = trim($input[$i]);
            $input[$i] = "";
            echo 'Client >>'.$line."\r\n";



$data=str_split($line);
 
 print_r($data);
 echo "\r\n";

//$data = explode("\t",$line);
//$data=str_split($data);
foreach($data as $v){
 echo dechex(ord($v))."\t";
 
 }
 echo "\r\n";




socket_getpeername($connections[$i],&$remoteIP,&$remotePort);
echo $remoteIP."\r\n";
echo $remotePort."\r\n";
//$data=str_split($buffer);
//print_r($data);
$str="\xFA\x01\x01\xFF\xAA\xAA\x00\x01\x00\x00\x00\x00\x00\x01";
 socket_send($connections[$i],$str,strlen($str),0);






        }
        foreach ($writefds as $wfd)
        {
            $i = (int)$wfd;
            $w = socket_write($wfd, "hello");
        }
    }   
}function close($i)
{
    global $connections, $input, $close;
    socket_shutdown($connections[$i]);
    socket_close($connections[$i]);
    unset($connections[$i]);
    unset($input[$i]);   
    unset($close[$i]);
}
?>

解决方案 »

  1.   

    完全模拟你的现场和代码
    $str="\xFA\x01\x01\xFF\xAA\xAA\x00\x01\x00\x00\x00\x00\x00\x01";$line = $str;
    $data = str_split($line);
    foreach($data as $v){
      echo dechex(ord($v))."\t";
    }
    得到
    fa 1 1 ff aa aa 0 1 0 0 0 0 0 1 没看出有什么差别
      

  2.   


    你这个模拟的是发给硬件的数据是正常的,我的需求是:硬件发的数据我用socket接受不正常,通过抓包工具得到的数据是正确的(FA 01 01 FF AA 03 00 01 00 0B 00 00 00 A3),而用socket得到的数据,在dos下是乱码,我通过dechex(ord(得到的数据))转换后是:fa 7 25 2 fa 2 0 9 f6 4 2c 88 fa 1(是错误的),我想得到的是和抓包工具得到的一样的数据(即:FA 01 01 FF AA 03 00 01 00 0B 00 00 00 A3)
      

  3.   

    你有 $line = trim($input[$i]); 这是接受到的数据吧?
    1、去掉 trim,否则传入的数据可能会被截断
    2、因为是二进制数据,你 echo base64_encode($input[$i]); 贴出结果
      

  4.   

    +gclAvoCAAn2BCyI+gEB+v/6AQH/qqoAAQAAAAAAAfoBAf+qqgABAAAA
    这是得到的数据
      

  5.   

    $s = base64_decode('+gclAvoCAAn2BCyI+gEB+v/6AQH/qqoAAQAAAAAAAfoBAf+qqgABAAAA');
    print_r(unpack('H*', $s));
    //或
    for($i=0; $i<strlen($s); $i++) printf(' %02X', ord($s{$i}));
      

  6.   

    我现在用php socket收到的数据是箭头所指的数据(并且放在变量$a中),我现在想将她转换成图中圈中阴影部分的数据(也就是16进制),改如何转换呢?
      

  7.   


    我现在用php socket收到的数据是箭头所指的数据(并且放在变量$a中),我现在想将她转换成图中圈中阴影部分的数据(也就是16进制),改如何转换呢?
      

  8.   


    现在的确是可以获取到代码了,但是少了3个16进制的数据获取到的代码是:fa072502fa020009f6042c88fa0101fafffa0101ffaa030001000b00抓包得到的是:FA 01 01 FF AA 03 00 01 00 0B 00 00 00 A3也就是少了 00 00 A3