DRAFT 11 -> FINAL?

Recordon, David drecordon at verisign.com
Tue Jan 30 21:13:08 UTC 2007


Thanks, fixed the HTML terminology  as a start.
http://openid.net/svn/diff.php?repname=specifications&path=%2Fauthentication%2F2.0%2Ftrunk%2Fopenid-authentication.xml&rev=292&sc=1

--David 

-----Original Message-----
From: specs-bounces at openid.net [mailto:specs-bounces at openid.net] On Behalf Of Claus Färber
Sent: Saturday, January 20, 2007 10:15 AM
To: specs at openid.net
Subject: Re: DRAFT 11 -> FINAL?

Dick Hardt <dick at sxip.com> schrieb/wrote:
> Are there any more issues with this specification:
> 	http://openid.net/specs/openid-authentication-2_0-11.html

> Can we make this final?

Ok, here are the problems I found during a quick review:

-----
| 4.1.1.  Key-Value Form Encoding
|
| A message in Key-Value form is a sequence of lines. Each line begins 
| with a key, followed by a colon, and the value associated with the 
| key. The line is terminated by a single newline (UCS codepoint 10, 
| "\n"). A key or value MUST NOT contain a newline and a key also MUST 
| NOT contain a colon.

While it's ok for keys to have a limited alphabet, not allowing them in the value may be a problem for future extensions (say, if AX wants to transfer a multiline postal address).

I don't think it's a good idea to invent a new format here. What's wrong with URI percent-encoding, which has to be implemented by OpenID software anyway?

OpenID could even use application/x-www-form-urlencoded for simple exchanges and multipart/form-data (HTML 4.01, section 17.13.4) for some aspects of AX (say, e.g. a JPEG photo).

Also, section 5.1.2 says that the response SHOULD be labelled as
"text/plain":

| 5.1.2.  Direct Response
|
| The body of a response to a Direct Request (Direct Request) consists 
| of an HTTP Response body in Key-Value Form (Key-Value Form Encoding).
| The content-type of the response SHOULD be "text/plain".

Together with section 4.1.1, this is incompatible with HTTP, the spec of which says (RFC 2616, section 3.7.1):

> When in canonical form, media subtypes of the "text" type use CRLF as 
> the text line break. HTTP relaxes this requirement and allows the 
> transport of text media with plain CR or LF alone representing a line 
> break when it is done consistently for an entire entity-body. HTTP 
> applications MUST accept CRLF, bare CR, and bare LF as being 
> representative of a line break in text media received via HTTP.

There are two options: Don't use a "text/*" subtype or bring the OpenID spec in line with HTTP (i.e. treat CRLF, CR and LF the same). If the later is chosen, "text/plain" must also be changed to "text/plain with a charset of UTF-8" as the default for HTTP is "ISO-8859-1" (RFC 2616, section 3.7.1).

-----

| 5.1.2.1.  Successful Responses
|
| A server receiving a valid request MUST send a response with an HTTP 
| status code of 200.

That may be incompatible with some HTTP caching/conditional response features. There is a slight chance that, for example, a 206 code might also be appropriate in some situations

-----

| 5.1.2.2.  Error Responses
|
| If a request is malformed or contains invalid arguments, the server 
| MUST send a response with a status code of 400.

This is incompatible with RFC 2616, which would also allow different error codes depending on the situation.

What about "... MUST send a response with an appropriate HTTP status code such as 400 (Bad Request)".

| The response body MUST be a Key-Value Form (Key-Value Form Encoding) 
| message with the following fields:
...
| *error
|     Value: A human-readable message indicating the cause of the error.

What about different languages?

This is actually tricky. The Accept-Language header from the user is not available to the OP if it is contacted by the RP directly, so the OP can't choose an appropriate language.

Note that RFC 2277 (= BCP 18) says:

> 4.2.  Requirement for language tagging
>
> Protocols that transfer text MUST provide for carrying information 
> about the language of that text.

While this technically isn't binding for a non-IETF spec, it's still an extremly good idea.

Same problem in 5.2.3 and 8.2.4.

-----

| 7.3.3.  HTML-Based Discovery
|
| HTML-Based discovery MUST be supported by Relying Parties. HTML-Based 
| discovery is only usable for discovery of Claimed Identifiers. OP 
| Identifiers must be XRIs or URLs that support XRDS discovery.
|
| To use HTML-Based discovery, an HTML document MUST be available at the 
| URL of the Claimed Identifier. In the HEAD section of the document:

It seems that it has been unclear to some implementers what "HEAD section" means. This is not surprising as the correct term is "HEAD element" (HTML 4.01, section 3.2.1).

|    A <LINK> tag MUST be included with attributes "rel" set to
|        "openid2.provider" and "href" set to an OP Endpoint URL
|    A <LINK> tag MAY be included with attributes "rel" set to
|       "openid2.local_id" and "href" set to the end user's OP-Local
|       Identifier

These should read "LINK element", not "<LINK> tag".

