Security.cs source code in C# .NET

Source code for the .NET framework in C#

                        

Code:

/ WCF / WCF / 3.5.30729.1 / untmp / Orcas / SP / ndp / cdf / src / WCF / TransactionBridge / Microsoft / Transactions / Wsat / Messaging / Security.cs / 1 / Security.cs

                            //------------------------------------------------------------------------------ 
// Copyright (c) Microsoft Corporation.  All rights reserved.
//-----------------------------------------------------------------------------

// Define some helper functions used for security 

using System; 
 
using System.ServiceModel;
using System.Collections.Generic; 
using System.Collections.ObjectModel;
using System.Diagnostics;
using System.DirectoryServices.ActiveDirectory;
using System.Globalization; 
using System.Net;
using System.Net.Security; 
using System.IdentityModel.Claims; 
using System.IdentityModel.Policy;
using System.IdentityModel.Tokens; 
using System.IdentityModel.Selectors;
using System.Security.Cryptography;
using System.Security.Cryptography.X509Certificates;
using System.Security.Permissions; 
using System.Security.Principal;
using System.Runtime.Serialization; 
using System.ServiceModel.Channels; 
using System.ServiceModel.Security;
using System.ServiceModel.Security.Tokens; 
using System.ServiceModel.Transactions;
using System.Text;
using System.Transactions;
using System.Xml; 

using DiagnosticUtility = Microsoft.Transactions.Bridge.DiagnosticUtility; 
using Microsoft.Transactions.Wsat.Protocol; 

namespace Microsoft.Transactions.Wsat.Messaging 
{
    class CoordinationServiceSecurity
    {
        IdentityVerifier identityVerifier = IdentityVerifier.CreateDefault(); 

        static SecurityContextSecurityTokenParameters securityContextSecurityTokenParameters; 
        public static SecurityContextSecurityTokenParameters SecurityContextSecurityTokenParameters 
        {
            get 
            {
                if (securityContextSecurityTokenParameters == null)
                    securityContextSecurityTokenParameters = new SecurityContextSecurityTokenParameters();
                return securityContextSecurityTokenParameters; 
            }
        } 
 
        static DataContractSerializer identifierElementSerializer10;
        static DataContractSerializer identifierElementSerializer11; 

        static DataContractSerializer IdentifierElementSerializer(ProtocolVersion protocolVersion)
        {
            ProtocolVersionHelper.AssertProtocolVersion(protocolVersion, typeof(CoordinationServiceSecurity), "IdentifierElementSerializer"); //assert valid protocol version 

            switch (protocolVersion) 
            { 
                case ProtocolVersion.Version10 :
                    if (identifierElementSerializer10 == null) 
                        identifierElementSerializer10 = new DataContractSerializer(typeof(IdentifierElement10));
                    return identifierElementSerializer10;

                case ProtocolVersion.Version11 : 
                    if (identifierElementSerializer11 == null)
                        identifierElementSerializer11 = new DataContractSerializer(typeof(IdentifierElement11)); 
                    return identifierElementSerializer11; 

                default: 
                    return null; // inaccessible path because we have asserted the protocol version
            }
        }
 
        //
        // Issued tokens / supporting tokens 
        // 

        static byte[] Label = Encoding.UTF8.GetBytes("WS-AT Supporting Token"); 
        static SecurityStandardsManager SecurityStandardsManager2007 =
            CreateStandardsManager(MessageSecurityVersion.WSSecurity11WSTrust13WSSecureConversation13WSSecurityPolicy12);

        static SecurityStandardsManager CreateStandardsManager(MessageSecurityVersion securityVersion) 
        {
            return new SecurityStandardsManager( 
                securityVersion, 
                new WSSecurityTokenSerializer(securityVersion.SecurityVersion, securityVersion.TrustVersion, securityVersion.SecureConversationVersion, false, null, null, null));
        } 

        static SecurityStandardsManager CreateStandardsManager(ProtocolVersion protocolVersion)
        {
            ProtocolVersionHelper.AssertProtocolVersion(protocolVersion, typeof(CoordinationServiceSecurity), "CreateStandardsManager"); 

            switch (protocolVersion) 
            { 
                case ProtocolVersion.Version10:
                    return SecurityStandardsManager.DefaultInstance; 

                case ProtocolVersion.Version11:
                    return CoordinationServiceSecurity.SecurityStandardsManager2007;
 
                default:
                    return null; // inaccessible path because we have asserted the protocol version 
            } 
        }
 
        //=======================================================================================
        public static byte[] DeriveIssuedTokenKey(Guid transactionId, string sctId)
        {
            return Psha1DerivedKeyGeneratorHelper.GenerateDerivedKey(transactionId.ToByteArray(), 
                                                                     Label,
                                                                     Encoding.UTF8.GetBytes(sctId), 
                                                                     SecurityAlgorithmSuite.Default.DefaultSymmetricKeyLength, 
                                                                     0);
        } 

