2013-05-24 2 views
6

Windows 2003 서버에서 .Net Framework 3.5와 함께 VS 2008 사용.SSO SAML (sha256 사용)에 대한 서명 된 XML 서명 확인

보안을 위해 SAML로 SSO를 구현했습니다. 우리는 클라이언트 시스템에서 생성 된 Signed XML SAML Assertuib 토큰의 유효성을 검사하는 서비스 제공 업체 측에서 작업합니다. 지금까지 서명 한 모든 문서는 서명 알고리즘 "rsa-sha1"을 사용했지만 이제는 서명 알고리즘이 "rsa-sha256"인 파일을 보내는 새로운 고객이 생겼습니다. 시작한 문제가 있습니다. 내가 (서명 알고리즘 RSA-sha256h로)이 새로운 고객을 위해 동일한 코드를하려고 할 때

public static string VerifySignature() 
{ 
    if (m_xmlDoc == null) 
     return "Could not load XMLDocument "; 

    try 
    { 
     XmlNamespaceManager nsm = new XmlNamespaceManager(new NameTable()); 
     nsm.AddNamespace("dsig", SignedXml.XmlDsigNamespaceUrl); 
     XmlElement sigElt = (XmlElement)m_xmlDoc.SelectSingleNode(
      "//dsig:Signature", nsm); 

     // Load the signature for verification 
     SignedXml sig = new SignedXml(m_xmlDoc); 
     sig.LoadXml(sigElt); 

     if (!sig.CheckSignature()) 
      return "Invalid Signature"; 
    } 
    catch (Exception ex) 
    { 
     return ex.Message; 
    } 
    return string.Empty; 
} 

지금 -이 작동하지 않습니다와 나는 오류가 "SignatureDescription가 제공 서명 알고리즘을 만들 수 없습니다 얻고있다. "

지난 2-3 일 동안 많은 블로그와 기사를 읽었을 때 SignedXml이 sha256을 지원하지 않는다는 사실을 알게되었습니다. 벌금. 그러나 다음은 무엇인가. WIF를 사용하는 곳에서 언급 한 바에 따르면 &도 시도했습니다. this입니다.

또한 RSAPKCS1SignatureDeformatter의 VerifySignature 메서드를 사용하려고합니다. 하지만 통과해야 할 두 가지 매개 변수는 무엇인지 확실하지 않습니다.

+0

X509Certificate2 개체를 지원하므로 암호화 알고리즘이 지원되었다는 인상을 받았습니다. sig.CheckSignature (...) 메서드에는 두 개의 매개 변수 인 X509Certificate2와 bool을 사용하는 오버로드가 있습니다. 당신은 그것을 사용하고 cert를 전달하고 사실입니까? –

답변

2

이것은 "단순한"것이지만 "해결책"이 아닐 수 있습니다. :) 우리가 만난 몇몇 클라이언트의 경우, SHA-1을 사용하여 IdP를 변경하도록 요청했습니다. 그들은 그것을 바꿀 수 있으며, 그것을하면 효과가 있습니다.

기술적 인 해결책이 아니지만 '현장에서'작업 했으므로 언급 할 것입니다.

+0

고객이 한숨을 쉬게했습니다. –

3
.NET 4

및 이전 버전, 난 당신 한 번 다음 작품에서 Security.Cryptography를 추가 발견 http://clrsecurity.codeplex.com/

(지문으로 인증서 저장소에서 서명 인증서를 찾습니다, X509CertificateFinder 내 자신 참고)

 /// <summary> 
     /// Validate an XmlDocuments signature 
     /// </summary> 
     /// <param name="xnlDoc"> The saml response with the signature elemenet to validate </param> 
     /// <returns> True if signature can be validated with certificate </returns> 
     public bool ValidateX509CertificateSignature(XmlDocument xnlDoc) 
     { 
      XmlNodeList XMLSignatures = xnlDoc.GetElementsByTagName("Signature", "http://www.w3.org/2000/09/xmldsig#"); 

      // Checking If the Response or the Assertion has been signed once and only once. 
      if (XMLSignatures.Count != 1) return false; 

      var signedXmlDoc = new SignedXml(xnlDoc); 
      signedXmlDoc.LoadXml((XmlElement)XMLSignatures[0]); 

      var certFinder = new X509CertificateFinder(); 
      var foundCert = certFinder.GetSignatureCertificate(); 

      CryptoConfig.AddAlgorithm(typeof(RSAPKCS1SHA256SignatureDescription), "http://www.w3.org/2001/04/xmldsig-more#rsa-sha256"); 
      return signedXmlDoc.CheckSignature(foundCert,false); 
     } 
