internal static bool Parse(byte[] data, out KerberosAuthorizationDataEncryptionNegotiation entry)
        {
            entry = null;
            DERValue[] values = DERParser.ParseData(data, 0);
            if (!values.CheckValueSequence())
            {
                return(false);
            }
            List <KerberosEncryptionType> enc_types = new List <KerberosEncryptionType>();

            try
            {
                foreach (var next in values[0].Children)
                {
                    if (!next.CheckPrimitive(UniversalTag.INTEGER))
                    {
                        return(false);
                    }
                    enc_types.Add((KerberosEncryptionType)next.ReadInteger());
                }
            }
            catch (InvalidDataException)
            {
                return(false);
            }

            entry = new KerberosAuthorizationDataEncryptionNegotiation(data, enc_types.AsReadOnly());
            return(true);
        }
Beispiel #2
0
 internal static bool TryParse(KERB_EXTERNAL_TICKET ticket, out KerberosExternalTicket result)
 {
     result = null;
     try {
         var ret = new KerberosExternalTicket();
         ret.ServiceName         = ParseName(ticket.ServiceName);
         ret.TargetName          = ParseName(ticket.TargetName);
         ret.ClientName          = ParseName(ticket.ClientName);
         ret.DomainName          = ticket.DomainName.ToString();
         ret.TargetDomainName    = ticket.TargetDomainName.ToString();
         ret.AltTargetDomainName = ticket.AltTargetDomainName.ToString();
         ret.SessionKey          = ParseKey(ret.ServiceName, ret.DomainName, ticket.SessionKey);
         ret.TicketFlags         = (KerberosTicketFlags)ticket.TicketFlags.SwapEndian();
         ret.Flags             = ticket.Flags;
         ret.KeyExpirationTime = ticket.KeyExpirationTime.ToDateTime();
         ret.StartTime         = ticket.StartTime.ToDateTime();
         ret.EndTime           = ticket.EndTime.ToDateTime();
         ret.RenewUntil        = ticket.RenewUntil.ToDateTime();
         ret.TimeSkew          = new TimeSpan(ticket.TimeSkew.QuadPart);
         byte[]     ticket_data = ticket.ReadTicket();
         DERValue[] values      = DERParser.ParseData(ticket_data, 0);
         if (values.Length != 1)
         {
             return(false);
         }
         ret.Ticket = KerberosTicket.Parse(values[0], ticket_data);
         result     = ret;
         return(true);
     } catch (InvalidDataException) {
         return(false);
     }
 }
Beispiel #3
0
 internal static NtResult <AuthenticodeCertificate> Parse(byte[] data, bool throw_on_error)
 {
     try
     {
         var cms = new SignedCms();
         cms.Decode(data);
         if (cms.ContentInfo.ContentType.Value != SPC_INDIRECT_DATA_OBJID)
         {
             return(NtStatus.STATUS_INVALID_PARAMETER.CreateResultFromError <AuthenticodeCertificate>(throw_on_error));
         }
         var values = DERParser.ParseData(cms.ContentInfo.Content, 0);
         if (values.Length < 1)
         {
             return(NtStatus.STATUS_INVALID_PARAMETER.CreateResultFromError <AuthenticodeCertificate>(throw_on_error));
         }
         return(new AuthenticodeCertificate(cms.Certificates.Cast <X509Certificate2>(), CheckForPageHash(values[0])).CreateResult());
     }
     catch (EndOfStreamException)
     {
         return(NtStatus.STATUS_END_OF_FILE.CreateResultFromError <AuthenticodeCertificate>(throw_on_error));
     }
     catch (CryptographicException)
     {
         return(NtStatus.STATUS_INVALID_PARAMETER.CreateResultFromError <AuthenticodeCertificate>(throw_on_error));
     }
     catch (InvalidDataException)
     {
         return(NtStatus.STATUS_INVALID_PARAMETER.CreateResultFromError <AuthenticodeCertificate>(throw_on_error));
     }
 }
