123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103 |
- package wei.yigulu.modbus.netty;
- import io.netty.buffer.ByteBuf;
- import io.netty.channel.ChannelHandlerContext;
- import lombok.Getter;
- import lombok.Setter;
- import lombok.experimental.Accessors;
- import org.joda.time.DateTime;
- import wei.yigulu.modbus.domain.datatype.numeric.P_BA;
- import wei.yigulu.netty.AbstractDelimiterHandler;
- import wei.yigulu.utils.CrcUtils;
- import wei.yigulu.utils.DataConvertor;
- /**
- * 未继承netty的数据帧处理拆包类
- *
- * @author 修唯xiuwei
- * @version 3.0
- */
- public class ModbusRtuMasterDelimiterHandler extends AbstractDelimiterHandler {
- @Setter
- @Accessors(chain = true)
- /**
- * 是否进行CRC校验判断
- */
- private boolean doCrcCheck = true;
- /**
- * 判断是否是断包的最大时间间隔
- */
- @Setter
- @Getter
- @Accessors(chain = true)
- protected int maxTimeSpace=1000;
- @Override
- public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {
- log.info("接收到原始的报文 :"+ DataConvertor.ByteBuf2String((ByteBuf) msg));
- if (isOverMaxLength((ByteBuf) msg)) {
- return;
- }
- //原crc值
- int crcO;
- //理论crc值
- int crcS;
- byte[] bs;
- int byteNum;
- int functionCode;
- while (cumulation.readableBytes() >= 5) {
- cumulation.markReaderIndex();
- cumulation.readBytes(1).release();
- functionCode = cumulation.readUnsignedByte();
- if (functionCode > 0x80 ) {
- //异常功能码 异常帧
- byteNum = 0;
- } else {
- byteNum = cumulation.readUnsignedByte();
- }
- if (byteNum < 0 || byteNum > 250) {
- cumulation.resetReaderIndex();
- log.error("该帧字节长度不在规定范围内,整帧舍弃:" + DataConvertor.ByteBuf2String(cumulation.readBytes(cumulation.readableBytes())));
- clearCumulation();
- return;
- }
- if (this.doCrcCheck) {
- bs = new byte[byteNum + 3];
- cumulation.resetReaderIndex();
- if (cumulation.readableBytes() < byteNum + 5) {
- break;
- }
- cumulation.readBytes(bs);
- crcO = cumulation.readUnsignedShortLE();
- crcS = CrcUtils.generateCRC16(bs).intValue();
- if (crcO == crcS) {
- cumulation.resetReaderIndex();
- ctx.fireChannelRead(cumulation.readBytes(byteNum + 5));
- } else {
- cumulation.resetReaderIndex();
- log.warn("数据帧crc校验错误,舍弃:" + DataConvertor.ByteBuf2String(cumulation) + "原CRC:" + DataConvertor.Byte2String(P_BA.decode(crcO)) + "理论CRC:" + DataConvertor.Byte2String(P_BA.decode(crcS)));
- clearCumulation();
- return;
- }
- } else {
- cumulation.resetReaderIndex();
- ctx.fireChannelRead(cumulation.readBytes(byteNum + 5));
- }
- }
- if (cumulation.readableBytes() == 0) {
- clearCumulation();
- }else{
- timeMark = DateTime.now();
- }
- }
- }
|