Esempio n. 1
0
        /**
         * Constructs a message from its binary representation.
         * @param binMessage the binary array that contains the encoded message
         * @param offset the index where the message starts.
         * @param arrayLen the length of the message
         * @return a Message object constructed from the binMessage array
         * @throws StunException ILLEGAL_ARGUMENT if one or more of the arguments
         * have invalid values.
         */
        public static Message Decode(byte[] binMessage, int offset, int arrayLen)
        {
            arrayLen = Math.Min(binMessage.Length, arrayLen);

            if (binMessage == null || arrayLen - offset < Message.HEADER_LENGTH)
            {
                throw new StunException(StunException.ILLEGAL_ARGUMENT,
                                        "The given binary array is not a valid StunMessage");
            }

            int messageType = (int)(((binMessage[offset++] << 8) & 0xff00) | (binMessage[offset++] & 0xFF));
            int mti         = (int)messageType;

            Message message;

            if (Message.IsResponseType(messageType))
            {
                message = new Response();
            }
            else
            {
                message = new Request();
            }
            message.SetMessageType(messageType);

            int length = (int)(((binMessage[offset++] << 8) & 0xff00) | (binMessage[offset++] & 0xFF));

            if (arrayLen - offset - TRANSACTION_ID_LENGTH < length)
            {
                throw new StunException(StunException.ILLEGAL_ARGUMENT,
                                        "The given binary array does not seem to "
                                        + "contain a whole StunMessage");
            }

            byte[] tranID = new byte[TRANSACTION_ID_LENGTH];
            for (int x = 0; x < TRANSACTION_ID_LENGTH; x++)
            {
                tranID[x] = binMessage[offset + x];
            }

            message.SetTransactionID(tranID);
            offset += TRANSACTION_ID_LENGTH;

            while (offset - Message.HEADER_LENGTH < length)
            {
                Attribute att = AttributeDecoder.decode(binMessage,
                                                        offset,
                                                        (length - offset));
                if (att != null)
                {
                    message.AddAttribute(att);
                    offset += att.GetDataLength() + Attribute.HEADER_LENGTH;
                }
                else
                {
                    offset += Attribute.HEADER_LENGTH;
                }
            }

            return(message);
        }