Beispiel #4
0
        internal static bool Parse(KerberosEncryptedData orig_data, byte[] decrypted, out KerberosEncryptedData ticket)
        {
            ticket = null;
            try {
                DERValue[] values = DERParser.ParseData(decrypted, 0);
                if (values.Length != 1)
                {
                    return(false);
                }
                DERValue value = values[0];
                if (!value.CheckApplication(27) || !value.HasChildren())
                {
                    return(false);
                }
                if (!value.Children[0].CheckSequence())
                {
                    return(false);
                }
                var ret = new KerberosAPReplyEncryptedPart(orig_data);
                foreach (var next in value.Children[0].Children)
                {
                    if (next.Type != DERTagType.ContextSpecific)
                    {
                        return(false);
                    }
                    switch (next.Tag)
                    {
                    case 0:
                        ret.ClientTime = next.ReadChildGeneralizedTime();
                        break;

                    case 1:
                        ret.ClientUSec = next.ReadChildInteger();
                        break;

                    case 2:
                        if (!next.HasChildren())
                        {
                            return(false);
                        }
                        ret.SubKey = KerberosAuthenticationKey.Parse(next.Children[0], string.Empty, new KerberosPrincipalName());
                        break;

                    case 3:
                        ret.SequenceNumber = next.ReadChildInteger();
                        break;

                    default:
                        return(false);
                    }
                }
                ticket = ret;
            } catch (InvalidDataException) {
                return(false);
            } catch (EndOfStreamException) {
                return(false);
            }
            return(true);
        }
Beispiel #5
0
        private static bool CheckForPageHash(DERValue root)
        {
            if (!root.CheckSequence() || !root.HasChildren())
            {
                return(false);
            }
            root = root.Children[0];
            if (!root.CheckSequence() || !root.HasChildren())
            {
                return(false);
            }
            if (root.Children.Length < 2 || root.ReadChildObjID() != SPC_PE_IMAGE_DATAOBJ || !root.Children[1].CheckSequence())
            {
                return(false);
            }
            root = root.Children[1];
            if (root.Children.Length < 2 || !root.Children[0].CheckPrimitive(UniversalTag.BIT_STRING) || !root.Children[1].CheckContext(0))
            {
                return(false);
            }
            root = root.Children[1];
            if (root.Children.Length < 1 || !root.Children[0].CheckContext(1))
            {
                return(false);
            }
            root = root.Children[0];
            if (root.Children.Length < 2 || !root.Children[0].CheckPrimitive(UniversalTag.OCTET_STRING) ||
                !root.Children[1].CheckPrimitive(UniversalTag.OCTET_STRING))
            {
                return(false);
            }
            if (root.Children[0].Data.Length != 16)
            {
                return(false);
            }
            if (new Guid(root.Children[0].Data) != SPCSERIALIZED_OBJECT)
            {
                return(false);
            }

            DERValue[] values = DERParser.ParseData(root.Children[1].Data, 0);
            if (values.Length < 1)
            {
                return(false);
            }
            var objid = values[0].GetChild(0)?.GetChild(0);

            if (!objid?.CheckPrimitive(UniversalTag.OBJECT_IDENTIFIER) ?? false)
            {
                return(false);
            }

            string objid_value = objid.Value.ReadObjID();

            return(objid_value == SPC_PE_IMAGE_PAGE_HASHES_V1_OBJID ||
                   objid_value == SPC_PE_IMAGE_PAGE_HASHES_V2_OBJID);
        }
Beispiel #6
0
        internal static bool Parse(byte[] data, out KerberosAuthorizationDataRestrictionEntry entry)
        {
            entry = null;
            DERValue[] values = DERParser.ParseData(data, 0);
            if (!values.CheckValueSequence())
            {
                return(false);
            }
            values = values[0].Children;
            if (!values.CheckValueSequence())
            {
                return(false);
            }
            byte[] lsap_data = null;
            try
            {
                foreach (var next in values[0].Children)
                {
                    if (next.Type != DERTagType.ContextSpecific)
                    {
                        return(false);
                    }
                    switch (next.Tag)
                    {
                    case 0:
                        // Ignore, should always be 0.
                        break;

                    case 1:
                        lsap_data = next.ReadChildOctetString();
                        break;
                    }
                }
            }
            catch (InvalidDataException)
            {
                return(false);
            }

            if (lsap_data == null || lsap_data.Length != 40)
            {
                return(false);
            }
            int flags = BitConverter.ToInt32(lsap_data, 0);
            int il    = BitConverter.ToInt32(lsap_data, 4);

            byte[] machine_id = new byte[32];
            Buffer.BlockCopy(lsap_data, 8, machine_id, 0, 32);
            entry = new KerberosAuthorizationDataRestrictionEntry(data, (KerberosRestrictionEntryFlags)flags, (TokenIntegrityLevel)il, machine_id);
            return(true);
        }
