In line ! > 22 feb 2016 kl. 05:08 skrev John Bradley <ve7...@ve7jtb.com>: > >> On Feb 22, 2016, at 9:22 AM, Nat Sakimura <n-sakim...@nri.co.jp> wrote: >> >> The risk impact of [case2] is more OAuth specific. The token is stolen as >> the token is going to be sent to a rogue resource, and the resource can use >> that to obtain the resource that was supposed to be only available to the >> proper client. >> >> The risk impact of [case3] is the most grave among these three. Now the >> attacker can create his own client that impersonates the compromised client. >> >> OAuth-mix-up >> --------------------------- >> OAuth-mix-up draft gives one way of addressing [case2] by introducing a new >> concept of “issuer” and “discovery” to RFC6749. It also returns client_id >> and verifies it in 4.2, but if the BadAS has assigned a same client_id to >> the client, it does not help. > > Client_id are not guaranteed to be unique. They need to be name spaced by > the AS. In OAuth currently we have no name for the AS this makes that > difficult, the client can use the authorization endpoint URI, but that logic > may well break in multi tenant situations. Having a clear issuer string > makes it easier for the client.
I stumbled over exactly this point when I made my implementation follow the Mix-Up draft. If not discovery is involved I think an AS has to have a name which is different from the endpoint URIs. >> One of the issue with this approach is that the central notion of “issuer” >> is new to the existing servers and clients. The verification rule in 4.1 >> states “Compare the issuer URL for the authorization server that the client >> received when it registered at the authorization server”, but in most >> existing pure OAuth cases, there is no such thing, so you cannot compare. >> This means that you would have to re-register, and if you are doing that, >> the per-AS redirect_uri seems to be a much simpler solution. > > The client developers I have talked to really hate per AS redirect URI as > being too awkward for deployments. I on the other hand found it quite easy to do per AS redirect URIs, so it might well be implementation dependent rather then contextual. >> >> Per AS Redirect URI >> -------------------------------- >> This does not involve wire protocol changes. It just adds requirements on >> the redirect uri. This by far is the simplest solution for [case2] (and >> [case1]), IMHO. >> >> Again, it is not a general framework for finding out tainted communication, >> so it may have other holes. > > This is probably the hardest for the client developer and for the deployer. > Yes it is simplest from a spec point of view. > We need more developer feedback on this. As I said above I found this quite simple to implement. >> (Extended) PKCE >> --------------------------------- >> To begin with, it works only with code flow. There has to be something else >> to deal with implicit flow. >> >> PKCE binds the authorization request/response to the token request. >> If used with a confidential client, it seems to mitigate the vulnerability. >> John points out that it is not the case. I must be missing something here… >> but my logic goes like: >> >> >> 1. The good client creates code_challenge-v and >> code_verifier-v=S256(code_challenge-v) and sends the client_id-v + >> code_challenge-v + state to the BadAS Authz EP. >> 2. BadAS as a client prepares a code_verifier-b and >> code_challenge-b=S256(code_verifer-b). >> 3. BadAS redirects to GoodAS with the client_id-v + code_challenge-b + >> state-v. >> 4. GoodAS stores the code_challenge-b. >> 5. GoodAS returns code-v + state-v to the client’s redirect uri. >> 6. The client finds the AS from the state and sends code-v + >> code_verifier-v + secret-b to the BadAS token endpoint. Now, code-v and >> code_verifer-v is phished. >> >> Now the attacker tries to use the code-v and code_verifier-v. >> >> ### Case A: >> 7. The BadAS as a client sends client_id-v + … but he does not have >> client secret for the good client, so it fails. >> >> ### Case B: >> 8. The BadAS as a client sends client_id-b + code-v + code_verifier-b + >> secret-b etc. to GoodAS. >> 9. GoodAS verifies the code_verifier-b is associated with code-v, but >> that code-v is not associated with client_id-b, so the token request fails. >> >> ### Case C: cut-n-paste >> 10. The attacker launches cut-n-paste attack by replacing the code-b with >> code-v. >> 11. The verifiers does not match, so fails. >> >> Please let me know what I am missing. > > In a step 0 the attacker has the good client create another request in the > attackers user agent to get state-0 and code_challange-0 > > Step 2 is not required. > Step 3 Bad AS redirects to good AS with client_id_v + state-v + > code_challenge-0 > Step 4 GoodAS stores code_challenge-0 > Step 5 GoodAS returns code-v + state-v to the clients redirect_uri > Step 6 The client finds the AS from the state and sends code-v + > code_verifier-v + secret-b to the BadAS token endpoint. Now, code-v and > code_verifer-v is phished. > > Case C1 : cut and paste > 10. The attacker launches cut-n-paste attack by inserting code-v into a > response using state-0 > 11. The client sends code-v and based on state-0 it sends code_verifyer-0 to > the good AS token endpoint. > 12. The GoodAS verifies that code-verifyer-0 is correct for code_challange-0 > that it bound to code in step 4 > 13. The GoodAS receives RT + AT. > 14. The attacker has now used the client to bind the users resource to it’s > account and is transferring money or looking at your data. > > This could be 3rd party financial app like Mint as an example or photos or > any other PII that could then be used to escalate identity theft. > > This variation of the attack combining cut and paste with confused client was > not mentioned in the research papers. > > I found it looking to see if PKCE could be used to mitigate the confused > client attack. > > As I mentioned in a response to William, while the current PKCE Challenge > methods only make the attack harder by forcing the attacker to get the client > to make a step 0 request to get a code_challenge to use in the request, we > could define a new challenge method that would be effective. > > That would remove the need to have a separate mechanism to prevent cut and > paste. > > The problem is that the PKCE challenge is independent of state so becomes > vulnerable to the confused client. > > What we would need to do is include state in the challenge so that if the AS > receives mismatched state and code_challange in step 3 the verification of > code verifier will fail. Effectively combining the cut and paste mitigation > with PKCE. > > I haven’t had time to write this up, but if the code_challenge == SHA256 > (SHA256(state) || token_endpoint URI || Authorization_endpoint URI || > client_id || code-veriyer) , then the attacker could not change state, > client_id, or token_endpoint independently of code_challenge. (note I am > using a hash of state to make storage size deterministic for the AS on the > grounds that the client already needs to be able to do the hash) (Some > attacks change the client_id in the request so I am including it in the hash) > > This is slightly more complicated than than S256, but not that much. I wish > I had thought of this when we were doing PKCE. Hit me with the stupid > stick, my fault. > > I don’t know if it stops all the confused client attacks though. > > If the client is confidential then it gives up it’s client secret assuming > compromised registration, so we can’t really count on that for symmetric > client authentication. > > By including the token endpoint in the comparison if the client is sending > the code to the attacker the client will use a different token endpoint_uri > in to calculate the code_challenge than the GoodAS will use to verify it. > This would stop both cut and paste as well as stopping the attacker from > using the code if they get it. The attacker can’t get Secret for state-0, > so it can’t create code_challenge that would be valid. > > This stops the registration attack where the client gets a bad AS discovery > endpoint that has all the Good AS info including dynamic registration > endpoint but the bad AS token endpoint. The bad AS would get the token, > client_secret and code_verier, but will fail pkce verification because the > token endpoint will be wrong. > > The attack where the client registers with the good AS but with bad token > endpoint and Authorization endpoint gives the attacker the ability to change > the code_challenge that the Good AS is going to see. It would need to make > a new challenge using state and the GoodAS token endpoint and it’s client_id. > To do that it needs the code_verifier to use to calculate the hash to use as > the code_challenge value. As long as the client is not tricked into > accepting a replay of the authentication response we should be safe. The > client would need to do replay protection on the code_verifier values before > it makes a request to the token endpoint. > > The BadAS could however make up a new code_challenge and code_verifier and > use that in the request. For this one the AS would need to do pull discovery > on the client to get a key, or the AS needs to return something in the > response. This attack can completely proxy all the endpoints as far as the > client is concerned and is taking advantage of the AS saying you are granting > permission to site X based on the redirect URI. > > I can’t see PKCE on it’s own being able to stop a client from being used as a > redirector back to the attacker unless you also returned the code_challenge > in the response from the authorization endpoint. > > Hypothetically if we returned code_challenge in the response from the > authorization endpoint and have a new PKCE challenge method we might find it > covers all of the attacks. > > We would need to put some serious analysis into this to see if it really > covers all the attacks. > > It however doesn’t address the “token” response_type or steeling the access > token by impersonating the RS. > > I think the correct way to stop the problem with access tokens is by audience > restricting them. > To do that the client needs to provide an audience in it’s request and the AS > needs to include that in the AT. > > I included the Authorization_endpoint URI in the hash to detect if the auth > request may have been tampered with to change the audience for the AT. > > For implicit we could have a version of PKCE where the AS returns a parameter > with S256( client_id || authorization_endpoint URI || resource endpoint URI) > to verify the request was not tampered with, and that would allow the AT to > be properly audience restricted. > > > This would be a completely new approach not involving discovery, logical > names for AS, or link relations. > > Effectively this code_challenge method becomes a signature over parts of the > request and the implicit audience of the token_endpoint URI. > > People keep asking why PKCE doesn’t stop these attacks, and it won’t with the > current PKCE methods, however a new method along the lines I sketched out > may let it work, or I could be completely wrong. Once you have written down something more definite I promise to implement it promptly such that we can do interop testing early in the process. Before John brought up this new PKCE mode I was on the Option A side of the fence now I’d like to see more of this PKCE idea before committing to one or the other. — Roland ”Everybody should be quiet near a little stream and listen." From ’Open House for Butterflies’ by Ruth Krauss
signature.asc
Description: Message signed with OpenPGP using GPGMail
_______________________________________________ OAuth mailing list OAuth@ietf.org https://www.ietf.org/mailman/listinfo/oauth