From nobody Tue Dec  8 22:47:49 2020
Return-Path: <philippe@pragmaticwebsecurity.com>
X-Original-To: oauth@ietfa.amsl.com
Delivered-To: oauth@ietfa.amsl.com
Received: from localhost (localhost [127.0.0.1])
 by ietfa.amsl.com (Postfix) with ESMTP id AF7C53A0D02
 for <oauth@ietfa.amsl.com>; Tue,  8 Dec 2020 22:47:47 -0800 (PST)
X-Virus-Scanned: amavisd-new at amsl.com
X-Spam-Flag: NO
X-Spam-Score: -2.117
X-Spam-Level: 
X-Spam-Status: No, score=-2.117 tagged_above=-999 required=5
 tests=[BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1,
 DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, HTML_FONT_FACE_BAD=0.001,
 HTML_MESSAGE=0.001, RCVD_IN_DNSWL_BLOCKED=0.001,
 RCVD_IN_MSPIKE_H3=-0.01, RCVD_IN_MSPIKE_WL=-0.01, SPF_PASS=-0.001,
 URIBL_BLOCKED=0.001] autolearn=ham autolearn_force=no
Authentication-Results: ietfa.amsl.com (amavisd-new); dkim=pass (2048-bit key)
 header.d=pragmaticwebsecurity.com header.b=lHO4qIQ7;
 dkim=pass (2048-bit key) header.d=messagingengine.com
 header.b=apM8LZEu
Received: from mail.ietf.org ([4.31.198.44])
 by localhost (ietfa.amsl.com [127.0.0.1]) (amavisd-new, port 10024)
 with ESMTP id LLn1WrblLmir for <oauth@ietfa.amsl.com>;
 Tue,  8 Dec 2020 22:47:44 -0800 (PST)
Received: from wout4-smtp.messagingengine.com (wout4-smtp.messagingengine.com
 [64.147.123.20])
 (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits))
 (No client certificate requested)
 by ietfa.amsl.com (Postfix) with ESMTPS id BAE563A074E
 for <oauth@ietf.org>; Tue,  8 Dec 2020 22:47:44 -0800 (PST)
Received: from compute3.internal (compute3.nyi.internal [10.202.2.43])
 by mailout.west.internal (Postfix) with ESMTP id 8DAF8A92;
 Wed,  9 Dec 2020 01:47:43 -0500 (EST)
Received: from mailfrontend2 ([10.202.2.163])
 by compute3.internal (MEProxy); Wed, 09 Dec 2020 01:47:43 -0500
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=
 pragmaticwebsecurity.com; h=from:message-id:content-type
 :mime-version:subject:date:in-reply-to:cc:to:references; s=fm2;
 bh=0I8B/iFHYnBNlKrbyXVIDn4V3q2m1FxU8O8ebTpeqzw=; b=lHO4qIQ7r+fH
 fxWYXxSm0+FHGS9IboNDe5RJ8hzXgrzEXwKBUgF+ZNRIl325gg4HKkV1wuiRLFll
 NKyYOABGRsYpXK6Q5ZdjdDv5Iei3/BzUnVR0ejoapy8ms3CuP5JQ3Re/lD09PlB8
 N8Oll0FKuS1ARpOQd0jo6kUXbtp3/rEK54YfRbIHuCp164UdK5u62/nHQG3SuvkS
 CAB7cv2lpIj/lMykLBxchI8+B9OxxzZ6og+TpSk1CTUgTpTLweuqpaTN2/hqswIB
 eOsXTDaQvL7rVyrnIm52YQfGe5D8RXcreHdshRTpTYxai29Br3GDq3AzQBJkUQ4F
 cYxa0iT0jw==
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=
 messagingengine.com; h=cc:content-type:date:from:in-reply-to
 :message-id:mime-version:references:subject:to:x-me-proxy
 :x-me-proxy:x-me-sender:x-me-sender:x-sasl-enc; s=fm1; bh=0I8B/i
 FHYnBNlKrbyXVIDn4V3q2m1FxU8O8ebTpeqzw=; b=apM8LZEuIHJJvBUcV2B9KP
 mevTuRM8Qm1H8yaoCZDVR1X6t67lee8qY+2exdq7VRhiyX//f3ESLXlO/vTH10cd
 oJVJ2tPUYnKQZ7g/QXbQ/+FPg2llF5A20WxWncip7/I4pyXfLujsscokSXPOsrE5
 qzQlnu4KeK9qKMrauMCuXmsJiWIM+Qgn3mNcad4aezCU+Jvqh3Fu8FFZiwx9zH89
 iHR4DNbree3Eq4AmiJQczA8wMXHrKq+ZK/ltpOySfmTcQhAiOfVeRJyP1DIAmIhk
 Srs3lXW93CMOSSJiTTpdipkbeQzfR5nOKxJx/04k4SjnB9pn/9rnDBwuim8f7Xsw
 ==
