Android JT808协议通讯,使用OkSocket实现长连接;

先看一下JT808数据的组成和OkSocket接收消息方式;

1、JT808数据的组成

标识位采用0x7e 表示,若校验码、消息头以及消息体中出现0x7e,则要进行转义处理,转义
规则定义如下:
0x7e <————> 0x7d后紧跟一个0x02;
0x7d <————> 0x7d后紧跟一个0x01。
转义处理过程 如下:
发送消息时:消息封装——>计算并填充校验码——>转义;
接收消息时:转义还原——>验证校验码——>解析消息。
示例:
发送一包内容为:0x3 00x7e 0x08 0x7d 0x55的数据包,
则经过封装如下:0x7e 0x30 7d 0x02 0x08 0x7d 0x01 0x55 0x7e。

2、OkSocket接收消息方式:

注意:
Header :指的是数据协议中定长部分,该部分应该包含后面不定长的Body(Payload)的字节长度.
Body(Payload) :指的是不定长部分,通常是数据区:

出现的问题:

我以为使用OkSocket实现JT808协议通讯这种方法是完美的,直到我频繁遇到这种数据(数据包②没有尾部标识位):

①、7E 80 01 00 05 01 56 51 82 18 22 00 7B 00 7C 00 02 00 4F 7E
②、7E 80 01 00 05 01 56 51 82 18 22 00 7C 00 7D 01 02 00 00 49

数据②中没有尾部标识位7E,我告诉后台应答的数据不全,后台检查后说没有问题,而且IOS端也没有出现该问题;

检查数据后发现数据②中有一个"7D 01"数据,该数据按照转义规则是由 "7E"转义后的,所以本来占一个Byte位 "7E"变成了占两个Byte位的"7D 01",根据OkSocket的规则(固定消息头,从消息头中获取消息体的长度)所以没有获取到最后的标识位;

正想通知后台把从消息头中获取消息体的长度改为转义后的,想到消息头中的数据包可能被转义,所以转义后的消息头就变为不固定长度的了;

按照JT808的数据组成规则,消息头的长度不是固定的;则不能使用OkSocket的接收方式;

解决方法:

重写OkSocket数据包接收方式OkSocket接收所有数据,可以不固定协议头


  //接收byte数组
    @Override
    public void read() throws RuntimeException {
        OriginalData originalData = new OriginalData();
        try {
            InputStream is = mInputStream;
            DataInputStream input = new DataInputStream(is);
            byte[] b = new byte[1024 * 1024];
            ByteArrayOutputStream bos = new ByteArrayOutputStream();

            int len = 0;
            while (true) {
                len = input.read(b);
                bos.write(b, 0, len);
                originalData.setBodyBytes(bos.toByteArray());
                mStateSender.sendBroadcast(IOAction.ACTION_READ_COMPLETE, originalData);
                bos.reset();
            }
        } catch (Exception e) {
            ReadException readException = new ReadException(e);
            throw readException;
        }
    }

把数据包全部放在消息体中:

  @Override
  public void onSocketReadResponse(ConnectionInfo info, String action, OriginalData data) {
         byte[] body = data.getBodyBytes(); //原数据
  }

这样就可以拿到全部的数据了,但是没有了从消息头确定消息尾的长度功能后,有可能会出现粘包的情况 Socket 粘包 拆包

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章