/// <summary>
        /// Parses an option from the given data.
        /// </summary>
        /// <param name="data">The data to parse.</param>
        /// <returns>The option if parsing was successful, null otherwise.</returns>
        public IpV6Option CreateInstance(DataSegment data)
        {
            if (data == null)
            {
                throw new ArgumentNullException("data");
            }
            if (data.Length < OptionDataMinimumLength)
            {
                return(null);
            }

            int sourceEndpointIdentifierLength      = data[Offset.SourceEndpointIdentifierLength];
            int destinationEndpointIdentifierLength = data[Offset.DestinationEndpointIdentifierLength];

            if (data.Length != OptionDataMinimumLength + sourceEndpointIdentifierLength + destinationEndpointIdentifierLength)
            {
                return(null);
            }

            DataSegment sourceEndpointIdentifier            = data.Subsegment(Offset.SourceEndpointIdentifier, sourceEndpointIdentifierLength);
            int         destinationEndpointIdentifierOffset = Offset.SourceEndpointIdentifier + sourceEndpointIdentifierLength;
            DataSegment destinationEndpointIdentifier       = data.Subsegment(destinationEndpointIdentifierOffset, destinationEndpointIdentifierLength);

            return(new IpV6OptionEndpointIdentification(sourceEndpointIdentifier, destinationEndpointIdentifier));
        }
        internal static DnsOptions Read(DataSegment data)
        {
            List <DnsOption> options = new List <DnsOption>();

            while (data.Length != 0)
            {
                if (data.Length < DnsOption.MinimumLength)
                {
                    return(null);
                }
                DnsOptionCode code             = (DnsOptionCode)data.ReadUShort(0, Endianity.Big);
                ushort        optionDataLength = data.ReadUShort(sizeof(ushort), Endianity.Big);

                int optionLength = DnsOption.MinimumLength + optionDataLength;
                if (data.Length < optionLength)
                {
                    return(null);
                }
                DnsOption option = DnsOption.CreateInstance(code, data.Subsegment(DnsOption.MinimumLength, optionDataLength));
                if (option == null)
                {
                    return(null);
                }
                options.Add(option);

                data = data.Subsegment(optionLength, data.Length - optionLength);
            }

            return(new DnsOptions(options));
        }
Example #3
0
        internal override DnsResourceData CreateInstance(DataSegment data)
        {
            if (data.Length < 3)
            {
                return((DnsResourceData)null);
            }
            int length1 = (int)data[0];

            if (data.Length < length1 + 3)
            {
                return((DnsResourceData)null);
            }
            string longitude = data.Subsegment(1, length1).Decode(Encoding.ASCII);

            data = data.Subsegment(length1 + 1, data.Length - length1 - 1);
            int length2 = (int)data[0];

            if (data.Length < length2 + 2)
            {
                return((DnsResourceData)null);
            }
            string latitude = data.Subsegment(1, length2).Decode(Encoding.ASCII);

            data = data.Subsegment(length2 + 1, data.Length - length2 - 1);
            int length3 = (int)data[0];

            if (data.Length != length3 + 1)
            {
                return((DnsResourceData)null);
            }
            string altitude = data.Subsegment(1, length3).Decode(Encoding.ASCII);

            return((DnsResourceData) new DnsResourceDataGeographicalPosition(longitude, latitude, altitude));
        }
        internal static DnsOptions Read(DataSegment data)
        {
            List <DnsOption> list = new List <DnsOption>();
            int offset;

            for (; data.Length != 0; data = data.Subsegment(offset, data.Length - offset))
            {
                if (data.Length < 4)
                {
                    return((DnsOptions)null);
                }
                DnsOptionCode code = (DnsOptionCode)data.ReadUShort(0, Endianity.Big);
                ushort        num  = data.ReadUShort(2, Endianity.Big);
                offset = 4 + (int)num;
                if (data.Length < offset)
                {
                    return((DnsOptions)null);
                }
                DnsOption instance = DnsOption.CreateInstance(code, data.Subsegment(4, (int)num));
                if (instance == null)
                {
                    return((DnsOptions)null);
                }
                list.Add(instance);
            }
            return(new DnsOptions((IList <DnsOption>)list));
        }
Example #5
0
        internal override IpV6AccessNetworkIdentifierSubOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
            {
                return(null);
            }

            bool isNetworkNameUtf8 = data.ReadBool(Offset.IsNetworkNameUtf8, Mask.IsNetworkNameUtf8);

            byte networkNameLength = data[Offset.NetworkNameLength];

            if (data.Length < OptionDataMinimumLength + networkNameLength)
            {
                return(null);
            }
            DataSegment networkName = data.Subsegment(Offset.NetworkName, networkNameLength);

            int  accessPointNameLengthOffset = Offset.NetworkName + networkNameLength;
            byte accessPointNameLength       = data[accessPointNameLengthOffset];

            if (data.Length != OptionDataMinimumLength + networkNameLength + accessPointNameLength)
            {
                return(null);
            }
            int         accessPointNameOffset = accessPointNameLengthOffset + sizeof(byte);
            DataSegment accessPointName       = data.Subsegment(accessPointNameOffset, accessPointNameLength);

            return(new IpV6AccessNetworkIdentifierSubOptionNetworkIdentifier(isNetworkNameUtf8, networkName, accessPointName));
        }
Example #6
0
        public DnsResourceDataDelegationSigner(ushort keyTag, DnsAlgorithm algorithm, DnsDigestType digestType, DataSegment digest)
        {
            if (digest == null)
            {
                throw new ArgumentNullException("digest");
            }
            this.KeyTag     = keyTag;
            this.Algorithm  = algorithm;
            this.DigestType = digestType;
            int val2;

            switch (this.DigestType)
            {
            case DnsDigestType.Sha1:
                val2 = 20;
                break;

            case DnsDigestType.Sha256:
                val2 = 32;
                break;

            default:
                val2 = int.MaxValue;
                break;
            }
            this.Digest      = digest.Subsegment(0, Math.Min(digest.Length, val2));
            this.ExtraDigest = digest.Subsegment(this.Digest.Length, digest.Length - this.Digest.Length);
        }
Example #7
0
            public NTLMSSP_CHALLENGE_MESSAGE(DataSegment commandDataArg) : base(commandDataArg)
            {
                var packetDataArray = commandDataArg.ToArray();

                TargetNameLen          = packetDataArray.ReadUShort(12, Endianity.Small);
                TargetNameMaxLen       = packetDataArray.ReadUShort(14, Endianity.Small);
                TargetNameBufferOffset = packetDataArray.ReadUInt(16, Endianity.Small);
                NegotiateFlags         = packetDataArray.ReadUInt(20, Endianity.Small);
                ServerChallenge        = commandDataArg.Subsegment(24, 8);//  packetDataArray.ReadULong(24, Endianity.Big);
                ReservedField1         = packetDataArray.ReadULong(32, Endianity.Small);
                TargetInfoLen          = packetDataArray.ReadUShort(40, Endianity.Small);
                TargetInfoMaxLen       = packetDataArray.ReadUShort(42, Endianity.Small);
                TargetInfoBufferOffset = packetDataArray.ReadUInt(44, Endianity.Small);
                Version = packetDataArray.ReadULong(48, Endianity.Big);
                Payload = commandDataArg.Subsegment(56, (commandDataArg.Length - 56));

                var payloadDataArray = Payload.ToArray();

                if (TargetNameLen > 0 && (TargetNameBufferOffset + TargetNameLen) < packetDataArray.Length)
                {
                    var TargetNameByteArray = packetDataArray.Subsegment(Convert.ToInt32(TargetNameBufferOffset), TargetNameLen).ToArray();
                    TargetName = Encoding.Unicode.GetString(TargetNameByteArray, 0, TargetNameByteArray.Length);
                }

                if (TargetInfoLen > 0 && (TargetInfoBufferOffset + TargetInfoLen) < packetDataArray.Length)
                {
                    ParseAttributeValuePairs(packetDataArray.Subsegment(Convert.ToInt32(TargetInfoBufferOffset), TargetInfoLen));
                }
            }