X-ME-Sender: <xms:DXPQXwK9J6SB1IAKkew-m1TPGyiYDJFcfOma_4_xSURGWWzwuUwCcA>
 <xme:DXPQXwJiidrp2O5I--aGjNwJYE6UWfJVy7bghryEjdriZh9z2q4D3NtLsK_2SS44h
 z2HbnsDGznW1tN4Bg>
X-ME-Proxy-Cause: gggruggvucftvghtrhhoucdtuddrgedujedrudejjedgleelucetufdoteggodetrfdotf
 fvucfrrhhofhhilhgvmecuhfgrshhtofgrihhlpdfqfgfvpdfurfetoffkrfgpnffqhgen
 uceurghilhhouhhtmecufedttdenucesvcftvggtihhpihgvnhhtshculddquddttddmne
 cujfgurhephffktgggufffjgfvfhfosegrtdhmrehhtdejnecuhfhrohhmpefrhhhilhhi
 phhpvgcuffgvucfthigtkhcuoehphhhilhhiphhpvgesphhrrghgmhgrthhitgifvggssh
 gvtghurhhithihrdgtohhmqeenucggtffrrghtthgvrhhnpeehvdduteeugfethfeigeeu
 lefhkeeguddtvdffieeulefgleelvdduffffffeljeenucffohhmrghinhepphhrrghgmh
 grthhitgifvggsshgvtghurhhithihrdgtohhmpdhgihhthhhusgdrtghomhdpihgvthhf
 rdhorhhgpdgvgigrmhhplhgvrdgtohhmpdgvgigrmhhplhgvrdgtohhmrdgrnhdphhhtth
 hpshefrgdvfhgvgigrmhhplhgvrdgtohhmnecukfhppeekuddrudeigedruddvledrleeh
 necuvehluhhsthgvrhfuihiivgeptdenucfrrghrrghmpehmrghilhhfrhhomhepphhhih
 hlihhpphgvsehprhgrghhmrghtihgtfigvsghsvggtuhhrihhthidrtghomh
X-ME-Proxy: <xmx:DXPQXwvfxIea_dvbnl6xCAlI0ZiGICnuArvlmg1aGNff_-YBJ9daGw>
 <xmx:DXPQX9ZFPhxKVstBDWgZ22YxZ4ZyWe7Cz-w8g02U1WhFsnNA0MPs3Q>
 <xmx:DXPQX3bEzSrJ6JWM7cBY4z55FXxAYcYFNx50HMBlxDWMz_AaRLOPUw>
 <xmx:D3PQX-z1q24rwwxOOsV7y78FKW_nH04fMRjUhah06b46mx2jB1S2Vw>
Received: from [192.168.1.16] (d51a4815f.access.telenet.be [81.164.129.95])
 by mail.messagingengine.com (Postfix) with ESMTPA id A72451080064;
 Wed,  9 Dec 2020 01:47:40 -0500 (EST)
From: Philippe De Ryck <philippe@pragmaticwebsecurity.com>
Message-Id: <EA539A6E-3F9F-4569-95BF-AE3894CE3CA6@pragmaticwebsecurity.com>
Content-Type: multipart/alternative;
 boundary="Apple-Mail=_BCD3D35C-32A0-4AEA-B417-B7CC1D87B53C"
Mime-Version: 1.0 (Mac OS X Mail 13.4 \(3608.120.23.2.4\))
Date: Wed, 9 Dec 2020 07:47:38 +0100
In-Reply-To: <CA+k3eCTnfYOFmZzu9j5XWbsZUj74f3UG54ZiWtqqyzAqRRj17Q@mail.gmail.com>
Cc: Neil Madden <neil.madden@forgerock.com>,
 Torsten Lodderstedt <torsten@lodderstedt.net>, oauth <oauth@ietf.org>
To: Brian Campbell <bcampbell@pingidentity.com>
References: <CA+k3eCSyMWyLYorWH7KY+XR1syAQUi4tQXdUuevKz4Y6xNMheA@mail.gmail.com>
 <CALAqi_8zWGAG8p5OnrTB=4q_jL00dJi5oYQrWXmzvqKGhfL28w@mail.gmail.com>
 <30D5F7BA-EA54-4E40-A2FC-222AA0C9AF8D@lodderstedt.net>
 <CALAqi_9AH5O6d2W+0UDz83=Csm9BbcU8j6qiRxz5rzLfzm6AQA@mail.gmail.com>
 <353E4494-2F80-44BC-9267-6FB8B37AA0FE@lodderstedt.net>
 <CE661132-5D86-4652-B115-E6089E39BC68@pragmaticwebsecurity.com>
 <1B663AA7-563D-4D25-A408-9ED10FD818AC@forgerock.com>
 <DE120562-2955-461B-9852-4F0B414B18FA@pragmaticwebsecurity.com>
 <CA+k3eCTnfYOFmZzu9j5XWbsZUj74f3UG54ZiWtqqyzAqRRj17Q@mail.gmail.com>
