Ejemplo n.º 1
0
        internal int handleRecvSeq(ByteChannel byteChannel, int recvByteCount)
        {
            int allowedRecv    = this.recvArm - this.recvSeq;
            int remainingBytes = recvByteCount;

            Utils.ensure(remainingBytes <= allowedRecv, ChabuErrorCode.PROTOCOL_DATA_OVERFLOW,
                         "Channel[{0}] received more data ({1}) as it can take ({2}). Violation of the ARM value.", channelId, remainingBytes, allowedRecv);

            int summedReadBytes = 0;

            while (remainingBytes > 0)
            {
                if (recvTargetBuffer == null)
                {
                    recvTargetBuffer = recvTarget.GetRecvBuffer(remainingBytes);

                    Utils.ensure(recvTargetBuffer != null, ChabuErrorCode.ASSERT,
                                 "Channel[{0}] recvTargetBuffer is null.", channelId);

                    Utils.ensure(recvTargetBuffer.remaining() <= remainingBytes, ChabuErrorCode.ASSERT,
                                 "Channel[{0}] recvTargetBuffer has more remaining ({1}) as requested ({2}).",
                                 channelId, recvTargetBuffer.remaining(), remainingBytes);

                    Utils.ensure(recvTargetBuffer.remaining() > 0, ChabuErrorCode.ASSERT,
                                 "Channel[{0}] recvTargetBuffer cannot take data.",
                                 channelId);
                }

                int readBytes = byteChannel.read(recvTargetBuffer);
                summedReadBytes += readBytes;
                remainingBytes  -= readBytes;

                recvSeq      += readBytes;
                recvPosition += readBytes;

                if (!recvTargetBuffer.hasRemaining())
                {
                    recvTargetBuffer = null;
                    recvTarget.RecvCompleted();
                }

                if (readBytes == 0)
                {
                    // could not read => try next time
                    break;
                }
            }
            return(summedReadBytes);
        }
Ejemplo n.º 2
0
        protected override void processSeq(ByteChannel channel)
        {
            // is SEQ packet
            recvBuf.position(HEADER_RECV_SZ);
            int channelId = recvBuf.getInt(8);
            int seq       = recvBuf.getInt(12);
            int pls       = recvBuf.getInt(16);
            int padding   = packetSize - HEADER_RECV_SZ - pls;
            ChabuChannelImpl chabuChannel = channels.get(channelId);

            if (seqPacketIndex == 0)
            {
                // first processing
                Utils.ensure(padding >= 0 && padding < 4, ChabuErrorCode.ASSERT, "padding inplausible packetSize:{0} pls:{1}", packetSize, pls);
                chabuChannel.verifySeq(seq);
            }

            if (seqPacketIndex < pls)
            {
                int toBeHandledLimit = pls - seqPacketIndex;
                int handledBytes     = chabuChannel.handleRecvSeq(channel, toBeHandledLimit);
                seqPacketIndex += handledBytes;
            }

            if (seqPacketIndex >= pls && seqPacketIndex + ChabuImpl.SEQ_MIN_SZ < packetSize)
            {
                int paddingRemaining = packetSize - seqPacketIndex - ChabuImpl.SEQ_MIN_SZ;
                recvBufPadding.clear();
                Utils.ensure(paddingRemaining <= 3 && paddingRemaining > 0, ChabuErrorCode.ASSERT, "paddingRemaining inplausible {0} ({1}, {2})", paddingRemaining, seqPacketIndex, packetSize);
                recvBufPadding.limit(paddingRemaining);
                seqPacketIndex += channel.read(recvBufPadding);
            }

            if (seqPacketIndex + ChabuImpl.SEQ_MIN_SZ >= packetSize)
            {
                seqPacketIndex = 0;
                recvBuf.clear();
                recvBuf.limit(HEADER_RECV_SZ);
                packetType = PacketType.NONE;
            }
            else
            {
                Utils.ensure(recvBuf.position() == 20, ChabuErrorCode.ASSERT, "");
                Utils.ensure(recvBuf.limit() == 20, ChabuErrorCode.ASSERT, "");
            }
        }
Ejemplo n.º 3
0
        public void recv(ByteChannel channel)
        {
            cancelCurrentReceive = false;
            while (!cancelCurrentReceive)
            {
                if (packetType == PacketType.NONE)
                {
                    Utils.ensure(recvBuf.limit() >= HEADER_RECV_SZ, ChabuErrorCode.UNKNOWN, "unknown header size: {0}", recvBuf);
                    channel.read(recvBuf);
                    if (recvBuf.position() < 8)
                    {
                        break;
                    }

                    packetSize = recvBuf.getInt(0);
                    int packetTypeId = recvBuf.getInt(4) & 0xFF;
                    packetType = PacketTypeExtension.findPacketType(packetTypeId);
                    if (packetType == PacketType.NONE)
                    {
                        throw new ChabuException(string.Format("Packet type 0x{0:X2} unexpected: packetSize {1}", packetTypeId, packetSize));
                    }
                }

                if (packetType != PacketType.SEQ)
                {
                    Utils.ensure(packetSize <= Constants.MAX_RECV_LIMIT_LOW, ChabuErrorCode.UNKNOWN, "unknown header size");
                    if (packetSize > recvBuf.position())
                    {
                        recvBuf.limit(packetSize);
                        channel.read(recvBuf);
                        if (recvBuf.hasRemaining())
                        {
                            // not fully read, try next time
                            break;
                        }
                    }
                }
                else
                {
                    if (HEADER_RECV_SZ > recvBuf.position())
                    {
                        recvBuf.limit(HEADER_RECV_SZ);
                        channel.read(recvBuf);
                        if (recvBuf.hasRemaining())
                        {
                            // not fully read, try next time
                            break;
                        }
                    }
                }

                recvBuf.flip();
                recvBuf.position(8);

                if (packetType != PacketType.SEQ)
                {
                    Utils.ensure(packetSize <= Constants.MAX_RECV_LIMIT_LOW, ChabuErrorCode.UNKNOWN, "unknown header size");
                    switch (packetType)
                    {
                    case PacketType.SETUP: processRecvSetup();    break;

                    case PacketType.ACCEPT: processRecvAccept();   break;

                    case PacketType.ABORT: processRecvAbort();    break;

                    case PacketType.ARM: processRecvArm();      break;

                    case PacketType.DAVAIL: processRecvDavail();   break;

                    case PacketType.NOP: processRecvNop();      break;

                    case PacketType.RST_REQ: processRecvResetReq(); break;

                    case PacketType.RST_ACK: processRecvResetAck(); break;

                    default: break;
                    }
                    Utils.ensure(recvBuf.remaining() < HEADER_RECV_SZ, ChabuErrorCode.ASSERT, "After normal command, the remaining bytes must be below the HEADER_RECV_SZ limit, but is {0}", recvBuf.limit());
                    Utils.ensure(recvBuf.position() == packetSize, ChabuErrorCode.ASSERT, "After normal command, the remaining bytes must be below the HEADER_RECV_SZ limit, but is {0}", recvBuf.limit());
                    recvBuf.compact();
                    recvBuf.limit(HEADER_RECV_SZ);
                    packetType = PacketType.NONE;
                    continue;
                }
                else
                {
                    processSeq(channel);

                    bool isContinuingSeq = packetType == PacketType.SEQ;
                    if (isContinuingSeq)
                    {
                        break;
                    }

                    continue;
                }
            }
        }