RFC 3075
XML-Signature Syntax and Processing
RFC 3075: XML-Signature Syntax and Processing ๐
Part 1 of 13, so more is coming! โจ
Okay bestie, this is RFC 3075, and it's a Standards Track doc from March 2001 ๐ . The authors are D. Eastlake (Motorola), J. Reagle (W3C/MIT), and D. Solo (Citigroup). The header has no Obsoletes or Updates lines, so it isn't replacing or patching any older RFC ๐ฆ.
Status of this Memo
Okay so this doc is an Internet standards track protocol for the Internet community, and it's asking for discussion and suggestions for improvements ๐ธ. If you want to know where this protocol stands in the standardization process, check the current edition of the "Internet Official Protocol Standards" (STD 1) ๐. And good news: distribution of this memo is unlimited ๐.
Copyright Notice
Copyright (c) 2001 The Internet Society & W3C (MIT, INRIA, Keio), All Rights Reserved. ๐
Abstract
Okay, the abstract is basically the whole vibe โจ. This document lays out the rules and syntax for XML digital signature processing (XML = Extensible Markup Language). XML Signatures give you integrity, message authentication, and/or signer authentication for data of any type ๐. That data can live inside the XML that holds the signature, or somewhere else entirely. Iconic. ๐
Table of Contents
1. Introduction ................................................ 3
1. Editorial Conventions .................................. 3
2. Design Philosophy ...................................... 4
3. Versions, Namespaces and Identifiers ................... 4
4. Acknowledgements ....................................... 5
2. Signature Overview and Examples ............................. 6
1. Simple Example (Signature, SignedInfo, Methods, and
References) ............................................ 7
1. More on Reference ................................. 9
2. Extended Example (Object and SignatureProperty) ........ 10
3. Extended Example (Object and Manifest) ................. 11
3. Processing Rules ............................................ 13
1. Core Generation .... ................................... 13
1. Reference Generation .............................. 13
2. Signature Generation .............................. 13
2. Core Validation ........................................ 13
1. Reference Validation .............................. 14
2. Signature Validation .............................. 14
4. Core Signature Syntax ....................................... 14
1. The Signature element .................................. 15
2. The SignatureValue Element ............................. 16
3. The SignedInfo Element ................................. 16
1. The CanonicalizationMethod Element ................ 17
2. The SignatureMethod Element ....................... 18
3. The Reference Element ............................. 19
1. The URI Attribute ............................ 19
2. The Reference Processing Model ............... 21
3. Same-Document URI-References ................. 23
4. The Transforms Element ....................... 24
5. The DigestMethod Element ..................... 25
6. The DigestValue Element ...................... 26
4. The KeyInfo Element .................................... 26
1. The KeyName Element ............................... 27
2. The KeyValue Element .............................. 28
3. The RetrievalMethod Element ....................... 28
4. The X509Data Element .............................. 29
5. The PGPData Element ............................... 31
6. The SPKIData Element .............................. 32
7. The MgmtData Element .............................. 32
5. The Object Element ..................................... 33
5. Additional Signature Syntax ................................. 34
1. The Manifest Element ................................... 34
2. The SignatureProperties Element ........................ 35
3. Processing Instructions ................................ 36
4. Comments in dsig Elements .............................. 36
6. Algorithms .................................................. 36
1. Algorithm Identifiers and Implementation Requirements .. 36
2. Message Digests ........................................ 38
1. SHA-1 ............................................. 38
3. Message Authentication Codes ........................... 38
1. HMAC .............................................. 38
4. Signature Algorithms ................................... 39
1. DSA ............................................... 39
2. PKCS1 ............................................. 40
5. Canonicalization Algorithms ............................ 42
1. Minimal Canonicalization .......................... 43
2. Canonical XML ..................................... 43
6. Transform Algorithms ................................... 44
1. Canonicalization .................................. 44
2. Base64 ............................................ 44
3. XPath Filtering ................................... 45
4. Enveloped Signature Transform ..................... 48
5. XSLT Transform .................................... 48
7. XML Canonicalization and Syntax Constraint Considerations ... 49
1. XML 1.0, Syntax Constraints, and Canonicalization ..... 50
2. DOM/SAX Processing and Canonicalization ................ 51
8. Security Considerations ..................................... 52
1. Transforms ............................................. 52
1. Only What is Signed is Secure ..................... 52
2. Only What is "Seen" Should be Signed .............. 53
3. "See" What is Signed .............................. 53
2. Check the Security Model ............................... 54
3. Algorithms, Key Lengths, Etc. .......................... 54
9. Schema, DTD, Data Model,and Valid Examples .................. 55
10. Definitions ................................................. 56
11. References .................................................. 58
12. Authors' Addresses .......................................... 63
13. Full Copyright Statement .................................... 64
1.0 Introduction โจ
Okay so this section sets the scene ๐ฌ. It defines the XML syntax and processing rules for making and representing digital signatures. XML Signatures can wrap up any digital content (a data object), XML included ๐ . One XML Signature can cover the content of one or more resources ๐ง.
There are two main flavors. Enveloped or enveloping signatures cover data inside the same XML document as the signature. Detached signatures cover data outside the signature element ๐ฆ. The spec defines two things: an XML signature element type, and an XML signature application. Conformance requirements for the element type come through schema definitions, and conformance requirements for the application come through prose ๐. It also includes other useful types for referencing collections of resources, algorithms, and keying and management information ๐.
The XML Signature is a way of linking a key to referenced data (octets) ๐. It does not normatively say how keys get tied to people or institutions, and it doesn't say what the referenced and signed data means ๐. So even though this spec is an important piece of secure XML apps, it's not enough on its own to handle every application security or trust concern. That's especially true when you're using signed XML (or other data formats) as the basis for human-to-human communication and agreement ๐. An application has to specify its own key, algorithm, processing, and rendering requirements. For more, check out Security Considerations (section 8) ๐ซถ.
Lowkey the big takeaway: a valid signature doesn't automatically mean the signed thing is trustworthy for humans. Your app has to add that part itself ๐.
1.1 Editorial and Conformance Conventions
Okay, for readability, brevity, and historic reasons, this doc uses the word "signature" to mean digital authentication values of all types ๐ธ. Strictly speaking, though, "signature" is for authentication values based on public keys that give you signer authentication ๐. When we're talking about authentication values based on symmetric secret key codes, we switch to the terms authenticators or authentication codes ๐. (See Check the Security Model, section 8.3.)
This spec uses both XML Schemas [XML-schema] and DTDs [XML]. If DTD syntax is new to you, Ron Bourret's "Declaring Elements and Attributes in an XML DTD" [Bourret] is a great read ๐. The schema definition is the normative one right now โจ.
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this spec are to be read as described in RFC2119 [KEYWORDS]. Here's the rule from that RFC, which is honestly iconic ๐:
"they MUST only be used where it is actually required for interoperation or to limit behavior which has potential for causing harm (e.g., limiting retransmissions)"
So we use these capitalized keywords to clearly spell out requirements for protocol and application features and behavior that affect interoperability and security ๐ . We don't use them in capitals to describe XML grammar. The schema definitions already describe those requirements unambiguously, and we want to save the big-attention caps for the natural language parts of the protocols and features ๐. For example, an XML attribute might be described as being "optional." ๐ง And compliance with the XML-namespace specification [XML-ns] is described as "REQUIRED." ๐
1.2 Design Philosophy
The design philosophy and requirements for this spec live in the XML-Signature Requirements document [XML-Signature-RD] ๐. Go check it out if you want the why behind all of this ๐ฆ.
1.3 Versions, Namespaces and Identifiers โจ
okay so there's no explicit version number in this syntax ๐ if a future version ever happens, it's gonna use a different namespace instead, which is honestly so smart. the XML namespace [XML-ns] URI that MUST be used by implementations of this (dated) specification is:
xmlns="http://www.w3.org/2000/09/xmldsig#"
this namespace is also the prefix for the algorithm identifiers ๐ ngl applications MUST support XML and XML-namespaces, but internal entities [XML], our "dsig" XML namespace prefix, and the defaulting/scoping conventions are OPTIONAL. we only use them to make the examples compact and readable ๐ซถ
This specification uses Uniform Resource Identifiers [URI] to identify resources, algorithms, and semantics โจ the URI in the namespace declaration above also serves as a prefix for URIs under this spec's control. for resources that aren't under our control, we use the Uniform Resource Names [URN] or Uniform Resource Locators [URL] defined by their own normative external specification. and if an external spec hasn't given itself a URI, we allocate one under our own namespace. for example:
SignatureProperties is identified and defined by this specification's
namespace
http://www.w3.org/2000/09/xmldsig#SignatureProperties
XSLT is identified and defined by an external URI
http://www.w3.org/TR/1999/PR-xslt-19991008
SHA1 is identified via this specification's namespace and defined via
a normative reference
http://www.w3.org/2000/09/xmldsig#sha1
FIPS PUB 180-1. Secure Hash Standard. U.S. Department of
Commerce/National Institute of Standards and Technology.
last thing, for terse namespace declarations we sometimes use XML internal entities [XML] inside URIs ๐ง like this:
<?xml version='1.0'?>
<!DOCTYPE Signature SYSTEM
"xmldsig-core-schema.dtd" [ <!ENTITY dsig
"http://www.w3.org/2000/09/xmldsig#"> ]>
<Signature xmlns="&dsig;" Id="MyFirstSignature">
<SignedInfo>
...
1.4 Acknowledgements ๐ธ
the working group members below all helped shape this spec, and we're so grateful ๐ฅน
- Mark Bartel, JetForm Corporation (Author)
- John Boyer, PureEdge (Author)
- Mariano P. Consens, University of Waterloo
- John Cowan, Reuters Health
- Donald Eastlake 3rd, Motorola (Chair, Author/Editor)
- Barb Fox, Microsoft (Author)
- Christian Geuer-Pollmann, University Siegen
- Tom Gindin, IBM
- Phillip Hallam-Baker, VeriSign Inc
- Richard Himes, US Courts
- Merlin Hughes, Baltimore
- Gregor Karlinger, IAIK TU Graz
- Brian LaMacchia, Microsoft
- Peter Lipp, IAIK TU Graz
- Joseph Reagle, W3C (Chair, Author/Editor)
- Ed Simon, Entrust Technologies Inc. (Author)
- David Solo, Citigroup (Author/Editor)
- Petteri Stenius, DONE Information, Ltd
- Raghavan Srinivas, Sun
- Kent Tamura, IBM
- Winchel Todd Vincent III, GSU
- Carl Wallace, Corsec Security, Inc.
- Greg Whitehead, Signio Inc.
and a big thank-you to the last call commenters too ๐
- Dan Connolly, W3C
- Paul Biron, Kaiser Permanente, on behalf of the XML Schema WG.
- Martin J. Duerst, W3C; and Masahiro Sekiguchi, Fujitsu; on behalf of the Internationalization WG/IG.
- Jonathan Marsh, Microsoft, on behalf of the Extensible Stylesheet Language WG.
2.0 Signature Overview and Examples ๐ฅ
this section is the overview with examples of the XML digital signature syntax ๐ the detailed processing lives in Processing Rules (section 3), and the formal syntax is in Core Signature Syntax (section 4) and Additional Signature Syntax (section 5).
here we use an informal representation and examples to show the structure of the signature syntax. just know that this might leave out some attributes, details, and features that get fully explained later ๐
okay so XML Signatures get applied to arbitrary digital content (data objects) through an indirection ๐ฆ the data objects get digested, the result goes into an element along with other info, and then that element gets digested and cryptographically signed. XML digital signatures are represented by the Signature element, which looks like this ("?" means zero or one occurrence, "+" means one or more, and "*" means zero or more):
<Signature>
<SignedInfo>
(CanonicalizationMethod)
(SignatureMethod)
(<Reference (URI=)? >
(Transforms)?
(DigestMethod)
(DigestValue)
</Reference>)+
</SignedInfo>
(SignatureValue)
(KeyInfo)?
(Object)*
</Signature>
signatures link to data objects via URIs [URI] ๐ inside an XML document, signatures point at local data objects with fragment identifiers. that local data can be included inside an enveloping signature, or it can enclose an enveloped signature. detached signatures cover external network resources or local data objects that live in the same XML document as sibling elements. so the signature is neither enveloping (signature is parent) nor enveloped (signature is child) ๐ and since a Signature element (and its Id attribute value/name) can coexist or be combined with other elements (and their IDs) in one XML document, be careful when you pick names so you don't get collisions that break the ID uniqueness validity constraint [XML] ๐ญ
2.1 Simple Example (Signature, SignedInfo, Methods, and References) ๐ง
this one's a detached signature of the content of the HTML4 in XML specification, and it's giving clean ๐
[s01] <Signature Id="MyFirstSignature"
xmlns="http://www.w3.org/2000/09/xmldsig#">
[s02] <SignedInfo>
[s03] <CanonicalizationMethod
Algorithm="http://www.w3.org/TR/2000/CR-xml-c14n-20001026"/>
[s04] <SignatureMethod
Algorithm="http://www.w3.org/2000/09/xmldsig#dsa-sha1"/>
[s05] <Reference URI="http://www.w3.org/TR/2000/REC-xhtml1-20000126/">
[s06] <Transforms>
[s07] <Transform Algorithm="http://www.w3.org/TR/2000/
CR-xml-c14n-20001026"/>
[s08] </Transforms>
[s09] <DigestMethod Algorithm="http://www.w3.org/2000/09/
xmldsig#sha1"/>
[s10] <DigestValue>j6lwx3rvEPO0vKtMup4NbeVu8nk=</DigestValue>
[s11] </Reference>
[s12] </SignedInfo>
[s13] <SignatureValue>MC0CFFrVLtRlk=...</SignatureValue>
[s14] <KeyInfo>
[s15a] <KeyValue>
[s15b] <DSAKeyValue>
[s15c] <P>...</P><Q>...</Q><G>...</G><Y>...</Y>
[s15d] </DSAKeyValue>
[s15e] </KeyValue>
[s16] </KeyInfo>
[s17] </Signature>
[s02-12] the SignedInfo element is the required part, and it's the info that actually gets signed ๐ซถ core validation of SignedInfo has two mandatory processes: validating the signature over SignedInfo, and validating each Reference digest inside SignedInfo. also, the algorithms used to compute the SignatureValue are included in the signed info too, even though the SignatureValue element sits outside SignedInfo ๐
[s03] the CanonicalizationMethod is the algorithm used to canonicalize SignedInfo before it gets digested as part of the signature operation ๐
[s04] the SignatureMethod is the algorithm that turns the canonicalized SignedInfo into the SignatureValue โจ it's a mix of a digest algorithm and a key-dependent algorithm, plus maybe other stuff like padding, for example RSA-SHA1. the algorithm names get signed so nobody can swap in a weaker algorithm and get away with it ๐ซ for app interoperability, we specify a set of signature algorithms that MUST be implemented, even though the signature creator decides whether to actually use them. we also list additional algorithms as RECOMMENDED or OPTIONAL to implement, and the signature design lets people specify their own algorithms too ๐
[s05-11] each Reference element includes the digest method and the resulting digest value, computed over the identified data object. it can also include the transforms that produced the input to the digest operation ๐ฆ a data object gets signed by computing its digest value, then signing that value. the signature gets checked later through reference and signature validation โ
[s14-16] KeyInfo tells you which key to use to validate the signature ๐ possible forms include certificates, key names, and key agreement algorithms and info (we only define a few of those). KeyInfo is optional for two reasons ๐ first, the signer might not want to reveal key info to every document processing party. second, the info might already be known from the application's context, so it doesn't need to be represented explicitly. KeyInfo sits outside SignedInfo, so if the signer wants to bind the keying info to the signature, a Reference can point at the KeyInfo and include it as part of the signature ๐
2.1.1 More on Reference ๐
[s05] <Reference URI="http://www.w3.org/TR/2000/REC-xhtml1-20000126/">
[s06] <Transforms>
[s07] <Transform
Algorithm="http://www.w3.org/TR/2000/
CR-xml-c14n-20001026"/>
[s08] </Transforms>
[s09] <DigestMethod Algorithm="http://www.w3.org/2000/09/
xmldsig#sha1"/>
[s10] <DigestValue>j6lwx3rvEPO0vKtMup4NbeVu8nk=</DigestValue>
[s11] </Reference>
[s05] the URI attribute on Reference is optional, and it names the data object to be signed ๐ it can be left out on at most one Reference in a Signature. (this limit exists so that references and objects can always be matched up unambiguously ๐)
[s05-08] this identification, together with the transforms, is the signer's own description of how they got the signed data object into the form that was digested, meaning the digested content ๐ the verifier can get the digested content some other way, as long as the digest verifies โจ specifically, the verifier can pull the content from a different location, like a local store, instead of the one in the URI.
[s06-08] Transforms is an optional, ordered list of processing steps applied to the resource's content before it's digested ๐ง transforms can include things like canonicalization, encoding/decoding (including compression/inflation), XSLT, and XPath ๐ XPath transforms let the signer derive an XML document that leaves out parts of the source document. because of that, those excluded parts can change without breaking the signature's validity ๐ for example, if the signed resource encloses the signature itself, you have to use a transform like that to exclude the signature value from its own computation ๐ if there's no Transforms element, the resource's content gets digested directly. we specify mandatory (and optional) canonicalization and decoding algorithms, and user-specified transforms are allowed too ๐
[s09-10] DigestMethod is the algorithm applied to the data after Transforms runs (if there are any) to produce the DigestValue ๐ฅ signing the DigestValue is what binds a resource's content to the signer's key. that's the whole flex ๐
โจ
2.2 Extended Example (Object and SignatureProperty) ๐
okay bestie, quick vibe check: this spec does NOT do statements or assertions ๐ โโ๏ธ what it does do is define what it means for something to be signed by an XML Signature (message authentication, integrity, and/or signer authentication) ๐ if an app wants other semantics, it has to lean on other tech like [XML, RDF] ๐ for example, an app could slap a foo:assuredby attribute in its own markup to point at a Signature element ๐ which means the app is the one that has to understand it and make the trust calls, based on whether the signature is valid and what assuredby actually means ๐ง (main character app energy, honestly).
We also define a SignatureProperties element type ๐ฆ for putting assertions about the signature itself in there, like signature semantics, the time of signing, or the serial number of the hardware doing the crypto โฐ๐ง. You can sign those assertions too, by including a Reference for the SignatureProperties in SignedInfo ๐ซถ. Signing apps, be careful what you sign!! ๐ญ you gotta understand what's in the SignatureProperty. Receiving apps have zero obligation to understand that semantic ๐คทโโ๏ธ (though the parent trust engine might want to ๐). Any content about how the signature was generated can live inside the SignatureProperty element ๐ธ. And the Target attribute is mandatory ๐ it points at the Signature element the property applies to.
Consider the example above, but with an extra reference to a local Object that holds a SignatureProperty element โจ. (This one would be detached [p02] AND enveloping [p03] ๐ double threat.)
[ ] <Signature Id="MySecondSignature" ...>
[p01] <SignedInfo>
[ ] ...
[p02] <Reference URI="http://www.w3.org/TR/xml-stylesheet/">
[ ] ...
[p03] <Reference URI="#AMadeUpTimeStamp"
[p04] Type="http://www.w3.org/2000/09/
xmldsig#SignatureProperties">
[p05] <DigestMethod Algorithm="http://www.w3.org/2000/09/
xmldsig#sha1"/>
[p06] <DigestValue>k3453rvEPO0vKtMup4NbeVu8nk=</DigestValue>
[p07] </Reference>
[p08] </SignedInfo>
[p09] ...
[p10] <Object>
[p11] <SignatureProperties>
[p12] <SignatureProperty Id="AMadeUpTimeStamp"
Target="#MySecondSignature">
[p13] <timestamp xmlns="http://www.ietf.org/rfc3075.txt">
[p14] <date>19990908</date>
[p15] <time>14:34:34:34</time>
[p16] </timestamp>
[p17] </SignatureProperty>
[p18] </SignatureProperties>
[p19] </Object>
[p20]</Signature>
okay so the optional Type attribute on Reference tells you about the resource the URI points to ๐ฏ it can say it's an Object, a SignatureProperty, or a Manifest element ๐งฉ apps can use that to kick off special processing for certain References. References to an XML data element inside an Object element SHOULD identify the actual element pointed to ๐. If the content isn't XML (maybe it's binary or encoded data), the reference should identify the Object instead, and if a Type is given, it SHOULD indicate Object ๐. Heads up though: Type is advisory ๐ core behaviour doesn't need any action based on it, or any checking of whether it's correct ๐.
Object is an optional element for stuffing data objects inside the signature element (or somewhere else) ๐. It can be typed and/or encoded, optionally ๐ซง.
Signature properties, like time of signing, can optionally be signed by pointing to them from a Reference โ๏ธ (people traditionally call these signature "attributes", even though that word has nothing to do with the XML term "attribute" ๐ total naming mix-up).
2.3 Extended Example (Object and Manifest) ๐ฆ
The Manifest element exists to cover extra needs that the mandatory parts of this spec don't handle directly ๐ง. There are two needs, and here's how the Manifest handles each one:
First, apps often need to efficiently sign loads of data objects, even when the signature operation itself is an expensive public key signature ๐ธ. You can do this by putting multiple Reference elements in SignedInfo, since each digest secures the data it covers โ . But some apps don't want the core validation that comes with that, because it forces every Reference in SignedInfo through reference validation (the DigestValue elements get checked) ๐ค. Those apps might want to keep the reference validation decision logic for themselves ๐. Like, an app might get a signature-valid SignedInfo with three Reference elements. If one Reference fails (the data object doesn't digest to the specified DigestValue), the signature fails core validation ๐. But the app might want to treat the signature over the two valid References as valid, or do different things depending on which one failed ๐ค. So SignedInfo references a Manifest element that holds one or more Reference elements (same structure as the ones in SignedInfo) ๐งฉ, and then reference validation of the Manifest is under the app's control ๐ .
Second, picture many signatures (using different keys) applied to a big pile of documents ๐. The inefficient move is a separate signature per key over a big SignedInfo (with lots of References), over and over ๐ต that's wasteful and redundant. The better move is to put lots of references into one Manifest, then reference that Manifest from multiple Signature elements ๐.
The example below has a Reference that signs a Manifest found inside the Object element ๐
[ ] ...
[m01] <Reference URI="#MyFirstManifest"
[m02] Type="http://www.w3.org/2000/09/xmldsig#Manifest">
[m03] <DigestMethod Algorithm="http://www.w3.org/2000/09/
xmldsig#sha1"/>
[m04] <DigestValue>345x3rvEPO0vKtMup4NbeVu8nk=</DigestValue>
[m05] </Reference>
[ ] ...
[m06] <Object>
[m07] <Manifest Id="MyFirstManifest">
[m08] <Reference>
[m09] ...
[m10] </Reference>
[m11] <Reference>
[m12] ...
[m13] </Reference>
[m14] </Manifest>
[m15] </Object>
3.0 Processing Rules โ๏ธ
okay, this section is the step-by-step for signature generation and validation ๐ ๏ธ bestie, read it slowly.
3.1 Core Generation ๐๏ธ
The REQUIRED steps cover generating the Reference elements and the SignatureValue over SignedInfo ๐.
3.1.1 Reference Generation
Here's the drill for each data object being signed:
- Apply the Transforms (the application decides which ones) to the data object.
- Calculate the digest value over the resulting data object.
- Create a Reference element, with the (optional) identification of the data object, any (optional) transform elements, the digest algorithm, and the DigestValue.
3.1.2 Signature Generation
- Create the SignedInfo element with SignatureMethod, CanonicalizationMethod and Reference(s).
- Canonicalize, then calculate the SignatureValue over SignedInfo based on the algorithms specified in SignedInfo.
- Construct the Signature element, which includes SignedInfo, Object(s) (if desired; the encoding can be different from what was used for signing), KeyInfo (if required), and SignatureValue ๐ง.
3.2 Core Validation ๐
The REQUIRED steps of core validation are (1) reference validation, which checks the digest in each Reference in SignedInfo, and (2) cryptographic signature validation of the signature calculated over SignedInfo.
Note, there may be valid signatures that some signature applications can't validate ๐ฌ. Reasons include failing to implement optional parts of this spec, being unable or unwilling to run the specified algorithms, or being unable or unwilling to dereference the specified URIs (some URI schemes can cause nasty side effects) ๐, and so on.
3.2.1 Reference Validation
For each Reference in SignedInfo:
- Canonicalize the SignedInfo element based on the CanonicalizationMethod in SignedInfo.
- Obtain the data object to be digested. (The signature application may rely on the identification (URI) and Transforms the signer provided in the Reference element, or it may get the content through other means, like a local cache ๐๏ธ.)
- Digest the resulting data object using the DigestMethod specified in its Reference specification.
- Compare the generated digest value against the DigestValue in the SignedInfo Reference. If there's any mismatch, validation fails ๐ซ.
Note, SignedInfo is canonicalized in step 1 so the application "Sees What is Signed" ๐, which is the canonical form. For instance, if the CanonicalizationMethod rewrote URIs (e.g., absolutizing relative URIs), signature processing has to be aware of that.
3.2.2 Signature Validation
- Obtain the keying information from KeyInfo or from an external source ๐.
- Obtain the canonical form of the SignatureMethod using the CanonicalizationMethod, and use the result (plus the KeyInfo you already got) to validate the SignatureValue over the SignedInfo element.
Note, KeyInfo (or some transformed version of it) may be signed via a Reference element. Transforming and validating that reference (3.2.1) is totally separate from Signature Validation, which uses KeyInfo as parsed ๐งฉ.
Additionally, the SignatureMethod URI may have been altered by canonicalization of SignedInfo (e.g., absolutization of relative URIs), and it is the canonical form that MUST be used. However, the required canonicalization [XML-C14N] of this specification does not change URIs ๐.
4.0 Core Signature Syntax ๐
The general structure of an XML signature is described in Signature Overview (section 2). This section gives the detailed syntax of the core signature features. Features described here are mandatory to implement unless otherwise indicated ๐ . The syntax is defined via DTDs and [XML-Schema], with the following XML preamble, declaration, internal entity, and simpleType:
Schema Definition:
<!DOCTYPE schema
PUBLIC "-//W3C//DTD XMLSCHEMA 200010//EN"
"http://www.w3.org/2000/10/XMLSchema.dtd"
[
<!ATTLIST schema
xmlns:ds CDATA #FIXED "http://www.w3.org/2000/09/xmldsig#">
<!ENTITY dsig 'http://www.w3.org/2000/09/xmldsig#'>
]>
<schema xmlns="http://www.w3.org/2000/10/XMLSchema"
xmlns:ds="&dsig;"
targetNamespace="&dsig;"
version="0.1"
elementFormDefault="qualified">
<!-- Basic Types Defined for Signatures -->
<simpleType name="CryptoBinary">
<restriction base="binary">
<encoding value="base64"/>
</restriction>
</simpleType>
DTD:
<!-- These entity declarations permit the flexible parts of Signature
content model to be easily expanded -->
<!ENTITY % Object.ANY '(#PCDATA|Signature|SignatureProperties|
Manifest)*'>
<!ENTITY % Method.ANY '(#PCDATA|HMACOutputLength)*'>
<!ENTITY % Transform.ANY '(#PCDATA|XPath|XSLT)'>
<!ENTITY % SignatureProperty.ANY '(#PCDATA)*'>
<!ENTITY % Key.ANY '(#PCDATA|KeyName|KeyValue|RetrievalMethod|
X509Data|PGPData|MgmtData|DSAKeyValue|RSAKeyValue)*'>
4.1 The Signature element ๐
The Signature element is the root element of an XML Signature. Signature elements MUST be laxly schema valid [XML-schema] with respect to the following schema definition:
Schema Definition:
<element name="Signature">
<complexType>
<sequence>
<element ref="ds:SignedInfo"/>
<element ref="ds:SignatureValue"/>
<element ref="ds:KeyInfo" minOccurs="0"/>
<element ref="ds:Object" minOccurs="0" maxOccurs="unbounded"/>
</sequence>
<attribute name="Id" type="ID" use="optional"/>
</complexType>
</element>
DTD:
<!ELEMENT Signature (SignedInfo, SignatureValue, KeyInfo?, Object*) >
<!ATTLIST Signature
xmlns CDATA #FIXED 'http://www.w3.org/2000/09/xmldsig#'
Id ID #IMPLIED >
4.2 The SignatureValue Element ๐
The SignatureValue element holds the actual value of the digital signature โจ, and it is always encoded using base64 [MIME]. We specify a mandatory set and an optional-to-implement set of SignatureMethod algorithms ๐ , but user specified algorithms are permitted ๐ซถ. Schema Definition:
<element name="SignatureValue" type="ds:CryptoBinary"/>
DTD:
<!ELEMENT SignatureValue (#PCDATA) >
4.3 The SignedInfo Element ๐ฆ
SignedInfo is the element that brings together the canonicalization algorithm, a signature algorithm, and one or more references ๐ธ. It may contain an optional ID attribute, which lets other signatures and objects reference it. Main character energy ๐
SignedInfo does not include explicit signature or digest properties, like calculation time or a cryptographic device serial number ๐. If an application needs to attach properties to the signature or digest, it may put that info in a SignatureProperties element inside an Object element ๐ง. Schema Definition:
<element name="SignedInfo">
<complexType>
<sequence>
<element ref="ds:CanonicalizationMethod"/>
<element ref="ds:SignatureMethod"/>
<element ref="ds:Reference" maxOccurs="unbounded"/>
</sequence>
<attribute name="Id" type="ID" use="optional"/>
</complexType>
</element>
DTD:
<!ELEMENT SignedInfo (CanonicalizationMethod,
SignatureMethod, Reference+) >
<!ATTLIST SignedInfo
Id ID #IMPLIED>
4.3.1 The CanonicalizationMethod Element ๐
Okay so CanonicalizationMethod is a required element ๐ that says which canonicalization algorithm gets applied to SignedInfo before any signature math happens. It uses the general algorithm structure from Algorithm Identifiers and Implementation Requirements (section 6.1). Implementations MUST support the REQUIRED Canonical XML [XML-C14N] method ๐ญ โจ.
Alternatives to the REQUIRED Canonical XML algorithm (section 6.5.2), like Canonical XML with Comments (section 6.5.2) and Minimal Canonicalization (the CRLF and charset normalization specified in section 6.5.1), may be explicitly specified ๐ but are NOT REQUIRED. So their use may not interoperate with other applications that do no support the specified algorithm (see XML Canonicalization and Syntax Constraint Considerations, section 7). Security issues may also show up in entity processing and comments if minimal or other non-XML aware canonicalization algorithms are not properly constrained (see section 8.2: Only What is "Seen" Should be Signed) ๐ this is the part to be careful with, bestie ๐จ.
The way SignedInfo gets handed to the canonicalization method depends on that method ๐. Here's how it works for the two types of algorithms in this document:
- Canonical XML [XML-C14N] (with or without comments) implementation MUST be provided with an XPath node-set originally formed from the document containing the SignedInfo and currently indicating the SignedInfo, its descendants, and the attribute and namespace nodes of SignedInfo and its descendant elements (such that the namespace context and similar ancestor information of the SignedInfo is preserved).
- Minimal canonicalization implementations MUST be provided with the octets that represent the well-formed SignedInfo element, from the first character to the last character of the XML representation, inclusive. This includes the entire text of the start and end tags of the SignedInfo element as well as all descendant markup and character data (i.e., the text) between those tags.
We RECOMMEND that resource constrained applications that do not implement the Canonical XML [XML-C14N] algorithm and instead choose minimal canonicalization (or some other form) be implemented to generate Canonical XML as their output serialization ๐ซถ, so they can easily mitigate some of these interoperability and security concerns. (While a result might not be the canonical form of the original, it can still be in canonical form.) For instance, such an implementation SHOULD (at least) generate standalone XML instances [XML] โจ.
Schema Definition:
<element name="CanonicalizationMethod">
<complexType>
<sequence>
<any namespace="##any" minOccurs="0" maxOccurs="unbounded"/>
</sequence>
<attribute name="Algorithm" type="uriReference" use="required"/>
</complexType>
</element>
DTD:
<!ELEMENT CanonicalizationMethod %Method.ANY; >
<!ATTLIST CanonicalizationMethod
Algorithm CDATA #REQUIRED >
4.3.2 The SignatureMethod Element ๐ฅ
SignatureMethod is a required element ๐ that specifies the algorithm used for signature generation and validation. This algorithm identifies all the cryptographic functions involved in the signature operation (e.g., hashing, public key algorithms, MACs, padding, etc.) ๐ง. This element uses the general structure here for algorithms described in section 6.1: Algorithm Identifiers and Implementation Requirements. While there is a single identifier, that identifier may specify a format containing multiple distinct signature values ๐ฆ.
Schema Definition:
<element name="SignatureMethod">
<complexType>
<sequence>
<any namespace="##any" minOccurs="0" maxOccurs="unbounded"/>
</sequence>
<attribute name="Algorithm" type="uriReference" use="required"/>
</complexType>
</element>
DTD:
<!ELEMENT SignatureMethod %Method.ANY; >
<!ATTLIST SignatureMethod
Algorithm CDATA #REQUIRED >
4.3.3 The Reference Element ๐ธ
Reference is an element that may occur one or more times ๐ . It specifies a digest algorithm and digest value, and optionally an identifier of the object being signed, the type of the object, and/or a list of transforms to be applied prior to digesting. The identification (URI) and transforms describe how the digested content (i.e., the input to the digest method) was created. The Type attribute helps with processing referenced data. For example, while this specification makes no requirements over external data, an application may wish to signal that the referent is a Manifest ๐. An optional ID attribute lets a Reference be referenced from elsewhere โจ.
Schema Definition:
<element name="Reference">
<complexType>
<sequence>
<element ref="ds:Transforms" minOccurs="0"/>
<element ref="ds:DigestMethod"/>
<element ref="ds:DigestValue"/>
</sequence>
<attribute name="Id" type="ID" use="optional"/>
<attribute name="URI" type="uriReference" use="optional"/>
<attribute name="Type" type="uriReference" use="optional"/>
</complexType>
</element>
DTD:
<!ELEMENT Reference (Transforms?, DigestMethod, DigestValue) >
<!ATTLIST Reference
Id ID #IMPLIED
URI CDATA #IMPLIED
Type CDATA #IMPLIED >
4.3.3.1 The URI Attribute ๐ฆ
The URI attribute identifies a data object using a URI-Reference, as specified by RFC2396 [URI]. The set of allowed characters for URI attributes is the same as for XML, namely [Unicode]. However, some Unicode characters are disallowed from URI references ๐, including all non-ASCII characters and the excluded characters listed in RFC2396 [URI, section 2.4]. However, the number sign (#), percent sign (%), and square bracket characters re-allowed in RFC 2732 [URI-Literal] are permitted. Disallowed characters must be escaped as follows:
- Each disallowed character is converted to [UTF-8] as one or more bytes.
- Any octets corresponding to a disallowed character are escaped with the URI escaping mechanism (that is, converted to %HH, where HH is the hexadecimal notation of the byte value).
- The original character is replaced by the resulting character sequence.
XML signature applications MUST be able to parse URI syntax ๐. We RECOMMEND they be able to dereference URIs in the HTTP scheme ๐. Dereferencing a URI in the HTTP scheme MUST comply with the Status Code Definitions of [HTTP] (e.g., 302, 305 and 307 redirects are followed to obtain the entity-body of a 200 status code response) ๐ฅ. Applications should also be cognizant of the fact that protocol parameter and state information (such as HTTP cookies, HTML device profiles or content negotiation) may affect the content yielded by dereferencing a URI ๐ง.
If a resource is identified by more than one URI, the most specific should be used (e.g. http://www.w3.org/2000/06/interop-pressrelease.html.en instead of http://www.w3.org/2000/06/interop-pressrelease). (See the Reference Validation (section 3.2.1) for further information on reference processing.) ๐
If the URI attribute is omitted altogether, the receiving application is expected to know the identity of the object. For example, a lightweight data protocol might omit this attribute given the identity of the object is part of the application context. This attribute may be omitted from at most one Reference in any particular SignedInfo, or Manifest ๐.
The optional Type attribute contains information about the type of object being signed. This is represented as a URI. For example:
Type="http://www.w3.org/2000/09/xmldsig#Object"
Type="http://www.w3.org/2000/09/xmldsig#Manifest"
The Type attribute applies to the item being pointed at, not its contents ๐ . For example, a reference that identifies an Object element containing a SignatureProperties element is still of type #Object. The type attribute is advisory. No validation of the type information is required by this specification ๐.
4.3.3.2 The Reference Processing Model ๐
okay so, first things first bestie: XPath is RECOMMENDED ๐ but signature apps don't have to conform to the [XPath] spec to be conformant ๐ ๐ธ. The XPath data model, definitions (like node-sets) and syntax are used in this doc just to describe the functionality for anyone who wants to process XML-as-XML (instead of plain octets) as part of signature generation โจ. If you want those features, a conformant [XPath] implementation is one way to do it, but it's NOT required ๐ฆ. A sufficiently functional replacement for a node-set works too, as long as you only implement the XPath expression behaviors that this spec REQUIRED ๐ง. We're mostly gonna say "XPath" without repeating the caveat every time, so just know that "XPath nodesets" requirements can include a node-set functional equivalent, and XPath processing requirements can include app behaviors equivalent to the matching XPath behavior ๐ซถ.
The data-type of the result of URI dereferencing or subsequent Transforms is either an octet stream or an XPath node-set ๐.
The Transforms in this doc are defined with respect to the input they need. Here's the default signature app behavior ๐:
- If the data object is an octet stream and the next transform requires a node-set, the signature application MUST attempt to parse the octets. ๐
- If the data object is a node-set and the next transform requires octets, the signature application MUST attempt to convert the node-set to an octet stream using the REQUIRED canonicalization algorithm [XML-C14N]. ๐ฅ
Users can specify alternative transforms that override these defaults when transitioning between Transforms that expect different inputs โญ. The final octet stream contains the data octets being secured ๐ธ. The digest algorithm named by DigestMethod is then applied to those data octets, which gives you the DigestValue ๐.
Unless the URI-Reference is a 'same-document' reference as defined in [URI, Section 4.2], dereferencing the URI-Reference MUST result in an octet stream ๐ญ. So an XML document identified by a URI is NOT parsed by the signature app unless the URI is a same-document reference, or a transform that needs XML parsing gets applied (see Transforms (section 4.3.3.1)) ๐ . When a fragment comes after an absolute or relative URI in the URI-Reference, the fragment's meaning is defined by the resource's MIME type ๐ฆ. Even for XML docs, URI dereferencing (fragment processing included) might be done by a proxy for the signature app ๐. So reference validation might fail if fragment processing isn't done in a standard way (as defined in the next section for same-document references) ๐. Which is why we RECOMMEND that the URI attribute NOT include fragment identifiers, and that this processing be specified as an additional XPath Transform โจ๐.
When a fragment is NOT preceded by a URI in the URI-Reference, XML signature apps MUST support the null URI and barename XPointer ๐. We RECOMMEND supporting the same-document XPointers '#xpointer(/)' and '#xpointer(id("ID"))' if the app also plans to support Minimal Canonicalization or Canonical XML with Comments ๐ฆ. (Otherwise URI="#foo" will automatically strip comments before Canonical XML with Comments can even be invoked ๐ญ.) All other XPointer support is OPTIONAL ๐, especially barename and other XPointers in external resources, since the app may not control how the fragment gets generated (which leads to interop problems and validation failures) ๐๐ซถ.
Here are some examples of what the URI attribute identifies and how it gets dereferenced ๐ง:
URI="http://example.com/bar.xml"
Identifies the octets that represent the external resource 'http//example.com/bar.xml', which is probably an XML document given its file extension ๐.
URI="http://example.com/bar.xml#chapter1"
Identifies the element with ID attribute value 'chapter1' of the external XML resource 'http://example.com/bar.xml', provided as an octet stream. Again, for interop's sake, the element identified as 'chapter1' SHOULD be obtained using an XPath transform rather than a URI fragment (barename XPointer resolution in external resources is NOT REQUIRED in this spec) ๐ธ.
URI=""
Identifies the nodeset (minus any comment nodes) of the XML resource containing the signature ๐.
URI="#chapter1"
Identifies a nodeset containing the element with ID attribute value 'chapter1' of the XML resource containing the signature. XML Signature (and its apps) modify this nodeset to include the element plus all descendants, including namespaces and attributes -- but not comments ๐โจ.
4.3.3.3 Same-Document URI-References ๐
Dereferencing a same-document reference MUST result in an XPath node-set suitable for use by Canonical XML ๐. Specifically, dereferencing a null URI (URI="") MUST result in an XPath node-set that includes every non-comment node of the XML document containing the URI attribute ๐ฅ. In a fragment URI, the characters after the number sign ('#') conform to the XPointer syntax [Xptr] ๐ฆ. When processing an XPointer, the app MUST behave as if the root node of the XML document containing the URI attribute were used to initialize the XPointer evaluation context ๐. The app MUST behave as if the result of XPointer processing were a node-set derived from the resultant location-set, as follows ๐ง:
- discard point nodes
- replace each range node with all XPath nodes having full or partial content within the range
- replace the root node with its children (if it is in the node-set)
- replace any element node E with E plus all descendants of E (text, comment, PI, element) and all namespace and attribute nodes of E and its descendant elements
- if the URI is not a full XPointer, then delete all comment nodes
The second-to-last replacement is necessary because XPointer typically indicates a subtree of an XML document's parse tree using just the element node at the root of the subtree ๐ธ. Canonical XML, on the other hand, treats a node-set as a set of nodes, where a missing descendant node means its representative text is missing from the canonical form ๐ญ.
The last step is performed for null URIs, barename XPointers and child sequence XPointers ๐ . To keep comments while selecting an element by an identifier ID, use this full XPointer: URI='#xpointer(id("ID"))' โจ. To keep comments while selecting the entire document, use this full XPointer: URI='#xpointer(/)' ๐. This XPointer contains a simple XPath expression that includes the root node, which the second-to-last step above replaces with all nodes of the parse tree (all descendants, plus all attributes, plus all namespace nodes) ๐ซถ.
4.3.3.4 The Transforms Element ๐ฆ
The optional Transforms element contains an ordered list of Transform elements, which describe how the signer obtained the data object that was digested ๐. The output of each Transform is the input to the next one ๐. The input to the first Transform is the result of dereferencing the URI attribute of the Reference element ๐. The output from the last Transform is the input for the DigestMethod algorithm ๐. When transforms are applied, the signer isn't signing the native (original) document, but the resulting (transformed) document ๐ญ (see Only What is Signed is Secure (section 8.1)) ๐.
Each Transform consists of an Algorithm attribute plus content parameters, if any, that fit the algorithm ๐ง. The Algorithm attribute value names the algorithm to be performed, and the Transform content gives extra data to control how the algorithm processes the transform input ๐. (See Algorithm Identifiers and Implementation Requirements (section 6).)
As described in The Reference Processing Model (section 4.3.3.2), some transforms take an XPath node-set as input while others need an octet stream ๐. If the actual input matches what the transform needs, the transform operates on the unaltered input โจ. If the transform's input requirement differs from the format of the actual input, then the input has to be converted ๐ธ.
Some Transforms may need an explicit MIME type, charset (IANA registered "character set"), or other such info about the data they're receiving from an earlier Transform or the source data ๐ . No Transform algorithm specified in this doc needs that explicit info, though ๐ฆ. Such data characteristics are provided as parameters to the Transform algorithm and should be described in the spec for that algorithm ๐ซถ.
Examples of transforms include, but aren't limited to, base64 decoding [MIME], canonicalization [XML-C14N], XPath filtering [XPath], and XSLT [XSLT] ๐. The generic definition of the Transform element also allows application-specific transform algorithms ๐. For example, the transform could be a decompression routine given by a Java class appearing as a base64 encoded parameter to a Java Transform algorithm ๐. However, apps SHOULD refrain from using application-specific transforms if they want their signatures to be verifiable outside their application domain ๐ญ๐ฅ. Transform Algorithms (section 6.6) defines the list of standard transformations ๐.
Schema Definition:
<element name="Transforms">
<complexType>
<sequence>
<element ref="ds:Transform" maxOccurs="unbounded"/>
</sequence>
</complexType>
</element>
<element name="Transform">
<complexType>
<choice maxOccurs="unbounded">
<any namespace="##other" processContents="lax" minOccurs="0"
maxOccurs="unbounded"/>
<element name="XSLT" type="string"/>
<!-- should be an xsl:stylesheet element -->
<element name="XPath" type="string"/>
</choice>
<attribute name="Algorithm" type="uriReference" use="required"/>
</complexType>
</element>
DTD:
<!ELEMENT Transforms (Transform+)>
<!ELEMENT Transform %Transform.ANY; >
<!ATTLIST Transform
Algorithm CDATA #REQUIRED >
<!ELEMENT XPath (#PCDATA) >
<!ELEMENT XSLT (#PCDATA) >
4.3.3.5 The DigestMethod Element ๐
okay bestie, DigestMethod is a required element ๐ฅ that names the digest algorithm you run on the signed object. It uses the general structure for algorithms from Algorithm Identifiers and Implementation Requirements (section 6.1) โจ
If the result of the URI dereference and Transforms is an XPath node-set (or a sufficiently functional replacement the application implements), then it must be converted the way the Reference Processing Model (section 4.3.3.2) describes ๐ซถ If the result is an octet stream instead, no conversion happens ๐ (comments might still be there if Minimal Canonicalization or Canonical XML with Comments was specified in the Transforms). The digest algorithm then runs over the data octets of that resulting octet stream ๐ฆ
Schema Definition:
<element name="DigestMethod">
<complexType>
<sequence>
<any namespace="##any" processContents="lax" minOccurs="0"
maxOccurs="unbounded"/>
</sequence>
<attribute name="Algorithm" type="uriReference" use="required"/>
</complexType>
</element>
DTD:
<!ELEMENT DigestMethod %Method.ANY; >
<!ATTLIST DigestMethod
Algorithm CDATA #REQUIRED >
4.3.3.6 The DigestValue Element ๐ง
DigestValue is the element that holds the encoded value of the digest ๐ The digest is always base64 encoded [MIME] ๐ธ
Schema Definition:
<element name="DigestValue" type="ds:CryptoBinary"/>
DTD:
<!ELEMENT DigestValue (#PCDATA) >
<!-- base64 encoded digest value -->
4.4 The KeyInfo Element ๐
KeyInfo is an optional element that helps the recipient(s) get the key they need to validate the signature ๐ KeyInfo can hold keys, names, certificates, and other public key management info, like in-band key distribution or key agreement data ๐ This spec only defines a few simple types, but applications can put their own key identification and exchange stuff in here through the XML-namespace facility [XML-ns] โจ
If KeyInfo is omitted, the recipient is expected to figure out the key from application context information ๐คท Multiple declarations inside KeyInfo refer to the same key ๐ Applications can use any mechanism they want by including elements from a different namespace ๐ but compliant versions MUST implement KeyValue (section 4.4.2) and SHOULD implement RetrievalMethod (section 4.4.3) ๐ซถ
Here's the list of KeyInfo types this spec defines. You can use these inside the RetrievalMethod Type attribute to describe the remote KeyInfo structure, represented as an octet stream ๐
http://www.w3.org/2000/09/xmldsig#X509Datahttp://www.w3.org/2000/09/xmldsig#PGPDatahttp://www.w3.org/2000/09/xmldsig#SPKIDatahttp://www.w3.org/2000/09/xmldsig#MgmtData
Besides the types above (which have structures we define), we also specify one more type for a binary X.509 Certificate ๐
Schema Definition:
<element name="KeyInfo">
<complexType>
<choice maxOccurs="unbounded">
<any processContents="lax" namespace="##other" minOccurs="0"
maxOccurs="unbounded"/>
<element name="KeyName" type="string"/>
<element ref="ds:KeyValue"/>
<element ref="ds:RetrievalMethod"/>
<element ref="ds:X509Data"/>
<element ref="ds:PGPData"/>
<element ref="ds:SPKIData"/>
<element name="MgmtData" type="string"/>
</choice>
<attribute name="Id" type="ID" use="optional"/>
</complexType>
</element>
DTD:
<!ELEMENT KeyInfo %Key.ANY; >
<!ATTLIST KeyInfo
Id ID #IMPLIED >
4.4.1 The KeyName Element ๐
KeyName holds a string value the signer can use to tell the recipient which key to use ๐๏ธ Usually KeyName has an identifier tied to the key pair that signed the message, but it can also hold other protocol info that points to a key pair indirectly โจ (Common uses are simple string names for keys, a key index, a distinguished name (DN), an email address, and so on ๐ )
Schema Definition:
<!-- type declared in KeyInfo -->
DTD:
<!ELEMENT KeyName (#PCDATA) >
4.4.2 The KeyValue Element ๐ฆ
KeyValue holds a single public key that could be useful for validating the signature ๐ Structured formats for DSA (REQUIRED) and RSA (RECOMMENDED) public keys are defined in Signature Algorithms (section 6.4) ๐ฅ
Schema Definition:
<element name="KeyValue">
<complexType mixed="true">
<choice>
<any namespace="##other" processContents="lax" minOccurs="0"
maxOccurs="unbounded"/>
<element ref="ds:DSAKeyValue"/>
<element ref="ds:RSAKeyValue"/>
</choice>
</complexType>
</element>
DTD:
<!ELEMENT KeyValue %Key.ANY; >
4.4.3 The RetrievalMethod Element ๐งโโ๏ธ
A RetrievalMethod element inside KeyInfo points to KeyInfo information stored somewhere else ๐บ๏ธ For example, several signatures in one document might all use a key verified by an X.509v3 certificate chain that shows up once in the document or lives remotely outside it ๐ญ Each signature's KeyInfo can reference that chain with one RetrievalMethod element, instead of copying the whole chain in as a sequence of X509Certificate elements ๐ซถ
RetrievalMethod uses the same syntax and dereferencing behavior as Reference's URI (section 4.3.3.1) and The Reference Processing Model (section 4.3.3.2), except there's no DigestMethod or DigestValue child elements and the URI is mandatory ๐ Note: if dereferencing and transforming the specified URI gives you a node set, it may need to be canonicalized. All the KeyInfo types this spec defines (section 4.4) represent octets, so the Signature application is expected to try canonicalizing the node set via The Reference Processing Model (section 4.3.3.2) ๐
Type is an optional identifier for the type of data to be retrieved โจ
Schema Definition
<element name="RetrievalMethod">
<complexType>
<sequence>
<element ref="ds:Transforms" minOccurs="0"/>
</sequence>
<attribute name="URI" type="uriReference"/>
<attribute name="Type" type="uriReference" use="optional"/>
</complexType>
</element>
DTD
<!ELEMENT RetrievalMethod (Transforms?) >
<!ATTLIST RetrievalMethod
URI CDATA #REQUIRED
Type CDATA #IMPLIED >
4.4.4 The X509Data Element ๐
Identifier
Type="http://www.w3.org/2000/09/xmldsig#X509Data"
(this can be used within a RetrievalMethod or Reference element
to identify the referent's type)
An X509Data element inside KeyInfo holds one or more identifiers of keys or X509 certificates (or certificate identifiers or revocation lists) ๐ Five types of X509Data are defined ๐ธ
- The X509IssuerSerial element, which contains an X.509 issuer distinguished name/serial number pair that SHOULD be compliant with RFC2253 [LDAP-DN] ๐งพ
- The X509SubjectName element, which contains an X.509 subject distinguished name that SHOULD be compliant with RFC2253 [LDAP-DN] ๐ซถ
- The X509SKI element, which contains an X.509 subject key identifier value. ๐
- The X509Certificate element, which contains a base64-encoded [X509v3] certificate, and ๐
- The X509CRL element, which contains a base64-encoded certificate revocation list (CRL) [X509v3]. ๐ซ
Multiple declarations about a single certificate (like an X509SubjectName and an X509IssuerSerial element) MUST be grouped inside a single X509Data element ๐ Multiple declarations about the same key but different certificates (related to that one key) MUST be grouped within a single KeyInfo element, but MAY occur in multiple X509Data elements ๐ฆ For example, this block has two pointers to certificate-A (issuer/serial number and SKI), a single reference to certificate-B (SubjectName), and also shows certificate elements in use ๐ญ
<KeyInfo>
<X509Data> <!-- two pointers to certificate-A -->
<X509IssuerSerial>
<X509IssuerName>CN=TAMURA Kent, OU=TRL, O=IBM,
L=Yamato-shi, ST=Kanagawa, C=JP</X509IssuerName>
<X509SerialNumber>12345678</X509SerialNumber>
</X509IssuerSerial>
<X509SKI>31d97bd7</X509SKI>
</X509Data>
<X509Data> <!-- single pointer to certificate-B -->
<X509SubjectName>Subject of Certificate B</X509SubjectName>
</X509Data> <!-- certificate chain -->
<!--Signer cert, issuer CN=arbolCA,OU=FVT,O=IBM,C=US, serial 4-->
<X509Certificate>MIICXTCCA..</X509Certificate>
<!-- Intermediate cert subject CN=arbolCA,OU=FVTO=IBM,C=US
issuer,CN=tootiseCA,OU=FVT,O=Bridgepoint,C=US -->
<X509Certificate>MIICPzCCA...</X509Certificate>
<!-- Root cert subject CN=tootiseCA,OU=FVT,O=Bridgepoint,C=US -->
<X509Certificate>MIICSTCCA...</X509Certificate>
</X509Data>
</KeyInfo>
Heads up ๐ there's no direct provision for a PKCS#7 encoded "bag" of certificates or CRLs. That said, a set of certificates or a CRL can sit inside an X509Data element, and multiple X509Data elements can show up in one KeyInfo โจ Whenever multiple certificates appear in one X509Data element, at least one of them must contain the public key that verifies the signature ๐ฅ
Schema Definition
<element name="X509Data">
<complexType>
<choice>
<sequence maxOccurs="unbounded">
<choice>
<element ref="ds:X509IssuerSerial"/>
<element name="X509SKI" type="ds:CryptoBinary"/>
<element name="X509SubjectName" type="string"/>
<element name="X509Certificate" type="ds:CryptoBinary"/>
</choice>
</sequence>
<element name="X509CRL" type="ds:CryptoBinary"/>
</choice>
</complexType>
</element>
<element name="X509IssuerSerial">
<complexType>
<sequence>
<element name="X509IssuerName" type="string"/>
<element name="X509SerialNumber" type="integer"/>
</sequence>
</complexType>
</element>
DTD
<!ELEMENT X509Data ((X509IssuerSerial | X509SKI | X509SubjectName |
X509Certificate)+ | X509CRL)>
<!ELEMENT X509IssuerSerial (X509IssuerName, X509SerialNumber) >
<!ELEMENT X509IssuerName (#PCDATA) >
<!ELEMENT X509SubjectName (#PCDATA) >
<!ELEMENT X509SerialNumber (#PCDATA) >
<!ELEMENT X509SKI (#PCDATA) >
<!ELEMENT X509Certificate (#PCDATA) >
<!ELEMENT X509CRL (#PCDATA) >
4.4.5 The PGPData element ๐
Identifier: Type="http://www.w3.org/2000/09/xmldsig#PGPData" (this can be used within a RetrievalMethod or Reference element to identify the referent's type ๐)
okay so PGPData is the KeyInfo element for PGP public key pairs and the signatures on those keys ๐โจ The PGPKeyID holds a string that's a standard PGP public key identifier, defined in [PGP, section 11.2] ๐ The PGPKeyPacket holds a base64-encoded Key Material Packet, defined in [PGP, section 5.5] ๐ง And the OpenPGP working group is allowed to define other sub-types of PGPData later, so keep an eye out ๐
Schema Definition:
<element name="PGPData">
<complexType>
<choice>
<any namespace="##other" processContents="lax" minOccurs="0"
maxOccurs="unbounded"/>
<sequence>
<element name="PGPKeyID" type="string"/>
<element name="PGPKeyPacket" type="ds:CryptoBinary"/>
</sequence>
</choice>
</complexType>
</element>
DTD:
<!ELEMENT PGPData (PGPKeyID, PGPKeyPacket) >
<!ELEMENT PGPKeyPacket (#PCDATA) >
<!ELEMENT PGPKeyID (#PCDATA) >
4.4.6 The SPKIData element ๐ธ
Identifier: Type="http://www.w3.org/2000/09/xmldsig#SPKIData" (this can be used within a RetrievalMethod or Reference element to identify the referent's type ๐ฆ)
so SPKIData is the one for SPKI public key pairs, certificates, and other SPKI data ๐ Its content is expected to be a Canonical S-expression, bestie ๐
Schema Definition:
<element name="SPKIData" type="string"/>
DTD:
<!ELEMENT SPKIData (#PCDATA) >
4.4.7 The MgmtData element ๐
Identifier: Type="http://www.w3.org/2000/09/xmldsig#MgmtData" (this can be used within a RetrievalMethod or Reference element to identify the referent's type โญ)
MgmtData is giving in-band key distribution or agreement data ๐ค It's a string value, and the examples are DH key exchange, RSA key encryption, etc. ๐
Schema Definition:
<!-- type declared in KeyInfo -->
DTD:
<!ELEMENT MgmtData (#PCDATA)>
4.5 The Object Element โจ
Identifier: Type="http://www.w3.org/2000/09/xmldsig#Object" (this can be used within a Reference element to identify the referent's type ๐)
Object is an optional element that can show up one or more times ๐ซถ When it's there, it can hold any data at all ๐ธ It can also carry optional MIME type, ID, and encoding attributes, which is very main character energy ๐
The MimeType attribute is optional and describes the data inside the Object ๐ It's a string whose values are defined by [MIME]. For example, if the Object holds XML, the MimeType could be text/xml. This attribute is purely advisory, and this specification doesn't require any validation of the MimeType information ๐
The Object's Id is commonly referenced from a Reference in SignedInfo, or Manifest ๐ฅ This element is typically used for enveloping signatures, where the object being signed goes right inside the signature element ๐ง The digest is calculated over the entire Object element, start and end tags included ๐
The Object's Encoding attribute can be used to give a URI that identifies how the object is encoded, like a binary file ๐ฆ
Note, if the application wants the <Object> tags left out of the digest calculation, the Reference has to identify the actual data object (easy for XML documents), or a transform has to be used to strip the Object tags (likely where the data object is non-XML) โญ Leaving out the object tags might be wanted when you want the signature to stay valid even if the data object gets moved from inside a signature to outside it (or the other way around) ๐ It might also be wanted when the content of the Object is an encoding of an original binary document, and you want to extract and decode it so you sign the original bitwise representation ๐
Schema Definition:
<element name="Object">
<complexType mixed="true">
<sequence maxOccurs="unbounded">
<any namespace="##any" processContents="lax"/>
</sequence>
<attribute name="Id" type="ID" use="optional"/>
<attribute name="MimeType" type="string" use="optional"/>
<!-- add a grep facet -->
<attribute name="Encoding" type="uriReference" use="optional"/>
</complexType>
</element>
DTD:
<!ELEMENT Object %Object.ANY; >
<!ATTLIST Object
Id ID #IMPLIED
MimeType CDATA #IMPLIED
Encoding CDATA #IMPLIED >
5.0 Additional Signature Syntax ๐
This section covers the optional-to-implement Manifest and SignatureProperties elements, and it explains how XML processing instructions and comments get handled ๐ซถ For Manifest and SignatureProperties, this section defines the syntax and barely any behaviour, since that's left up to the application ๐ These elements can appear anywhere the parent's content model allows, but the Signature content model only lets them show up within Object ๐ฅ
5.1 The Manifest Element ๐
Identifier: Type="http://www.w3.org/2000/09/xmldsig#Manifest" (this can be used within a Reference element to identify the referent's type ๐)
The Manifest element is a list of References ๐ง The difference from the list in SignedInfo is that the application decides which digests, if any, actually get checked against the referenced objects, and what to do if an object can't be reached or the digest compare fails ๐ If a Manifest is pointed to from SignedInfo, the digest over the Manifest itself gets checked by the core signature validation behaviour ๐ The digests inside that Manifest get checked at the application's discretion โจ And if a Manifest is referenced from another Manifest, even the overall digest of that two-level-deep Manifest might not get checked ๐ญ
Schema Definition:
<element name="Manifest">
<complexType>
<sequence>
<element ref="ds:Reference" maxOccurs="unbounded"/>
</sequence>
<attribute name="Id" type="ID" use="optional"/>
</complexType>
</element>
DTD:
<!ELEMENT Manifest (Reference+) >
<!ATTLIST Manifest
Id ID #IMPLIED >
5.2 The SignatureProperties Element ๐ฆ
Identifier: Type="http://www.w3.org/2000/09/xmldsig#SignatureProperties" (this can be used within a Reference element to identify the referent's type ๐ธ)
Extra info about how the signature(s) got made can go in a SignatureProperty element ๐ฐ๏ธ Think date/time stamps, or the serial number of the cryptographic hardware used to make the signature ๐
Schema Definition:
<element name="SignatureProperties">
<complexType>
<sequence>
<element ref="ds:SignatureProperty" maxOccurs="unbounded"/>
</sequence>
<attribute name="Id" type="ID" use="optional"/>
</complexType>
</element>
<element name="SignatureProperty">
<complexType mixed="true">
<choice minOccurs="0" maxOccurs="unbounded">
<any namespace="##other" processContents="lax" minOccurs="0"
maxOccurs="unbounded"/>
</choice>
<attribute name="Target" type="uriReference" use="required"/>
<attribute name="Id" type="ID" use="optional"/>
</complexType>
</element>
DTD:
<!ELEMENT SignatureProperties (SignatureProperty+) >
<!ATTLIST SignatureProperties
Id ID #IMPLIED >
<!ELEMENT SignatureProperty %SignatureProperty.ANY >
<!ATTLIST SignatureProperty
Target CDATA #REQUIRED
Id ID #IMPLIED >
5.3 Processing Instructions in Signature Elements ๐ง
No XML processing instructions (PIs) are used by this specification ๐ โโ๏ธ
Heads up, though: PIs placed inside SignedInfo by an application will be signed, unless the CanonicalizationMethod algorithm throws them away ๐ (This is true for any signed XML content.) All of the CanonicalizationMethods specified within this specification keep PIs ๐ When a PI is part of content that gets signed (like within SignedInfo or in referenced XML documents), any change to the PI will obviously cause a signature failure ๐ญ
5.4 Comments in Signature Elements ๐ฌ
XML comments are not used by this specification ๐ โโ๏ธ
Note that unless CanonicalizationMethod removes comments within SignedInfo or any other referenced XML (which [XML-C14N] does), they will be signed ๐ซฃ So if they're kept, changing a comment will cause a signature failure ๐ Similarly, the XML signature over any XML data will be sensitive to comment changes, unless a comment-ignoring canonicalization/transform method, such as the Canonical XML [XML-C14N], is specified ๐
6.0 Algorithms ๐งฎ
This section identifies the algorithms used with the XML digital signature specification ๐ฆ Each entry has the identifier to use in Signature elements, a reference to the formal specification, and definitions (where they apply) for how keys and the results of cryptographic operations are represented ๐
6.1 Algorithm Identifiers and Implementation Requirements ๐
Algorithms are identified by URIs that show up as an attribute on the element that names the algorithm's role (DigestMethod, Transform, SignatureMethod, or CanonicalizationMethod) ๐ All the algorithms here take parameters, but in lots of cases the parameters are implicit ๐ For example, a SignatureMethod is implicitly given two parameters: the keying info and the output of CanonicalizationMethod ๐ Explicit extra parameters to an algorithm show up as content elements inside the algorithm role element ๐ Those parameter elements have a descriptive element name, which is often algorithm specific, and they MUST be in the XML Signature namespace or an algorithm specific namespace ๐ซถ
This specification defines a set of algorithms, their URIs, and the requirements for implementing them ๐ The requirements are about implementation, not about what's needed for signature use ๐ง And the mechanism is extensible, so signature applications can use alternative algorithms too ๐ธ
(Note that the normative identifier is the complete URI in the table, even though they're sometimes abbreviated in XML syntax, e.g., "&dsig;base64".) โจ
Algorithm Type
Algorithm - Requirements - Algorithm URI
Digest
SHA1 - REQUIRED - &dsig;sha1
Encoding
base64 - REQUIRED - &dsig;base64
MAC
HMAC-SHA1 - REQUIRED - &dsig;hmac-sha1
Signature
DSAwithSHA1(DSS) - REQUIRED - &dsig;dsa-sha1
RSAwithSHA1 - RECOMMENDED - &dsig;rsa-sha1
Canonicalization
minimal - RECOMMENDED - &dsig;minimal
Canonical XML with Comments - RECOMMENDED -
http://www.w3.org/TR/2000/CR-xml-c14n-20001026#WithComments
Canonical XML (omits comments) - REQUIRED -
http://www.w3.org/TR/2000/CR-xml-c14n-20001026
Transform
XSLT - OPTIONAL - http://www.w3.org/TR/1999/REC-xslt-19991116
XPath - RECOMMENDED -
http://www.w3.org/TR/1999/REC-xpath-19991116
Enveloped Signature* - REQUIRED - &dsig;enveloped-signature
* The Enveloped Signature transform removes the Signature element from the calculation of the signature when the signature sits inside the content it's signing ๐ซง This MAY be implemented via the RECOMMENDED XPath specification specified in 6.6.4: Enveloped Signature Transform, but it MUST have the same effect as the one specified by the XPath Transform ๐
6.2. Message Digests
okay so only one digest algorithm is defined in this doc ๐ but the US Advanced Encryption Standard crowd is expected to cook up more strong ones, so stay tuned โจ and ngl, using MD5 [MD5] is NOT RECOMMENDED bc recent advances in cryptography have made people side-eye its strength ๐ญ
6.2.1. SHA-1
Identifier:
http://www.w3.org/2000/09/xmldsig#sha1
The SHA-1 algorithm [SHA-1] takes no explicit parameters, so it's giving low-maintenance ๐ง Here's an example of a SHA-1 DigestAlg element: <DigestMethod Algorithm="&dsig;sha1"/>
A SHA-1 digest is a 160-bit string. The content of the DigestValue element shall be the base64 encoding of that bit string, viewed as a 20-octet octet stream ๐ธ For example, take this message digest from Appendix A of the SHA-1 standard:
A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D
and the DigestValue element for it would be:
<DigestValue>qZk+NkcGgWq6PiVxeFDCbJzQ2J0=</DigestValue>
6.3. Message Authentication Codes
MAC algorithms take two implicit parameters: their keying material, which is determined from KeyInfo, and the octet stream output by CanonicalizationMethod ๐ MACs and signature algorithms are syntactically identical, but a MAC implies a shared secret key, while a signature implies something else entirely ๐ซถ
6.3.1. HMAC
Identifier:
http://www.w3.org/2000/09/xmldsig#hmac-sha1
The HMAC algorithm (RFC2104 [HMAC]) takes the truncation length in bits as a parameter. If that parameter isn't specified, then all the bits of the hash get output ๐ Here's an example of an HMAC SignatureMethod element:
<SignatureMethod Algorithm="&dsig;hmac-sha1">
<HMACOutputLength>128</HMACOutputLength>
</SignatureMethod>
The output of the HMAC algorithm is ultimately the output (possibly truncated) of the chosen digest algorithm. This value shall be base64 encoded in the same straightforward fashion as the output of the digest algorithms ๐ฆ For example, the SignatureValue element for the HMAC-SHA1 digest
9294727A 3638BB1C 13F48EF8 158BFC9D
from the test vectors in [HMAC] would be:
<SignatureValue>kpRyejY4uxwT9I74FYv8nQ==</SignatureValue>
Schema Definition:
<element name="HMACOutputLength" type="integer"/>
DTD:
<!ELEMENT HMACOutputLength (#PCDATA)>
6.4. Signature Algorithms
Signature algorithms take two implicit parameters too: their keying material, determined from KeyInfo, and the octet stream output by CanonicalizationMethod ๐ Signature and MAC algorithms are syntactically identical, but a signature implies public key cryptography, which is the whole main character energy of this section ๐
6.4.1. DSA
Identifier:
http://www.w3.org/2000/09/xmldsig#dsa-sha1
The DSA algorithm [DSS] takes no explicit parameters. Here's an example of a DSA SignatureMethod element:
<SignatureMethod Algorithm="&dsig;dsa"/>
The output of the DSA algorithm is a pair of integers, usually referred to as the pair (r, s). The signature value is the base64 encoding of the concatenation of two octet streams, which come from octet-encoding the values r and s respectively ๐ Integer to octet stream conversion has to be done according to the I2OSP operation defined in the RFC 2437 [PKCS1] specification, with a k parameter equal to 20. For example, here's the SignatureValue element for a DSA signature (r, s), with the values written in hexadecimal:
r = 8BAC1AB6 6410435C B7181F95 B16AB97C 92B341C0
s = 41E2345F 1F56DF24 58F426D1 55B4BA2D B6DCD8C8
from the example in Appendix 5 of the DSS standard would be:
<SignatureValue>
i6watmQQQ1y3GB+VsWq5fJKzQcBB4jRfH1bfJFj0JtFVtLotttzYyA==</SignatureValue>
DSA key values have the following set of fields ๐ P, Q, G and Y are mandatory when they appear as a key value. J, seed and pgenCounter are optional but should be present. (The seed and pgenCounter fields must appear together or be absent.) All parameters are encoded as base64 [MIME] values.
Schema:
<element name="DSAKeyValue">
<complexType>
<sequence>
<sequence>
<element name="P" type="ds:CryptoBinary"/>
<element name="Q" type="ds:CryptoBinary"/>
<element name="G" type="ds:CryptoBinary"/>
<element name="Y" type="ds:CryptoBinary"/>
<element name="J" type="ds:CryptoBinary" minOccurs="0"/>
</sequence>
<sequence minOccurs="0">
<element name="Seed" type="ds:CryptoBinary"/>
<element name="PgenCounter" type="ds:CryptoBinary"/>
</sequence>
</sequence>
</complexType>
</element>
DTD:
<!ELEMENT DSAKeyValue (P, Q, G, Y, J?, (Seed, PgenCounter)?) >
<!ELEMENT P (#PCDATA) >
<!ELEMENT Q (#PCDATA) >
<!ELEMENT G (#PCDATA) >
<!ELEMENT Y (#PCDATA) >
<!ELEMENT J (#PCDATA) >
<!ELEMENT Seed (#PCDATA) >
<!ELEMENT PgenCounter (#PCDATA) >
6.4.2. PKCS1
Identifier:
http://www.w3.org/2000/09/xmldsig#rsa-sha1
Arbitrary-length integers (aka "bignums", like RSA modulii) are represented in XML as octet strings ๐ง First the integer value gets converted to a "big endian" bitstring. Then the bitstring is padded with leading zero bits so the total number of bits == 0 mod 8, which means an even number of bytes. If the bitstring has entire leading bytes that are zero, those get removed, so the high-order byte is always non-zero. Then this octet string is base64 [MIME] encoded. (The integer-to-octet-string conversion is equivalent to IEEE 1363's I2OSP [1363] with minimal length.)
The expression "RSA algorithm" as used in this document refers to the RSASSA-PKCS1-v1_5 algorithm described in RFC 2437 [PKCS1]. The RSA algorithm takes no explicit parameters. An example of an RSA SignatureMethod element is:
<SignatureMethod Algorithm="&dsig;rsa-
sha1"/>
The SignatureValue content for an RSA signature is the base64 [MIME] encoding of the octet string computed as per RFC 2437 [PKCS1, section 8.1.1: Signature generation for the RSASSA-PKCS1-v1_5 signature scheme]. As specified in the EMSA-PKCS1-V1_5-ENCODE function RFC 2437 [PKCS1, section 9.2.1], the value input to the signature function MUST contain a pre-pended algorithm object identifier for the hash function. However, the availability of an ASN.1 parser and recognition of OIDs is not required of a signature verifier ๐ The PKCS#1 v1.5 representation looks like this:
CRYPT (PAD (ASN.1 (OID, DIGEST (data))))
Note that the padded ASN.1 will be of the following form:
01 | FF* | 00 | prefix | hash
where "|" is concatentation, "01", "FF", and "00" are fixed octets of the corresponding hexadecimal value, "hash" is the SHA1 digest of the data, and "prefix" is the ASN.1 BER SHA1 algorithm designator prefix required in PKCS1 [RFC 2437], that is:
hex 30 21 30 09 06 05 2B 0E 03 02 1A 05 00 04 14
This prefix is included to make it easier to use standard cryptographic libraries ๐ The FF octet MUST be repeated the maximum number of times such that the value of the quantity being CRYPTed is one octet shorter than the RSA modulus.
The resulting base64 [MIME] string is the value of the child text node of the SignatureValue element, for example:
<SignatureValue>IWijxQjUrcXBYoCei4QxjWo9Kg8D3p9tlWoT4
t0/gyTE96639In0FZFY2/rvP+/bMJ01EArmKZsR5VW3rwoPxw=
</SignatureValue>
RSA key values have two fields, Modulus and Exponent:
<RSAKeyValue>
<Modulus>xA7SEU+e0yQH5rm9kbCDN9o3aPIo7HbP7tX6WOocLZAtNfyxSZDU16ksL6W
jubafOqNEpcwR3RdFsT7bCqnXPBe5ELh5u4VEy19MzxkXRgrMvavzyBpVRgBUwUlV
5foK5hhmbktQhyNdy/6LpQRhDUDsTvK+g9Ucj47es9AQJ3U=
</Modulus>
<Exponent>AQAB</Exponent>
</RSAKeyValue>
Schema:
<element name="RSAKeyValue">
<complexType>
<sequence>
<element name="Modulus" type="ds:CryptoBinary"/>
<element name="Exponent" type="ds:CryptoBinary"/>
</sequence>
</complexType>
</element>
DTD:
<!ELEMENT RSAKeyValue (Modulus, Exponent) >
<!ELEMENT Modulus (#PCDATA) >
<!ELEMENT Exponent (#PCDATA) >
6.5. Canonicalization Algorithms
If canonicalization is performed over octets, the canonicalization algorithms take two implicit parameters: the content and its charset ๐ฐ The charset is derived according to the rules of the transport protocols and media types (for example, RFC2376 [XML-MT] defines the media types for XML). This information is necessary to correctly sign and verify documents, and it often requires careful server-side configuration, so don't skip it ๐ค
Various canonicalization algorithms require conversion to [UTF-8]. The two algorithms below understand at least [UTF-8] and [UTF-16] as input encodings. We RECOMMEND that externally specified algorithms do the same. Knowledge of other encodings is OPTIONAL.
Various canonicalization algorithms transcode from a non-Unicode encoding to Unicode. The two algorithms below perform text normalization during transcoding [NFC]. We RECOMMEND that externally specified canonicalization algorithms do the same. (Note, there can be ambiguities when converting existing charsets to Unicode. For an example, see the XML Japanese Profile [XML-Japanese] NOTE ๐)
6.5.1. Minimal Canonicalization
Identifier:
http://www.w3.org/2000/09/xmldsig#minimal
An example of a minimal canonicalization element is:
<CanonicalizationMethod Algorithm="&dsig;minimal"/>
The minimal canonicalization algorithm:
- converts the character encoding to UTF-8 (without any byte order mark (BOM)). If an encoding is given in the XML declaration, it must be removed. Implementations MUST understand at least [UTF-8] and [UTF-16] as input encodings. Non-Unicode to Unicode transcoding MUST perform text normalization [NFC].
- normalizes line endings as provided by [XML]. (See XML and Canonicalization and Syntactical Considerations (section 7).)
This algorithm requires as input the octet stream of the resource to be processed, and the algorithm outputs an octet stream ๐ When used to canonicalize SignedInfo, the algorithm MUST be provided with the octets that represent the well-formed SignedInfo element (and its children and content), as described in The CanonicalizationMethod Element (section 4.3.1).
If the signature application has a node set, then the signature application must convert it into octets as described in The Reference Processing Model (section 4.3.3.2). However, Minimal Canonicalization is NOT RECOMMENDED for processing XPath node-sets, the results of same-document URI references, and the output of other types of XML-based transforms. It is only RECOMMENDED for simple character normalization of well-formed XML that has no namespace or external entity complications โญ
6.5.2. Canonical XML
Identifier for REQUIRED Canonical XML (omits comments):
http://www.w3.org/TR/2000/CR-xml-c14n-20001026
Identifier for Canonical XML with Comments:
http://www.w3.org/TR/2000/CR-xml-c14n-20001026#WithComments
An example of an XML canonicalization element is:
<CanonicalizationMethod Algorithm="http://www.w3.org/TR/2000/CR-xml-
c14n-20001026"/>
The normative specification of Canonical XML is [XML-C14N]. The algorithm can take as input either an octet stream or an XPath node-set (or a sufficiently functional alternative), and it produces an octet stream as output ๐ฆ Canonical XML is easily parameterized (via an additional URI) to omit or retain comments, which is so iconic ๐
6.6 Transform Algorithms
okay so a Transform algorithm only has one implicit parameter ๐ It's an octet stream, and it comes either from the Reference or from the output of an earlier Transform.
Application developers are strongly encouraged to support every transform in this section as RECOMMENDED ๐ซถ unless their environment is resource-constrained enough that it's genuinely impractical. Supporting them all maximizes interoperability, and libraries should exist that let you add these without a ton of dev work โจ
6.6.1 Canonicalization
Any canonicalization algorithm that can be used for CanonicalizationMethod (like the ones in Canonicalization Algorithms (section 6.5)) can also be used as a Transform ๐ฆ
6.6.2 Base64
Identifiers: http://www.w3.org/2000/09/xmldsig#base64
The normative spec for base 64 decoding transforms is [MIME] ๐ธ The base64 Transform element has no content, and the algorithms do the decoding for you. This one is useful when an app wants to sign the raw data inside an element's encoded content ๐
This transform needs an octet stream as input. If you hand it an XPath node-set (or something equally capable), it gets turned into an octet stream by doing the logical equivalent of two steps: first applying an XPath transform with the expression self::text(), then taking the string-value of the node-set ๐ง So if an element is found with a barename XPointer in the Reference URI, and its content is only base64 character data, this transform quietly strips off the start and end tags of that element, plus any descendant elements, descendant comments, and processing instructions. The output is an octet stream ๐
6.6.3 XPath Filtering
Identifier: http://www.w3.org/TR/1999/REC-xpath-19991116
The normative spec for XPath expression evaluation is [XPath] ๐ The XPath expression being evaluated shows up as the character content of a transform parameter child element named XPath.
The input for this transform is an XPath node-set ๐ฅ Heads up: if the actual input is an XPath node-set coming from a null URI or a barename XPointer dereference, then comment nodes have already been dropped. If the actual input is an octet stream instead, the application MUST convert that octet stream into an XPath node-set that works with Canonical XML with Comments. (The REQUIRED Canonical XML algorithm that runs later will strip those comments back out.) In other words, the input node-set should end up matching the one you'd get from this process:
- Start an XPath evaluation context with the initial node set to the input XML document's root node, and set the context position and size to 1.
- Evaluate the XPath expression
(//. | //@* | //namespace::*)
Evaluating that expression pulls in every node in the document, comments included, to build the node-set that represents the octet stream ๐
The output of this transform is also an XPath node-set ๐ The XPath expression in the XPath parameter gets evaluated once for each node in the input node-set. The result is converted to a boolean. If that boolean is true, the node goes into the output node-set. If it's false, the node gets left out.
Note: Even when comments have been removed from the input node-set, the comment nodes still live in the underlying parse tree, and they can split text nodes apart. For example, the markup<e>Hello, <!-- comment --> world!</e>has two text nodes, soself::text()[string()="Hello, world!"]would fail ๐ญ If you run into this, you can either canonicalize the document before the XPath transform to physically remove the comments, or match the node based on the parent element's string value, likeself::text()[string(parent::e)="Hello, world!"].
The whole point of this transform is to make sure that only specifically defined changes to the input XML document are allowed after the signature is attached ๐ It works by leaving out exactly the nodes that are allowed to change once the signature exists, and including every other input node in the output. The XPath expression's author is responsible for including all nodes whose change could affect how the transform output gets interpreted in the application context ๐ง
Here's an important scenario: a document that needs two enveloped signatures. Each signature has to leave itself out of its own digest calculations. But it's also necessary to exclude the second signature element from the first signature's digest calculation, so that adding the second signature doesn't break the first one ๐
For each node of the input node-set, the XPath transform sets up this evaluation context:
- A context node equal to a node of the input node-set.
- A context position, initialized to 1.
- A context size, initialized to 1.
- A library of functions equal to the function set defined in XPath, plus a function named
here. - A set of variable bindings. No means for initializing these is defined, so the set of variable bindings is empty, and using a variable reference in the XPath expression results in an error.
- The set of namespace declarations in scope for the XPath expression.
Because of how the context node is set, the XPath expressions in this transform end up looking a lot like the ones used in [XSLT], except that size and position are always 1. That's because the transform is automatically visiting every node (in XSLT, you'd recursively call apply-templates to visit the nodes of the input tree) ๐ฆ
The here() function is defined like this:
Function: node-set here()
The here function returns a node-set containing the attribute or processing instruction node, or the parent element of the text node, that directly bears the XPath expression. If the containing XPath expression doesn't appear in the same XML document that the XPath expression is being evaluated against, this results in an error ๐
Note: The definition of here() is meant to match its definition in XPointer. Some minor differences are currently being discussed between the Working Groups, though ๐
Let's look at an example. Say you're creating an enveloped signature, which is a Signature element that's a descendant of the element being signed. The signed content shouldn't change after signing, but the elements inside the Signature element do change, since the digest value has to go inside the DigestValue and the SignatureValue gets calculated afterward. One way to keep those changes from invalidating the digest value is to add an XPath Transform that leaves out all Signature elements and their descendants. For example:
<Document>
<Signature xmlns="&dsig;">
<SignedInfo>
...
<Reference URI="">
<Transforms>
<Transform
Algorithm="http://www.w3.org/TR/1999/REC-xpath-19991116">
<XPath xmlns:dsig="&dsig;">
not(ancestor-or-self::dsig:Signature)
</XPath>
</Transform>
</Transforms>
<DigestMethod
Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/>
<DigestValue></DigestValue>
</Reference>
</SignedInfo>
<SignatureValue></SignatureValue>
</Signature>
...
</Document>
Since the Reference URI is null in this example, the XPath transform's input node-set contains every node in the entire parse tree, starting from the root node (except the comment nodes). For each node in that node-set, the node is included in the output node-set, unless the node or one of its ancestors is a Signature tag in the namespace given by the replacement text for the entity &dsig; ๐ธ
There's a more elegant solution that uses the here function to leave out only the Signature containing the XPath Transform. That way, enveloped signatures can sign other signatures ๐ In the example above, you'd use this XPath element:
<XPath xmlns:dsig="&dsig;">
count(ancestor-or-self::dsig:Signature |
here()/ancestor::dsig:Signature[1]) >
count(ancestor-or-self::dsig:Signature)</XPath>
The XPath equality operator converts node-sets to string values before comparing them, so we have to use the XPath union operator (|) instead ๐ง For each node in the document, the predicate is true if and only if the node-set containing that node and its Signature element ancestors does not include the enveloped Signature element that holds the XPath expression. (The union doesn't produce a bigger set when the enveloped Signature element is already in the node-set given by ancestor-or-self::Signature.)
6.6.4 Enveloped Signature Transform
Identifier: http://www.w3.org/2000/09/xmldsig#enveloped-signature
An enveloped signature transform T removes the whole Signature element containing T from the digest calculation of the Reference element containing T ๐ฆ The entire string of characters that an XML processor uses to match the Signature with the XML production element gets removed too. The output of this transform is equivalent to what you'd get by replacing T with an XPath transform that has this XPath parameter element:
<XPath xmlns:dsig="&dsig;">
count(ancestor-or-self::dsig:Signature |
here()/ancestor::dsig:Signature[1]) >
count(ancestor-or-self::dsig:Signature)</XPath>
The input and output requirements of this transform are identical to the XPath transform's. You don't actually need an XPath expression evaluator to build this transform ๐ง However, this transform MUST produce output in exactly the same way as the XPath transform parameterized by the XPath expression above ๐
6.6.5 XSLT Transform
Identifier: http://www.w3.org/TR/1999/REC-xslt-19991116
The normative spec for XSL Transformations is [XSLT] ๐ The XSL style sheet or transform to be evaluated shows up as the character content of a transform parameter child element named XSLT. The root element of an XSLT style sheet SHOULD be <xsl:stylesheet> โจ
This transform needs an octet stream as input. If the actual input is an XPath node-set, the signature application is encouraged to try converting it to octets by applying Canonical XML, as described in the Reference Processing Model (section 4.3.3.2) ๐ซถ
The output of this transform is an octet stream. The processing rules for the XSL style sheet or transform element are stated in the XSLT specification [XSLT]. We RECOMMEND that XSLT transform authors use an output method of xml for XML and HTML ๐ Since XSLT implementations don't produce consistent serializations of their output, we further RECOMMEND inserting a transform after the XSLT transform that canonicalizes the output. These steps help ensure interoperability of the resulting signatures among applications that support the XSLT transform ๐ฅ Note that if the output is actually HTML, then the result of these steps is logically equivalent [XHTML] ๐
7.0 XML Canonicalization and Syntax Constraint Considerations โจ
Okay so digital signatures are super picky ๐ง. The verification math has to run on exactly the same bits that got signed, or it's over ๐. If the way the data looks can change between signing and verifying, you need some way to standardize that changeable part first. Like, even plain ASCII text has at least three popular line ending sequences. If signed text can flip from one line ending style to another between signing and checking, you have to canonicalize the line endings to one standard form before signing and verifying, or the signatures just break. Not me having a meltdown over a newline ๐ญ
XML is literally a surface-representation mess ๐ซ , and some processing throws away surface info too. So XML digital signatures have a way to name the canonicalization method right in the signature, so the verifier can use the same one the signer used. Iconic behavior ๐
Throughout this spec we treat the canonicalization of a Signature element differently from other signed XML data objects ๐ฆ. An isolated XML document can be handled as plain binary data so nothing changes, and then its digest won't change and it doesn't need canonicalizing if it's signed and verified that way. BUT XML that gets read and processed with normal XML parsing tools often loses or modifies some of its surface info. This happens a lot to the Signature and the SignedInfo elements inside it, since they (and maybe the whole XML document around them) get processed as XML.
Same deal for Manifest, Object, and SignatureProperties elements if they've been digested, their DigestValue is getting checked, and they're being processed as XML ๐ธ.
The XML changes that might need canonicalizing come in three flavors ๐. First, the basic [XML] stuff, which we get into in 7.1 below. Second, [DOM], [SAX], or similar processing, covered in 7.2 below. And third, coded character set conversion, like going between UTF-8 and UTF-16. Both of those are things every [XML] compliant processor is required to support ๐ซถ
Any canonicalization algorithm should spit out output in one specific fixed coded character set ๐. For both the minimal canonicalization defined in this spec and Canonical XML [XML-C14N], that character set is UTF-8 (without a byte order mark (BOM)). Neither the minimal canonicalization nor the Canonical XML [XML-C14N] algorithms do character normalization, though ๐. We RECOMMEND that signature applications create XML content (Signature elements and their descendents/content) in Normalization Form C [NFC], and check that any XML they consume is in that form too. If it isn't, signatures may fail to validate as a result โ ๏ธ. Also, none of these algorithms do data type normalization. Apps that normalize data types in different formats (like (true, false) or (1,0)) might not be able to validate each other's signatures. Main character energy for sure ๐
7.1 XML 1.0, Syntax Constraints, and Canonicalization
Okay so XML 1.0 [XML] sets up an interface where a conformant app reading XML gets certain info from that XML and not other info ๐ฅ. Specifically:
- line endings are normalized to the single character
#xAby dropping#xDcharacters if they are immediately followed by a#xAand replacing them with#xAin all other cases, - missing attributes declared to have default values are provided to the application as if present with the default value,
- character references are replaced with the corresponding character,
- entity references are replaced with the corresponding declared entity,
- attribute values are normalized by
- A. replacing character and entity references as above,
- B. replacing occurrences of
#x9,#xA, and#xDwith#x20(space) except that the sequence#xD#xAis replaced by a single space, and - C. if the attribute is not declared to be CDATA, stripping all leading and trailing spaces and replacing all interior runs of spaces with a single space.
Note that items (2), (4), and (5C) depend on the presence of a schema, DTD, or similar declarations ๐ง . The Signature element type is laxly schema valid [XML-schema], so external XML, or even XML in the same document as the signature, may be (only) well formed or from another namespace (where the signature schema permits it). The noted items may not be present in that case. So a signature with that kind of content will only be verifiable by other signature apps if these syntax constraints are followed when generating any signed material, including the SignedInfo element ๐:
- attributes having default values be explicitly present,
- all entity references (except
amp,lt,gt,apos,quot, and other character entities not representable in the encoding chosen) be expanded, - attribute value white space be normalized
7.2 DOM/SAX Processing and Canonicalization
Besides the canonicalization and syntax constraints we just covered, lots of XML apps use the Document Object Model [DOM] or The Simple API for XML [SAX] ๐. DOM maps XML into a tree of nodes and usually assumes it'll be used on a whole document, with later processing happening on that tree. SAX turns XML into a series of events, like a start tag, content, and so on ๐ง. Either way, a bunch of surface stuff gets lost, like the order of attributes and insignificant white space inside start and end tags. Namespace declarations also get mapped onto the nodes they apply to, so the namespace prefixes from the source text are gone, and in most cases you can't tell where the namespace declarations originally showed up in the instance either ๐ฉ.
If an XML Signature is going to be produced or verified on a system using DOM or SAX, you need a canonical method to serialize the relevant part of a DOM tree or sequence of SAX events ๐. XML canonicalization specs, like [XML-C14N], are based only on info that DOM and SAX actually preserve. So for an XML Signature to be verifiable by a DOM or SAX implementation, the XML 1.0 syntax constraints from the previous section MUST be followed, AND an appropriate XML canonicalization MUST be specified so the verifier can re-serialize the DOM/SAX mediated input into the same octect stream that was signed ๐. Both MUSTs, no skipping!
Heads up bestie ๐จ: the signature won't verify if the bytes don't match exactly what got signed, so don't skip the canonicalization step, even if it feels like extra work ๐
8.0 Security Considerations โ ๏ธ
The XML Signature spec gives you a super flexible digital signature mechanism ๐ฆ. Implementors really need to think about their own application threat models, and also the factors below, because this stuff is powerful and powerful = dangerous if you're careless ๐ค.
8.1 Transforms
A requirement of this spec is to let signatures "apply to a part or totality of a XML document." (See [XML-Signature-RD, section 3.1.3].) The Transforms mechanism handles that by letting you sign data derived from processing the content of the identified resource โจ. For example, say an app wants to sign a form but still lets users type in limited field data without breaking an earlier signature on the form. It could use [XPath] to exclude the parts the user needs to change ๐ธ. Transforms can be specified pretty much however you want. They can include encoding transforms, canonicalization instructions, or even XSLT transformations ๐ง. Three cautions come up with this feature, and we cover them in the following sections ๐.
Note, core validation behavior does NOT confirm that the signed data was obtained by applying each step of the indicated transforms ๐. (Though it DOES check that the digest of the resulting content matches the one specified in the signature.) For example, some apps might be totally fine verifying an XML signature over a cached copy of data that was already transformed ๐ซ . Other apps might require that the content be freshly dereferenced and transformed, and that's valid too, so pick what fits your situation ๐ .
Quick reminder ๐: "core validation" only checks the digest. It does NOT prove each transform step was really run on the data.
8.1.1 Only What is Signed is Secure ๐
First, obviously, signatures over a transformed document do not secure any information discarded by transforms: only what is signed is secure ๐. Like, if the transform threw it away, the signature isn't protecting it, period.
Note that using Canonical XML [XML-C14N] ensures that all internal entities and XML namespaces get expanded within the content being signed ๐. All entities are replaced with their definitions, and the canonical form explicitly represents the namespace an element would otherwise inherit. Apps that do NOT canonicalize XML content (especially the SignedInfo element) SHOULD NOT use internal entities, and they SHOULD represent the namespace explicitly within the content being signed, since they can't rely on canonicalization to do that for them ๐ง.
8.1.2 Only What is "Seen" Should be Signed ๐๏ธ
Additionally, the signature secures any info introduced by the transform: only what is "seen" (meaning whatever is shown to the user visually, aurally, or through other media) should be signed ๐. If signing is meant to convey a user's judgment or consent (whether that's an automated mechanism or a person), then it's normally necessary to secure, as exactly as practical, the info that was presented to that user ๐. You can do that by literally signing what was presented, like the screen images a user saw. But that can produce data that's hard for later software to manipulate ๐ตโ๐ซ. So instead, you can sign the data along with whatever filters, style sheets, client profile, or other info affects how it gets presented โจ.
8.1.3 "See" What is Signed โจ
okay bestie, just like a user should only sign what they "see" ๐, persons and automated mechanisms that trust a transformed document because of a valid signature should operate over the data that was transformed (including canonicalization) and signed, not the original pre-transformed data ๐ซถ this applies to transforms specified inside the signature AND to ones included in the document itself. so like, if an XML document has an embedded style sheet [XSLT], it's the transformed document that should be shown to the user and signed ๐ and if a document points at an external style sheet, the content of that external resource should also be signed as a signature Reference, or else that outside content could change and alter the resulting document without breaking the signature ๐ญ main character energy is NOT letting that happen ๐
some applications might operate over the original or intermediary data, but they should be extremely careful about weaknesses that can sneak in between the original and transformed data ๐จ this is a trust decision about what the transforms actually do to the character and meaning of the data, so an application has to make that call with caution ๐ง think about a canonicalization algorithm that normalizes character case (lower to upper) or character composition ('e and accent' to 'accented-e') ๐ธ an adversary could make changes that get normalized away and are therefore inconsequential to signature validity, but still matter to a DOM processor ๐ like, changing the case of a character could influence the result of an XPath selection. the serious risk is when that change gets normalized for signature validation, but the processor operates over the original data and returns a different result than intended ๐ฑ so while we RECOMMEND that all documents operated upon and generated by signature applications be in [NFC] (otherwise intermediate processors might unintentionally break the signature), encoding normalizations SHOULD NOT be done as part of a signature transform ๐ โโ๏ธ or to say it another way: if normalization does occur, the application SHOULD always "see" (operate over) the normalized form โจ
8.2 Check the Security Model
okay so this spec uses public key signatures AND keyed hash authentication codes ๐ and these have substantially different security models, which is so important to get ๐ค plus it permits user specified algorithms, and those might have other models entirely ๐
with public key signatures, any number of parties can hold the public key and verify signatures, while only the parties with the private key can create signatures ๐ฆ the number of holders of the private key should be minimized and preferably be one ๐ verifiers also need to be confident in the public key they're using and its binding to the entity or capabilities represented by the corresponding private key. that's an important issue, and it's usually handled by certificate or online authority systems ๐
keyed hash authentication codes, based on secret keys, are typically much more efficient in terms of computational effort ๐๏ธ BUT they have the characteristic that all verifiers need to have possession of the same key as the signer. so, any verifier can forge signatures ๐ญ that's the tea โ
this spec permits user provided signature algorithms and keying information designators, and those user provided algorithms may have different security models ๐ for example, methods involving biometrics usually depend on a physical characteristic of the authorized user that can not be changed the way public or secret keys can be, and they may have other security model differences ๐ง
8.3 Algorithms, Key Lengths, Certificates, Etc.
the strength of a particular signature depends on ALL the links in the security chain ๐ that includes the signature and digest algorithms used, the strength of key generation [RANDOM] and the size of the key, the security of key and certificate authentication and distribution mechanisms, certificate chain validation policy, protection of cryptographic processing from hostile observation and tampering, etc. ๐
applications need to be careful when executing the various algorithms that may be specified in an XML signature, and when processing any "executable content" that might be passed to those algorithms as parameters, such as XSLT transforms โ ๏ธ the algorithms in this document will usually be implemented via a trusted library, but even there, perverse parameters might cause unacceptable processing or memory demand ๐ฅต even more care may be warranted with application defined algorithms ๐
the security of an overall system also depends on the security and integrity of its operating procedures, its personnel, and the administrative enforcement of those procedures ๐ฐ all the factors in this section matter to the overall security of a system, but most of them are beyond the scope of this specification ๐ซ
9.0 Schema, DTD, Data Model, and Valid Examples ๐
here's the whole collection of goodies you can check out ๐
- XML Signature Schema Instance:
http://www.w3.org/TR/2000/CR-xmldsig-core-20001031/xmldsig-core-schema.xsd. This is a valid XML schema instance based on the 20000922 Schema/DTD [XML-Schema] โจ - XML Signature DTD:
http://www.w3.org/TR/2000/CR-xmldsig-core-20001031/xmldsig-core-schema.dtd๐ธ - RDF Data Model:
http://www.w3.org/TR/2000/CR-xmldsig-core-20001031/xmldsig-datamodel-20000112.gif๐ฆ - XML Signature Object Example:
http://www.w3.org/TR/2000/CR-xmldsig-core-20001031/signature-example.xml. This is a cryptographically invalid XML example that includes foreign content and validates under the schema. (It validates under the DTD when the foreign content is removed or the DTD is modified accordingly.) ๐ - RSA XML Signature Example:
http://www.w3.org/TR/2000/CR-xmldsig-core-20001031/signature-example-rsa.xml. An XML Signature example with generated cryptographic values by Merlin Hughes and validated by Gregor Karlinger ๐ฅ - DSA XML Signature Example:
http://www.w3.org/TR/2000/CR-xmldsig-core-20001031/signature-example-dsa.xml. Similar to above, but it uses DSA ๐
10.0 Definitions โจ
okay bestie, this is the glossary ๐๐ every term here has a very specific meaning in this spec, so let's get them all straight before we move on ๐
Authentication Code ๐
A value generated by applying a shared key to a message with a cryptographic algorithm. It has the properties of message authentication (integrity) but not signer authentication. So it proves the message wasn't changed, but not who sent it ๐ซถ
Authentication, Message ๐ก๏ธ
"A signature should identify what is signed, making it impracticable to falsify or alter either the signed matter or the signature without detection." [Digital Signature Guidelines, ABA] Basically, nobody can fake or quietly change what got signed, or the signature itself, without it being noticed ๐
Authentication, Signer ๐๏ธ
"A signature should indicate who signed a document, message or record, and should be difficult for another person to produce without authorization." [Digital Signature Guidelines, ABA] This one is the "who did this" energy, and it's giving security ๐
Core ๐ง
The syntax and processing defined by this specification, including core validation. We use this term to tell our stuff apart from other markup, processing, and application semantics, so nobody mixes up the vibes โจ
Data Object (Content/Document) ๐ฆ
The actual binary/octet data being operated on (transformed, digested, or signed) by an application -- frequently an HTTP entity [HTTP]. Note that the proper noun Object designates a specific XML element. Sometimes we call a data object a document or a resource's content. The term element content is used to describe the data between XML start and end tags [XML]. The term XML document is used to describe data objects which conform to the XML specification [XML]. ๐ธ
Integrity ๐
The inability to change a message without also changing the signature value. See message authentication.
Object ๐
An XML Signature element where arbitrary (non-core) data can be placed. An Object element is just one type of digital data (or document) that can be signed via a Reference. ๐ฆ
Resource ๐
"A resource can be anything that has identity. Familiar examples include an electronic document, an image, a service (e.g., 'today's weather report for Los Angeles'), and a collection of other resources.... The resource is the conceptual mapping to an entity or set of entities, not necessarily the entity which corresponds to that mapping at any particular instance in time. Thus, a resource can remain constant even when its content---the entities to which it currently corresponds---changes over time, provided that the conceptual mapping is not changed in the process." [URI]
To avoid a collision with the term entity in the URI and XML specs, we use data object, content, or document for the actual bits being operated on ๐
Signature โ๏ธ
Formally speaking, a value generated by applying a private key to a message with a cryptographic algorithm, so that it has the properties of signer authentication and message authentication (integrity). Sometimes we use the term signature more loosely so it also covers Authentication Code values, but we're careful to make the distinction whenever signer authentication matters to the explanation. A signature may be (non-exclusively) described as detached, enveloping, or enveloped. ๐ซง
Signature, Application ๐งโ๐ป
An application that implements the MANDATORY (REQUIRED/MUST) portions of this specification. These conformance requirements cover the structure of the Signature element type and its children (including SignatureValue), plus mandatory-to-support algorithms. ๐
Signature, Detached ๐ชฝ
The signature is over content external to the Signature element, and it can be identified via a URI or transform. That means the signature is "detached" from the content it signs. This definition typically applies to separate data objects, but it also includes the case where the Signature and the data object live in the same XML document as sibling elements. ๐
Signature, Enveloping ๐
The signature is over content found within an Object element of the signature itself. The Object (or its content) is identified via a Reference (through a URI fragment identifier or a transform). ๐ง
Signature, Enveloped ๐
The signature is over the XML content that contains the signature as an element. That content provides the root XML document element. Obviously, enveloped signatures must take care not to include their own value in the calculation of the SignatureValue.
Enveloped signatures can't include their own value when computing the SignatureValue. That would be a whole circular mess, bestie ๐
Transform ๐
The processing of an octet stream from source content into derived content. Typical transforms include XML Canonicalization, XPath, and XSLT. โญ
Validation, Core โ
The core processing requirements of this specification that call for signature validation and SignedInfo reference validation. ๐
Validation, Reference ๐
The hash value of the identified and transformed content, specified by Reference, matches its specified DigestValue. It's a match, so we're good ๐
Validation, Signature ๐งพ
The SignatureValue matches the result of processing SignedInfo with CanonicalizationMethod and SignatureMethod as specified in Core Validation (section 3.2). โจ
Validation, Trust/Application ๐ซถ
The application decides that the semantics associated with a signature are valid. For example, an application may validate the time stamps or the integrity of the signer key. That behavior is external to this core specification, so it's the app's call, not the spec's ๐
11.0 References โจ
okay bestie, this is the reading list ๐ every source the spec leans on, so you can go check the originals. I've kept each label, title, author list, date and link exactly as they were (I just joined the URLs that got split across lines, since those were only line-wrapping) ๐ซถ
- ABA: Digital Signature Guidelines.
http://www.abanet.org/scitech/ec/isc/dsgfree.html - Bourret: Declaring Elements and Attributes in an XML DTD. Ron Bourret.
http://www.informatik.tu-darmstadt.de/DVS1/staff/bourret/xml/xmldtd.html - DOM: Document Object Model (DOM) Level 1 Specification. W3C Recommendation. V. Apparao, S. Byrne, M. Champion, S. Isaacs, I. Jacobs, A. Le Hors, G. Nicol, J. Robie, R. Sutor, C. Wilson, L. Wood. October 1998.
http://www.w3.org/TR/1998/REC-DOM-Level-1-19981001/๐ - DSS: FIPS PUB 186-1. Digital Signature Standard (DSS). U.S. Department of Commerce/National Institute of Standards and Technology.
http://csrc.nist.gov/fips/fips1861.pdf - HMAC: Krawczyk, H., Bellare, M. and R. Canetti, "HMAC: Keyed-Hashing for Message Authentication", RFC 2104, February 1997.
http://www.ietf.org/rfc/rfc2104.txt - HTTP: Fielding, R., Gettys, J., Mogul, J., Frystyk, H., Masinter, L., Leach, P. and T. Berners-Lee, "Hypertext Transfer Protocol -- HTTP/1.1", RFC 2616, June 1999.
http://www.ietf.org/rfc/rfc2616.txt๐ธ - KEYWORDS: Bradner, S., "Key words for use in RFCs to Indicate Requirement Levels", BCP 14, RFC 2119, March 1997.
http://www.ietf.org/rfc/rfc2119.txt๐ฅ the one that explains all those capital words we've been slaying all along - LDAP-DN: Wahl, M., Kille, S. and T. Howes, "Lightweight Directory Access Protocol (v3): UTF-8 String Representation of Distinguished Names", RFC 2253, December 1997.
http://www.ietf.org/rfc/rfc2253.txt - MD5: Rivest, R., "The MD5 Message-Digest Algorithm", RFC 1321, April 1992.
http://www.ietf.org/rfc/rfc1321.txt - MIME: Freed, N. and N. Borenstein, "Multipurpose Internet Mail Extensions (MIME) Part One: Format of Internet Message Bodies", RFC 2045, November 1996.
http://www.ietf.org/rfc/rfc2045.txt๐ - NFC: TR15. Unicode Normalization Forms. M. Davis, M. Drst. Revision 18: November 1999.
- PGP: Callas, J., Donnerhacke, L., Finney, H. and R. Thayer, "OpenPGP Message Format", November 1998.
http://www.ietf.org/rfc/rfc2440.txt - RANDOM: Eastlake, D., Crocker, S. and J. Schiller, "Randomness Recommendations for Security", RFC 1750, December 1994.
http://www.ietf.org/rfc/rfc1750.txt - RDF: RDF Schema W3C Candidate Recommendation. D. Brickley, R.V. Guha. March 2000.
http://www.w3.org/TR/2000/CR-rdf-schema-20000327/RDF Model and Syntax W3C Recommendation. O. Lassila, R. Swick. February 1999.http://www.w3.org/TR/1999/REC-rdf-syntax-19990222/๐ง - 1363: IEEE 1363: Standard Specifications for Public Key Cryptography. August 2000.
- PKCS1: Kaliski, B. and J. Staddon, "PKCS #1: RSA Cryptography Specifications Version 2.0", RFC 2437, October 1998.
http://www.ietf.org/rfc/rfc2437.txt - SAX: SAX: The Simple API for XML David Megginson et. al. May 1998.
http://www.megginson.com/SAX/index.html - SHA-1: FIPS PUB 180-1. Secure Hash Standard. U.S. Department of Commerce/National Institute of Standards and Technology.
http://csrc.nist.gov/fips/fip180-1.pdf - Unicode: The Unicode Consortium. The Unicode Standard.
http://www.unicode.org/unicode/standard/standard.html๐ - UTF-16: Hoffman, P. and F. Yergeau, "UTF-16, an encoding of ISO 10646", RFC 2781, February 2000.
http://www.ietf.org/rfc/rfc2781.txt - UTF-8: Yergeau, F., "UTF-8, a transformation format of ISO 10646", RFC 2279, January 1998.
http://www.ietf.org/rfc/rfc2279.txt - URI: Berners-Lee, T., Fielding, R. and L. Masinter, "Uniform Resource Identifiers (URI): Generic Syntax", RFC 2396, August 1998.
http://www.ietf.org/rfc/rfc2396.txt - URI-Literal: Hinden, R., Carpenter, B. and L. Masinter, "Format for Literal IPv6 Addresses in URL's", RFC 2732, December 1999.
http://www.ietf.org/rfc/rfc2732.txt - URL: Berners-Lee, T., Masinter, L. and M. McCahill, "Uniform Resource Locators (URL)", RFC 1738, December 1994.
http://www.ietf.org/rfc/rfc1738.txt - URN: Moats, R., "URN Syntax" RFC 2141, May 1997.
http://www.ietf.org/rfc/rfc2141.txtDaigle, L., van Gulik, D., Iannella, R. and P. Faltstrom, "URN Namespace Definition Mechanisms", RFC 2611, June 1999.http://www.ietf.org/rfc/rfc2611.txt - X509v3: ITU-T Recommendation X.509 version 3 (1997). "Information Technology - Open Systems Interconnection - The Directory Authentication Framework" ISO/IEC 9594-8:1997. ๐
- XHTML 1.0: XHTML(tm) 1.0: The Extensible Hypertext Markup Language Recommendation. S. Pemberton, D. Raggett, et. al. January 2000.
http://www.w3.org/TR/2000/REC-xhtml1-20000126/ - XLink: XML Linking Language. Working Draft. S. DeRose, D. Orchard, B. Trafford. July 1999.
http://www.w3.org/1999/07/WD-xlink-19990726 - XML: Extensible Markup Language (XML) 1.0 Recommendation. T. Bray, J. Paoli, C. M. Sperberg-McQueen. February 1998.
http://www.w3.org/TR/1998/REC-xml-19980210 - XML-C14N: J. Boyer, "Canonical XML Version 1.0", RFC 3076, September 2000.
http://www.w3.org/TR/2000/CR-xml-c14n-20001026http://www.ietf.org/rfc/rfc3076.txt - XML-Japanese: XML Japanese Profile. W3C NOTE. M. MURATA April 2000
http://www.w3.org/TR/2000/NOTE-japanese-xml-20000414/ - XML-MT: Whitehead, E. and M. Murata, "XML Media Types", July 1998.
http://www.ietf.org/rfc/rfc2376.txt - XML-ns: Namespaces in XML Recommendation. T. Bray, D. Hollander, A. Layman. Janury 1999.
http://www.w3.org/TR/1999/REC-xml-names-19990114 - XML-schema: XML Schema Part 1: Structures Working Draft. D. Beech, M. Maloney, N. Mendelshohn. September 2000.
http://www.w3.org/TR/2000/WD-xmlschema-1-20000922/XML Schema Part 2: Datatypes Working Draft. P. Biron, A. Malhotra. September 2000.http://www.w3.org/TR/2000/WD-xmlschema-2-20000922/ - XML-Signature-RD: Reagle, J., "XML Signature Requirements", RFC 2907, April 2000.
http://www.w3.org/TR/1999/WD-xmldsig-requirements-19991014http://www.ietf.org/rfc/rfc2807.txt - XPath: XML Path Language (XPath)Version 1.0. Recommendation. J. Clark, S. DeRose. October 1999.
http://www.w3.org/TR/1999/REC-xpath-19991116 - XPointer: XML Pointer Language (XPointer). Candidate Recommendation. S. DeRose, R. Daniel, E. Maler.
http://www.w3.org/TR/2000/CR-xptr-20000607 - XSL: Extensible Stylesheet Language (XSL) Working Draft. S. Adler, A. Berglund, J. Caruso, S. Deach, P. Grosso, E. Gutentag, A. Milowski, S. Parnell, J. Richman, S. Zilles. March 2000.
http://www.w3.org/TR/2000/WD-xsl-20000327/xslspec.html - XSLT: XSL Transforms (XSLT) Version 1.0. Recommendation. J. Clark. November 1999.
http://www.w3.org/TR/1999/REC-xslt-19991116.html
12. Authors' Addresses ๐
here's who wrote it, and how to reach them ๐ฆ
Donald E. Eastlake 3rd Motorola, Mail Stop: M2-450 20 Forbes Boulevard Mansfield, MA 02048 USA
Phone: 1-508-261-5434 EMail: Donald.Eastlake@motorola.com
Joseph M. Reagle Jr., W3C Massachusetts Institute of Technology Laboratory for Computer Science NE43-350, 545 Technology Square Cambridge, MA 02139
Phone: 1.617.258.7621 EMail: reagle@w3.org
David Solo Citigroup 909 Third Ave, 16th Floor NY, NY 10043 USA
Phone: +1-212-559-2900 EMail: dsolo@alum.mit.edu
13. Full Copyright Statement โญ
the legal bit, kept word for word so nothing gets lost in translation ๐
Copyright (C) The Internet Society (2001). All Rights Reserved.
This document and translations of it may be copied and furnished to others, and derivative works that comment on or otherwise explain it or assist in its implementation may be prepared, copied, published and distributed, in whole or in part, without restriction of any kind, provided that the above copyright notice and this paragraph are included on all such copies and derivative works. However, this document itself may not be modified in any way, such as by removing the copyright notice or references to the Internet Society or other Internet organizations, except as needed for the purpose of developing Internet standards in which case the procedures for copyrights defined in the Internet Standards process must be followed, or as required to translate it into languages other than English.
The limited permissions granted above are perpetual and will not be revoked by the Internet Society or its successors or assigns.
This document and the information contained herein is provided on an "AS IS" basis and THE INTERNET SOCIETY AND THE INTERNET ENGINEERING TASK FORCE DISCLAIMS ALL WARRANTIES, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTY THAT THE USE OF THE INFORMATION HEREIN WILL NOT INFRINGE ANY RIGHTS OR ANY IMPLIED WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
Acknowledgement ๐ซถ
Funding for the RFC Editor function is currently provided by the Internet Society. and that's a wrap, bestie! ๐๐
๐ฆ where this page comes from
- ietf: rfc3075 2001-03
- ๐ girlified by claude-haiku-5-5 on : a language model's rewrite of the original, under its terms