X-Mailer: Apple Mail (2.3608.120.23.2.4)
Archived-At: <https://mailarchive.ietf.org/arch/msg/oauth/kiQ5gCgeaHGdbpnaPWKJl6BlH68>
Subject: Re: [OAUTH-WG] DPoP followup I: freshness and coverage of signature
X-BeenThere: oauth@ietf.org
X-Mailman-Version: 2.1.29
Precedence: list
List-Id: OAUTH WG <oauth.ietf.org>
List-Unsubscribe: <https://www.ietf.org/mailman/options/oauth>,
 <mailto:oauth-request@ietf.org?subject=unsubscribe>
List-Archive: <https://mailarchive.ietf.org/arch/browse/oauth/>
List-Post: <mailto:oauth@ietf.org>
List-Help: <mailto:oauth-request@ietf.org?subject=help>
List-Subscribe: <https://www.ietf.org/mailman/listinfo/oauth>,
 <mailto:oauth-request@ietf.org?subject=subscribe>
X-List-Received-Date: Wed, 09 Dec 2020 06:47:48 -0000


--Apple-Mail=_BCD3D35C-32A0-4AEA-B417-B7CC1D87B53C
Content-Transfer-Encoding: quoted-printable
Content-Type: text/plain;
	charset=utf-8

Yeah, browser-based apps are pure fun, aren=E2=80=99t they? :)

The reason I covered a couple of (pessimistic) XSS scenarios is that the =
discussion started with an assumption that the attacker already =
successfully exploited an XSS vulnerability. I pointed out how, at that =
point, finetuning DPoP proof contents will have little to no effect to =
stop an attack. I believe it is important to make this very clear, to =
avoid people turning to DPoP as a security mechanism for browser-based =
applications.


Specifically to your question on including the hash in the proof, I =
think these considerations are important:

1. Does the inclusion of the AT hash stop a concrete attack scenario?
2. Is the =E2=80=9Ccost=E2=80=9D (implementation, getting it right, =E2=80=
=A6) worth the benefits?


Here=E2=80=99s my view on these considerations (specifically for =
browser-based apps, not for other types of applications):

1. The proof precomputation attack is already quite complex, and short =
access token lifetimes already reduce the window of attack. If the =
attacker can steal a future AT, they could also precompute new proofs =
then.=20
2. For browser-based apps, it seems that doing this complicates the =
implementation, without adding much benefit. Of course, libraries could =
handle this, which significantly reduces the cost.=20


Note that these comments are specifically to complicating the spec and =
implementation. DPoP=E2=80=99s capabilities of using sender-constrained =
access tokens are still useful to counter various other scenarios (e.g., =
middleboxes or APIs abusing access tokens). If other applications would =
significantly benefit from having the hash in the proof, I=E2=80=99m all =
for it.

On a final note, I would be happy to help clear up the details on =
web-based threats and defenses if necessary.

=E2=80=94
Pragmatic Web Security
Security for developers
https://pragmaticwebsecurity.com/


