@Override
  protected Object decode(
      final ChannelHandlerContext ctx, final Channel channel, final ChannelBuffer buffer)
      throws Exception {

    while (buffer.readable()) {

      byte c = buffer.readByte();

      // check if last character read was DLE
      if (foundDLE) {
        foundDLE = false;

        if (c == DleStxEtxConstants.STX && !foundPacket) {

          foundPacket = true;

        } else if (c == DleStxEtxConstants.ETX && foundPacket) {

          ChannelBuffer packetRead = packet;
          resetDecodingState();
          return packetRead;

        } else if (c == DleStxEtxConstants.DLE && foundPacket) {

          // Stuffed DLE found
          packet.writeByte(DleStxEtxConstants.DLE);

        } else {

          if (log.isWarnEnabled()) {
            log.warn(
                "Incomplete packet received: {}",
                StringUtils.toHexString(
                    packet.array(), packet.readerIndex(), packet.readableBytes()));
          }
          resetDecodingState();
        }

      } else {

        if (c == DleStxEtxConstants.DLE) {
          // log.trace("Plain DLE received");
          foundDLE = true;
        } else if (foundPacket) {
          packet.writeByte(c);
        }
      }
    }

    // decoding is not yet complete, we'll need more bytes until we find DLE
    // ETX
    return null;
  }