Example #8
0
        /// <summary>
        /// Constructs an instance out of the key tag, algorithm, digest type and digest fields.
        /// </summary>
        /// <param name="keyTag">
        /// Lists the key tag of the DNSKEY RR referred to by the DS record.
        /// The Key Tag used by the DS RR is identical to the Key Tag used by RRSIG RRs.
        /// Calculated as specified in RFC 2535.
        /// </param>
        /// <param name="algorithm">Algorithm must be allowed to sign DNS data.</param>
        /// <param name="digestType">An identifier for the digest algorithm used.</param>
        /// <param name="digest">
        /// Calculated over the canonical name of the delegated domain name followed by the whole RDATA of the KEY record (all four fields).
        /// digest = hash(canonical FQDN on KEY RR | KEY_RR_rdata)
        /// KEY_RR_rdata = Flags | Protocol | Algorithm | Public Key
        /// The size of the digest may vary depending on the digest type.
        /// </param>
        public DnsResourceDataDelegationSigner(ushort keyTag, DnsAlgorithm algorithm, DnsDigestType digestType, DataSegment digest)
        {
            if (digest == null)
            {
                throw new ArgumentNullException("digest");
            }

            KeyTag     = keyTag;
            Algorithm  = algorithm;
            DigestType = digestType;
            int maxDigestLength;

            switch (DigestType)
            {
            case DnsDigestType.Sha1:
                maxDigestLength = 20;
                break;

            case DnsDigestType.Sha256:
                maxDigestLength = 32;
                break;

            default:
                maxDigestLength = int.MaxValue;
                break;
            }
            Digest      = digest.Subsegment(0, Math.Min(digest.Length, maxDigestLength));
            ExtraDigest = digest.Subsegment(Digest.Length, digest.Length - Digest.Length);
        }
        internal override IpV6Option CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;
            
            int sourceEndpointIdentifierLength = data[Offset.SourceEndpointIdentifierLength];
            int destinationEndpointIdentifierLength = data[Offset.DestinationEndpointIdentifierLength];
            if (data.Length != OptionDataMinimumLength + sourceEndpointIdentifierLength + destinationEndpointIdentifierLength)
                return null;

            DataSegment sourceEndpointIdentifier = data.Subsegment(Offset.SourceEndpointIdentifier, sourceEndpointIdentifierLength);
            int destinationEndpointIdentifierOffset = Offset.SourceEndpointIdentifier + sourceEndpointIdentifierLength;
            DataSegment destinationEndpointIdentifier = data.Subsegment(destinationEndpointIdentifierOffset, destinationEndpointIdentifierLength);
            return new IpV6OptionEndpointIdentification(sourceEndpointIdentifier, destinationEndpointIdentifier);
        }
        internal static IpV6ExtensionHeaderMobilityHomeAgentSwitchMessage ParseMessageData(IpV4Protocol nextHeader, ushort checksum, DataSegment messageData)
        {
            if (messageData.Length < MinimumMessageDataLength)
            {
                return(null);
            }

            byte numberOfAddresses      = messageData[MessageDataOffset.NumberOfAddresses];
            int  homeAgentAddressesSize = numberOfAddresses * IpV6Address.SizeOf;

            if (messageData.Length < MinimumMessageDataLength + homeAgentAddressesSize)
            {
                return(null);
            }

            IpV6Address[] homeAgentAddresses = new IpV6Address[numberOfAddresses];
            for (int i = 0; i != numberOfAddresses; ++i)
            {
                homeAgentAddresses[i] = messageData.ReadIpV6Address(MessageDataOffset.HomeAgentAddresses + i * IpV6Address.SizeOf, Endianity.Big);
            }

            int optionsOffset           = MessageDataOffset.HomeAgentAddresses + homeAgentAddressesSize;
            IpV6MobilityOptions options = new IpV6MobilityOptions(messageData.Subsegment(optionsOffset, messageData.Length - optionsOffset));

            return(new IpV6ExtensionHeaderMobilityHomeAgentSwitchMessage(nextHeader, checksum, homeAgentAddresses, options));
        }
Example #11
0
        internal override DnsResourceData CreateInstance(DataSegment data)
        {
            if (data.Length < ConstantPartLength)
            {
                return(null);
            }

            bool                      authenticationProhibited  = data.ReadBool(Offset.AuthenticationProhibited, Mask.AuthenticationProhibited);
            bool                      confidentialityProhibited = data.ReadBool(Offset.ConfidentialityProhibited, Mask.ConfidentialityProhibited);
            bool                      experimental     = data.ReadBool(Offset.Experimental, Mask.Experimental);
            bool                      isFlagsExtension = data.ReadBool(Offset.IsFlagsExtension, Mask.IsFlagsExtension);
            bool                      userAssociated   = data.ReadBool(Offset.UserAssociated, Mask.UserAssociated);
            bool                      ipSec            = data.ReadBool(Offset.IpSec, Mask.IpSec);
            bool                      email            = data.ReadBool(Offset.Email, Mask.Email);
            DnsKeyNameType            nameType         = (DnsKeyNameType)(data[Offset.NameType] & Mask.NameType);
            DnsKeySignatoryAttributes signatory        = (DnsKeySignatoryAttributes)(data[Offset.Signatory] & Mask.Signatory);
            DnsKeyProtocol            protocol         = (DnsKeyProtocol)data[Offset.Protocol];
            DnsAlgorithm              algorithm        = (DnsAlgorithm)data[Offset.Algorithm];
            ushort?                   flagsExtension   = (isFlagsExtension ? ((ushort?)data.ReadUShort(Offset.FlagsExtension, Endianity.Big)) : null);
            int         publicKeyOffset = Offset.FlagsExtension + (isFlagsExtension ? sizeof(ushort) : 0);
            DataSegment publicKey       = data.Subsegment(publicKeyOffset, data.Length - publicKeyOffset);

            return(new DnsResourceDataKey(authenticationProhibited, confidentialityProhibited, experimental, userAssociated, ipSec, email, nameType, signatory,
                                          protocol, algorithm, flagsExtension, publicKey));
        }
Example #12
0
            private void ParseSecurityBuffer()
            {
                if (securityBuffer == null)
                {
                    return;
                }

                if (securityBuffer.Length <= 8)
                {
                    return;
                }

                var packetDataArray = securityBuffer.ToArray();
                int newOffset       = packetDataArray.Find(0, packetDataArray.Length, NTLMSSPstring);

                if (newOffset < packetDataArray.Length)
                {
                    NTLMSSPData = securityBuffer.Subsegment(newOffset, (packetDataArray.Length - newOffset));

                    var NTLMSSPPacketType = NTLMSSPData.ToArray().ReadUInt(8, Endianity.Small);

                    if (NTLMSSPPacketType == 0x2)
                    {
                        NTLMSSPMessage = new NTLMSSP_CHALLENGE_MESSAGE(NTLMSSPData);
                    }
                    else if (NTLMSSPPacketType == 0x3)
                    {
                        NTLMSSPMessage = new NTLMSSP_AUTHENTICATE_MESSAGE(NTLMSSPData);
                    }
                }
            }