> On 8 Dec 2020, at 22:47, Brian Campbell <bcampbell@pingidentity.com> =
wrote:
>=20
> Danial recently added some text to the working copy of the draft with =
https://github.com/danielfett/draft-dpop/commit/f4b42058 =
<https://github.com/danielfett/draft-dpop/commit/f4b42058> that I think =
aims to better convey the "nutshell: XSS =3D Game over" sentiment and =
maybe dissuade folks from looking to DPoP as a cure-all for browser =
based applications. Admittedly a lot of the initial impetus behind =
producing the draft in the first place was born out of discussions =
around browser based apps. But it's neither specific to browser based =
apps nor a panacea for them. I hope the language in the document and how =
it's recently been presented is reflective of that reality.=20
>=20
> The more specific discussions/recommendations around in-browser apps =
are valuable (if somewhat over my head) but might be more appropriate in =
the OAuth 2.0 for Browser-Based Apps =
<https://datatracker.ietf.org/doc/draft-ietf-oauth-browser-based-apps/> =
draft.
>=20
> With respect to the contents of the DPoP draft, I am still keen to try =
and flush out some consensus around the question posed in the start of =
this thread, which is effectively whether or not to include a hash of =
the access token in the proof.  Acknowledging that "XSS =3D Game over" =
does sort of evoke a tendency to not even bother with such incremental =
protections (what I've tried to humorously coin as "XSS Nihilism" with =
no success). And as such, I do think that leaving it how it is (no AT =
hash in the proof) is not unreasonable. But, as Filip previously =
articulated, including the AT hash in the proof would prevent =
potentially prolonged access to protected resources even when the victim =
is offline. And that seems maybe worthwhile to have in the protocol, =
given that it's not a huge change to the spec. But it's a trade-off =
either way and I'm personally on the fence about it.
>=20
> Including an RT hash in the proof seems more niche. Best I can tell, =
it would guard against prolonged offline access to protected resources =
when access tokens are bearer and the RT was DPoP-bound and also gets =
rotated. The trade-off there seems less worth it (I think an RT hash =
would be more awkward in the protocol too).=20
>=20
>=20
>=20
>=20
>=20
>=20
>=20
> On Fri, Dec 4, 2020 at 5:40 AM Philippe De Ryck =
<philippe@pragmaticwebsecurity.com =
<mailto:philippe@pragmaticwebsecurity.com>> wrote:
>=20
>> The suggestion to use a web worker to ensure that proofs cannot be =
pre-computed is a good one I think. (You could also use a sandboxed =
iframe for a separate sub/sibling-domain - dpop.example.com =
<http://dpop.example.com/>).
>=20
> An iframe with a different origin would also work (not really =
sandboxing, as that implies the use of the sandbox attribute to enforce =
behavioral restrictions). The downside of an iframe is the need to host =
additional HTML, vs a script file for the worker, but the effect is =
indeed the same.
>=20
>> For scenario 4, I think this only works if the attacker can =
trick/spoof the AS into using their redirect_uri? Otherwise the AC will =
go to the legitimate app which will reject it due to mismatched =
state/PKCE. Or are you thinking of XSS on the redirect_uri itself? I =
think probably a good practice is that the target of a redirect_uri =
should be a very minimal and locked down page to avoid this kind of =
possibility. (Again, using a separate sub-domain to handle tokens and =
DPoP seems like a good idea).
>=20
> My original thought was to use a silent flow with Web Messaging. The =
scenario would go as follows:
>=20
> 1. Setup a Web Messaging listener to receive the incoming code
> 2. Create a hidden iframe with the DOM APIs
> 3. Create an authorization request such as =
=E2=80=9C/authorize?response_type=3Dcode&client_id=3D...&redirect_uri=3Dht=
tps%3A%2F%example.com =
<http://example.com/>&state=3D...&code_challenge=3D7-ffnU1EzHtMfxOAdlkp_Wi=
xnAM_z9tMh3JxgjazXAk&code_challenge_method=3DS256&prompt=3Dnone&response_m=
ode=3Dweb_message=E2=80=9D
> 4. Load this URL in the iframe, and wait for the result
> 5. Retrieve code in the listener, and use PKCE (+ DPoP if needed) to =
exchange it for tokens
>=20
> This puts the attacker in full control over every aspect of the flow, =
so no need to manipulate any of the parameters.
>=20
>=20
> After your comment, I also believe an attacker can run the same =
scenario without the =E2=80=9Cresponse_mode=3Dweb_message=E2=80=9D. This =
would go as follows:
>=20
> 1. Create a hidden iframe with the DOM APIs
> 2. Setup polling to read the URL (this will be possible for =
same-origin pages, not for cross-origin pages)
> 3. Create an authorization request such as =
=E2=80=9C/authorize?response_type=3Dcode&client_id=3D...&redirect_uri=3Dht=
tps%3A%2F%example.com =
<http://example.com/>&state=3D...&code_challenge=3D7-ffnU1EzHtMfxOAdlkp_Wi=
xnAM_z9tMh3JxgjazXAk&code_challenge_method=3DS256=E2=80=9D
> 4. Load this URL in the iframe, and keep polling
> 5. Detect the redirect back to the application with the code in the =
URL, retrieve code, and use PKCE (+ DPoP if needed) to exchange it for =
tokens
>=20
> In step 5, the application is likely to also try to exchange the code. =
This will fail due to a mismatching PKCE verifier. While noisy, I =
don=E2=80=99t think it affects the scenario.=20
>=20
>=20
>> IMO, the online attack scenario (i.e., proxying malicious requests =
through the victim=E2=80=99s browser) is quite appealing to an attacker, =
despite the apparent inconvenience:
>>=20
>>  - the victim=E2=80=99s browser may be inside a corporate firewall or =
VPN, allowing the attacker to effectively bypass these restrictions
>>  - the attacker=E2=80=99s traffic is mixed in with the user=E2=80=99s =
own requests, making them harder to distinguish or to block
>>=20
>> Overall, DPoP can only protect against XSS to the same level as =
HttpOnly cookies. This is not nothing, but it means it only prevents =
relatively naive attacks. Given the association of public key signatures =
with strong authentication, people may have overinflated expectations if =
DPoP is pitched as an XSS defence.
>=20
> Yes, in the cookie world this is known as =E2=80=9CSession Riding=E2=80=9D=
. Having the worker for token isolation would make it possible to =
enforce a coarse-grained policy on outgoing requests to prevent total =
abuse of the AT.
>=20
> My main concern here is the effort of doing DPoP in a browser versus =
the limited gains. It may also give a false sense of security.=20
>=20
>=20
>=20
> With all this said, I believe that the AS can lock down its =
configuration to reduce these attack vectors. A few initial ideas:
>=20
> 1. Disable silent flows for SPAs using RT rotation
> 2. Use the sec-fetch headers to detect and reject non-silent =
iframe-based flows
>=20
> For example,  an OAuth 2.0 flow in an iframe in Brave/Chrome carries =
these headers:
> sec-fetch-dest: iframe
> sec-fetch-mode: navigate
> sec-fetch-site: cross-site
> sec-fetch-user: ?1
>=20
>=20
> Philippe
>=20
>=20
> CONFIDENTIALITY NOTICE: This email may contain confidential and =
privileged material for the sole use of the intended recipient(s). Any =
review, use, distribution or disclosure by others is strictly =
prohibited.  If you have received this communication in error, please =
notify the sender immediately by e-mail and delete the message and any =
file attachments from your computer. Thank you.


--Apple-Mail=_BCD3D35C-32A0-4AEA-B417-B7CC1D87B53C
Content-Transfer-Encoding: quoted-printable
Content-Type: text/html;
	charset=utf-8

<html><head><meta http-equiv=3D"Content-Type" content=3D"text/html; =
charset=3Dutf-8"></head><body style=3D"word-wrap: break-word; =
-webkit-nbsp-mode: space; line-break: after-white-space;" class=3D"">Yeah,=
 browser-based apps are pure fun, aren=E2=80=99t they? :)<div =