Beispiel #7
0
        /// <summary>
        /// Try and parse data into an Negotiate authentication token.
        /// </summary>
        /// <param name="data">The data to parse.</param>
        /// <param name="token">The Negotiate authentication token.</param>
        /// <param name="client">True if this is a token from a client.</param>
        /// <param name="token_count">The token count number.</param>
        /// <returns>True if parsed successfully.</returns>
        internal static bool TryParse(byte[] data, int token_count, bool client, out NegotiateAuthenticationToken token)
        {
            token = null;
            try
            {
                byte[] token_data;
                if (GSSAPIUtils.TryParse(data, out token_data, out string oid))
                {
                    if (oid != OIDValues.SPNEGO)
                    {
                        return(false);
                    }
                }
                else
                {
                    token_data = data;
                }

                DERValue[] values = DERParser.ParseData(token_data, 0);
                if (values.Length != 1 || values[0].Type != DERTagType.ContextSpecific)
                {
                    return(false);
                }

                if (values[0].CheckContext(0))
                {
                    return(ParseInit(data, values[0].Children, token_count, client, out token));
                }
                else if (values[0].CheckContext(1))
                {
                    return(ParseResp(data, values[0].Children, token_count, client, out token));
                }
                else
                {
                    return(false);
                }
            }
            catch (EndOfStreamException)
            {
            }
            catch (InvalidDataException)
            {
            }
            return(false);
        }