        //=======================================================================================
        public static void CreateIssuedToken(Guid transactionId,
                                             string coordinationContextId, 
                                             ProtocolVersion protocolVersion,
                                             out RequestSecurityTokenResponse issuedToken, 
                                             out string sctId) 
        {
            sctId = CoordinationContext.CreateNativeIdentifier(Guid.NewGuid()); 
            byte[] derivedKey = DeriveIssuedTokenKey(transactionId, sctId);

            DateTime now = DateTime.UtcNow;
            SecurityContextSecurityToken sct = new SecurityContextSecurityToken(new UniqueId(sctId), 
                                                                                derivedKey,
                                                                                now, 
                                                                                now + TimeSpan.FromDays(100 * 365)); 

            BinarySecretSecurityToken proof = new BinarySecretSecurityToken(derivedKey); 
            SecurityStandardsManager standardsManager = CreateStandardsManager(protocolVersion);
            RequestSecurityTokenResponse rstr = new RequestSecurityTokenResponse(standardsManager);
            rstr.TokenType = standardsManager.SecureConversationDriver.TokenTypeUri;
            rstr.RequestedUnattachedReference = SecurityContextSecurityTokenParameters.CreateKeyIdentifierClause(sct, SecurityTokenReferenceStyle.External); 
            rstr.RequestedAttachedReference = SecurityContextSecurityTokenParameters.CreateKeyIdentifierClause(sct, SecurityTokenReferenceStyle.Internal);
            rstr.RequestedSecurityToken = sct; 
            rstr.RequestedProofToken = proof; 

            DataContractSerializer identifierElementSerializer = IdentifierElementSerializer(protocolVersion); 

            ProtocolVersionHelper.AssertProtocolVersion(protocolVersion, typeof(CoordinationServiceSecurity), "CreateIssuedToken"); //assert valid protocol version

            switch(protocolVersion) 
            {
                case ProtocolVersion.Version10 : 
                    rstr.SetAppliesTo(new IdentifierElement10(coordinationContextId), 
                                            identifierElementSerializer);
                    break; 

                case ProtocolVersion.Version11 :
                    rstr.SetAppliesTo(new IdentifierElement11(coordinationContextId),
                                            identifierElementSerializer); 
                    break;
 
                default : 
                    break; // inaccessible path because we have asserted the protocol version
            } 


            rstr.MakeReadOnly();
 
            if (DebugTrace.Verbose)
            { 
                DebugTrace.Trace(TraceLevel.Verbose, 
                                 "Created issued token with id {0} for transaction {1}",
                                 sctId, transactionId); 
            }

            issuedToken = rstr;
        } 

        //======================================================================================== 
        public static void AddIssuedToken(Message message, RequestSecurityTokenResponse rstr) 
        {
            TransactionFlowProperty transactionFlowProp = TransactionFlowProperty.Ensure(message); 
            transactionFlowProp.IssuedTokens.Add(rstr);

            if (DebugTrace.Verbose)
            { 
                DebugTrace.Trace(TraceLevel.Verbose, "Added issued token to message");
            } 
        } 

        //======================================================================================= 
        // This function can throw XmlException
        public static RequestSecurityTokenResponse GetIssuedToken(Message message, string identifier, ProtocolVersion protocolVersion)
        {
 
            ICollection rstrCollection = TransactionFlowProperty.TryGetIssuedTokens(message);
            if (rstrCollection == null) 
            { 
                if (DebugTrace.Verbose)
                    DebugTrace.Trace(TraceLevel.Verbose, "No issued tokens found in message"); 

                return null;
            }
 
            string coordIdentifier = CoordinationStrings.Version(protocolVersion).Identifier;
            string coordNamespace = CoordinationStrings.Version(protocolVersion).Namespace; 
 
            foreach (RequestSecurityTokenResponse rstr in rstrCollection)
            { 
                string name, ns;
                rstr.GetAppliesToQName(out name, out ns);

                if (name == coordIdentifier && 
                    ns == coordNamespace)
                { 
                    if (DebugTrace.Verbose) 
                        DebugTrace.Trace(TraceLevel.Verbose, "Found issued token in message");
 
                    try
                    {
                        IdentifierElement id = null;
                        DataContractSerializer identifierElementSerializer = IdentifierElementSerializer(protocolVersion); 

                        ProtocolVersionHelper.AssertProtocolVersion(protocolVersion, typeof(CoordinationServiceSecurity), "GetIssuedToken"); //assert valid protocol version 
 
                        switch (protocolVersion)
                        { 
                            case ProtocolVersion.Version10 :
                                id = rstr.GetAppliesTo(identifierElementSerializer);
                                break;
 
                            case ProtocolVersion.Version11 :
                                id = rstr.GetAppliesTo(identifierElementSerializer); 
                                break; 

                            // no default - we have asserted the protocol version 
                        }

                        // Make sure the identifier matches the expected value
                        if (id.Identifier != identifier) 
                        {
                            if (DebugTrace.Error) 
                                DebugTrace.Trace(TraceLevel.Error, 
                                                 "Issued token identifier does not match expected {0}",
                                                 identifier); 

                            throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
                                new XmlException(SR.GetString(SR.IssuedTokenIdentifierMismatch)));
                        } 
                    }
                    catch (SerializationException e) 
                    { 
                        if (DebugTrace.Error)
                            DebugTrace.Trace(TraceLevel.Error, 
                                             "Issued token AppliesTo element could not be deserialized: {0}",
                                             e.Message);

                        throw DiagnosticUtility.ExceptionUtility.ThrowHelperError( 
                            new XmlException(e.Message, e));
                    } 
 
                    return rstr;
                } 
            }