class=3D""><br class=3D""></div><div class=3D"">The reason I covered a =
couple of (pessimistic) XSS scenarios is that the discussion started =
with an assumption that the attacker already successfully exploited an =
XSS vulnerability. I pointed out how, at that point, finetuning DPoP =
proof contents will have little to no effect to stop an attack. I =
believe it is important to make this very clear, to avoid people turning =
to DPoP as a security mechanism for browser-based =
applications.</div><div class=3D""><br class=3D""></div><div =
class=3D""><br class=3D""></div><div class=3D"">Specifically to your =
question on including the hash in the proof, I think these =
considerations are important:</div><div class=3D""><br =
class=3D""></div><div class=3D"">1. Does the inclusion of the AT hash =
stop a concrete attack scenario?</div><div class=3D"">2. Is the =
=E2=80=9Ccost=E2=80=9D (implementation, getting it right, =E2=80=A6) =
worth the benefits?</div><div class=3D""><br class=3D""></div><div =
class=3D""><br class=3D""></div><div class=3D"">Here=E2=80=99s my view =
on these considerations (<b class=3D""><i class=3D"">specifically for =
browser-based apps, not for other types of =
applications</i></b>):</div><div class=3D""><br class=3D""></div><div =
class=3D"">1. The proof precomputation attack is already quite complex, =
and short access token lifetimes already reduce the window of attack. If =
the attacker can steal a future AT, they could also precompute new =
proofs then.&nbsp;</div><div class=3D"">2. For browser-based apps, it =
seems that doing this complicates the implementation, without adding =
much benefit. Of course, libraries could handle this, which =
significantly reduces the cost.&nbsp;</div><div class=3D""><br =
class=3D""></div><div class=3D""><br class=3D""></div><div class=3D"">Note=
 that these comments are specifically to complicating the spec and =
