In the past, after logging in some Jabber clients sent one &xep0030; and one &xep0092; request to each entity from which they received presence. That "disco/version flood" resulted in an excessive use of bandwidth and was impractical on a larger scale, particularly for users with large rosters. Therefore this document defines a more robust and scalable solution: namely, a presence-based mechanism
In the past, after logging in some Jabber clients sent one &xep0030; and one &xep0092; request to each entity from which they received presence. That "disco/version flood" resulted in an excessive use of bandwidth and was impractical on a larger scale, particularly for users with large rosters. Therefore this document defines a more robust and scalable solution: namely, a presence-based mechanism
This section provides a friendly introduction to entity capabilities ("caps").
@@ -147,7 +148,7 @@ ver='SrFo9ar2CCk2EnOH4q4QANeuxLQ='/> ]]> -The 'node' attribute represents the client software Romeo is using. The 'ver' attribute is a specially-constructed string that represents the entity's service discovery identity (category and type as registered at &DISCOCATEGORIES; as well as, optionally, the service discovery name) and supported features (as registered at &DISCOFEATURES; as well as, optionally, &xep0128; data registered at &FORMTYPES;).
+The 'node' attribute represents the client software Romeo is using. The 'ver' attribute is a specially-constructed string (called a "verification string") that represents the entity's service discovery identity (category and type as registered at &DISCOCATEGORIES;, as well as, optionally, xml:lang and name) and supported features (as registered at &DISCOFEATURES; as well as, optionally, extended service discovery information data registered at &FORMTYPES;).
At this point, your client has no idea what the capabilities are of someone with a version string 'SrFo9ar2CCk2EnOH4q4QANeuxLQ='. Your client therefore sends a service discovery query to Romeo, asking what his client can do.
+ ver='OSkaDqG4Q46zrXf5G6WSjfzgzGo='/>
]]>
... or the following presence ...
@@ -220,7 +221,7 @@The protocol defined herein addresses the following requirements:
** Note: Before version 1.4 of this specification, the 'ver' attribute was used to specify the released version of the software; while the values of the 'ver' attribute that result from use of the algorithm specified herein are backwards-compatible, applications SHOULD appropriately handle the Legacy Format.
-In order to help prevent poisoning of entity capabilities information, the value of the 'ver' attribute MUST be generated according to the following method.
-Note: All sorting operations MUST be performed using "i;octet" collation as specified in Section 9.3 of &rfc4790;.
-Consider an entity whose category is "client", whose service discovery type is "pc", whose service discovery name is "Exodus 0.9.1", and whose supported features are "http://jabber.org/protocol/disco#info", "http://jabber.org/protocol/disco#items", and "http://jabber.org/protocol/muc". Using the SHA-1 algorithm, the value of the 'ver' attribute would be generated as follows:
-Consider a more complex example, where the entity includes several identities (with the service discovery name in different languages) as well as extended information formatted according to XEP-0128.
-
+
+
+ In order to help prevent poisoning of entity capabilities information, the value of the verification string MUST be generated according to the following method.
+ Note: All sorting operations MUST be performed using "i;octet" collation as specified in Section 9.3 of &rfc4790;.
+
+ - Initialize an empty string S.
+ - Sort the service discovery identities
A registry of service discovery identities is located at &DISCOCATEGORIES;. by category and then by type (if it exists) and then by xml:lang (if it exists), formatted as CATEGORY '/' [TYPE] '/' [LANG] '/' [NAME]. Note that each slash is included even if the TYPE, LANG, or NAME is not included.
+ - For each identity, append the 'category/type/lang/name' to S, followed by the '<' character.
+ - Sort the supported service discovery features.
A registry of service discovery features is located at &DISCOFEATURES;.
+ - For each feature, append the feature to S, followed by the '<' character.
+ - If the service discovery information response includes XEP-0128 data forms, sort the forms by the FORM_TYPE field.
+ - For each extended service discovery information form:
+
+ - Append the value of the FORM_TYPE field, followed by the '<' character.
+ - Sort the fields by the value of the "var" attribute.
+ - For each field:
+
+ - Append the value of the "var" attribute, followed by the '<' character.
+ - Sort values by the XML character data of the <value/> element.
+ - For each <value/> element, append the XML character data, followed by the '<' character.
+
+
+
+
+ - Compute ver by hashing S using the algorithm specified in the 'hash' attribute (e.g., SHA-1 as defined in &rfc3174;). The hashed data MUST be generated with binary output and encoded using Base64 as specified in Section 4 of &rfc4648; (note: the Base64 output MUST NOT include whitespace and MUST set padding bits to zero).
The OpenSSL command for producing such output with SHA-1 is "echo -n 'S' | openssl dgst -binary -sha1 | openssl enc -nopad -base64".
+
+
+
+ Consider an entity whose category is "client", whose service discovery type is "pc", whose service discovery name is "Exodus 0.9.1", and whose supported features are "http://jabber.org/protocol/disco#info", "http://jabber.org/protocol/disco#items", and "http://jabber.org/protocol/muc". Using the SHA-1 algorithm, the verification string would be generated as follows:
+
+ - S = ''
+ - Only one identity: "client/pc"
+ - S = 'client/pc//Exodus 0.9.1<'
+ - Sort the features: "http://jabber.org/protocol/disco#info", "http://jabber.org/protocol/disco#items", "http://jabber.org/protocol/muc".
+ - S = 'client/pc//Exodus 0.9.1<http://jabber.org/protocol/disco#info<http://jabber.org/protocol/disco#items<http://jabber.org/protocol/muc<'
+ - ver = SrFo9ar2CCk2EnOH4q4QANeuxLQ=
+
+
+
+ Consider a more complex example, where the entity includes several identities (with the service discovery name in different languages) as well as extended information formatted according to XEP-0128.
+
<iq from='benvolio@capulet.lit/230193'>
id='disco1'
to='juliet@capulet.lit/chamber'
type='result'>
<query xmlns='http://jabber.org/protocol/disco#info'
- node='http://psi-im.org#P0wEGAHIj5lRBc5Oa872bmRB8Bg='>
- <identity xml:lang='en' category='client' name='Psi' type='pc'/>
- <identity xml:lang='el' category='client' name='Ψ' type='pc'/>
+ node='http://psi-im.org#OSkaDqG4Q46zrXf5G6WSjfzgzGo='>
+ <identity xml:lang='en' category='client' name='Psi 0.9.1' type='pc'/>
+ <identity xml:lang='el' category='client' name='Ψ 0.9.1' type='pc'/>
<feature var='http://jabber.org/protocol/disco#info'/>
<feature var='http://jabber.org/protocol/disco#items'/>
<feature var='http://jabber.org/protocol/muc'/>
<x xmlns='jabber:x:data' type='result'>
<field var='FORM_TYPE' type='hidden'>
- <value>urn:xmpp:dataforms:clientinfo</value>
+ <value>urn:xmpp:dataforms:softwareinfo</value>
</field>
<field var='ip_version'>
<value>ipv4</value>
@@ -316,7 +328,10 @@
<value>Mac</value>
</field>
<field var='os_version'>
- <value>OS X Mach-O</value>
+ <value>10.5.1</value>
+ </field>
+ <field var='software'>
+ <value>Psi</value>
</field>
<field var='software_version'>
<value>0.11</value>
@@ -324,18 +339,51 @@
</x>
</query>
</iq>
-
- Using the SHA-1 algorithm, the value of the 'ver' attribute would be generated as follows:
-
- - S = ''
- - Two identities: "client/pc/Psi" and "client/pc/Ψ"
- - S = 'client/pc/el/Ψ<client/pc/en/Psi<'
- - Sort the features: "http://jabber.org/protocol/disco#info", "http://jabber.org/protocol/disco#items", "http://jabber.org/protocol/muc".
- - Sort and append the extended information: "ip_version<ipv4<ipv6", "os<Mac", "os_version<OS X 10.5.1", "software_version<0.11".
- - S = 'client/pc/el/Ψ<client/pc/en/Psi<http://jabber.org/protocol/disco#info<http://jabber.org/protocol/disco#items<http://jabber.org/protocol/muc<
- ip_version<ipv4<ipv6<os<Mac<os_version<OS X 10.5.1<software_version<0.11<'
- - ver = P0wEGAHIj5lRBc5Oa872bmRB8Bg=
-
+
+ Using the SHA-1 algorithm, the verification string would be generated as follows (note: line breaks in the verification string are included only for the purposes of readability):
+When an entity receives a value of the 'ver' attribute that appears to be a verification string generated in accordance with the generation method defined in this specification, it MUST process the 'ver' according to the following method.
+If the supported features change during a generating entity's presence session (e.g., a user installs an updated version of a client plugin), the application MUST recompute the 'ver' attribute and SHOULD send a new presence broadcast.
+If the supported features change during a generating entity's presence session (e.g., a user installs an updated version of a client plugin), the application MUST recompute the verification string and SHOULD send a new presence broadcast.
The requesting entity MUST check the identities and supported features against the 'ver' value by calculating the hash as described under Generation of the ver Attribute and making sure that the values match. If the values do not match, the requesting entity MUST NOT accept or cache the 'ver' value as reliable and SHOULD check the service discovery identity and supported features of another generating entity who advertises that value (if any). This helps to prevent poisoning of entity capabilities information.
+Note: If the generating entity incorporated multiple identities with different xml:lang values in its verification string, it MUST return all of the identities even if the request specified a particular xml:lang.
@@ -408,7 +456,7 @@ ver='ItBTI0XLDFvVxZ72NQElAzKS9sU='> ]]> -When a connected client or peer server sends a service discovery information request to determine the entity capabilities of a server that advertises capabilities via the stream feature, the requesting entity MUST send the disco#info request to the server's JID as provided in the 'from' attribute of the response stream header (the 'from' attribute was recommended by &rfc3920; and is required by &rfc3920bis;). To enable this functionality, a server that advertises support for entity capabilities MUST provide a 'from' address in its response stream headers, in accordance with rfc3921bis.
+When a connected client or peer server sends a service discovery information request to determine the entity capabilities of a server that advertises capabilities via the stream feature, the requesting entity MUST send the disco#info request to the server's JID as provided in the 'from' attribute of the response stream header (the 'from' attribute was recommended by &rfc3920; and is required by &rfc3920bis;). To enable this functionality, a server that advertises support for entity capabilities MUST provide a 'from' address in its response stream headers, in accordance with rfc3920bis.
An application should maintain a list of hashing algorithms it supports, which MUST include the Mandatory-to-Implement Technologies. If the application receives a caps notification that was generated using one of its supported hashing algorithms, then it SHOULD verify the hash and cache the value globally. If the application receives a caps notification generated using a hash it does not support, then it SHOULD NOT attempt to verify the hash but SHOULD cache it on a per-JID basis (i.e., it SHOULD send a service discovery information request to the JID and cache the results for that JID only).
+An application SHOULD maintain a list of hashing algorithms it supports, which MUST include the algorithm or algorithms listed in the Mandatory-to-Implement Technologies section of this document.
It is RECOMMENDED for an application that processes entity capabilities information to cache associations between the 'ver' attribute and discovered features within the scope of one presence session. This obviates the need for extensive service discovery requests within a session.
+It is RECOMMENDED for an application that processes entity capabilities information to cache associations between the verification string and discovered identity+features within the scope of one presence session. This obviates the need for extensive service discovery requests within a session.
It is OPTIONAL for an application to cache associates across presence sessions. However, since this obviates the need for extensive service discovery requests at the beginning of a session, such caching is strongly encouraged, especially in bandwidth-constrained environments.
It currently seems extremely unlikely that an attacker could meet all of the foregoing conditions in the foreseeable future. However, the XMPP Council shall continue to monitor the state of cryptanalysis regarding the mandatory-to-implement hash function as well as the possibility that any vulnerabilities in that function might lead to practical threats against the entity capabilities protocol. If and when it becomes practical (or even possible) to launch effective preimage attacks against the entity capabilities protocol, the XMPP Council shall consider updating this specification to change the mandatory-to-implement hashing algorithm to a safer technology.
Adherence to the method defined in the Generation of the ver Attribute section of this document for both generation and checking of the 'ver' attribute helps to guard against poisoning of entity capabilities information by malicious or improperly implemented entities.
-If the value of the 'ver' attribute is a hash as defined herein (i.e., if the 'ver' attribute is not generated according to the Legacy Format), inclusion of the 'hash' attribute is REQUIRED. Knowing explicitly that the value of the 'ver' attribute is a hash enables the recipient to avoid spurious notification of invalid or poisoned hashes.
+Adherence to the method defined in the Verification String section of this document for both generation and processing of the 'ver' attribute helps to guard against poisoning of entity capabilities information by malicious or improperly implemented entities.
+If the value of the 'ver' attribute is a verification string as defined herein (i.e., if the 'ver' attribute is not generated according to the Legacy Format), inclusion of the 'hash' attribute is REQUIRED. Knowing explicitly that the value of the 'ver' attribute is a verification string enables the recipient to avoid spurious notification of invalid or poisoned hashes.
Use of entity capabilities might make it easier for an attacker to launch certain application-specific attacks, since the attacker could more easily determine the type of client being used as well as its capabilities. However, since most clients respond to Service Discovery and Software Version requests without performing access control checks, there is no new vulnerability. Entities that wish to restrict access to capabilities information SHOULD use &xep0016; to define appropriate communications blocking (e.g., an entity MAY choose to allow IQ requests only from "trusted" entities, such as those with whom it has a presence subscription of "both"); note, however, that such restrictions may be incompatible with the recommendation regarding Directed Presence.