Example #13
0
        internal override DnsResourceData CreateInstance(DataSegment data)
        {
            DnsSecNSec3HashAlgorithm hashAlgorithm;
            DnsSecNSec3Flags         flags;
            ushort      iterations;
            DataSegment salt;

            if (!DnsResourceDataNextDomainSecure3Base.TryReadParameters(data, out hashAlgorithm, out flags, out iterations, out salt))
            {
                return((DnsResourceData)null);
            }
            int parametersLength = DnsResourceDataNextDomainSecure3Base.GetParametersLength(salt.Length);

            if (data.Length - parametersLength < 1)
            {
                return((DnsResourceData)null);
            }
            int offset = parametersLength + 1;
            int length = (int)data[parametersLength];

            if (data.Length - offset < length)
            {
                return((DnsResourceData)null);
            }
            DataSegment    nextHashedOwnerName = data.Subsegment(offset, length);
            int            num      = offset + length;
            DnsTypeBitmaps instance = DnsTypeBitmaps.CreateInstance(data.Buffer, data.StartOffset + num, data.Length - num);

            if (instance == null)
            {
                return((DnsResourceData)null);
            }
            return((DnsResourceData) new DnsResourceDataNextDomainSecure3(hashAlgorithm, flags, iterations, salt, nextHashedOwnerName, instance));
        }
        internal static IpV6ExtensionHeaderMobilityBindingRevocationMessage ParseMessageData(IpV4Protocol nextHeader, ushort checksum, DataSegment messageData)
        {
            if (messageData.Length < MinimumMessageDataLength)
            {
                return(null);
            }

            IpV6MobilityBindingRevocationType bindingRevocationType = (IpV6MobilityBindingRevocationType)messageData[MessageDataOffset.BindingRevocationType];
            byte   revocationTriggerOrStatus = messageData[MessageDataOffset.RevocationTriggerOrStatus];
            ushort sequenceNumber            = messageData.ReadUShort(MessageDataOffset.SequenceNumber, Endianity.Big);
            bool   proxyBinding = messageData.ReadBool(MessageDataOffset.ProxyBinding, MessageDataMask.ProxyBinding);
            bool   ipV4HomeAddressBindingOnly = messageData.ReadBool(MessageDataOffset.IpV4HomeAddressBindingOnly, MessageDataMask.IpV4HomeAddressBindingOnly);
            bool   global = messageData.ReadBool(MessageDataOffset.Global, MessageDataMask.Global);
            IpV6MobilityOptions options =
                new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));

            switch (bindingRevocationType)
            {
            case IpV6MobilityBindingRevocationType.BindingRevocationIndication:
                return(new IpV6ExtensionHeaderMobilityBindingRevocationIndicationMessage(nextHeader, checksum, (Ipv6MobilityBindingRevocationTrigger)revocationTriggerOrStatus, sequenceNumber,
                                                                                         proxyBinding, ipV4HomeAddressBindingOnly, global, options));

            case IpV6MobilityBindingRevocationType.BindingRevocationAcknowledgement:
                return(new IpV6ExtensionHeaderMobilityBindingRevocationAcknowledgementMessage(nextHeader, checksum,
                                                                                              (Ipv6MobilityBindingRevocationStatus)revocationTriggerOrStatus,
                                                                                              sequenceNumber, proxyBinding, ipV4HomeAddressBindingOnly,
                                                                                              global, options));

            default:
                return(null);
            }
        }
        internal static IpV6ExtensionHeaderRouting ParseData(IpV4Protocol nextHeader, DataSegment data)
        {
            if (data.Length < DataMinimumLength)
                return null;
            IpV6RoutingType routingType = (IpV6RoutingType)data[DataOffset.RoutingType];
            byte segmentsLeft = data[DataOffset.SegmentsLeft];
            DataSegment routingData = data.Subsegment(DataOffset.TypeSpecificData, data.Length - DataOffset.TypeSpecificData);
            switch (routingType)
            {
                case IpV6RoutingType.SourceRoute:
                    return IpV6ExtensionHeaderRoutingSourceRoute.ParseRoutingData(nextHeader, segmentsLeft, routingData);

                case IpV6RoutingType.Nimrod:
                    // Unused.
                    return null;

                case IpV6RoutingType.Type2RoutingHeader:
                    return IpV6ExtensionHeaderRoutingHomeAddress.ParseRoutingData(nextHeader, segmentsLeft, routingData);

                case IpV6RoutingType.RplSourceRouteHeader:
                    return IpV6ExtensionHeaderRoutingRpl.ParseRoutingData(nextHeader, segmentsLeft, routingData);

                default:
                    return null;
            }
        }
        private static IpV6ExtensionHeader CreateStandardInstance(IpV4Protocol nextHeader, DataSegment extensionHeaderData, out int numBytesRead)
        {
            numBytesRead = 0;
            if (extensionHeaderData.Length < MinimumLength)
                return null;
            IpV4Protocol nextNextHeader = (IpV4Protocol)extensionHeaderData[Offset.NextHeader];
            int length = (extensionHeaderData[Offset.HeaderExtensionLength] + 1) * 8;
            if (extensionHeaderData.Length < length)
                return null;

            DataSegment data = extensionHeaderData.Subsegment(Offset.Data, length - Offset.Data);
            numBytesRead = data.Length;

            switch (nextHeader)
            {
                case IpV4Protocol.IpV6HopByHopOption: // 0
                    return IpV6ExtensionHeaderHopByHopOptions.ParseData(nextNextHeader, data);

                case IpV4Protocol.IpV6Route: // 43
                    return IpV6ExtensionHeaderRouting.ParseData(nextNextHeader, data);

                case IpV4Protocol.FragmentHeaderForIpV6: // 44
                    return IpV6ExtensionHeaderFragmentData.ParseData(nextNextHeader, data);
                
                case IpV4Protocol.IpV6Opts:                     // 60
                    return IpV6ExtensionHeaderDestinationOptions.ParseData(nextNextHeader, data);

                case IpV4Protocol.MobilityHeader:        // 135
                    return IpV6ExtensionHeaderMobility.ParseData(nextNextHeader, data);

                default:
                    throw new InvalidOperationException("Invalid nextHeader value" + nextHeader);
            }
        }
        internal static bool TryReadParameters(DataSegment data, out DnsSecNSec3HashAlgorithm hashAlgorithm, out DnsSecNSec3Flags flags, out ushort iterations, out DataSegment salt)
        {
            if (data.Length < ConstantPartLength)
            {
                hashAlgorithm = DnsSecNSec3HashAlgorithm.Sha1;
                flags         = DnsSecNSec3Flags.None;
                iterations    = 0;
                salt          = null;
                return(false);
            }

            hashAlgorithm = (DnsSecNSec3HashAlgorithm)data[Offset.HashAlgorithm];
            flags         = (DnsSecNSec3Flags)data[Offset.Flags];
            iterations    = data.ReadUShort(Offset.Iterations, Endianity.Big);

            int saltLength = data[Offset.SaltLength];

            if (data.Length - Offset.Salt < saltLength)
            {
                salt = null;
                return(false);
            }
            salt = data.Subsegment(Offset.Salt, saltLength);
            return(true);
        }