implementation. DPoP=E2=80=99s capabilities of using sender-constrained =
access tokens are still useful to counter various other scenarios (e.g., =
middleboxes or APIs abusing access tokens). If other applications would =
significantly benefit from having the hash in the proof, I=E2=80=99m all =
for it.</div><div class=3D""><br class=3D""></div><div class=3D"">On a =
final note, I would be happy to help clear up the details on web-based =
threats and defenses if necessary.</div><div class=3D""><div =
class=3D""><br class=3D""><div class=3D"">
<div dir=3D"auto" style=3D"word-wrap: break-word; -webkit-nbsp-mode: =
space; line-break: after-white-space;" class=3D""><div =
style=3D"caret-color: rgb(0, 0, 0); color: rgb(0, 0, 0); font-family: =
Helvetica; font-size: 12px; font-style: normal; font-variant-caps: =
normal; font-weight: normal; letter-spacing: normal; text-align: start; =
text-indent: 0px; text-transform: none; white-space: normal; =
word-spacing: 0px; -webkit-text-stroke-width: 0px; text-decoration: =
none;">=E2=80=94<br class=3D""><b class=3D"">Pragmatic Web =
Security</b><br class=3D""><i class=3D"">Security for developers</i><br =
class=3D""><a href=3D"https://pragmaticwebsecurity.com/" =
class=3D"">https://pragmaticwebsecurity.com/</a><br class=3D""><br =
class=3D""></div></div>
</div>
<div><br class=3D""><blockquote type=3D"cite" class=3D""><div =
class=3D"">On 8 Dec 2020, at 22:47, Brian Campbell &lt;<a =
href=3D"mailto:bcampbell@pingidentity.com" =
class=3D"">bcampbell@pingidentity.com</a>&gt; wrote:</div><br =
class=3D"Apple-interchange-newline"><div class=3D""><div dir=3D"ltr" =
class=3D""><div class=3D"">Danial recently added some text  to the =
working copy of the draft with <a =
href=3D"https://github.com/danielfett/draft-dpop/commit/f4b42058" =
target=3D"_blank" =
class=3D"">https://github.com/danielfett/draft-dpop/commit/f4b42058</a>  =
that I think aims to better convey the "nutshell: XSS =3D Game over" =
sentiment and maybe dissuade folks from looking to DPoP as a cure-all =
for browser based applications. Admittedly a lot of the initial impetus =
behind producing the draft in the first place was born out of =
discussions around browser based apps. But it's neither specific to =
browser based apps nor a panacea for them. I hope the language in the =
document and how it's recently been presented is reflective of that =
reality. <br class=3D""></div><div class=3D""><br class=3D""></div><div =
class=3D"">The more specific discussions/recommendations around =
in-browser apps are valuable (if somewhat over my head) but might be =
more appropriate in the <a =
href=3D"https://datatracker.ietf.org/doc/draft-ietf-oauth-browser-based-ap=
ps/" target=3D"_blank" class=3D"">OAuth 2.0 for Browser-Based Apps</a> =
draft. </div><div class=3D""><br class=3D""></div><div class=3D"">With =
respect to the contents of the DPoP draft, I am still keen to try and =
flush out some consensus around the question posed in the start of this =
thread, which is effectively whether or not to include a hash of the =
access token in the proof.&nbsp; Acknowledging that "XSS =3D Game over" =
does sort of evoke a tendency to not even bother with such incremental =
protections (what I've  tried to humorously coin as "XSS Nihilism" with =
no success). And as such, I do think that leaving it how it is (no AT =
hash in the proof) is not unreasonable. But, as Filip previously =
articulated, including the AT hash in the proof would prevent =
potentially  prolonged access to protected resources even when the =
victim is offline. And that seems maybe worthwhile to have in the =
protocol, given that it's not a huge change to the spec. But it's a =
trade-off either way and I'm personally on the fence about it.</div><div =
class=3D""><br class=3D""></div><div class=3D"">Including an RT hash in =
the proof seems more niche. Best I can tell, it would guard against =
prolonged offline access to protected resources when access tokens are =
bearer and the RT was DPoP-bound and also gets rotated. The trade-off =
there seems less worth it (I think an RT hash would be more awkward in =
the protocol too). <br class=3D""></div><div class=3D""><br =
class=3D""></div><div class=3D""><br class=3D""></div><div class=3D""><br =
class=3D""></div><div class=3D""><br class=3D""></div><div class=3D""><br =
class=3D""></div><br class=3D""></div><br class=3D""><div =
class=3D"gmail_quote"><div dir=3D"ltr" class=3D"gmail_attr">On Fri, Dec =
4, 2020 at 5:40 AM Philippe De Ryck &lt;<a =
href=3D"mailto:philippe@pragmaticwebsecurity.com" target=3D"_blank" =
class=3D"">philippe@pragmaticwebsecurity.com</a>&gt; wrote:<br =
class=3D""></div><blockquote class=3D"gmail_quote" style=3D"margin:0px =
0px 0px 0.8ex;border-left:1px solid =
rgb(204,204,204);padding-left:1ex"><div class=3D""><div class=3D""><br =
class=3D""></div><div class=3D""><div class=3D""><blockquote type=3D"cite"=
 class=3D""><div class=3D""><div class=3D""><div class=3D"">The =