Beispiel #8
0
        internal static bool Parse(byte[] data, out KerberosChecksum checksum)
        {
            checksum = null;

            try
            {
                KerberosChecksumGSSApi ret = new KerberosChecksumGSSApi(KerberosChecksumType.GSSAPI, data);

                BinaryReader reader         = new BinaryReader(new MemoryStream(data));
                int          binding_length = reader.ReadInt32();
                ret.ChannelBinding = reader.ReadAllBytes(binding_length);
                ret.ContextFlags   = (KerberosChecksumGSSApiFlags)reader.ReadInt32();
                if (ret.ContextFlags.HasFlagSet(KerberosChecksumGSSApiFlags.Delegate))
                {
                    ret.DelegationOptionIdentifier = reader.ReadUInt16();
                    int    cred_length = reader.ReadUInt16();
                    byte[] cred        = reader.ReadAllBytes(cred_length);

                    DERValue[] values = DERParser.ParseData(cred, 0);
                    if (!KerberosCredential.TryParse(cred, values, out KerberosCredential cred_token))
                    {
                        return(false);
                    }
                    ret.Credentials = cred_token;
                }
                if (reader.RemainingLength() > 0)
                {
                    ret.Extensions = reader.ReadToEnd();
                }

                checksum = ret;
                return(true);
            }
            catch (EndOfStreamException)
            {
            }

            return(false);
        }
        internal static KerberosAuthorizationData Parse(DERValue value)
        {
            if (!value.CheckSequence())
            {
                throw new InvalidDataException();
            }
            KerberosAuthorizationDataType type = 0;

            byte[] data = null;
            foreach (var next in value.Children)
            {
                if (next.Type != DERTagType.ContextSpecific)
                {
                    throw new InvalidDataException();
                }
                switch (next.Tag)
                {
                case 0:
                    type = (KerberosAuthorizationDataType)next.ReadChildInteger();
                    break;

                case 1:
                    data = next.ReadChildOctetString();
                    break;

                default:
                    throw new InvalidDataException();
                }
            }

            if (type == 0 || data == null)
            {
                throw new InvalidDataException();
            }

            if (type == KerberosAuthorizationDataType.AD_IF_RELEVANT)
            {
                DERValue[] values = DERParser.ParseData(data, 0);
                if (values.Length != 1 || !values[0].CheckSequence() || !values[0].HasChildren())
                {
                    throw new InvalidDataException();
                }

                return(Parse(values[0].Children[0]));
            }
            else if (type == KerberosAuthorizationDataType.KERB_AD_RESTRICTION_ENTRY)
            {
                if (KerberosAuthorizationDataRestrictionEntry.Parse(data,
                                                                    out KerberosAuthorizationDataRestrictionEntry entry))
                {
                    return(entry);
                }
            }
            else if (type == KerberosAuthorizationDataType.AD_ETYPE_NEGOTIATION)
            {
                if (KerberosAuthorizationDataEncryptionNegotiation.Parse(data,
                                                                         out KerberosAuthorizationDataEncryptionNegotiation entry))
                {
                    return(entry);
                }
            }
            else if (type == KerberosAuthorizationDataType.AD_WIN2K_PAC)
            {
                if (KerberosAuthorizationDataPAC.Parse(data,
                                                       out KerberosAuthorizationDataPAC entry))
                {
                    return(entry);
                }
            }

            return(new KerberosAuthorizationData(type, data));
        }
        internal static bool Parse(KerberosTicket orig_ticket, KerberosEncryptedData orig_data, byte[] decrypted, KerberosKeySet keyset, out KerberosEncryptedData ticket)
        {
            ticket = null;
            try
            {
                DERValue[] values = DERParser.ParseData(decrypted, 0);
                if (values.Length != 1)
                {
                    return(false);
                }
                DERValue value = values[0];
                if (!value.CheckApplication(2) || !value.HasChildren())
                {
                    return(false);
                }
                if (!value.Children[0].CheckSequence())
                {
                    return(false);
                }
                var ret = new KerberosAuthenticator(orig_data);
                foreach (var next in value.Children[0].Children)
                {
                    if (next.Type != DERTagType.ContextSpecific)
                    {
                        return(false);
                    }
                    switch (next.Tag)
                    {
                    case 0:
                        if (next.ReadChildInteger() != 5)
                        {
                            return(false);
                        }
                        break;

                    case 1:
                        ret.ClientRealm = next.ReadChildGeneralString();
                        break;

                    case 2:
                        if (!next.Children[0].CheckSequence())
                        {
                            return(false);
                        }
                        ret.ClientName = KerberosPrincipalName.Parse(next.Children[0]);
                        break;

                    case 3:
                        if (!next.Children[0].CheckSequence())
                        {
                            return(false);
                        }
                        ret.Checksum = KerberosChecksum.Parse(next.Children[0]);
                        break;

                    case 4:
                        ret.ClientUSec = next.ReadChildInteger();
                        break;

                    case 5:
                        ret.ClientTime = next.ReadChildGeneralizedTime();
                        break;

                    case 6:
                        if (!next.HasChildren())
                        {
                            return(false);
                        }
                        ret.SubKey = KerberosAuthenticationKey.Parse(next.Children[0], orig_ticket.Realm, orig_ticket.ServerName);
                        break;

                    case 7:
                        ret.SequenceNumber = next.ReadChildInteger();
                        break;

                    case 8:
                        if (!next.HasChildren())
                        {
                            return(false);
                        }
                        ret.AuthorizationData = KerberosAuthorizationData.ParseSequence(next.Children[0]);
                        break;

                    default:
                        return(false);
                    }
                }

                if (ret.Checksum is KerberosChecksumGSSApi gssapi && gssapi.Credentials != null)
                {
                    KerberosKeySet tmp_keyset = new KerberosKeySet(keyset.AsEnumerable() ?? new KerberosAuthenticationKey[0]);
                    if (ret.SubKey != null)
                    {
                        tmp_keyset.Add(ret.SubKey);
                    }

                    gssapi.Decrypt(tmp_keyset);
                }

                ticket = ret;
            }
            catch (InvalidDataException)
            {
                return(false);
            }
            catch (EndOfStreamException)
            {
                return(false);
            }
            return(true);
        }
        internal static IEnumerable <KerberosAuthorizationData> Parse(DERValue value)
        {
            if (!value.CheckSequence())
            {
                throw new InvalidDataException();
            }
            KerberosAuthorizationDataType type = 0;

            byte[] data = null;
            foreach (var next in value.Children)
            {
                if (next.Type != DERTagType.ContextSpecific)
                {
                    throw new InvalidDataException();
                }
                switch (next.Tag)
                {
                case 0:
                    type = (KerberosAuthorizationDataType)next.ReadChildInteger();
                    break;

                case 1:
                    data = next.ReadChildOctetString();
                    break;

                default:
                    throw new InvalidDataException();
                }
            }

            if (type == 0 || data == null)
            {
                throw new InvalidDataException();
            }

            List <KerberosAuthorizationData> ret = new List <KerberosAuthorizationData>();

            if (type == KerberosAuthorizationDataType.AD_IF_RELEVANT)
            {
                DERValue[] values = DERParser.ParseData(data, 0);
                if (values.Length != 1 || !values[0].CheckSequence() || !values[0].HasChildren())
                {
                    throw new InvalidDataException();
                }

                ret.AddRange(values[0].Children.SelectMany(c => Parse(c)));
            }
            else if (type == KerberosAuthorizationDataType.KERB_AD_RESTRICTION_ENTRY)
            {
                if (KerberosAuthorizationDataRestrictionEntry.Parse(data,
                                                                    out KerberosAuthorizationDataRestrictionEntry entry))
                {
                    ret.Add(entry);
                }
            }
            else if (type == KerberosAuthorizationDataType.AD_ETYPE_NEGOTIATION)
            {
                if (KerberosAuthorizationDataEncryptionNegotiation.Parse(data,
                                                                         out KerberosAuthorizationDataEncryptionNegotiation entry))
                {
                    ret.Add(entry);
                }
            }
            else if (type == KerberosAuthorizationDataType.AD_WIN2K_PAC)
            {
                if (KerberosAuthorizationDataPAC.Parse(data,
                                                       out KerberosAuthorizationDataPAC entry))
                {
                    ret.Add(entry);
                }
            }
            else if (type == KerberosAuthorizationDataType.AD_AUTH_DATA_AP_OPTIONS)
            {
                if (KerberosAuthorizationDataApOptions.Parse(data,
                                                             out KerberosAuthorizationDataApOptions entry))
                {
                    ret.Add(entry);
                }
            }
            else if (type == KerberosAuthorizationDataType.AD_AUTH_DATA_TARGET_NAME)
            {
                if (KerberosAuthorizationDataTargetName.Parse(data,
                                                              out KerberosAuthorizationDataTargetName entry))
                {
                    ret.Add(entry);
                }
            }
            else if (type == KerberosAuthorizationDataType.KERB_LOCAL)
            {
                if (KerberosAuthorizationDataKerbLocal.Parse(data,
                                                             out KerberosAuthorizationDataKerbLocal entry))
                {
                    ret.Add(entry);
                }
            }

            if (ret.Count == 0)
            {
                ret.Add(new KerberosAuthorizationData(type, data));
            }
            return(ret);
        }
        internal static bool Parse(KerberosTicket orig_ticket, byte[] decrypted, KerberosKeySet keyset, out KerberosTicket ticket)
        {
            ticket = null;
            try {
                DERValue[] values = DERParser.ParseData(decrypted, 0);
                if (values.Length != 1)
                {
                    return(false);
                }
                DERValue value = values[0];
                if (!value.CheckApplication(3) || !value.HasChildren())
                {
                    return(false);
                }
                if (!value.Children[0].CheckSequence())
                {
                    return(false);
                }
                var ret = new KerberosTicketDecrypted(orig_ticket);
                foreach (var next in value.Children[0].Children)
                {
                    if (next.Type != DERTagType.ContextSpecific)
                    {
                        return(false);
                    }
                    switch (next.Tag)
                    {
                    case 0:
                        ret.Flags = ConvertTicketFlags(next.ReadChildBitString());
                        break;

                    case 1:
                        if (!next.HasChildren())
                        {
                            return(false);
                        }
                        ret.Key = KerberosAuthenticationKey.Parse(next.Children[0], orig_ticket.Realm, orig_ticket.ServerName);
                        keyset.Add(ret.Key);
                        break;

                    case 2:
                        ret.ClientRealm = next.ReadChildGeneralString();
                        break;

                    case 3:
                        if (!next.Children[0].CheckSequence())
                        {
                            return(false);
                        }
                        ret.ClientName = KerberosPrincipalName.Parse(next.Children[0]);
                        break;

                    case 4:
                        if (!next.HasChildren())
                        {
                            return(false);
                        }
                        ret.TransitedType = KerberosTransitedEncoding.Parse(next.Children[0]);
                        break;

                    case 5:
                        ret.AuthTime = next.ReadChildGeneralizedTime();
                        break;

                    case 6:
                        ret.StartTime = next.ReadChildGeneralizedTime();
                        break;

                    case 7:
                        ret.EndTime = next.ReadChildGeneralizedTime();
                        break;

                    case 8:
                        ret.RenewTill = next.ReadChildGeneralizedTime();
                        break;

                    case 9:
                        if (!next.HasChildren())
                        {
                            return(false);
                        }
                        ret.HostAddresses = KerberosHostAddress.ParseSequence(next.Children[0]);
                        break;

                    case 10:
                        if (!next.HasChildren())
                        {
                            return(false);
                        }
                        ret.AuthorizationData = KerberosAuthorizationData.ParseSequence(next.Children[0]);
                        break;

                    default:
                        return(false);
                    }
                }
                ticket = ret;
            } catch (InvalidDataException) {
                return(false);
            } catch (EndOfStreamException) {
                return(false);
            }
            return(true);
        }
 private protected ASN1AuthenticationToken(byte[] data)
     : this(data, DERParser.ParseData(data, 0))
 {
 }