Example #18
0
            private void ParseCommandData()
            {
                if (commandData == null)
                {
                    return;
                }

                if (commandData.Length <= 8)
                {
                    return;
                }

                var packetDataArray = commandData.ToArray();

                StructureSize = packetDataArray.ReadUShort(SESSION_SETUP_Response_Offsets.StructureSize, Endianity.Small);
                try
                {
                    SessionFlags = (SESSION_SETUP_Response_Flag_Names)packetDataArray.ReadUShort(SESSION_SETUP_Response_Offsets.SessionFlags, Endianity.Small);
                }
                catch
                {
                    SessionFlags = SESSION_SETUP_Response_Flag_Names.SMB2_SESSION_UNKNOWN;
                }

                SecurityBufferOffset = packetDataArray.ReadUShort(SESSION_SETUP_Response_Offsets.SecurityBufferOffset, Endianity.Small);
                SecurityBufferLength = packetDataArray.ReadUShort(SESSION_SETUP_Response_Offsets.SecurityBufferLength, Endianity.Small);
                SecurityBuffer       = commandData.Subsegment(SESSION_SETUP_Response_Offsets.Buffer, (commandData.Length - SESSION_SETUP_Response_Offsets.Buffer));
            }
        internal static bool ParseMessageDataToFields(DataSegment messageData, out ushort sequenceNumber,
                                                      out bool acknowledge, out bool homeRegistration, out bool linkLocalAddressCompatibility,
                                                      out bool keyManagementMobilityCapability, out ushort lifetime, out IpV6MobilityOptions options)
        {
            if (messageData.Length < MinimumMessageDataLength)
            {
                sequenceNumber   = 0;
                acknowledge      = false;
                homeRegistration = false;
                linkLocalAddressCompatibility   = false;
                keyManagementMobilityCapability = false;
                lifetime = 0;
                options  = null;
                return(false);
            }

            sequenceNumber   = messageData.ReadUShort(MessageDataOffset.SequenceNumber, Endianity.Big);
            acknowledge      = messageData.ReadBool(MessageDataOffset.Acknowledge, MessageDataMask.Acknowledge);
            homeRegistration = messageData.ReadBool(MessageDataOffset.HomeRegistration, MessageDataMask.HomeRegistration);
            linkLocalAddressCompatibility   = messageData.ReadBool(MessageDataOffset.LinkLocalAddressCompatibility, MessageDataMask.LinkLocalAddressCompatibility);
            keyManagementMobilityCapability = messageData.ReadBool(MessageDataOffset.KeyManagementMobilityCapability,
                                                                   MessageDataMask.KeyManagementMobilityCapability);
            lifetime = messageData.ReadUShort(MessageDataOffset.Lifetime, Endianity.Big);
            options  = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));
            return(true);
        }
        internal override IpV6MobilityOption CreateInstance(DataSegment data)
        {
            List <IpV6MobilityOptionContextRequestEntry> requests = new List <IpV6MobilityOptionContextRequestEntry>();
            int offset = Offset.Requests;

            while (data.Length > offset)
            {
                byte requestType = data[offset++];

                if (offset >= data.Length)
                {
                    return(null);
                }
                byte requestLength = data[offset++];

                if (offset + requestLength > data.Length)
                {
                    return(null);
                }

                DataSegment requestOption = data.Subsegment(offset, requestLength);
                offset += requestLength;

                requests.Add(new IpV6MobilityOptionContextRequestEntry(requestType, requestOption));
            }

            return(new IpV6MobilityOptionContextRequest(requests));
        }
        internal static IpV6ExtensionHeaderRouting ParseData(IpV4Protocol nextHeader, DataSegment data)
        {
            if (data.Length < DataMinimumLength)
            {
                return(null);
            }
            IpV6RoutingType routingType  = (IpV6RoutingType)data[DataOffset.RoutingType];
            byte            segmentsLeft = data[DataOffset.SegmentsLeft];
            DataSegment     routingData  = data.Subsegment(DataOffset.TypeSpecificData, data.Length - DataOffset.TypeSpecificData);

            switch (routingType)
            {
            case IpV6RoutingType.SourceRoute:
                return(IpV6ExtensionHeaderRoutingSourceRoute.ParseRoutingData(nextHeader, segmentsLeft, routingData));

            case IpV6RoutingType.Nimrod:
                // Unused.
                return(null);

            case IpV6RoutingType.Type2RoutingHeader:
                return(IpV6ExtensionHeaderRoutingHomeAddress.ParseRoutingData(nextHeader, segmentsLeft, routingData));

            case IpV6RoutingType.RoutingProtocolLowPowerAndLossyNetworksSourceRouteHeader:
                return(IpV6ExtensionHeaderRoutingProtocolLowPowerAndLossyNetworks.ParseRoutingData(nextHeader, segmentsLeft, routingData));

            default:
                return(null);
            }
        }
        /// <summary>
        /// Parses an option from the given data.
        /// </summary>
        /// <param name="data">The data to parse.</param>
        /// <returns>The option if parsing was successful, null otherwise.</returns>
        public IpV6Option CreateInstance(DataSegment data)
        {
            if (data == null)
            {
                throw new ArgumentNullException("data");
            }
            if (data.Length < OptionDataMinimumLength)
            {
                return(null);
            }

            IpV6CalipsoDomainOfInterpretation domainOfInterpretation = (IpV6CalipsoDomainOfInterpretation)data.ReadUInt(Offset.DomainOfInterpretation,
                                                                                                                        Endianity.Big);
            byte compartmentLength        = data[Offset.CompartmentLength];
            int  compartmentLengthInBytes = compartmentLength * sizeof(int);

            if (OptionDataMinimumLength + compartmentLengthInBytes > data.Length)
            {
                return(null);
            }
            byte        sensitivityLevel  = data[Offset.SensitivityLevel];
            ushort      checksum          = data.ReadUShort(Offset.Checksum, Endianity.Big);
            DataSegment compartmentBitmap = data.Subsegment(Offset.CompartmentBitmap, compartmentLengthInBytes);

            return(new IpV6OptionCalipso(domainOfInterpretation, sensitivityLevel, checksum, compartmentBitmap));
        }
        internal override DnsResourceData CreateInstance(DataSegment data)
        {
            DnsFingerprintPublicKeyAlgorithm algorithm = (DnsFingerprintPublicKeyAlgorithm)data[Offset.Algorithm];
            DnsFingerprintType fingerprintType         = (DnsFingerprintType)data[Offset.FingerprintType];
            DataSegment        fingerprint             = data.Subsegment(Offset.Fingerprint, data.Length - ConstPartLength);

            return(new DnsResourceDataSshFingerprint(algorithm, fingerprintType, fingerprint));
        }
        internal override IpV6MobilityOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;

            DataSegment linkLayerIdentifier = data.Subsegment(Offset.LinkLayerIdentifier, data.Length - Offset.LinkLayerIdentifier);
            return new IpV6MobilityOptionMobileNodeLinkLayerIdentifier(linkLayerIdentifier);
        }
        internal static IpV6ExtensionHeaderMobilityFastNeighborAdvertisement ParseMessageData(IpV4Protocol nextHeader, ushort checksum, DataSegment messageData)
        {
            if (messageData.Length < MinimumMessageDataLength)
                return null;

            IpV6MobilityOptions options = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));
            return new IpV6ExtensionHeaderMobilityFastNeighborAdvertisement(nextHeader, checksum, options);
        }
        internal override IpV6FlowIdentificationSubOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;

            IpV6FlowIdentificationTrafficSelectorFormat trafficSelectorFormat = (IpV6FlowIdentificationTrafficSelectorFormat)data[Offset.TrafficSelectorFormat];
            DataSegment trafficSelector = data.Subsegment(Offset.TrafficSelector, data.Length - Offset.TrafficSelector);
            return new IpV6FlowIdentificationSubOptionTrafficSelector(trafficSelectorFormat, trafficSelector);
        }
