適切なXML排他的正規化はどれですか?
-
18-09-2019 - |
質問
私は試してみて、SOAP文書に署名する xmlseclibs を使用していますが、それはありません私が署名するか検証してるかどうかに応じて、同じ方法で物事を正規化していないよう。
私はあなたの例をあげます。これは私が署名しようとしているXMLです。
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Header/>
<soapenv:Body>
<samlp:Response xmlns:samlp="urn:oasis:names:tc:SAML:1.0:protocol" xmlns:saml="urn:oasis:names:tc:SAML:1.0:assertion" MajorVersion="1" MinorVersion="1" IssueInstant="2010-02-04T15:27:43Z" ResponseID="pfxe85313e6-e688-299a-df06-30f55e24f65a">
<samlp:Status>
<samlp:StatusCode Value="samlp:Requester"/>
</samlp:Status>
</samlp:Response>
</soapenv:Body>
</soapenv:Envelope>
私は、公開鍵と秘密鍵証明書の組み合わせを使用して、それに署名するためにPHPで働いていくつかのコードを持って、動作するように見えました。これは、すべての適切なもので<ds:Signature>
要素を追加し、それは素晴らしい見えました。しかし、私はすぐにxmlseclibs(および公開鍵証明書)で再度、それに署名した後、それを検証しようとすることで、それをテストしたが、検証が失敗しました。だから、まったく同じコードライブラリは、署名と検証を両方をやっているが、2つのプロセスが何らかの理由で同意しない。
私はそれがやっているかを調べるためにxmlseclibsためにいくつかのデバッグコードを追加した、と私はそれが2つの状況で違ったものを正規化するための理由、それは思い付く署名鍵とそれが思い付く検証鍵が異なっていることに気づきました。
:私は<samlp:Response>
要素に署名するよう指示すると、これは署名正規形(私は読みやすさのためにここに改行を追加しました)です
<samlp:Response xmlns:samlp="urn:oasis:names:tc:SAML:1.0:protocol" IssueInstant="2010-02-04T15:27:43Z" MajorVersion="1" MinorVersion="1" ResponseID="pfxe85313e6-e688-299a-df06-30f55e24f65a" xmlns:saml="urn:oasis:names:tc:SAML:1.0:assertion">
<samlp:Status>
<samlp:StatusCode Value="samlp:Requester">
</samlp:StatusCode>
</samlp:Status>
</samlp:Response>
それは署名を検証するために行くとき、しかし、これは(再び、私はここに改行を追加しました)に対して検証するために計算し、正規の形式です。
<samlp:Response xmlns:samlp="urn:oasis:names:tc:SAML:1.0:protocol" IssueInstant="2010-02-04T15:27:43Z" MajorVersion="1" MinorVersion="1" ResponseID="pfxe85313e6-e688-299a-df06-30f55e24f65a">
<samlp:Status>
<samlp:StatusCode Value="samlp:Requester">
</samlp:StatusCode>
</samlp:Status>
</samlp:Response>
あなたが見ることができるように、第1にはないながら、、このバージョンは、xmlns:saml
要素から<samlp:Response>
属性を省略します。 (これは、両方に含まれているxmlns:samlp
属性とは異なるので注意してください。)これはxmlseclibsのバグのように、かなりはっきりと見えますが、それにもかかわらず、それは私がちょうど標準的な形式が正しいだった知っていた場合、私は自分自身を修正させていただき一つです1。その属性は、排他的正規化では省略されるべきか?あるいは、それが含まれるべき?どちらが正しいの排他的正規形です?
解決
あなたは不適切DOM文書を作成し、不正なメモリ内のツリーを使用しようとしています。どちらのシリアライズやシリアライズされた結果を使用するか、適切に署名しようとする前に、ツリー内の名前空間宣言を作成します。 http://code.google:詳細については、バグレポートを参照してください。 COM / P / xmlseclibs /問題/詳細?ID = 6 の
他のヒント
どちらも正しい標準的な形式です!
署名XMLドキュメントの順序ルールを破る非名前空間の属性、後に来る名前空間宣言があります:
名前空間ノードは、属性ノードより小さい文書順位置を有している。
検証XMLは完全にsaml
の名前空間ノードが欠落しています。それらを参照する子のコンテンツが存在しないためCanonicalisationは、単に名前空間ノードを削除しません。それだけで冗長な名前空間ノード(つまり、親の影響で、すでにだった名前空間)を削除します。
私はなぜこれが起こっていると言うためにxmlseclibsについて十分に知らないが、それは両方のカウントに間違いなく間違っているのです。 FWIW私のDOMにC14N機能は、ここに述べています:
<samlp:Response xmlns:saml="urn:oasis:names:tc:SAML:1.0:assertion" xmlns:samlp="urn:oasis:names:tc:SAML:1.0:protocol" IssueInstant="2010-02-04T15:27:43Z" MajorVersion="1" MinorVersion="1" ResponseID="pfxe85313e6-e688-299a-df06-30f55e24f65a">
<samlp:Status>
<samlp:StatusCode Value="samlp:Requester"></samlp:StatusCode>
</samlp:Status>
</samlp:Response>
ETA:私はちょうどSVNでxmlseclibs.php
を見て、その現在のアプローチが根本的に欠陥があるとして、このための簡単な修正はありません。それは「canonicalised」DOMを作成しようとした後、昔ながらのsaveXML()
でそれをserialises。属性順と文字についてC14NシリアライゼーションルールがありますようsaveXML
が従うことを約束していないことをエスケープし、これはおそらく仕事ができる方法はありません。