            if (DebugTrace.Verbose)
                DebugTrace.Trace(TraceLevel.Verbose, "No matching issued token found in message"); 

            return null; 
        } 

        //======================================================================================== 
        public static void AddSupportingToken(Message message, RequestSecurityTokenResponse rstr)
        {
            // Currently, we only support a binary secret as the proof of RSTR
            GenericXmlSecurityToken supportingToken = rstr.GetIssuedToken(null, null, SecurityKeyEntropyMode.ServerEntropy, null, null, null); 

            SecurityMessageProperty property = new SecurityMessageProperty(); 
            SupportingTokenSpecification spec = new SupportingTokenSpecification(supportingToken, new List().AsReadOnly(), SecurityTokenAttachmentMode.Endorsing, SecurityContextSecurityTokenParameters); 
            property.OutgoingSupportingTokens.Add(spec);
            message.Properties.Security = property; 

            if (DebugTrace.Verbose)
            {
                DebugTrace.Trace (TraceLevel.Verbose, 
                                  "Attached supporting token {0} to register message",
                                  rstr.Context); 
            } 
        }
 
        //
        // Per-enlistment security
        //
 
        //========================================================================================
        public static string GetSenderName (Message message) 
        { 
            return GetSenderName(message.Properties);
        } 

        //=======================================================================================
        public static string GetSenderName (MessageProperties messageProperties)
        { 
            SecurityMessageProperty securityMessageProperty = messageProperties.Security;
            if (securityMessageProperty == null) 
            { 
                return "anonymous";
            } 

            ServiceSecurityContext securityContext = securityMessageProperty.ServiceSecurityContext;
            if (securityContext == null || securityContext.IsAnonymous)
            { 
                return "anonymous";
            } 
 
            IIdentity identity = securityContext.PrimaryIdentity;
            if (identity != null) 
            {
                return identity.Name;
            }
 
            return securityContext.PrimaryIdentity.ToString();
        } 
 
        //========================================================================================
        public bool CheckIdentity(Proxy proxy, Message message) 
        {
            EndpointAddress service = proxy.To;
            bool access = this.identityVerifier.CheckAccess(service, message);
 
            TraceCheckIdentityResult(access, service, message);
 
            return access; 
        }
 
        //=======================================================================================
        void TraceCheckIdentityResult(bool access, EndpointAddress service, Message message)
        {
            if (DebugTrace.Verbose) 
            {
                if (DebugTrace.Pii) 
                { 
                    string sender = GetSenderName(message);
                    if (access) 
                    {
                        DebugTrace.Trace(TraceLevel.Verbose,
                                         "Access granted by identity verifier to {0}",
                                         sender); 
                    }
                    else 
                    { 
                        DebugTrace.Trace(TraceLevel.Verbose,
                                         "Access denied by identity verifier to {0}, expected {1}", 
                                         sender,
                                         service.Identity == null ? service.Uri.AbsoluteUri :
                                                                    service.Identity.ToString());
                    } 
                }
                else 
                { 
                    if (access)
                    { 
                        DebugTrace.Trace(TraceLevel.Verbose, "Access granted by identity verifier");
                    }
                    else
                    { 
                        DebugTrace.Trace(TraceLevel.Verbose, "Access denied by identity verifier");
                    } 
                } 
            }
        } 
    }
}

// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
// Copyright (c) Microsoft Corporation. All rights reserved.


                        

Link Menu

Network programming in C#, Network Programming in VB.NET, Network Programming in .NET
This book is available now!
Buy at Amazon US or
Buy at Amazon UK