From d15edaf38717fae7ad482e73c9fcda66da8756a4 Mon Sep 17 00:00:00 2001 From: Anton Tananaev Date: Tue, 27 Jun 2017 17:18:29 +1200 Subject: Support AZ735 GT06 protocol variant --- src/org/traccar/protocol/Gt06ProtocolDecoder.java | 61 ++++++++++++++++------- 1 file changed, 44 insertions(+), 17 deletions(-) (limited to 'src') diff --git a/src/org/traccar/protocol/Gt06ProtocolDecoder.java b/src/org/traccar/protocol/Gt06ProtocolDecoder.java index 0821de722..261c86825 100644 --- a/src/org/traccar/protocol/Gt06ProtocolDecoder.java +++ b/src/org/traccar/protocol/Gt06ProtocolDecoder.java @@ -44,6 +44,8 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { private boolean forceTimeZone = false; private final TimeZone timeZone = TimeZone.getTimeZone("UTC"); + private int serverIndex; + private final Map photos = new HashMap<>(); public Gt06ProtocolDecoder(Gt06Protocol protocol) { @@ -71,6 +73,8 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { public static final int MSG_LBS_STATUS = 0x19; public static final int MSG_GPS_PHONE = 0x1A; public static final int MSG_GPS_LBS_EXTEND = 0x1E; + public static final int MSG_AZ735_GPS = 0x32; + public static final int MSG_AZ735_ALARM = 0x33; public static final int MSG_X1_GPS = 0x34; public static final int MSG_X1_PHOTO_INFO = 0x35; public static final int MSG_X1_PHOTO_DATA = 0x36; @@ -100,13 +104,18 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { || type == MSG_GPS_LBS_STATUS_1 || type == MSG_GPS_LBS_STATUS_2 || type == MSG_GPS_LBS_STATUS_3; } - private void sendResponse(Channel channel, int type, int index) { + private void sendResponse(Channel channel, boolean extended, int type) { if (channel != null) { ChannelBuffer response = ChannelBuffers.dynamicBuffer(); - response.writeShort(0x7878); // header - response.writeByte(5); // size + if (extended) { + response.writeShort(0x7979); + response.writeShort(5); + } else { + response.writeShort(0x7878); + response.writeByte(5); + } response.writeByte(type); - response.writeShort(index); + response.writeShort(++serverIndex); response.writeShort(Checksum.crc16(Checksum.CRC16_X25, response.toByteBuffer(2, response.writerIndex() - 2))); response.writeByte('\r'); response.writeByte('\n'); // ending @@ -124,7 +133,7 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { response.writeInt(pictureId); response.writeInt(photo.writerIndex()); response.writeShort(Math.min(photo.writableBytes(), 1024)); - response.writeShort(1); + response.writeShort(++serverIndex); response.writeShort(Checksum.crc16(Checksum.CRC16_X25, response.toByteBuffer(2, response.writerIndex() - 2))); response.writeByte('\r'); response.writeByte('\n'); // ending @@ -132,13 +141,17 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { } } - private void decodeGps(Position position, ChannelBuffer buf) { + private boolean decodeGps(Position position, ChannelBuffer buf, boolean hasLength) { DateBuilder dateBuilder = new DateBuilder(timeZone) .setDate(buf.readUnsignedByte(), buf.readUnsignedByte(), buf.readUnsignedByte()) .setTime(buf.readUnsignedByte(), buf.readUnsignedByte(), buf.readUnsignedByte()); position.setTime(dateBuilder.getDate()); + if (hasLength && buf.readUnsignedByte() == 0) { + return false; + } + int length = buf.readUnsignedByte(); position.set(Position.KEY_SATELLITES, BitUtil.to(length, 4)); length = BitUtil.from(length, 4); @@ -168,9 +181,11 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { if (length > 0) { buf.skipBytes(length - 12); // skip reserved } + + return true; } - private void decodeLbs(Position position, ChannelBuffer buf, boolean hasLength) { + private boolean decodeLbs(Position position, ChannelBuffer buf, boolean hasLength) { int lbsLength = 0; if (hasLength) { @@ -183,9 +198,11 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { if (lbsLength > 0) { buf.skipBytes(lbsLength - 9); } + + return true; } - private void decodeStatus(Position position, ChannelBuffer buf) { + private boolean decodeStatus(Position position, ChannelBuffer buf) { int status = buf.readUnsignedByte(); @@ -214,6 +231,8 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { position.set(Position.KEY_BATTERY, buf.readUnsignedByte()); position.set(Position.KEY_RSSI, buf.readUnsignedByte()); position.set(Position.KEY_ALARM, decodeAlarm(buf.readUnsignedByte())); + + return true; } private String decodeAlarm(short value) { @@ -329,8 +348,7 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { } if (getDeviceSession(channel, remoteAddress, imei) != null) { - buf.skipBytes(buf.readableBytes() - 6); - sendResponse(channel, type, buf.readUnsignedShort()); + sendResponse(channel, false, type); } } else if (type == MSG_X1_GPS) { @@ -341,7 +359,7 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { buf.readUnsignedInt(); // data and alarm - decodeGps(position, buf); + decodeGps(position, buf, false); buf.readUnsignedShort(); // terminal info @@ -407,7 +425,7 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { } else if (isSupported(type)) { if (hasGps(type)) { - decodeGps(position, buf); + decodeGps(position, buf, false); } else { getLastLocation(position, null); } @@ -428,16 +446,13 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { buf.skipBytes(dataLength); if (type != MSG_COMMAND_0 && type != MSG_COMMAND_1 && type != MSG_COMMAND_2) { - sendResponse(channel, type, buf.readUnsignedShort()); + sendResponse(channel, false, type); } return null; } - if (buf.readableBytes() > 6) { - buf.skipBytes(buf.readableBytes() - 6); - } - sendResponse(channel, type, buf.readUnsignedShort()); + sendResponse(channel, false, type); return position; @@ -515,6 +530,18 @@ public class Gt06ProtocolDecoder extends BaseProtocolDecoder { photos.remove(pictureId); } + } else if (type == MSG_AZ735_GPS || type == MSG_AZ735_ALARM) { + + if (!decodeGps(position, buf, true)) { + getLastLocation(position, position.getDeviceTime()); + } + + decodeLbs(position, buf, true); + + sendResponse(channel, true, type); + + return position; + } return null; -- cgit v1.2.3