Example #27
0
        internal override DnsResourceData CreateInstance(DataSegment data)
        {
            ushort        keyTag     = data.ReadUShort(Offset.KeyTag, Endianity.Big);
            DnsAlgorithm  algorithm  = (DnsAlgorithm)data[Offset.Algorithm];
            DnsDigestType digestType = (DnsDigestType)data[Offset.DigestType];
            DataSegment   digest     = data.Subsegment(Offset.Digest, data.Length - ConstPartLength);

            return(new DnsResourceDataDelegationSigner(keyTag, algorithm, digestType, digest));
        }
        internal override IpV6MobilityOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;

            uint vendorId = data.ReadUInt(Offset.VendorId, Endianity.Big);
            byte subType = data[Offset.SubType];
            DataSegment vendorSpecificData = data.Subsegment(Offset.Data, data.Length - Offset.Data);
            return new IpV6MobilityOptionVendorSpecific(vendorId, subType, vendorSpecificData);
        }
Example #29
0
        internal override DnsResourceData CreateInstance(DataSegment data)
        {
            if (data.Length < 2)
            {
                return((DnsResourceData)null);
            }
            DnsCertificationAuthorityAuthorizationFlags flags = (DnsCertificationAuthorityAuthorizationFlags)data[0];
            byte num    = data[1];
            int  offset = 2 + (int)num;

            if (data.Length < offset)
            {
                return((DnsResourceData)null);
            }
            DataSegment tag         = data.Subsegment(2, (int)num);
            DataSegment dataSegment = data.Subsegment(offset, data.Length - offset);

            return((DnsResourceData) new DnsResourceDataCertificationAuthorityAuthorization(flags, tag, dataSegment));
        }
        internal override IpV6MobilityOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;

            IpV6MobilityLinkLayerAddressCode code = (IpV6MobilityLinkLayerAddressCode)data[Offset.OptionCode];
            DataSegment linkLayerAddress = data.Subsegment(Offset.LinkLayerAddress, data.Length - Offset.LinkLayerAddress);

            return new IpV6MobilityOptionLinkLayerAddress(code, linkLayerAddress);
        }
        internal override IpV6AccessNetworkIdentifierSubOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;

            IpV6AccessNetworkIdentifierOperatorIdentifierType identifierType = (IpV6AccessNetworkIdentifierOperatorIdentifierType)data[Offset.IdentifierType];
            DataSegment identifier = data.Subsegment(Offset.Identifier, data.Length - Offset.Identifier);

            return new IpV6AccessNetworkIdentifierSubOptionOperatorIdentifier(identifierType, identifier);
        }
Example #32
0
        internal override DnsResourceData CreateInstance(DataSegment data)
        {
            if (data.Length < ConstantPartLength)
            {
                return(null);
            }

            DnsCertificationAuthorityAuthorizationFlags flags = (DnsCertificationAuthorityAuthorizationFlags)data[Offset.Flags];
            byte tagLength   = data[Offset.TagLength];
            int  valueOffset = ConstantPartLength + tagLength;

            if (data.Length < valueOffset)
            {
                return(null);
            }
            DataSegment tag   = data.Subsegment(Offset.Tag, tagLength);
            DataSegment value = data.Subsegment(valueOffset, data.Length - valueOffset);

            return(new DnsResourceDataCertificationAuthorityAuthorization(flags, tag, value));
        }
        internal static IpV6ExtensionHeaderMobilityBindingRefreshRequest ParseMessageData(IpV4Protocol nextHeader, ushort checksum, DataSegment messageData)
        {
            if (messageData.Length < MinimumMessageDataLength)
            {
                return(null);
            }

            IpV6MobilityOptions options = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));

            return(new IpV6ExtensionHeaderMobilityBindingRefreshRequest(nextHeader, checksum, options));
        }
        internal override IpV6MobilityOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;

            IpV6AuthenticationSubtype subtype = (IpV6AuthenticationSubtype)data[Offset.Subtype];
            uint mobilitySecurityParameterIndex = data.ReadUInt(Offset.MobilitySecurityParameterIndex, Endianity.Big);
            DataSegment authenticationData = data.Subsegment(Offset.AuthenticationData, data.Length - Offset.AuthenticationData);

            return new IpV6MobilityOptionAuthentication(subtype, mobilitySecurityParameterIndex, authenticationData);
        }
Example #35
0
        internal static DataSegment ReadString(DataSegment data, ref int offset)
        {
            if (data.Length <= offset)
                return null;
            int stringLength = data[offset++];
            if (data.Length < offset + stringLength)
                return null;
            DataSegment str = data.Subsegment(ref offset, stringLength);

            return str;
        }
        internal override IpV6MobilityOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
            {
                return(null);
            }

            DataSegment linkLayerIdentifier = data.Subsegment(Offset.LinkLayerIdentifier, data.Length - Offset.LinkLayerIdentifier);

            return(new IpV6MobilityOptionMobileNodeLinkLayerIdentifier(linkLayerIdentifier));
        }
Example #37
0
        internal override IpV6FlowIdentificationSubOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
            {
                return(null);
            }

            IpV6FlowIdentificationTrafficSelectorFormat trafficSelectorFormat = (IpV6FlowIdentificationTrafficSelectorFormat)data[Offset.TrafficSelectorFormat];
            DataSegment trafficSelector = data.Subsegment(Offset.TrafficSelector, data.Length - Offset.TrafficSelector);

            return(new IpV6FlowIdentificationSubOptionTrafficSelector(trafficSelectorFormat, trafficSelector));
        }
Example #38
0
        internal override DnsResourceData CreateInstance(DataSegment data)
        {
            if (data.Length < ConstantPartLength)
            {
                return(null);
            }

            DnsAtmAddressFormat format  = (DnsAtmAddressFormat)data[Offset.Format];
            DataSegment         address = data.Subsegment(Offset.Address, data.Length - ConstantPartLength);

            return(new DnsResourceDataAtmAddress(format, address));
        }
        internal override IpV6MobilityOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
            {
                return(null);
            }

            uint        securityParameterIndex = data.ReadUInt(Offset.SecurityParameterIndex, Endianity.Big);
            DataSegment authenticator          = data.Subsegment(Offset.Authenticator, data.Length - Offset.Authenticator);

            return(new IpV6MobilityOptionBindingAuthorizationDataForFmIpV6(securityParameterIndex, authenticator));
        }
Example #40
0
        internal override IpV6MobilityOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
            {
                return(null);
            }

            IpV6MobilityLinkLayerAddressCode code = (IpV6MobilityLinkLayerAddressCode)data[Offset.OptionCode];
            DataSegment linkLayerAddress          = data.Subsegment(Offset.LinkLayerAddress, data.Length - Offset.LinkLayerAddress);

            return(new IpV6MobilityOptionLinkLayerAddress(code, linkLayerAddress));
        }
        internal override IpV6Option CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;

            int lineIdentificationLegnth = data[Offset.LineIdentificationLength];
            if (data.Length != OptionDataMinimumLength + lineIdentificationLegnth)
                return null;

            DataSegment lineIdentification = data.Subsegment(Offset.LineIdentification, data.Length - Offset.LineIdentification);
            return new IpV6OptionLineIdentificationDestination(lineIdentification);
        }
