<?xml version="1.0" encoding="US-ASCII"?>
<!DOCTYPE rfc SYSTEM "rfc2629.dtd">
<?rfc toc="yes"?>
<?rfc tocompact="yes"?>
<?rfc tocdepth="3"?>
<?rfc tocindent="yes"?>
<?rfc symrefs="yes"?>
<?rfc sortrefs="yes"?>
<?rfc comments="yes"?>
<?rfc inline="yes"?>
<?rfc compact="yes"?>
<?rfc subcompact="no"?>
<rfc category="std" docName="draft-ietf-oauth-spop-15" ipr="trust200902">
  <front>
    <title abbrev="oauth_pkce">Proof Key for Code Exchange by OAuth Public Clients</title>

    <author fullname="Nat Sakimura" initials="N." role="editor"
            surname="Sakimura">
      <organization>Nomura Research Institute</organization>

      <address>
        <postal>
          <street>1-6-5 Marunouchi, Marunouchi Kitaguchi Bldg.</street>
          <city>Chiyoda-ku</city>
          <code>100-0005</code>
          <region>Tokyo</region>
          <country>Japan</country>
        </postal>
        <phone>+81-3-5533-2111</phone>
        <email>n-sakimura@nri.co.jp</email>
        <uri>http://nat.sakimura.org/</uri>
      </address>
    </author>

    <author fullname="John Bradley" initials="J." surname="Bradley">
      <organization>Ping Identity</organization>

      <address>
        <postal>
          <street>Casilla 177, Sucursal Talagante</street>
          <city>Talagante</city>
          <region>RM</region>
          <code/>
          <country>Chile</country>
        </postal>
        <phone>+44 20 8133 3718</phone>
        <facsimile/>
        <email>ve7jtb@ve7jtb.com</email>
        <uri>http://www.thread-safe.com/</uri>
      </address>
    </author>

    <author fullname="Naveen Agarwal" initials="N." surname="Agarwal">
      <organization>Google</organization>

      <address>
        <postal>
          <street>1600 Amphitheatre Pkwy</street>
          <city>Mountain View</city>
          <region>CA</region>
          <code>94043</code>
          <country>USA</country>
        </postal>
        <phone>+1 650-253-0000</phone>
        <facsimile/>
        <email>naa@google.com</email>
        <uri>http://google.com/</uri>
      </address>
    </author>

    <date day="8" month="July" year="2015"/>

    <area>Security</area>

    <workgroup>OAuth Working Group</workgroup>

    <abstract>
      <t>OAuth 2.0 public clients utilizing the Authorization Code Grant are 
      susceptible to the authorization code interception attack.  This specification 
      describes the attack as well as a technique to mitigate against the threat 
      through the use of Proof Key for Code Exchange (PKCE, pronounced "pixy"). </t>
    </abstract>


  </front>

  <middle>
    <section title="Introduction" anchor="intro">
      <t><xref target="RFC6749">OAuth 2.0 </xref> public clients are
      susceptible to the authorization code
      interception attack.</t>
      
      <t>The attacker thereby intercepts the authorization code returned 
      from the authorization endpoint within communication path not 
      protected by TLS, such as inter-app communication within the 
      operating system of the client.</t>
      
      <t>Once the attacker has gained access to the authorization code it 
      can use it to obtain the access token.</t>
      
      <t>Figure 1 shows the attack graphically. In step (1) the native
      app running on the end device, such as a smart phone, issues
      an OAuth 2.0 Authorization Request via the browser/operating system. 
      The Redirection Endpoint URI in this case typically uses a 
      custom URI scheme. 
      Step (1) happens through a secure API that cannot be intercepted, 
      though it may potentially be observed in advanced attack scenarios. 
      The request then gets forwarded to the OAuth 2.0 authorization server in
      step (2). 
      Because OAuth requires the use of TLS, this communication is protected by TLS, 
      and also cannot be intercepted. 
      
      The authorization server returns the authorization code
      in step (3). 
      In step (4), the Authorization Code is returned to the requester 
      via the Redirection Endpoint URI that was provided in step (1).
      </t>
      <t>
      A malicious app that has been designed to attack this native app 
      has previously registered itself as a handler for the custom URI scheme 
      is now able to intercept the Authorization Code in step (4). 
      This allows the attacker to request and obtain an access token 
      in steps (5) and (6), respectively.
      </t>
      
      <figure anchor="figure_code_interception_attack"
       title="Authorization Code Interception Attack.">
             <artwork><![CDATA[
 +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
 | End Device (e.g., Smart Phone) |
 |                                |
 | +-------------+   +----------+ | (6) Access Token  +----------+
 | |Legitimate   |   | Malicious|<--------------------|          |
 | |OAuth 2.0 App|   | App      |-------------------->|          |
 | +-------------+   +----------+ | (5) Authorization |          |
 |        |    ^          ^       |        Grant      |          |
 |        |     \         |       |                   |          |
 |        |      \   (4)  |       |                   |          |
 |    (1) |       \  Authz|       |                   |          |
 |   Authz|        \ Code |       |                   |  Authz   |
 | Request|         \     |       |                   |  Server  |
 |        |          \    |       |                   |          |
 |        |           \   |       |                   |          |
 |        v            \  |       |                   |          |
 | +----------------------------+ |                   |          |
 | |                            | | (3) Authz Code    |          |
 | |     Operating System/      |<--------------------|          |
 | |         Browser            |-------------------->|          |
 | |                            | | (2) Authz Request |          |
 | +----------------------------+ |                   +----------+
 +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~+
             ]]></artwork>
      </figure>
      
      <t>A number of pre-conditions need to hold in order for this attack
      to work:</t>
      <t>
          <list style="hanging">
            <t hangText="1)">The attacker manages to register a malicious application on
            the client device and registers a custom URI scheme that is
            also used by another application.
            <vspace />
            The operating systems must allow a custom URI schemes to
            be registered by multiple applications.
            </t>
            <t hangText="2)">The OAuth 2.0 authorization code grant is used.
            </t>
            <t hangText="3)">The attacker has access to the 
            <xref target="RFC6749">OAuth 2.0 </xref> client_id and 
            client_secret(if provisioned). All OAuth 2.0 native app
            client-instances use the same client_id. Secrets provisioned in client 
            binary applications cannot be considered confidential.
            </t>
            <t hangText="4a)">The attacker (via the installed app) is able to observe
            only the responses from the authorization endpoint. 
            The plain code_challenge_method mitigates only this attack.</t>
            
            <t hangText="4b)"> A more
            sophisticated attack scenario allows the attacker 
            to observe requests (in addition to responses) to the
            authorization endpoint. The attacker is, however, not
            able to act as a man-in-the-middle.  This has been caused by leaking http log 
            information in the OS.  To mitigate this the S256 code_challenge_method
             or cryptographically
            secure code_challenge_method extension must be used.
            </t>
          </list>
        </t>
        
      <t>While this is a long list of pre-conditions the described attack
      has been observed in the wild and has to be considered in
      OAuth 2.0 deployments.
      <vspace/> 
      While the OAuth 2.0 Threat Model 
      <xref target="RFC6819">Section 4.4.1</xref>
      describes mitigation techniques they are, unfortunately, not applicable
      since they rely on a per-client instance secret or aper client
      instance redirect URI.</t>

      <t>To mitigate this attack, this extension utilizes a dynamically created
      cryptographically random key called "code verifier". A unique code verifier
      is created for every authorization request and its transformed value, 
      called "code challenge", is sent to the authorization server to obtain the
      authorization code. The authorization code obtained is
      then sent to the token endpoint with the "code verifier" and the server
      compares it with the previously received request code so that it can
      perform the proof of possession of the "code verifier" by the client. This
      works as the mitigation since the attacker would not know this one-time
      key, since it is sent over TLS and cannot be intercepted.</t>

      <section title="Protocol Flow" anchor="ProtocolFlow">

         <figure anchor="figure_abstract_protocol_flow" title="Abstract Protocol Flow">
             <artwork><![CDATA[
                                              +-------------------+
                                              |   Authz Server    |
    +--------+                                | +---------------+ |
    |        |--(A)- Authorization Request ---->|               | |
    |        |       + t(code_verifier), t_m  | | Authorization | |
    |        |                                | |    Endpoint   | |
    |        |<-(B)---- Authorization Code -----|               | |
    |        |                                | +---------------+ |
    | Client |                                |                   |
    |        |                                | +---------------+ |
    |        |--(C)-- Access Token Request ---->|               | |
    |        |          + code_verifier       | |    Token      | |
    |        |                                | |   Endpoint    | |
    |        |<-(D)------ Access Token ---------|               | |
    +--------+                                | +---------------+ |
                                              +-------------------+
             ]]></artwork>
         </figure>

        <t>This specification adds additional parameters to the OAuth 2.0 Authorization 
            and Access Token Requests, shown in abstract form in Figure 1.
        </t>

        <t>
          <list style="hanging">
            <t hangText="A.">The client creates and records a secret named the 
            <spanx style="verb">code_verifier</spanx>,
              and derives a transformed version <spanx style="verb">t(code_verifier)</spanx>
              (referred to as the <spanx style="verb">code_challenge</spanx>) 
              which is sent in the OAuth 2.0 Authorization Request, along with 
              the transformation method <spanx style="verb">t_m</spanx>.
            </t>
            <t hangText="B.">The Authorization Endpoint responds as usual, but records 
              <spanx style="verb">t(code_verifier)</spanx> and the transformation method.
            </t>
            <t hangText="C.">The client then sends the authorization code in the Access Token 
              Request as usual, but includes the <spanx style="verb">code_verifier</spanx>
              secret generated at (A).
            </t>
            <t hangText="D.">The authorization server transforms <spanx style="verb">code_verifier</spanx> 
              and compares it to <spanx style="verb">t(code_verifier)</spanx> from (B). Access is 
              denied if they are not equal.
            </t>
          </list>
        </t>

        <t>
          An attacker who intercepts the Authorization Grant at (B) is unable to redeem 
          it for an Access Token, as they are not in
          possession of the <spanx style="verb">code_verifier</spanx> secret.
        </t>

      </section>

    </section>

    <section title="Notational Conventions" anchor="NotationalConventions">
        <t>
          The key words "MUST", "MUST NOT", "REQUIRED", "SHALL",
          "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY",
          and "OPTIONAL" in this document are to be interpreted as
          described in
	  Key words for use in RFCs to Indicate Requirement Levels <xref target='RFC2119' />.
	  If these words are used without being spelled in uppercase then
	  they are to be interpreted with their normal natural language meanings.
        </t>

  <t>
    This specification uses the Augmented Backus-Naur Form (ABNF)
    notation of <xref target="RFC5234" />.
  </t>
    <t>
    STRING denotes a sequence of zero or more ASCII <xref target="RFC0020"/> characters. 
    </t>
    <t>OCTETS denotes a sequence of zero or more octets. </t>
    
    <t>ASCII(STRING) denotes the octets of the ASCII <xref target="RFC0020"/> representation 
    of STRING where STRING is a sequence of zero or more ASCII characters. </t>
    
	<t>
	  BASE64URL-ENCODE(OCTETS) denotes the base64url encoding of OCTETS,
	  per <xref target="Terminology"/> producing a STRING.
	</t>
	<t>
	  BASE64URL-DECODE(STRING) denotes the base64url decoding of STRING,
	  per <xref target="Terminology"/>, producing a sequence of octets.
	</t>
	<t>
	  SHA256(OCTETS) denotes a SHA2 256bit hash <xref target="RFC6234" /> of OCTETS.
	</t>
	
    </section>
      
    <section title="Terminology" anchor="Terminology">
      <t>In addition to the terms defined in <xref target="RFC6749">OAuth
      2.0</xref>, this specification defines the following terms:</t>
       
    <t>
      <list style="hanging">
      
      <t hangText="code verifier"><vspace/>
        A cryptographically random string that is used to correlate the 
        authorization request to the token request.</t>
     

      <t hangText="code challenge"><vspace/>
        A challenge derived from the code verifier that is sent in the
        authorization request, to be verified against later.</t>

      
      <t hangText="Base64url Encoding"><vspace/>
	    Base64 encoding using the URL- and filename-safe
	    character set defined in Section 5 of <xref target="RFC4648"/>,
	    with all trailing '=' characters omitted 
	    (as permitted by Section 3.2 of <xref target="RFC4648"/>)
	    and without the inclusion of any line breaks, whitespace, or other additional 
	    characters. (See <xref target="base64urlnotes" /> for notes on
	    implementing base64url encoding without padding.)
	  </t>
	  </list>
	  </t>
	  <section title="Abbreviations" anchor="abbreviations">
	  	<t>
	  		<list style="hanging">
	  		<t hangText="ABNF">Augmented Backus-Naur Form</t>
	  		<t hangText="Authz">Authorization</t>
	  		<t hangText="PKCE">Proof Key for Code Exchange</t>
	  		<t hangText="MITM">Man-in-the-middle</t>
	  		<t hangText="MTI">Mandatory To Implement</t>
	  		</list>
	  	</t>
	  </section>
    </section>

    <section title="Protocol" anchor="protocol">
      <t/>

      <section title="Client creates a code verifier" anchor="create_code_verifier">
        
        <t>The client first creates a code verifier, <spanx style="verb">code_verifier</spanx>,
        for each <xref target="RFC6749">OAuth 2.0</xref> Authorization Request,
        in the following manner:</t>

        <t>code_verifier = high entropy cryptographic random STRING
        using the Unreserved Characters 
         [A-Z] / [a-z] / [0-9] / "-" / "." / "_" / "~" from Sec 2.3 of 
        <xref target="RFC3986"/>, with a minimum length of 43 characters 
        and a maximum length of 128 characters.</t>
		 <t>ABNF for <spanx style="verb">code_verifier</spanx> is as follows.</t>
		 
		 <figure><artwork><![CDATA[
code-verifier = 43*128unreserved
unreserved = ALPHA / DIGIT / "-" / "." / "_" / "~"
ALPHA = %x41-5A / %x61-7A
DIGIT = %x30-39
		 ]]></artwork></figure>

        <t>NOTE: code verifier SHOULD have enough entropy to make it
        impractical to guess the value. 
		 It is RECOMMENDED that the output of a suitable random number generator 
        be used to create a 32-octet sequence.  The Octet sequence is then base64url encoded
        to produce a 43-octet URL safe string to use as the code verifier.</t>
      </section>
	  
	  <section title="Client creates the code challenge" anchor="create_code_challenge">
	    <t>The client then creates a code challenge 
        derived from the code verifier by using
        one of the following transformations on 
        the code verifier:
        </t>
		<t>
		 <list style="hanging">
        <t hangText="plain"><vspace/>
          code_challenge = code_verifier</t>
        <t hangText="S256"><vspace/>
    		code_challenge = 
    		BASE64URL-ENCODE(SHA256(ASCII(code_verifier)))
        </t>
		</list></t>
		<t>
				If the client is capable of using <spanx style="verb">S256</spanx>, 
				it MUST use <spanx style="verb">S256</spanx>, as 
				<spanx style="verb">S256</spanx> 
				is Mandatory To Implement (MTI) on the server. 
				Clients are permitted to use <spanx style="verb">plain</spanx> 
				only if they cannot support 
				<spanx style="verb">S256</spanx> for 
				some technical reason and know via out of band configuration 
				that the server supports 
				<spanx style="verb">plain</spanx>. 
			</t>
        <t>The plain transformation is 
        for compatibility with existing deployments and for constrained environments that
        can't use the S256 transformation.</t>
        
		 <t>ABNF for <spanx style="verb">code_challenge</spanx> is as follows.</t>
		 
		 <figure><artwork><![CDATA[
code-challenge = 43*128unreserved
unreserved = ALPHA / DIGIT / "-" / "." / "_" / "~"
ALPHA = %x41-5A / %x61-7A
DIGIT = %x30-39
		 ]]></artwork></figure>
	  </section>

      <section title="Client sends the code challenge with the authorization request"
	    anchor="auth_req">
 
        <t>The client sends the code challenge as part of the 
        OAuth 2.0 Authorization
        Request (Section 4.1.1 of <xref target="RFC6749"/>.) 
        using the following additional parameters:</t>

        <t><list style="hanging">
            <t hangText="code_challenge">REQUIRED. Code challenge.</t>
          </list>
          <list style="hanging">
            <t hangText="code_challenge_method">OPTIONAL, defaults to 
            <spanx style="verb">plain</spanx> if not present in the request. 
            Code verifier transformation method, 
			<spanx style="verb">S256</spanx> or <spanx style="verb">plain</spanx>.  </t>
          </list></t>
      </section>

      <section title="Server returns the code" anchor="auth_res">
        <t>When the server issues the authorization code in the 
        authorization response,
        it MUST associate the <spanx style="verb">code_challenge</spanx> and 
        <spanx style="verb">code_challenge_method</spanx> values with
        the authorization code so it can be verified later.</t>

        <t>Typically, the <spanx style="verb">code_challenge</spanx> and 
        <spanx style="verb">code_challenge_method</spanx> values are stored in 
        encrypted form in the <spanx style="verb">code</spanx> itself, but
        could alternatively be stored on the server, associated with the
        code. The server MUST NOT include the <spanx style="verb">code_challenge</spanx>
        value in client requests in a form that other entities can extract.</t>
		    
        <t>The exact method that the server uses to associate the 
        <spanx style="verb">code_challenge</spanx>
        with the issued <spanx style="verb">code</spanx> is out of scope for this 
        specification.</t>
		<section title="Error Response" anchor="auth_res_err">
			<t>
				If the server requires 
				Proof Key for Code Exchange (PKCE) by OAuth Public Clients, 
				and the client does not send 
				the <spanx style="verb">code_challenge</spanx> in the request, 
				the authorization endpoint MUST return the authorization error response with 
				<spanx style="verb">error</spanx> value set to <spanx style="verb">invalid_request</spanx>.  
				The <spanx style="verb">error_description</spanx> or the response of 
				<spanx style="verb">error_uri</spanx> SHOULD explain the nature of error, 
				e.g., code challenge required. 
			</t>
			<t>
				If the server supporting PKCE does not support the requested transform,  
				the authorization endpoint MUST return the authorization error response with 
				<spanx style="verb">error</spanx> value set to <spanx style="verb">invalid_request</spanx>.  
				The <spanx style="verb">error_description</spanx> or the response of 
				<spanx style="verb">error_uri</spanx> SHOULD explain the nature of error, 
				e.g., transform algorithm not supported. 
			</t>
			
		</section>
      </section>

      <section title="Client sends the Authorization Code and the Code Verifier to the token endpoint" anchor="token_req">
        <t>Upon receipt of the Authorization Code, the client
        sends the Access Token Request to the token endpoint. In addition to the 
        parameters defined in the OAuth 2.0 Access Token Request (Section 4.1.3 of 
        <xref target="RFC6749"/>), it
        sends the following parameter:</t>

        <t><list style="hanging">
            <t hangText="code_verifier">REQUIRED. Code verifier</t>
          </list></t>
          
          <t>The code_challenge_method is bound to the Authorization Code 
          when the Authorization Code is issued.
          That is the method that the token endpoint MUST use to verify the 
          code_verifier.</t>
      </section>

      <section title="Server verifies code_verifier before returning the tokens" anchor="token_res">
        <t>Upon receipt of the request at the Access Token endpoint, the server
        verifies it by calculating the code challenge from received <spanx
        style="verb">code_verifier</spanx> and comparing it with the
        previously associated <spanx style="verb">code_challenge</spanx>, 
        after first transforming it according to the <spanx 
        style="verb">code_challenge_method</spanx> method specified by the client.</t>
        
        <t>If the <spanx style="verb">code_challenge_method</spanx> from 
        <xref target="create_code_challenge" ></xref>
        was <spanx style="verb">S256</spanx>, the received <spanx style="verb">code_verifier</spanx> 
        is hashed by SHA-256, then base64url encoded, and then compared to the <spanx 
        style="verb">code_challenge</spanx>. i.e.,
		</t>
		<t>BASE64URL-ENCODE(SHA256(ASCII(<spanx style="verb">code_verifier</spanx> )))
        == <spanx style="verb">code_challenge</spanx></t>
       
        <t>If the <spanx style="verb">code_challenge_method</spanx> from 
        <xref target="create_code_challenge" > </xref>
        was <spanx style="verb">plain</spanx>, they are compared 
        directly. i.e., </t>
		<t><spanx style="verb">code_verifier</spanx> == <spanx style="verb">code_challenge</spanx>.</t>
        
        <t>If the values are equal, the Access Token endpoint MUST continue 
        processing as normal (as defined by <xref 
        target="RFC6749">OAuth 2.0</xref>). If the values are not equal, an 
        error response indicating <spanx style="verb">invalid_grant</spanx> as
        described in section 5.2 of <xref target="RFC6749"/> 
        MUST be returned.</t>
      </section>

    </section>

    <section title="Compatibility" anchor="compatibility">
      <t>Server implementations of this specification MAY accept OAuth2.0 Clients that
      do not implement this extension. If the <spanx style="verb">code_verifier</spanx> is 
      not received from the client
      in the Authorization Request, servers supporting backwards compatibility revert
      to a normal <xref target="RFC6749">OAuth 2.0</xref> protocol.</t>

      <t>As the <xref target="RFC6749">OAuth 2.0</xref> server 
      responses are unchanged by this specification, client 
      implementations of this specification do not need to know if the 
      server has implemented this specification or not,
      and SHOULD send the additional parameters as defined in Section 3. to 
      all servers.</t>
    </section>


    <section anchor="IANA" title="IANA Considerations">
      <t>This specification makes a registration request as follows:</t>

      <section title="OAuth Parameters Registry" anchor="reg">
        <t>This specification registers the following parameters in the IANA
        OAuth Parameters registry defined in <xref target="RFC6749">OAuth
        2.0</xref>.</t>

        <t>
          <list style="symbols">
            <t>Parameter name: code_verifier</t>

            <t>Parameter usage location: token request</t>

            <t>Change controller: IESG</t>

            <t>Specification document(s): this document</t>
          </list>
        </t>
        <t>
          <list style="symbols">
            <t>Parameter name: code_challenge</t>

            <t>Parameter usage location: authorization request</t>

            <t>Change controller: IESG</t>

            <t>Specification document(s): this document</t>
          </list>
        </t>
        <t>
          <list style="symbols">
            <t>Parameter name: code_challenge_method</t>

            <t>Parameter usage location: authorization request</t>

            <t>Change controller: IESG</t>

            <t>Specification document(s): this document</t>
          </list>
        </t>
      </section>
      <section title="PKCE Code Challenge Method Registry" anchor="ccmr">
      <t>This specification establishes the PKCE Code Challenge Method registry.
      The new registry should be a sub-registry of OAuth Parameters registry.</t>
          
        <t>Additional code_challenge_method types for use with the authorization
        endpoint are registered using the Specification Required policy
        <xref target="RFC5226"/>, which includes review of the request by one or more
        Designated Experts.  The DEs will ensure there is at least a two-week
        review of the request on the oauth-ext-review@ietf.org mailing list,
        and that any discussion on that list converges before they respond to
        the request.  To allow for the allocation of values prior to
        publication, the Designated Expert(s) may approve registration once
        they are satisfied that an acceptable specification will be
        published.</t>

		<t>Registration requests and discussion on the oauth-ext-review@ietf.org mailing 
		list should use an appropriate subject, such as "Request for PKCE
        code_challenge_method: example").
        </t>

        <t>The Designated Expert(s) should consider the discussion on the
		  mailing list, as well as the overall security properties of the challenge Method
		   when evaluating registration requests.  New methods should not disclose the 
		   value of the code_verifier in the request to the Authorization endpoint.
		    Denials should include an explanation
		  and, if applicable, suggestions as to how to make the request
		  successful.
		  </t>
		
		
		<section anchor="ccm_template" title="Registration Template">
		          <t>
            <list style='hanging'>
              <t hangText='Code Challenge Method Parameter Name:'>
		<vspace/>
                The name requested (e.g., "example").
		Because a core goal of this specification is for the resulting
		representations to be compact, it is RECOMMENDED that the name be short
		-- not to exceed 8 characters without a compelling reason to do so.
		This name is case-sensitive.
		Names may not match other registered names in a case-insensitive manner
		unless the Designated Expert(s) state that there is a compelling reason
		to allow an exception in this particular case.
              </t>
             
              <t hangText='Change Controller:'>
                <vspace/>
                For Standards Track RFCs, state "IESG". For others, give the name of the
                responsible party. Other details (e.g., postal address, email address, 
                home page URI) may also be included.
              </t>
              <t hangText='Specification Document(s):'>
                <vspace/>
                Reference to the document(s) that specify the parameter, preferably 
                including URI(s) that can be used to retrieve copies of the document(s). 
                An indication of the relevant
                sections may also be included but is not required.
              </t>
            </list>
          </t>
		</section>
		        <section title="Initial Registry Contents" anchor="ccm-r-Contents">
	  <t>
	    This specification registers the Code Challenge Method Parameter names defined in
	    <xref target="create_code_challenge"/> in this registry.
	  </t>
	  <t> <?rfc subcompact="yes"?>
            <list style='symbols'>
              <t>
                Code Challenge Method Parameter Name: <spanx style="verb">plain</spanx>
              </t>
              
              <t>
                Change Controller: IESG
              </t>
              <t>
                Specification Document(s): <xref target="create_code_challenge"/> of [[ this document ]]
              </t>
            </list>
	  </t>
	  <t>
	    <list style='symbols'>
              <t>
                 Code Challenge Method Parameter Name: <spanx style="verb">S256</spanx>
              </t>
              
              <t>
                Change Controller: IESG
              </t>
              <t>
                Specification Document(s): <xref target="create_code_challenge"/> of [[ this document ]]
              </t>
            </list>
	  </t>
	  
          
	</section>
      </section>
    </section>

    <section anchor="Security" title="Security Considerations">
	  <section title="Entropy of the code_verifier" anchor="code_verifier_entropy">
      <t>The security model relies on the fact that the code verifier is not
      learned or guessed by the attacker. It is vitally important to adhere to
      this principle. As such, the code verifier has to be created in such a
      manner that it is cryptographically random and has high entropy that it
      is not practical for the attacker to guess. 
      <vspace blankLines="1"/>
	  The client SHOULD create a code_verifier with a minimum of 256bits of entropy.
        This can be done by having a suitable random number generator create a 32-octet 
        sequence.  The Octet sequence can then be base64url encoded to produce a 43-octet
        URL safe string to use as a code_challenge that has the required entropy. 
	  </t>
     </section>
	 <section title="Protection against eavesdroppers" anchor="eavesdrop">
		<t>Clients MUST NOT downgrade to <spanx style="verb">plain</spanx> after trying 
		<spanx style="verb">S256</spanx> method. 
		Servers that support PKCE are required to support <spanx style="verb">S256</spanx>,
		and servers that do not support PKCE will simply ignore the unknown   
		<spanx style="verb">code_verifier</spanx> OAuth 2.0 (see Section 3.2 of  
		<xref target="RFC6749"/>. 
		 Because of that, an error when <spanx style="verb">S256</spanx> is presented 
		 can only mean that the server is faulty or that a MITM attacker is trying a 
		 downgrade attack. 
		</t>
		<t>
		<spanx style="verb">S256</spanx> method protects against 
		eavesdroppers observing or intercepting the <spanx style="verb">code_challenge</spanx>, 
		because the challenge cannot be used without the verifier.  
		With the <spanx style="verb">plain</spanx> method, 
		there is a chance that <spanx style="verb">code_challenge</spanx> will be 
		observed by the attacker on the device, or in the http request. 
		Since the code challenge is the same as the code verifier in 
		this case, <spanx style="verb">plain</spanx> method does not protect 
		against the eavesdropping of the initial request. 
		</t>
		<t>
		The use of <spanx style="verb">S256</spanx> protects against disclosure of 
		<spanx style="verb">code_verifier</spanx> value to an attacker. 
		</t>
		<t>
		Because of this, <spanx style="verb">plain</spanx> SHOULD NOT be used, 
		and exists only for compatibility with deployed implementations 
		where the request path is already protected. 
		The <spanx style="verb">plain</spanx> method SHOULD NOT be used 
		in new implementations, unless they cannot support 
		<spanx style="verb">S256</spanx> for some technical reason.
		</t>

		<t>The <spanx style="verb">S256</spanx> code_challenge_method or other 
		cryptographically secure code_challenge_method extension SHOULD be used.
		The plain code_challenge_method relies on the operating system and transport 
		security not to disclose the request to an attacker. 
		</t>
		<t>
		If the code_challenge_method is plain, and the
		 <spanx style="verb">code_challenge</spanx> is to be returned
		inside authorization <spanx style="verb">code</spanx> to achieve a stateless server, 
		it MUST be encrypted in such 
		a manner that only the server can decrypt and extract it.
		</t>
     </section>

     <section title="Salting the code_challenge" anchor="salt">
     
        <t>
        In order to reduce implementation complexity Salting is not used in the production 
        of the code_challenge, as the code_verifier
        contains sufficient entropy to prevent brute force attacks.   Concatenating a 
        publicly known value to a code_verifier (containing 256 bits of entropy) and then 
        hashing it with SHA256 to produce a code_challenge would not increase the number 
        of attempts necessary to brute force a valid value for code_verifier.
        <vspace blankLines="1"/>
        While the S256 transformation is like hashing a password there are important 
        differences.  Passwords tend to be relatively low entropy words that can be hashed 
        offline and the hash looked up in a dictionary.  By concatenating a unique though 
        public value to each password prior to hashing, the dictionary space that an attacker
        needs to search is greatly expanded. 
        <vspace blankLines="1"/>
        Modern graphics processors now allow attackers to calculate 
        hashes in real time faster than they could be looked up from a disk.  
        This eliminates the value of the salt in increasing the complexity of
        a brute force attack for even low entropy passwords.

		 </t>
     </section>
     <section title="OAuth security considerations" anchor="oauth_sec">
      <t>All the OAuth security analysis presented in <xref target="RFC6819"/>
      applies so readers SHOULD carefully follow it.</t>
	  </section>
	  
	  <section title="TLS security considerations" anchor="tls_sec">
      <t>Curent security
      considerations can be found in <xref target="BCP195">Recommendations
      for Secure Use of TLS and DTLS</xref>.  This 
      supersedes the TLS version recommendations in <xref target="RFC6749">OAuth
        2.0</xref>.</t>
	  </section>
    </section>

    <section anchor="Acknowledgements" title="Acknowledgements">
      <t>The initial draft of this specification was created by the OpenID
      AB/Connect Working Group of the OpenID Foundation. </t>

      <t>This specification is the work of the OAuth Working Group, which
      includes dozens of active and dedicated participants.  In particular,
      the following individuals contributed ideas, feedback, and wording
      that shaped and formed the final specification:</t>
      <t><list>
          <t>Anthony Nadalin, Microsoft</t>
          <t>Axel Nenker, Deutsche Telekom</t>
          <t>Breno de Medeiros, Google</t>
          <t>Brian Campbell, Ping Identity</t>
          <t>Chuck Mortimore, Salesforce</t>
          <t>Dirk Balfanz, Google</t>
          <t>Eduardo Gueiros, Jive Communications</t>
          <t>Hannes Tschonfenig, ARM</t>
          <t>James Manger, Telstra</t>
          <t>John Bradley, Ping Identity</t>
          <t>Justin Richer, MIT Kerberos</t>
          <t>Josh Mandel, Boston Children's Hospital</t>
          <t>Lewis Adam, Motorola Solutions</t>
          <t>Madjid Nakhjiri, Samsung</t>
          <t>Michael B. Jones, Microsoft</t>
          <t>Nat Sakimura, Nomura Research Institute</t>
          <t>Naveen Agarwal, Google</t>
          <t>Paul Madsen, Ping Identity</t>
          <t>Phil Hunt, Oracle</t>
          <t>Prateek Mishra, Oracle</t>
          <t>Ryo Ito, mixi</t>
          <t>Scott Tomilson, Ping Identity</t>
          <t>Sergey Beryozkin</t>
          <t>Takamichi Saito</t>
          <t>Torsten Lodderstedt, Deutsche Telekom</t>
          <t>William Denniss, Google</t>        
      </list></t>
   

    </section>

    <section title="Revision History" anchor="hist">
    <t>-15</t>
        <t>
            <list style="symbols">
            <t>Addressed Barry's IESG comments around IANA Registration</t>
            <t>Addressed Barry's IESG comments around Sec 7.2 downgrade attack</t>
            <t>fix a typo for William and make a small change to Fig 1.1 clarifying t_m</t>
            <t>more wording changes to sec 7.2 re Barry</t>
            <t>made the two SHOULD NOT use plain recommendations consistent.</t>
            <t>slightly cleaned up grammer in Sec 7.2</t>
            </list>
        </t>
    <t>-14</t>
        <t>
            <list style="symbols">
            <t>#38. Expanded Section 7.2 to explain why plain should not be used.</t>
            <t>#39. Modified Section 4.4.1 to discourage the use of plain.</t>
            <t>#40. Modified Intro text to explain the attack better.</t>
            <t>#41. Added explanation that the token request is protected in the 
            Last paragraph of the Introduction.</t>
            <t>#42. Sec 4.2: Removed redundant double quotes caused by spanx.</t>
            <t>#43. Sec 4.4: Replaced code with authorization code. </t>
            <t>#44. Sec 4.5: say "code_verifier" rather than "secret"</t>
            <t>#45. Sec 4.4.1: Expanded PKCE. </t>
            <t>#46. Sec 5: SHOULD in para 1 removed.</t>
            <t>Added abbreviations section. </t>
            </list>
        </t>
    <t>-13</t>
		<t>
		    <list style="symbols">
			<t>Fix the parameter usage locations for the OAuth Parameters Registry per 
			Hannes response.</t>
			<t>Clarify for IANA that the new registry is a  sub-registry of OAuth Parameters registry</t>
			<t>aded text on why the code_challenge_method is not sent to the token endpoint.</t>

			
			</list>
		</t>
    <t>-12</t>
		<t>
		    <list style="symbols">
			<t>clarify that the client secret we are talking about in the Introduction
			is a OAuth 2 client_secret.</t>
			<t>Update salting security consideration based on Ben's feedback</t>
			
			</list>
		</t>
        <t>-11</t>
		<t>
		    <list style="symbols">
			<t>add spanx for plain in sec 4.4 RE Kathleen's comment</t>
			<t>Add security consideration on TLS and reference BCP195</t>
			<t>Update to make clearer that plain can only be used for backwards
			 compatibility and constrained environments</t>
			</list>
		</t>
    
    <t>-10</t>
		<t>
		    <list style="symbols">
		    <t>re #33 specify lower limit to code_verifier in prose</t>
		    <t>remove base64url decode from draft, all steps now use encode only</t>
		    <t>Expanded MTI </t>
		    <t>re #33 change length of 32 octet base64url encoded string back to 43 octets</t>
			</list>
		</t>

        <t>-09</t>
		<t>
		    <list style="symbols">
		    <t>clean up some external references so they don't point at internal sections</t>
			</list>
		</t>

		
        <t>-08</t>
		<t>
			<list style="symbols">
			<t>changed BASE64URL to BASE64URL-ENCODE to be more consistent with appendix A
			Fixed lowercase base64url in appendix B</t>
			<t>Added appendix B as an example of S256 processing </t>
			<t>Change reference for unreserved characters to RFC3986 from base64URL</t>
			</list>
		</t>

        <t>-07</t>
		<t>
			<list style="symbols">
			<t>removed unused discovery reference and UTF8</t>
			<t>re #32 added ASCII(STRING) to make clear that it is the byte array that is being hashed</t>
			<t>re #2  Remove discovery requirement section.</t>
			<t>updated Acknowledgement</t>
			<t>re #32 remove unneeded UTF8(STRING) definition, and define STRING for ASCII(STRING)</t>
			<t>re #32 remove unneeded utf8 reference from BASE64URL-DECODE(STRING) def</t>
			<t>resolves #31 unused definition of concatenation </t>
			<t>re #30 Update figure text call out the endpoints</t>
			<t>re #30 Update figure to call out the endpoints</t>
			<t>small wording change to the introduction</t>
			</list>
		</t>
    <t>-06</t>
		<t>
			<list style="symbols">
			    <t> fix date</t>
			    <t>replace spop with pkce for registry and other references</t>
			    <t>re #29 change name again</t>
			    <t>re #27 removed US-ASCII reference</t>
			    <t>re #27 updated ABNF for code_verifier </t>
			    <t>resolves #24 added security consideration for salting</t>
			    <t>resolves #29 Changed title</t>
			    <t>updated reference to RFC4634 to RFC6234 re #27</t>
			    <t>changed reference for US-ASCII to RFC20 re #27</t>
			    <t>resolves #28 added Acknowledgements</t>
			    <t>resolves #27 updated ABNF</t>
			    <t>resolves #26 updated abstract and added Hannes figure</t>

				
			</list>
		</t>
    <t>-05</t>
		<t>
			<list style="symbols">
				<t>Added IANA registry for code_challenge_method + fixed some broken 
				internal references.</t>
			</list>
		</t>

	<t>-04</t>
		<t>
			<list style="symbols">
				<t>Added error response to authorization response.</t>
			</list>
		</t>

    <t>-03</t>
      <t>
        <list style="symbols">
          <t>Added an abstract protocol diagram and explanation</t>
        </list>
      </t>
    
    <t>-02</t>

      <t>
        <list style="symbols">
          <t>Copy edits</t>
        </list>
      </t>
    

	  <t>-01</t>

      <t><list style="symbols">
	      <t>Specified exactly two supported transformations</t> 
		   <t>Moved discovery steps to security considerations.</t>
          <t>Incorporated readability comments by Eduardo Gueiros.</t>
		   <t>Changed MUST in 3.1 to SHOULD.</t>
        </list>
		</t>
		
      <t>-00</t>

      <t><list style="symbols">
          <t>Initial IETF version.</t>
        </list></t>
    </section>
  </middle>

  <back>
    <references title="Normative References">
      <?rfc include='reference.RFC.0020' ?>

      <?rfc include='reference.RFC.2119'?>
      
      <?rfc include='reference.RFC.3986'?>
      
      <?rfc include='reference.RFC.4648' ?>

      <?rfc include='reference.RFC.5234'?>

      <?rfc include='reference.RFC.6234'?>

      <?rfc include='reference.RFC.6749'?>
      
      <?rfc include='reference.RFC.5226'?>
      
		<reference anchor='BCP195'>

		<front>
		<title>Recommendations for Secure Use of Transport Layer Security (TLS) and 
		Datagram Transport Layer Security (DTLS)</title>
		<author initials='Y.' surname='Sheffer' fullname='Y. Sheffer'>
		<organization /></author>
		<author initials='R.' surname='Holz' fullname='R. Holz'>
		<organization /></author>
		<author initials='P.' surname='Saint-Andre' fullname='P. Saint-Andre'>
		<organization /></author>
		<date year='2015' month='May' />
		<abstract>
		<t>Transport Layer Security (TLS) and Datagram Transport Layer Security (DTLS) are
		 widely used to protect data exchanged over application protocols such as HTTP, 
		 SMTP, IMAP, POP, SIP, and XMPP.  Over the last few years, several serious 
		 attacks on TLS have emerged, including attacks on its most commonly used cipher 
		 suites and their modes of operation.  This document provides recommendations for 
		 improving the security of deployed services that use TLS and DTLS.  The 
		 recommendations are applicable to the majority of use cases.</t></abstract></front>

		<seriesInfo name='BCP' value='195' />
		<seriesInfo name='RFC' value='7525' />
		<format type='TXT' octets='60283' target='http://www.rfc-editor.org/bcp/bcp195.txt' />
		</reference> 
		
    </references>

    <references title="Informative References">
      <?rfc include='reference.RFC.6819'?>

      <!--<?rfc include="http://xml.resource.org/public/rfc/bibxml/reference.RFC.4949"?>-->


    </references>
    
        <section title="Notes on implementing base64url encoding without padding" anchor="base64urlnotes">

      <t>
	This appendix describes how to implement a base64url encoding
	function without padding based upon standard
	base64 encoding function that uses padding.
      </t>
      <t>
	To be concrete, example C# code implementing these functions
	is shown below.  Similar code could be used in other
	languages.
      </t>

      <figure><artwork><![CDATA[
  static string base64urlencode(byte [] arg)
  {
    string s = Convert.ToBase64String(arg); // Regular base64 encoder
    s = s.Split('=')[0]; // Remove any trailing '='s
    s = s.Replace('+', '-'); // 62nd char of encoding
    s = s.Replace('/', '_'); // 63rd char of encoding
    return s;
  }

]]></artwork></figure>

    
      <t>
	An example correspondence between unencoded and encoded values
	follows.  The octet sequence below encodes into the string
	below, which when decoded, reproduces the octet sequence.
      </t>

      <figure><artwork>3 236 255 224 193</artwork></figure>

      <figure><artwork>A-z_4ME</artwork></figure>
      </section>
      
      <section title="Example for the S256 code_challenge_method" anchor="examples256">
      
      <t>The client uses output of a suitable random number generator to create a
       32-octet sequence.  The octets representing the value in this example
       (using JSON array notation) are:"</t>
       
      <figure><artwork><![CDATA[
   [116, 24, 223, 180, 151, 153, 224, 37, 79, 250, 96, 125, 216, 173,
   187, 186, 22, 212, 37, 77, 105, 214, 191, 240, 91, 88, 5, 88, 83,
   132, 141, 121]
]]></artwork></figure>
        
        <t>Encoding this octet sequence as a Base64url provides the value of the code_verifier:</t>
         
      <figure><artwork><![CDATA[
    dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW1gFWFOEjXk
]]></artwork></figure>

      <t>The code_verifier is then hashed via the SHA256 hash function to produce:</t>
<figure><artwork><![CDATA[
  [19, 211, 30, 150, 26, 26, 216, 236, 47, 22, 177, 12, 76, 152, 46,
   8, 118, 168, 120, 173, 109, 241, 68, 86, 110, 225, 137, 74, 203, 
   112, 249, 195]
]]></artwork></figure>      
      
      <t>Encoding this octet sequence as a base64url provides the value of the code_challenge:</t>
      
<figure><artwork><![CDATA[
    E9Melhoa2OwvFrEMTJguCHaoeK1t8URWbuGJSstw-cM
]]></artwork></figure> 

       <t>The authorization request includes:</t>
       
       <figure><artwork><![CDATA[
    code_challenge=E9Melhoa2OwvFrEMTJguCHaoeK1t8URWbuGJSstw-cM
    &code_challange_method=S256
]]></artwork></figure> 

        <t>The Authorization server then records the code_challenge and 
        code_challenge_method along with the code that is granted to the client.</t>
        
        <t>in the request to the token_endpoint the client includes the code received in 
        the authorization response as well as the additional paramater:</t>
        
       <figure><artwork><![CDATA[
    code_verifier=dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW1gFWFOEjXk
]]></artwork></figure>
      
      <t>The Authorization server retrieves the information for the code grant.  
      Based on the recorded code_challange_method being S256, it then hashes 
      and base64url encodes the value of
      code_verifier. BASE64URL-ENCODE(SHA256(ASCII(<spanx style="verb">code_verifier</spanx> )))</t>
      
      <t>The calculated value is then compared with the value of 
      <spanx style="verb">code_challenge</spanx>: </t>
      
           
           <t>BASE64URL-ENCODE(SHA256(ASCII(<spanx style="verb">code_verifier</spanx> ))) 
           == code_challenge</t>

        <t>
        If the two values are equal then the Authorization server can provide the tokens
        as long as there are no other errors in the request.  If the values are not equal
        then the request must be rejected, and an error returned.
        </t>
           
      </section>
      
  </back>
</rfc>