suggestion to use a web worker to ensure that proofs cannot be =
pre-computed is a good one I think. (You could also use a sandboxed =
iframe for a separate sub/sibling-domain - <a =
href=3D"http://dpop.example.com/" target=3D"_blank" =
class=3D"">dpop.example.com</a>).</div></div></div></blockquote><div =
class=3D""><br class=3D""></div><div class=3D"">An iframe with a =
different origin would also work (not really sandboxing, as that implies =
the use of the sandbox attribute to enforce behavioral restrictions). =
The downside of an iframe is the need to host additional HTML, vs a =
script file for the worker, but the effect is indeed the same.</div><div =
class=3D""><br class=3D""></div><blockquote type=3D"cite" class=3D""><div =
class=3D""><div class=3D""><div class=3D"">For scenario 4, I think this =
only works if the attacker can trick/spoof the AS into using their =
redirect_uri? Otherwise the AC will go to the legitimate app which will =
reject it due to mismatched state/PKCE. Or are you thinking of XSS on =
the redirect_uri itself? I think probably a good practice is that the =
target of a redirect_uri should be a very minimal and locked down page =
to avoid this kind of possibility. (Again, using a separate sub-domain =
to handle tokens and DPoP seems like a good =
idea).</div></div></div></blockquote><div class=3D""><br =
class=3D""></div><div class=3D"">My original thought was to use a silent =
flow with Web Messaging. The scenario would go as follows:</div><div =
class=3D""><br class=3D""></div><div class=3D"">1. Setup a Web Messaging =
listener to receive the incoming code</div><div class=3D"">2. Create a =
hidden iframe with the DOM APIs</div><div class=3D"">3. Create an =
authorization request such as =E2=80=9C<i =
class=3D"">/authorize?response_type=3Dcode&amp;client_id=3D...&amp;redirec=
t_uri=3Dhttps%3A%2F%<a href=3D"http://example.com/" target=3D"_blank" =
class=3D"">example.com</a>&amp;state=3D...&amp;code_challenge=3D7-ffnU1EzH=
tMfxOAdlkp_WixnAM_z9tMh3JxgjazXAk&amp;code_challenge_method=3DS256&amp;pro=
mpt=3Dnone&amp;response_mode=3Dweb_message</i>=E2=80=9D</div><div =
class=3D"">4. Load this URL in the iframe, and wait for the =
result</div><div class=3D"">5. Retrieve code in the listener, and use =
PKCE (+ DPoP if needed) to exchange it for tokens</div><div class=3D""><br=
 class=3D""></div><div class=3D"">This puts the attacker in full control =