Example #42
0
        internal static IpV6ExtensionHeaderMobilityCareOfTestInit ParseMessageData(IpV4Protocol nextHeader, ushort checksum, DataSegment messageData)
        {
            if (messageData.Length < MinimumMessageDataLength)
            {
                return(null);
            }

            ulong careOfInitCookie      = messageData.ReadULong(MessageDataOffset.CareOfInitCookie, Endianity.Big);
            IpV6MobilityOptions options = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));

            return(new IpV6ExtensionHeaderMobilityCareOfTestInit(nextHeader, checksum, careOfInitCookie, options));
        }
        internal override IpV6MobilityOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;

            IpV6MobileNodeIdentifierSubtype subtype = (IpV6MobileNodeIdentifierSubtype)data[Offset.Subtype];
            DataSegment identifier = data.Subsegment(Offset.Identifier, data.Length - Offset.Identifier);
            if (subtype == IpV6MobileNodeIdentifierSubtype.NetworkAccessIdentifier && identifier.Length < MinNetworkAccessIdentifierLength)
                return null;

            return new IpV6MobilityOptionMobileNodeIdentifier(subtype, identifier);
        }
        /// <summary>
        /// Parses an option from the given data.
        /// </summary>
        /// <param name="data">The data to parse.</param>
        /// <returns>The option if parsing was successful, null otherwise.</returns>
        public IpV6Option CreateInstance(DataSegment data)
        {
            if (data == null) 
                throw new ArgumentNullException("data");
            if (data.Length < OptionDataMinimumLength)
                return null;

            int lineIdentificationLegnth = data[Offset.LineIdentificationLength];
            if (data.Length != OptionDataMinimumLength + lineIdentificationLegnth)
                return null;

            DataSegment lineIdentification = data.Subsegment(Offset.LineIdentification, data.Length - Offset.LineIdentification);
            return new IpV6OptionLineIdentificationDestination(lineIdentification);
        }
        internal static IpV6ExtensionHeaderMobilityHomeTest ParseMessageData(IpV4Protocol nextHeader, ushort checksum, DataSegment messageData)
        {
            if (messageData.Length < MinimumMessageDataLength)
                return null;

            ushort homeNonceIndex = messageData.ReadUShort(MessageDataOffset.HomeNonceIndex, Endianity.Big);
            ulong homeInitCookie = messageData.ReadULong(MessageDataOffset.HomeInitCookie, Endianity.Big);
            ulong homeKeygenToken = messageData.ReadULong(MessageDataOffset.HomeKeygenToken, Endianity.Big);
            IpV6MobilityOptions options = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));
            return new IpV6ExtensionHeaderMobilityHomeTest(nextHeader, checksum, homeNonceIndex, homeInitCookie, homeKeygenToken, options);
        }
        internal override IpV6MobilityOption CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;

            IpV6DnsUpdateStatus status = (IpV6DnsUpdateStatus)data[Offset.Status];
            bool remove = data.ReadBool(Offset.Remove, Mask.Remove);
            DataSegment mobileNodeIdentity = data.Subsegment(Offset.MobileNodeIdentity, data.Length - Offset.MobileNodeIdentity);

            return new IpV6MobilityOptionDnsUpdate(status, remove, mobileNodeIdentity);
        }
        internal static IpV6ExtensionHeaderRoutingRpl ParseRoutingData(IpV4Protocol nextHeader, byte segmentsLeft, DataSegment routingData)
        {
            if (routingData.Length < RoutingDataMinimumLength)
                return null;

            byte commonPrefixLengthForNonLastAddresses =
                (byte)((routingData[RoutingDataOffset.CommonPrefixLengthForNonLastAddresses] & RoutingDataMask.CommonPrefixLengthForNonLastAddresses) >>
                       RoutingDataShift.CommonPrefixLengthForNonLastAddresses);
            if (commonPrefixLengthForNonLastAddresses >= MaxCommonPrefixLength)
                return null;

            byte commonPrefixLengthForLastAddress =
                (byte)(routingData[RoutingDataOffset.CommonPrefixLengthForLastAddress] & RoutingDataMask.CommonPrefixLengthForLastAddress);
            if (commonPrefixLengthForLastAddress > MaxCommonPrefixLength)
                return null;

            byte padSize = (byte)((routingData[RoutingDataOffset.PadSize] & RoutingDataMask.PadSize) >> RoutingDataShift.PadSize);
            if (padSize > MaxPadSize)
                return null;

            int numAddresses = (routingData.Length - RoutingDataOffset.Addresses - padSize - (IpV6Address.SizeOf - commonPrefixLengthForLastAddress)) /
                               (IpV6Address.SizeOf - commonPrefixLengthForNonLastAddresses) + 1;
            if (numAddresses < 0)
                return null;

            IpV6Address[] addresses = new IpV6Address[numAddresses];
            if (numAddresses > 0)
            {
                byte[] addressBytes = new byte[IpV6Address.SizeOf];
                for (int i = 0; i < numAddresses - 1; ++i)
                {
                    DataSegment addressSegment =
                        routingData.Subsegment(RoutingDataOffset.Addresses + i * (IpV6Address.SizeOf - commonPrefixLengthForNonLastAddresses),
                                               commonPrefixLengthForNonLastAddresses);
                    addressSegment.Write(addressBytes, 0);
                    addresses[i] = addressBytes.ReadIpV6Address(0, Endianity.Big);
                }

                addressBytes = new byte[IpV6Address.SizeOf];
                DataSegment lastAddressSegment =
                    routingData.Subsegment(RoutingDataOffset.Addresses + (numAddresses - 1) * (IpV6Address.SizeOf - commonPrefixLengthForNonLastAddresses),
                                           commonPrefixLengthForLastAddress);
                lastAddressSegment.Write(addressBytes, 0);
                addresses[numAddresses - 1] = addressBytes.ReadIpV6Address(0, Endianity.Big);
            }
            return new IpV6ExtensionHeaderRoutingRpl(nextHeader, segmentsLeft, commonPrefixLengthForNonLastAddresses, commonPrefixLengthForLastAddress, padSize,
                                                     addresses);
        }
        internal static IpV6ExtensionHeaderMobilityBindingError ParseMessageData(IpV4Protocol nextHeader, ushort checksum, DataSegment messageData)
        {
            if (messageData.Length < MinimumMessageDataLength)
                return null;

            IpV6BindingErrorStatus status = (IpV6BindingErrorStatus)messageData[MessageDataOffset.Status];
            IpV6Address homeAddress = messageData.ReadIpV6Address(MessageDataOffset.HomeAddress, Endianity.Big);
            IpV6MobilityOptions options = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));
            return new IpV6ExtensionHeaderMobilityBindingError(nextHeader, checksum, status, homeAddress, options);
        }
        internal static IpV6ExtensionHeaderMobilityHeartbeatMessage ParseMessageData(IpV4Protocol nextHeader, ushort checksum, DataSegment messageData)
        {
            if (messageData.Length < MinimumMessageDataLength)
                return null;

            bool isUnsolicitedHeartbeatResponse = messageData.ReadBool(MessageDataOffset.IsUnsolicitedHeartbeatResponse, MessageDataMask.IsUnsolicitedHeartbeatResponse);
            bool isResponse = messageData.ReadBool(MessageDataOffset.IsResponse, MessageDataMask.IsResponse);
            uint sequenceNumber = messageData.ReadUInt(MessageDataOffset.SequenceNumber, Endianity.Big);
            IpV6MobilityOptions options = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.MobilityOptions, messageData.Length - MessageDataOffset.MobilityOptions));
            return new IpV6ExtensionHeaderMobilityHeartbeatMessage(nextHeader, checksum, isUnsolicitedHeartbeatResponse, isResponse, sequenceNumber, options);
        }
        internal static bool ParseMessageDataToFields(DataSegment messageData, out ushort sequenceNumber, out ushort lifetime, out IpV6MobilityOptions options)
        {
            if (messageData.Length < MinimumMessageDataLength)
            {
                sequenceNumber = 0;
                lifetime = 0;
                options = null;
                return false;
            }

            sequenceNumber = messageData.ReadUShort(MessageDataOffset.SequenceNumber, Endianity.Big);
            lifetime = messageData.ReadUShort(MessageDataOffset.Lifetime, Endianity.Big);
            options = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));
            return true;
        }
        /// <summary>
        /// Parses an option from the given data.
        /// </summary>
        /// <param name="data">The data to parse.</param>
        /// <returns>The option if parsing was successful, null otherwise.</returns>
        public IpV6Option CreateInstance(DataSegment data)
        {
            if (data == null) 
                throw new ArgumentNullException("data");
            if (data.Length < OptionDataMinimumLength)
                return null;
            
            int sourceEndpointIdentifierLength = data[Offset.SourceEndpointIdentifierLength];
            int destinationEndpointIdentifierLength = data[Offset.DestinationEndpointIdentifierLength];
            if (data.Length != OptionDataMinimumLength + sourceEndpointIdentifierLength + destinationEndpointIdentifierLength)
                return null;

            DataSegment sourceEndpointIdentifier = data.Subsegment(Offset.SourceEndpointIdentifier, sourceEndpointIdentifierLength);
            int destinationEndpointIdentifierOffset = Offset.SourceEndpointIdentifier + sourceEndpointIdentifierLength;
            DataSegment destinationEndpointIdentifier = data.Subsegment(destinationEndpointIdentifierOffset, destinationEndpointIdentifierLength);
            return new IpV6OptionEndpointIdentification(sourceEndpointIdentifier, destinationEndpointIdentifier);
        }