| The protocol version when HTML discovery is performed is "http:// 
| specs.openid.net/auth/2.0/signon".
|
| The host of the HTML document MAY be different from the end user's 
| OP's host.
|
| The "openid2.provider" and "openid2.local_id" URLs MUST NOT include 
| entities other than "&amp;", "&lt;", "&gt;", and "&quot;". Other 
| characters that would not be valid in the HTML document or that cannot 
| be represented in the document's character encoding MUST be escaped 
| using the percent-encoding (%xx) mechanism described in [RFC3986] 
| (Berners-Lee, T., "Uniform Resource Identifiers (URI): Generic 
| Syntax," .).

This is incompatible with HTML parsing rules.

First, there is only one character - &amp; - that is allowed in URIs but needs to be encoded within URLs. The other three are not valid in URIs (RFC 3986, section 2) anyway.

However, it is always legal in HTML documents to escape _any_ character, including 'a' as '&#97;' or '.' as '&#x2E;' (note that these are "numerical character references", not "character entity references").

I think the whole section is flawed and should be replaced with a small note as a warning:

  Note: If the "openid2.provider" and "openid2.local_id" contain an
  ampersand (&), this character MUST be escaped as "&amp;" according to
  HTML rules.

There should also be a normative reference to HTML parsing:

  The Relying Party MUST parse HTML/XHTML according to HTML/XHTML
  specifications.

  Note: In HTML (but not in XHTML), some elements such as HTML, HEAD or
  BODY have optional start and end tags. Any character can be encoded
  using a numeric entity reference or an entity character reference.

BTW, good HTML parsers are mandatory to protect against HTML injection attacks. An ad-hoc parser might simply fall for something like that:

  <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN">
  <link rel=openid2.provider href='http://openid.example.com/~user'>
  <title>Nice test</title>
  <form action="doit">
  <p>Send me your comment:
  <input type=text name=comment value='<html><head><link rel=openid2.provider href="http://bogous.example.net"></head>'>
  <input type=submit>
  </form>

Yes, this is valid HTML and yes, a HTML "sanitizer" that intends to do the shortest possible representation would produce something like this.

-----

| 8.1.2.  Diffie-Hellman Request Parameters
|
| The following parameters are common to requests whose requested 
| association session type is "DH-SHA1" or "DH-SHA256":
|
| * openid.dh_modulus
|   Value: base64(btwoc(p))
...
| NOTE: The 'btwoc' function is defined in Section 4.2 (Integer 
| Representations).

And the 'base64' function? Note that there are different variants of
Base64 wrt to padding, ("="), line endings (allowed and/or required), and alphabet.

| 8.2.2.  Unencrypted Response Parameters
|
| * mac_key
|   The MAC key (shared secret) for this association, Base 64 [RFC3548]
|   encoded.

Even RFC 3548 has two variants. Which one? Section 3?

-----

| 8.4.1.  No-Encryption Association Sessions
|
| In a "no-encryption" association session, the OP sends the association 
| MAC key in plain-text to the Relying Party. This makes it possible for 
| an eavesdropper to intercept the key, and forge messages to this 
| Relying Party. Therefore, "no-encryption" association sessions SHOULD 
| NOT be used unless the messages are using transport layer encryption.
| NOT be used unless the messages are using transport layer encryption.

"... and the Relying Party has been able to verify the OP's server certificate".

Encryption does not prevent MITM attacks.

-----

| 9.2.  Realms
|
| A realm pattern is a URL, with the following changes:
|
|   * A realm MUST NOT contain a URI fragment
|   * A realm MAY contain a wild-card at the beginning of the URL
|     authority section. A wild-card consists of the characters "*."
|     prepended to the DNS name in the authority section of the URL.

That's "reg-name", not "authority" in RFC 3986.

| A URL matches a realm if:
|    * The URL scheme and port of the URL are identical to those in the
|       realm. See [RFC3986], section 3.1 for rules about URI matching.
|    * The URL's path is equal to or a sub-directory of the realm's
|      path.
|    * Either:
|        1. The realm's domain contains the wild-card characters "*.",
|           and the trailing part of the URL's domain is identical to
|           the part of the realm following the "*." wildcard, or
|        2. The URL's domain is identical to the realm's domain

So "bogousexample.com" matches "*.example.com"?

     * Either:
         1. The URL's reg-name is identical to the realm's reg-name.
         2. The realm's reg-name starts with the wildcard characters
            "*.", and the URL's reg-name is identical to the part of
             the realm's reg-name following the initial "*.".
         2. The realm's reg-name starts with the wildcard characters
            "*.", and the URL's reg-name ends with a dot (".") and the
             part of the realm's reg-name following the initial "*.".

-----

| 11.1.  Verifying the Return URL
|
| To verify that the "openid.return_to" URL matches the URL that is processing this assertion:
|
|   * The URL scheme, authority, and path MUST be the same between the two URLs.
|   * Any query parameters that are present in the "openid.return_to"
|     URL MUST also be present with the same values in the URL of the
|     HTTP request the RP received.

http://example.com/do?dosomethingharmless=yes

matches

http://example.com/do?dosomethingharmless=yes&deleteverything=YES

    * Any query parameters that are not present in the
      "openid.return_to" URL but are present in the URL of the
      HTTP request the RP received MUST start with "openid."

Claus


_______________________________________________
specs mailing list
specs at openid.net
http://openid.net/mailman/listinfo/specs



More information about the specs mailing list