+2

.NET 4.5부터는 .net 4.0 이하와 달리 타사 라이브러리를 설치할 필요가 없습니다. System.Deployment에 대한 참조를 추가하고 원래 질문의 코드가 SHA256 해시와 함께 작동하면'System.Security.Cryptography.CryptoConfig.AddAlgorithm (typeof (RSAPKCS1SHA256SignatureDescription), RsaSha256Namespace); '를 호출하면됩니다. . http://blogs.msdn.com/b/winsdk/archive/2015/11/15/using-sha256-with-signedxml.aspx – Rory

+0

'const string RsaSha256Namespace = "http://www.w3.org/도 참조하십시오. 2001/04/xmldsig-more # rsa-sha256 "; ' – maddoxej

1

SHA-256은 .NET 4.5에서 기본적으로 사용할 수 없습니다. 따라서 .NET 3.5 또는 4.0을 사용하는 경우 codeplex.com에서 보안 라이브러리를 다운로드해야합니다. SHA-2 알고리즘에 대한 유효성 검사 및 SAML 서명 생성에 대한 자세한 내용은 http://www.componentpro.com/doc/saml/working-with-sha-256.htmhttp://www.componentpro.com/doc/saml/Verifying-XML-Signatures.htm을 참조하십시오.

당신은 Ultimate SAML library for .NET.

8

DOTNET 4.6.2+가 내장 된 새로운 sha 해시를 가지고해야합니다. DOTNET 4 +를 들어, RSA-SHA512, RSA-SHA384, 및 RSA-SHA256에 액세스하려면 다음을 수행해야 이 코드를 어딘가에 포함 시키십시오.

/// <summary>Declare the signature type for rsa-sha512</summary> 
public class RsaPkCs1Sha512SignatureDescription : SignatureDescription 
{ 
    public RsaPkCs1Sha512SignatureDescription() 
    { 
     KeyAlgorithm = typeof(RSACryptoServiceProvider).FullName; 
     DigestAlgorithm = typeof(SHA512CryptoServiceProvider).FullName; 
     FormatterAlgorithm = typeof(RSAPKCS1SignatureFormatter).FullName; 
     DeformatterAlgorithm = typeof(RSAPKCS1SignatureDeformatter).FullName; 
    } 

    public override AsymmetricSignatureDeformatter CreateDeformatter(AsymmetricAlgorithm key) 
    { 
     var sigProcessor = (AsymmetricSignatureDeformatter)CryptoConfig.CreateFromName(DeformatterAlgorithm); 
     sigProcessor.SetKey(key); 
     sigProcessor.SetHashAlgorithm("SHA512"); 
     return sigProcessor; 
    } 

    public override AsymmetricSignatureFormatter CreateFormatter(AsymmetricAlgorithm key) 
    { 
     var sigProcessor = 
      (AsymmetricSignatureFormatter)CryptoConfig.CreateFromName(FormatterAlgorithm); 
     sigProcessor.SetKey(key); 
     sigProcessor.SetHashAlgorithm("SHA512"); 
     return sigProcessor; 
    } 
} 

