haskell / haskell/HTTP

digest auth with qop=auth is violating the RFC

Offen
#54 1 Kommentar 0 Reaktionen 0 zugewiesene Personen Auf GitHub ansehen
Vorherrschende Sprache
Haskell
Sterne
186
Forks
59
PR-Merge-Kennzahlen
Keine gemergten PRs in 30 T.

Beschreibung

RFC2617 https://tools.ietf.org/html/rfc2617 says about `qop` and related fields (key bits highlighted):

> qop
> Indicates what "quality of protection" the client has applied to
> the message. If present, its value MUST be one of the alternatives
> the server indicated it supports in the WWW-Authenticate header.
> These values affect the computation of the request-digest. Note
> that this is a single token, not a quoted list of alternatives as
> in WWW- Authenticate. This directive is optional in order to
> preserve backward compatibility with a minimal implementation of
> RFC 2069 [6], but SHOULD be used if the server indicated that qop
> is supported by providing a qop directive in the WWW-Authenticate
> header field.
>
> cnonce
> This **MUST be specified if a qop directive is sent (see above)**, and
> MUST NOT be specified if the server did not send a qop directive in
> the WWW-Authenticate header field. The cnonce-value is an opaque
> quoted string value provided by the client and used by both client
> and server to avoid chosen plaintext attacks, to provide mutual
> authentication, and to provide some message integrity protection.
> See the descriptions below of the calculation of the response-
> digest and request-digest values.
>
> nonce-count
> This **MUST be specified if a qop directive is sent (see above)**, and
> MUST NOT be specified if the server did not send a qop directive in
> the WWW-Authenticate header field. The nc-value is the hexadecimal
> count of the number of requests (including the current request)
> that the client has sent with the nonce value in this request. For
> example, in the first request sent in response to a given nonce
> value, the client sends "nc=00000001". The purpose of this
> directive is to allow the server to detect request replays by
> maintaining its own copy of this count - if the same nc-value is
> seen twice, then the request is a replay. See the description
> below of the construction of the request-digest value.

That is, if the client sends `qop=auth` then it **MUST** also send `nc=xxx` and `cnonce=xxx`. Servers are well within their right to reject requests without these as malformed.

Currently the HTTP package does not support the nc or cnonce fields, and yet it will automatically send `qop=auth` if the server offered it. Either this support should be disabled or the nc/cnonce support should be added. That is it should either follow RFC2069 (which has no notion of `qop`) or RFC2617 (which introduces `qop` and its related directives) but not a partial mixture of the two.

We currently have a problem with the hackage-server https://github.com/haskell/hackage-server/pull/199 where we want to support RFC2617 style digest auth (because a certain browser only supports the newer RFC), but if we send `qop=auth` then the HTTP package (and thus cabal etc) return broken responses. The server is currently correctly rejecting requests that use `qop=auth` but without the other required fields. We will probably have to relax that and allow these incorrect requests. But other servers may not be so forgiving, and we should fix it. The easiest thing would be to simply stop sending `qop=auth`, e.g.

``` diff
diff --git a/Network/HTTP/Auth.hs b/Network/HTTP/Auth.hs
index 4af0d67..5dad7cc 100644
--- a/Network/HTTP/Auth.hs
+++ b/Network/HTTP/Auth.hs
@@ -95,7 +95,8 @@ withAuthority a rq = case a of
-- plus optional stuff:
, fromMaybe "" (fmap (\ alg -> ",algorithm=" ++ quo (show alg)) (auAlgorithm a))
, fromMaybe "" (fmap (\ o -> ",opaque=" ++ quo o) (auOpaque a))
- , if null (auQop a) then "" else ",qop=auth"
+ --TODO: we currently do not support qop=auth or auth-int
+ -- if we send qop=auth then we MUST also send 'nc' and 'cnonce'
]
```

Beitragsleitfaden

Für dieses Repository ist kein Beitragsleitfaden indexiert

Rechercherichtung

Beginne in Network/HTTP/Auth.hs bei withAuthority, wo qop=auth zum Authorization-Header hinzugefügt wird. Lies die RFC2617-Anforderungen in diesem Issue und untersuche die umgebenden Auth-Felder. Als erledigt gilt, dass das Paket entweder keine unvollständige qop=auth-Antwort mehr ausgibt oder die erforderlichen nc- und cnonce-Felder bereitstellt; überprüfe das resultierende Digest-Auth-Verhalten.

Vom Indexierungsmodell aus dem Issue-Text verfasst.

Bewertung

Tech-Stack
haskell
Bereich
authentication, backend
Issue-Typ
Bug
Schwierigkeit
2/5
Geschätzter Aufwand
1-3 Stunden
Aktivitätsstatus
Veraltet
Klarheit
Klar beschrieben
Anfängerfreundlichkeit
45/100

Neue Issues direkt in Ihr Postfach

Eine kurze Übersicht über anfängerfreundliche GitHub-Issues.