123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180 |
- <?php
- namespace Workerman\Protocols;
- class Gps {
-
-
- public static function input( $buffer, $connection ){
- if (strlen($buffer) < 4) {
- return 0;
- }
- $unpack_data = unpack('C1magic/C1method/n1length', $buffer);
- return $unpack_data['length'] + 6;
- }
-
-
- private static function bin2str( $hex, $space ){
- $data = unpack("C*chars",$hex);
- $bin = '';
- foreach($data as $key=>$value){
- $bin .= sprintf('%02X',$value);
- if($space)
- $bin .= ' ';
- }
- return trim($bin);
- }
-
-
- private static function packValue( $value ){
- if($value['cmd'] == 0x02){
- return pack('C1',$value['result']);
- }
- elseif($value['cmd'] == 0x04){
- return pack('C1',$value['result']);
- }
- elseif($value['cmd'] == 0x03){
- return pack('n1',$value['data']);
- }
- elseif($value['cmd'] == 0x01 || $value['cmd'] == 0xBE){
- return pack('H*', $value['data']);
- }
- else{
- return false;
- }
- }
-
-
- private static function unpackValue( $cmd, $value, $length ){
- if($cmd == 0x01){ //设备注册
- if($length == 6)
- return array('uid' => self::bin2str($value,false) );
- else
- return null;
- }
- elseif($cmd == 0x05){ //设备心跳
- return null;
- }
- elseif($cmd == 0x07){ //上报IMSI
- if($length == 21){
- return array(
- 'uid' => self::bin2str(substr($value,0,6),false) ,
- 'imsi' => substr($value,6,15)
- );
- }
- else
- return null;
- }
- elseif($cmd == 0x08){ //设备响应
- if($length == 2){
- return array(
- 'type' => Ord(substr($value,0,1)) ,
- 'result' => Ord(substr($value,1,1))
- );
- }
- else
- return null;
- }
- elseif($cmd == 0xbe){ //上报地理位置
- if($length == 20){
- //解析设置的时间间隔,设置的设备数量
- //$info = unpack('C1status/C1nbsphere/C1dxsphere/C1speed1/C1speed2/n1longitude/n1latitude/', substr($value,10,4));
- $info = array();
- //定位状态
- $info['state'] = Ord(substr($value,0,1));
- //南北半球
- $info['nbsphere'] = Ord(substr($value,1,1));
- //东西半球
- $info['dxsphere'] = Ord(substr($value,2,1));
- //速度
- $speed1 = Ord(substr($value,3,1));
- $speed2 = Ord(substr($value,4,1));
- $info['speed'] = $speed1 .'.'.$speed2;
- //经度
- $longitude1 = Ord(substr($value,5,1));
- $longitude2 = Ord(substr($value,6,1))*256*256+Ord(substr($value,7,1))*256+Ord(substr($value,8,1));
- $info['longitude'] = $longitude1 .'.'.sprintf("%05d", $longitude2);
- //纬度
- $latitude1 = Ord(substr($value,9,1));
- $latitude2 = Ord(substr($value,10,1))*256*256+Ord(substr($value,11,1))*256+Ord(substr($value,12,1));
- $info['latitude'] = $latitude1 .'.'. sprintf("%05d", $latitude2);
- //解析时间
- $year1 = Ord(substr($value,13,1));
- $year2 = Ord(substr($value,14,1));
- $month = Ord(substr($value,15,1));
- $day = Ord(substr($value,16,1));
- $hour = Ord(substr($value,17,1));
- $minute = Ord(substr($value,18,1));
- $second = Ord(substr($value,19,1));
- $info['time'] = sprintf("%02d%02d-%02d-%02d %02d:%02d:%02d",$year1 ,$year2 ,$month, $day, $hour, $minute, $second);
-
- return $info;
- }
- else
- return null;
- }
- elseif($cmd == 0xbd){ //上报报警
- if($length == 1)
- return array('v' => self::bin2str($value) );
- else
- return null;
- }
- return $value;
- }
-
-
- public static function decode( $buffer ){
- //解码头部数据
- $unpack_head = unpack('C1magic/C1cmd/n1length', $buffer);
- $unpack_head['method'] = sprintf("method%'04x",$unpack_head['cmd']);
- //判断头部引导符
- if( $unpack_head['magic'] != 0xEC )
- return null;
- //判断最后结尾符
- if( Ord(substr($buffer,-1)) != 0x68 )
- return null;
- //判断签名是否正确
-
- //如果长度等于0则没有值数据
- if($unpack_head['length'] == 0)
- return $unpack_head;
-
- //解码值数据
- $value = substr($buffer,4,$unpack_head['length']);
- $unpack_value = self::unpackValue($unpack_head['cmd'],$value,$unpack_head['length']);
- if(!$unpack_value)
- return null;
-
- //头部+值一起返回
- return array_merge($unpack_head,$unpack_value);
- }
-
-
- public static function encode( $value ){
- $pack_value = self::packValue($value);
- $length = strlen($pack_value);
- $sign = $value['cmd'] + $length;
- for($i=0;$i<strlen($pack_value);$i++){
- $sign += Ord($pack_value[$i]);
- }
- $buf = pack('C1C1n1', 0xEC,$value['cmd'],$length) . $pack_value .pack('C1', $sign). pack('C1', 0x68);
- return $buf;
- }
-
-
- private static function str2bin( $text ){
- if (!is_string($text))
- return null;
- $arr = explode(' ',$text);
- $bin = '';
- foreach($arr as $hex){
- if(strlen($hex) == 2){
- $bin .= chr( hexdec($hex) );
- }
- }
- return $bin;
- }
-
- }
|