Example #52
0
        /// <summary>
        /// Parses an option from the given data.
        /// </summary>
        /// <param name="data">The data to parse.</param>
        /// <returns>The option if parsing was successful, null otherwise.</returns>
        public IpV6Option CreateInstance(DataSegment data)
        {
            if (data == null)
                throw new ArgumentNullException("data");
            if (data.Length < OptionDataMinimumLength)
                return null;

            IpV6CalipsoDomainOfInterpretation domainOfInterpretation = (IpV6CalipsoDomainOfInterpretation)data.ReadUInt(Offset.DomainOfInterpretation,
                                                                                                                        Endianity.Big);
            byte compartmentLength = data[Offset.CompartmentLength];
            int compartmentLengthInBytes = compartmentLength * sizeof(int);
            if (OptionDataMinimumLength + compartmentLengthInBytes > data.Length)
                return null;
            byte sensitivityLevel = data[Offset.SensitivityLevel];
            ushort checksum = data.ReadUShort(Offset.Checksum, Endianity.Big);
            DataSegment compartmentBitmap = data.Subsegment(Offset.CompartmentBitmap, compartmentLengthInBytes);

            return new IpV6OptionCalipso(domainOfInterpretation, sensitivityLevel, checksum, compartmentBitmap);
        }
        internal static IpV6OptionSmfDpdSequenceBased CreateSpecificInstance(DataSegment data)
        {
            IpV6TaggerIdType taggerIdType = (IpV6TaggerIdType)((data[Offset.TaggerIdType] & Mask.TaggerIdType) >> Shift.TaggerIdType);
            int taggerIdLength = (taggerIdType == IpV6TaggerIdType.Null ? 0 : (data[Offset.TaggerIdLength] & Mask.TaggerIdLength) + 1);
            if (data.Length < Offset.TaggerId + taggerIdLength)
                return null;
            DataSegment identifier = data.Subsegment(Offset.TaggerId + taggerIdLength, data.Length - Offset.TaggerId - taggerIdLength);
            switch (taggerIdType)
            {
                case IpV6TaggerIdType.Null:
                    return new IpV6OptionSmfDpdNull(identifier);
                    
                case IpV6TaggerIdType.Default:
                    return new IpV6OptionSmfDpdDefault(data.Subsegment(Offset.TaggerId, taggerIdLength), identifier);

                case IpV6TaggerIdType.IpV4:
                    if (taggerIdLength != IpV4Address.SizeOf)
                        return null;
                    IpV4Address ipV4Address = data.ReadIpV4Address(0, Endianity.Big);
                    return new IpV6OptionSmfDpdIpV4(ipV4Address, identifier);

                case IpV6TaggerIdType.IpV6:
                    if (taggerIdLength != IpV6Address.SizeOf)
                        return null;
                    IpV6Address ipV6Address = data.ReadIpV6Address(0, Endianity.Big);
                    return new IpV6OptionSmfDpdIpV6(ipV6Address, identifier);

                default:
                    return null;
            }
        }
        internal static bool ParseMessageDataToFields(DataSegment messageData, out ushort sequenceNumber,
                                                      out bool acknowledge, out bool homeRegistration, out bool linkLocalAddressCompatibility,
                                                      out bool keyManagementMobilityCapability, out ushort lifetime, out IpV6MobilityOptions options)
        {
            if (messageData.Length < MinimumMessageDataLength)
            {
                sequenceNumber = 0;
                acknowledge = false;
                homeRegistration = false;
                linkLocalAddressCompatibility = false;
                keyManagementMobilityCapability = false;
                lifetime = 0;
                options = null;
                return false;
            }

            sequenceNumber = messageData.ReadUShort(MessageDataOffset.SequenceNumber, Endianity.Big);
            acknowledge = messageData.ReadBool(MessageDataOffset.Acknowledge, MessageDataMask.Acknowledge);
            homeRegistration = messageData.ReadBool(MessageDataOffset.HomeRegistration, MessageDataMask.HomeRegistration);
            linkLocalAddressCompatibility = messageData.ReadBool(MessageDataOffset.LinkLocalAddressCompatibility, MessageDataMask.LinkLocalAddressCompatibility);
            keyManagementMobilityCapability = messageData.ReadBool(MessageDataOffset.KeyManagementMobilityCapability,
                                                                   MessageDataMask.KeyManagementMobilityCapability);
            lifetime = messageData.ReadUShort(MessageDataOffset.Lifetime, Endianity.Big);
            options = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));
            return true;
        }
        internal static bool ParseMessageDataFields(DataSegment messageData, out IpV6BindingAcknowledgementStatus status,
                                                    out bool keyManagementMobilityCapability, out ushort sequenceNumber, out ushort lifetime,
                                                    out IpV6MobilityOptions options)
        {
            if (messageData.Length < MinimumMessageDataLength)
            {
                status = IpV6BindingAcknowledgementStatus.BindingUpdateAccepted;
                keyManagementMobilityCapability = false;
                sequenceNumber = 0;
                lifetime = 0;
                options = null;
                return false;
            }

            status = (IpV6BindingAcknowledgementStatus)messageData[MessageDataOffset.Status];
            keyManagementMobilityCapability = messageData.ReadBool(MessageDataOffset.KeyManagementMobilityCapability,
                                                                   MessageDataMask.KeyManagementMobilityCapability);

            sequenceNumber = messageData.ReadUShort(MessageDataOffset.SequenceNumber, Endianity.Big);
            lifetime = messageData.ReadUShort(MessageDataOffset.Lifetime, Endianity.Big);
            options = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));
            return true;
        }
        internal static IpV6ExtensionHeaderAuthentication CreateInstance(DataSegment extensionHeaderData, out int numBytesRead)
        {
            if (extensionHeaderData.Length < MinimumLength)
            {
                numBytesRead = 0;
                return null;
            }
            IpV4Protocol nextHeader = (IpV4Protocol)extensionHeaderData[Offset.NextHeader];
            byte payloadLength = extensionHeaderData[Offset.PayloadLength];
            if (extensionHeaderData.Length < Offset.AuthenticationData + payloadLength)
            {
                numBytesRead = 0;
                return null;
            }

            uint securityParametersIndex = extensionHeaderData.ReadUInt(Offset.SecurityParametersIndex, Endianity.Big);
            uint sequenceNumber = extensionHeaderData.ReadUInt(Offset.SequenceNumber, Endianity.Big);
            DataSegment authenticationData = extensionHeaderData.Subsegment(Offset.AuthenticationData, payloadLength);
            numBytesRead = Offset.AuthenticationData + payloadLength;

            return new IpV6ExtensionHeaderAuthentication(nextHeader, securityParametersIndex, sequenceNumber, authenticationData);
        }
        internal static IpV6ExtensionHeaderMobility ParseData(IpV4Protocol nextHeader, DataSegment data)
        {
            if (data.Length < MinimumDataLength)
                return null;

            IpV6MobilityHeaderType mobilityHeaderType = (IpV6MobilityHeaderType)data[DataOffset.MobilityHeaderType];
            ushort checksum = data.ReadUShort(DataOffset.Checksum, Endianity.Big);
            DataSegment messageData = data.Subsegment(DataOffset.MessageData, data.Length - DataOffset.MessageData);

            switch (mobilityHeaderType)
            {
                case IpV6MobilityHeaderType.BindingRefreshRequest: // 0
                    return IpV6ExtensionHeaderMobilityBindingRefreshRequest.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.HomeTestInit: // 1
                    return IpV6ExtensionHeaderMobilityHomeTestInit.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.CareOfTestInit: // 2
                    return IpV6ExtensionHeaderMobilityCareOfTestInit.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.HomeTest: // 3
                    return IpV6ExtensionHeaderMobilityHomeTest.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.CareOfTest: // 4
                    return IpV6ExtensionHeaderMobilityCareOfTest.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.BindingUpdate: // 5
                    return IpV6ExtensionHeaderMobilityBindingUpdate.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.BindingAcknowledgement: // 6
                    return IpV6ExtensionHeaderMobilityBindingAcknowledgement.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.BindingError: // 7
                    return IpV6ExtensionHeaderMobilityBindingError.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.FastBindingUpdate: // 8
                    return IpV6ExtensionHeaderMobilityFastBindingUpdate.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.FastBindingAcknowledgement: // 9
                    return IpV6ExtensionHeaderMobilityFastBindingAcknowledgement.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.FastNeighborAdvertisement: // 10
                    return IpV6ExtensionHeaderMobilityFastNeighborAdvertisement.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.Experimental: // 11
                    return IpV6ExtensionHeaderMobilityExperimental.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.HomeAgentSwitchMessage: // 12
                    return IpV6ExtensionHeaderMobilityHomeAgentSwitchMessage.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.HeartbeatMessage: // 13
                    return IpV6ExtensionHeaderMobilityHeartbeatMessage.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.HandoverInitiateMessage: // 14
                    return IpV6ExtensionHeaderMobilityHandoverInitiateMessage.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.HandoverAcknowledgeMessage: // 15
                    return IpV6ExtensionHeaderMobilityHandoverAcknowledgeMessage.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.BindingRevocationMessage: // 16
                    return IpV6ExtensionHeaderMobilityBindingRevocationMessage.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.LocalizedRoutingInitiation: // 17
                    return IpV6ExtensionHeaderMobilityLocalizedRoutingInitiation.ParseMessageData(nextHeader, checksum, messageData);

                case IpV6MobilityHeaderType.LocalizedRoutingAcknowledgement: // 18
                    return IpV6ExtensionHeaderMobilityLocalizedRoutingAcknowledgement.ParseMessageData(nextHeader, checksum, messageData);

                default:
                    return null;
            }
        }
        internal static IpV6ExtensionHeaderMobilityHandoverAcknowledgeMessage ParseMessageData(IpV4Protocol nextHeader, ushort checksum, DataSegment messageData)
        {
            if (messageData.Length < MinimumMessageDataLength)
                return null;

            ushort sequenceNumber = messageData.ReadUShort(MessageDataOffset.SequenceNumber, Endianity.Big);
            IpV6MobilityHandoverAcknowledgeCode code = (IpV6MobilityHandoverAcknowledgeCode)messageData[MessageDataOffset.Code];
            IpV6MobilityOptions options = new IpV6MobilityOptions(messageData.Subsegment(MessageDataOffset.Options, messageData.Length - MessageDataOffset.Options));
            return new IpV6ExtensionHeaderMobilityHandoverAcknowledgeMessage(nextHeader, checksum, sequenceNumber, code, options);
        }
        internal override IpV6Option CreateInstance(DataSegment data)
        {
            if (data.Length < OptionDataMinimumLength)
                return null;

            bool down = data.ReadBool(Offset.Down, Mask.Down);
            bool rankError = data.ReadBool(Offset.RankError, Mask.RankError);
            bool forwardingError = data.ReadBool(Offset.ForwardingError, Mask.ForwardingError);
            byte rplInstanceId = data[Offset.RplInstanceId];
            ushort senderRank = data.ReadUShort(Offset.SenderRank, Endianity.Big);
            DataSegment subTlvs = data.Subsegment(Offset.SubTlvs, data.Length - Offset.SubTlvs);

            return new IpV6OptionRoutingProtocolLowPowerAndLossyNetworks(down, rankError, forwardingError, rplInstanceId, senderRank, subTlvs);
        }
        internal static IpV6ExtensionHeaderEncapsulatingSecurityPayload CreateInstance(DataSegment extensionHeaderData, out int numBytesRead)
        {
            if (extensionHeaderData.Length < MinimumLength)
            {
                numBytesRead = 0;
                return null;
            }
            uint securityParametersIndex = extensionHeaderData.ReadUInt(Offset.SecurityParametersIndex, Endianity.Big);
            uint sequenceNumber = extensionHeaderData.ReadUInt(Offset.SequenceNumber, Endianity.Big);
            DataSegment encryptedDataAndAuthenticationData = extensionHeaderData.Subsegment(Offset.PayloadData, extensionHeaderData.Length - Offset.PayloadData);
            numBytesRead = extensionHeaderData.Length;

            return new IpV6ExtensionHeaderEncapsulatingSecurityPayload(securityParametersIndex, sequenceNumber, encryptedDataAndAuthenticationData);
        }