/// <summary>Declare the signature type for rsa-sha384</summary> 
public class RsaPkCs1Sha384SignatureDescription : SignatureDescription { 
    public RsaPkCs1Sha384SignatureDescription() 
    { 
     KeyAlgorithm = typeof(RSACryptoServiceProvider).FullName; 
     DigestAlgorithm = typeof(SHA384CryptoServiceProvider).FullName; 
     FormatterAlgorithm = typeof(RSAPKCS1SignatureFormatter).FullName; 
     DeformatterAlgorithm = typeof(RSAPKCS1SignatureDeformatter).FullName; 
    } 

    public override AsymmetricSignatureDeformatter CreateDeformatter(AsymmetricAlgorithm key) 
    { 
     var sigProcessor = (AsymmetricSignatureDeformatter) CryptoConfig.CreateFromName(DeformatterAlgorithm); 
     sigProcessor.SetKey(key); 
     sigProcessor.SetHashAlgorithm("SHA384"); 
     return sigProcessor; 
    } 

    public override AsymmetricSignatureFormatter CreateFormatter(AsymmetricAlgorithm key) 
    { 
     var sigProcessor = 
      (AsymmetricSignatureFormatter)CryptoConfig.CreateFromName(FormatterAlgorithm); 
     sigProcessor.SetKey(key); 
     sigProcessor.SetHashAlgorithm("SHA384"); 
     return sigProcessor; 
    } 
} 

/// <summary>Declare the signature type for rsa-sha256</summary> 
public class RsaPkCs1Sha256SignatureDescription : SignatureDescription 
{ 
    public RsaPkCs1Sha256SignatureDescription() 
    { 
     KeyAlgorithm = typeof(RSACryptoServiceProvider).FullName; 
     DigestAlgorithm = typeof(SHA256CryptoServiceProvider).FullName; 
     FormatterAlgorithm = typeof(RSAPKCS1SignatureFormatter).FullName; 
     DeformatterAlgorithm = typeof(RSAPKCS1SignatureDeformatter).FullName; 
    } 

    public override AsymmetricSignatureDeformatter CreateDeformatter(AsymmetricAlgorithm key) 
    { 
     var sigProcessor = 
      (AsymmetricSignatureDeformatter) CryptoConfig.CreateFromName(DeformatterAlgorithm); 
     sigProcessor.SetKey(key); 
     sigProcessor.SetHashAlgorithm("SHA256"); 
     return sigProcessor; 
    } 

    public override AsymmetricSignatureFormatter CreateFormatter(AsymmetricAlgorithm key) 
    { 
     var sigProcessor = 
      (AsymmetricSignatureFormatter)CryptoConfig.CreateFromName(FormatterAlgorithm); 
     sigProcessor.SetKey(key); 
     sigProcessor.SetHashAlgorithm("SHA256"); 
     return sigProcessor; 
    } 
} 

그런 다음 이러한 sig 설명은 다음과 같은 코드를 호출하여 활성화해야합니다. 원한다면 정적 생성자에서 호출 할 수 있도록 한 번만 호출하면됩니다.

CryptoConfig.AddAlgorithm(typeof(RsaPkCs1Sha512SignatureDescription), 
     "http://www.w3.org/2001/04/xmldsig-more#rsa-sha512"); 
    CryptoConfig.AddAlgorithm(typeof(RsaPkCs1Sha384SignatureDescription), 
     "http://www.w3.org/2001/04/xmldsig-more#rsa-sha384"); 
    CryptoConfig.AddAlgorithm(typeof(RsaPkCs1Sha256SignatureDescription), 
     "http://www.w3.org/2001/04/xmldsig-more#rsa-sha256"); 

팁 O 'SO에 Microsoft's Carlos LopezBitSchupsterAndrew에 모자.

+0

발견 된 작업 .. 많은 시간을 절약 해 주셔서 고마워요. – amesh

+3

.... 및 프레임 워크 4.6.2가 처리됩니다. 여분의 코드가 필요없이이 문제가 발생합니다. –

+0

@OllieJones - 대상이 4.6.2로 대상이되는 이후에 코드가 중단되는지 알 수 있습니까? –

0

.NET 프레임 워크 4.6.01590 이상으로 업데이트하면 코드를 변경하지 않고도 SHA-512까지 지원할 수 있습니다.