over every aspect of the flow, so no need to manipulate any of the =
parameters.</div><div class=3D""><br class=3D""></div><div class=3D""><br =
class=3D""></div><div class=3D"">After your comment, I also believe an =
attacker can run the same scenario without the =E2=80=9C<i =
class=3D"">response_mode=3Dweb_message</i>=E2=80=9D. This would go as =
follows:</div><div class=3D""><br class=3D""></div><div class=3D""><div =
class=3D"">1. Create a hidden iframe with the DOM APIs</div><div =
class=3D"">2. Setup polling to read the URL (this will be possible for =
same-origin pages, not for cross-origin pages)</div><div class=3D"">3. =
Create an authorization request such as =E2=80=9C<i =
class=3D"">/authorize?response_type=3Dcode&amp;client_id=3D...&amp;redirec=
t_uri=3Dhttps%3A%2F%<a href=3D"http://example.com/" target=3D"_blank" =
class=3D"">example.com</a>&amp;state=3D...&amp;code_challenge=3D7-ffnU1EzH=
tMfxOAdlkp_WixnAM_z9tMh3JxgjazXAk&amp;code_challenge_method=3DS256</i>=E2=80=
=9D</div><div class=3D"">4. Load this URL in the iframe, and keep =
polling</div><div class=3D"">5. Detect the redirect back to the =
application with the code in the URL, retrieve code, and use PKCE (+ =
DPoP if needed) to exchange it for tokens</div><div class=3D""><br =
class=3D""></div><div class=3D"">In step 5, the application is likely to =
also try to exchange the code. This will fail due to a mismatching PKCE =
verifier. While noisy, I don=E2=80=99t think it affects the =
scenario.&nbsp;</div></div><div class=3D""><br class=3D""></div><br =
class=3D""><blockquote type=3D"cite" class=3D""><div class=3D""><div =
class=3D""><div class=3D"">IMO, the online attack scenario (i.e., =
proxying malicious requests through the victim=E2=80=99s browser) is =
quite appealing to an attacker, despite the apparent =
inconvenience:</div><div class=3D""><br class=3D""></div><div =
class=3D"">&nbsp;- the victim=E2=80=99s browser may be inside a =
corporate firewall or VPN, allowing the attacker to effectively bypass =
these restrictions</div><div class=3D"">&nbsp;- the attacker=E2=80=99s =
traffic is mixed in with the user=E2=80=99s own requests, making them =
harder to distinguish or to block</div><div class=3D""><br =
class=3D""></div><div class=3D"">Overall, DPoP can only protect against =
XSS to the same level as HttpOnly cookies. This is not nothing, but it =
means it only prevents relatively naive attacks. Given the association =
of public key signatures with strong authentication, people may have =
overinflated expectations if DPoP is pitched as an XSS =
defence.</div></div></div></blockquote><div class=3D""><br =
class=3D""></div><div class=3D"">Yes, in the cookie world this is known =
as =E2=80=9CSession Riding=E2=80=9D. Having the worker for token =
isolation would make it possible to enforce a coarse-grained policy on =
outgoing requests to prevent total abuse of the AT.</div><div =
class=3D""><br class=3D""></div><div class=3D"">My main concern here is =
the effort of doing DPoP in a browser versus the limited gains. It may =
also give a false sense of security.&nbsp;</div><div class=3D""><br =
class=3D""></div><div class=3D""><br class=3D""></div><div class=3D""><br =
class=3D""></div><div class=3D"">With all this said, I believe that the =
AS can lock down its configuration to reduce these attack vectors. A few =
initial ideas:</div><div class=3D""><br class=3D""></div><div =
class=3D"">1. Disable silent flows for SPAs using RT rotation</div><div =
class=3D"">2. Use the sec-fetch headers to detect and reject non-silent =
iframe-based flows</div><div class=3D""><br class=3D""></div><div =
class=3D"">For example, &nbsp;an OAuth 2.0 flow in an iframe in =
Brave/Chrome carries these headers:</div><div class=3D""><div =
class=3D""><font color=3D"#303942" class=3D""><span =
style=3D"white-space:nowrap" class=3D""><i class=3D""><div =
class=3D"">sec-fetch-dest: iframe</div><div class=3D"">sec-fetch-mode: =
navigate</div><div class=3D"">sec-fetch-site: cross-site</div><div =
class=3D"">sec-fetch-user: ?1</div></i></span></font></div><div =
class=3D""><font face=3D".SFNSDisplay-Regular, Helvetica Neue, Lucida =
Grande, sans-serif" color=3D"#303942" class=3D""><span =
style=3D"white-space:nowrap" class=3D""><br =
class=3D""></span></font></div><div class=3D""><font =
face=3D".SFNSDisplay-Regular, Helvetica Neue, Lucida Grande, sans-serif" =
color=3D"#303942" class=3D""><span style=3D"white-space:nowrap" =
class=3D""><br class=3D""></span></font></div><div class=3D""><font =
face=3D".SFNSDisplay-Regular, Helvetica Neue, Lucida Grande, sans-serif" =
color=3D"#303942" class=3D""><span style=3D"white-space:nowrap" =
class=3D"">Philippe</span></font></div></div><blockquote type=3D"cite" =
class=3D""><div class=3D""><span =
style=3D"color:rgb(23,43,77);font-family:-apple-system,BlinkMacSystemFont,=
&quot;Segoe UI&quot;,Roboto,Oxygen,Ubuntu,&quot;Fira =
Sans&quot;,&quot;Droid Sans&quot;,&quot;Helvetica =
Neue&quot;,sans-serif;background-color:rgb(255,255,255)" class=3D""><font =
size=3D"1" class=3D""></font></span></div></blockquote></div><br =
class=3D""></div></div></blockquote></div>

<br class=3D"">
<i =
style=3D"margin:0px;padding:0px;border:0px;outline:0px;vertical-align:base=
line;background:rgb(255,255,255);font-family:proxima-nova-zendesk,system-u=
i,-apple-system,system-ui,&quot;Segoe =
UI&quot;,Roboto,Oxygen-Sans,Ubuntu,Cantarell,&quot;Helvetica =
Neue&quot;,Arial,sans-serif;color:rgb(85,85,85)" class=3D""><span =
style=3D"margin:0px;padding:0px;border:0px;outline:0px;vertical-align:base=
line;background:transparent;font-family:proxima-nova-zendesk,system-ui,-ap=
ple-system,BlinkMacSystemFont,&quot;Segoe =
UI&quot;,Roboto,Oxygen-Sans,Ubuntu,Cantarell,&quot;Helvetica =
Neue&quot;,Arial,sans-serif;font-weight:600" class=3D""><font size=3D"2" =
class=3D"">CONFIDENTIALITY NOTICE: This email may contain confidential =
and privileged material for the sole use of the intended recipient(s). =
Any review, use, distribution or disclosure by others is strictly =
prohibited.&nbsp; If you have received this communication in error, =
please notify the sender immediately by e-mail and delete the message =
and any file attachments from your computer. Thank =
you.</font></span></i></div></blockquote></div><br =
class=3D""></div></div></body></html>=

--Apple-Mail=_BCD3D35C-32A0-4AEA-B417-B7CC1D87B53C--

