Copyright © 2014 W3C® (MIT, ERCIM, Keio, Beihang), All Rights Reserved. W3C liability, trademark and document use rules apply.
This is a first attempt at specifying Curve25519 ECDH in WebCrypto.
First draft.
This describes using Elliptic Curve Diffie-Hellman (ECDH) for key generation and key agreement, as specified by Curve25519.
The recognized algorithm name for
this algorithm is "ECDH-CURVE25519"
.
Operation | Parameters | Result |
---|---|---|
generateKey | None | CryptoKeyPair |
deriveBits | EcdhKeyDeriveParams | Octet string |
importKey | None | CryptoKey |
exportKey | None | object |
If usages contains a value which is not
one of "deriveKey"
or "deriveBits"
,
then return an error named
InvalidAccessError
.
Generate an Elliptic Curve key pair, as defined in [Curve25519].
If performing the operation results in an error,
then return an error named
OperationError
.
Let algorithm be a new KeyAlgorithm object.
Set the name member of
algorithm to "ECDH-CURVE25519"
.
Let publicKey be a new CryptoKey object representing the public key of the generated key pair.
Set the [[type]] internal slot of
publicKey to "public"
Set the [[algorithm]] internal slot of publicKey to algorithm.
Set the [[extractable]] internal slot of publicKey to true.
Set the [[usages]] internal slot of publicKey to be the empty list.
Let privateKey be a new CryptoKey object representing the private key of the generated key pair.
Set the [[type]] internal slot of
privateKey to "private"
Set the [[algorithm]] internal slot of privateKey to algorithm.
Set the [[extractable]] internal slot of privateKey to extractable.
Set the [[usages]] internal slot of
privateKey to be the
usage intersection of
usages and [ "deriveKey", "deriveBits" ]
.
Let result be a new CryptoKeyPair dictionary.
Set the publicKey attribute of result to be publicKey.
Set the privateKey attribute of result to be privateKey.
Return the result of converting result to an ECMAScript Object, as defined by [WEBIDL].
If the [[type]] internal slot of
key is not "private"
, then return an error named InvalidAccessError
.
Let publicKey be the public member of normalizedAlgorithm.
If the name attribute of the [[algorithm]] internal slot of
publicKey is not "ECDH-CURVE25519"
, then return an error named InvalidAccessError
.
If the [[type]] internal slot of
publicKey is not "public"
, then return an error named InvalidAccessError
.
Perform the Curve25519 function specified in Curve25519 with key as the EC private key (first argument) and the EC public key represented by the [[handle]] internal slot of publicKey (second argument).
If performing the operation results in an error,
then return an error named
OperationError
.
Let secret be the 32-byte octet string output from the Curve25519 function defined in Curve25519. In other words, secret is the unique 32-byte little-endian encoding of an integer >= 0 and < 2255-19.
DataError
.
Let keyData be the key data to be imported.
"jwk"
:Let jwk be the JsonWebKey dictionary represented by keyData.
If an error occurred while parsing,
then return an error named
DataError
.
If the "kty"
field of
jwk is not
"oct"
,
then return an error named
DataError
.
If the "use"
field of jwk is present,
then return an error named
DataError
.
If the "key_ops"
field of jwk is present, and
is invalid according to the requirements of JSON Web
Key, or it does not contain all of the specified usages
values, then return an error
named DataError
.
If the "ext"
field of jwk is present and
has the value false and extractable is true,
then return an error named
DataError
.
If the "k"
field of
jwk is not a base64url encoding of a 32-byte
octet string then return an error named
DataError
.
If the "k"
field of
jwk does not have bits 0, 1, and 2 of the first
byte clear, bit 7 of the last byte clear, and bit 6 of the
last byte set, as per Curve25519 Section 3, then return an error named
DataError
.
Let key be a new CryptoKey object that represents the
Elliptic Curve private key
identified by interpreting the "k"
field of
jwk as a private key
according to Curve25519.
Let algorithm be a new instance of a KeyAlgorithm object.
Set the name attribute of
algorithm to "ECDH-CURVE25519"
.
Set the [[algorithm]] internal slot of key to algorithm.
"raw"
:
If usages is not the empty list,
then return an error named
DataError
.
If extractable is false,
then return an error named
InvalidAccessError
.
Let Q be the Curve25519 public key identified by interpreting keyData according to Curve25519. In other words, keyData is the 32-byte little-endian encoding of an integer >= 0 and < 2255-19. The high-order bit is ignored. If the remaining 255 bits encode a number >= 2255-19, that number is reduced modulo 2255-19.
Let algorithm be a new KeyAlgorithm object.
Set the name attribute of
algorithm to "ECDH-CURVE25519"
.
Let key be a new CryptoKey object.
Set the [[type]] internal slot
of key to "public"
Set the [[algorithm]] internal slot of key to algorithm.
Set the [[usages]] internal slot of key to usages.
Set the [[extractable]] internal slot of key to extractable.
Return an error named
NotSupportedError
.
Return key
Let key be the CryptoKey to be exported.
If the underlying cryptographic key material represented by the [[handle]] internal slot of key
cannot be accessed, then return an
error named OperationError
.
"jwk"
:
If the [[type]] internal slot
of key is not
"private"
, then return an
error named OperationError
.
Let jwk be a new JsonWebKey dictionary.
Set the kty
attribute of jwk to
"oct"
.
Set the k
attribute of
jwk to a base64url encoding of the 32-octet curve25519
private key. In other words, the base64url-encoded value
is a 32-byte encoding of a little-endian integer with bits 0, 1, and 2 of the first byte clear, bit 7 of the last
byte clear, and bit 6 of the last byte set.
Set the key_ops
attribute of jwk to the
usages attribute of key.
Set the ext
attribute of jwk to the [[extractable]] internal slot
of key.
Let result be the result of converting jwk to an ECMAScript Object, as defined by [WEBIDL].
"raw"
:
If the [[type]] internal slot
of key is not "public"
, then return an error named InvalidAccessError
.
Let data be the 32-byte octet string representing the Curve25519 public key represented by [[handle]] internal slot of key according to Curve25519. In other words, data is the unique 32-byte little-endian encoding of an integer >= 0 and < 2255-19.
Let result be a new ArrayBuffer
containing
data.
Return an error named
NotSupportedError
.
Return result.
Thanks to Dan Berstein for Curve25519. Thanks to Ryan Sleevi for advice.