0

我正在构建需要 wse 安全性的肥皂消息,出于某种原因,客户端需要 KeyInfo、主题和序列号。但是为 x509 显示的序列号是十六进制的,不符合整数 X509SerialNumber 节点的 xsd 要求。我读过这需要发行人序列号,但它不是证书的一部分。这是一个自签名证书。如何确定序列号是什么?

请不要告诉我使用 WCF。如果我可以使用它,我会的。我知道 WCF 会让事情变得更容易,我为 WCF 持有 MCTS。

4

2 回答 2

3

证书只有一个序列号字段,是二进制数据。发行人可以把任何东西放在那里。事实上,序列号被视为一个非常大的整数,但是如果您只检查保存该数字的字节数组,那么这个数字看起来就像一个二进制数。因此,您需要将此值视为一个巨大的数字并将其转换为“可读”形式。例如。如果您有 4 字节长的字节数组,其中包含 FF 00 FF 00(4 个字节),则字符串表示形式将为“4278255360”

更新:我上面的解释适用于 XMLDSig 和 XMLEnc 标准。在其他标准(或仅出于显示目的)中,可以使用其他格式(例如 base64、base16 编码等)。

于 2011-01-28T17:53:59.727 回答
1

我找到了我需要的东西。 http://www.dotnetmonster.com/Uwe/Forum.aspx/dotnet-security/2875/Manually-computing-sha1-digest-of-reference-含

只需要添加一些代码。X509ChainElement.Certificate.GetSerialNumberString() 给了我我需要的东西,我不需要计算任何东西。

这是我现在使用的代码

public static XmlElement GenerateSignature(XmlElement xmlToSign, StoreName storeName, StoreLocation storeLocation, X509Certificate2 certificate, string referenceID)
    {
        SignedXml signedXml = new SignedXml(xmlToSign);

        signedXml.SignedInfo.CanonicalizationMethod = SignedXml.XmlDsigExcC14NTransformUrl;
        signedXml.SigningKey = certificate.PrivateKey;

        Reference tRef = new Reference(referenceID);
        XmlDsigExcC14NTransform env = new XmlDsigExcC14NTransform();

        tRef.AddTransform(env);
        signedXml.AddReference(tRef);

        KeyInfo keyInfo = new KeyInfo();
        X509Chain x509Chain = new X509Chain();
        x509Chain.Build(certificate);

        foreach (X509ChainElement element in x509Chain.ChainElements)
        {
            KeyInfoX509Data x509Data = new KeyInfoX509Data(element.Certificate);
            string issuer = element.Certificate.Issuer;
            x509Data.AddIssuerSerial(issuer, element.Certificate.GetSerialNumberString());
            keyInfo.AddClause(x509Data);
        }

        signedXml.KeyInfo = keyInfo;
        signedXml.ComputeSignature();

        XmlElement xmlDsig = signedXml.GetXml();
        return xmlDsig;
    }
于 2011-01-28T20:33:13.387 回答