EST-coaps uses CoAP to transfer EST messages, aided by Block-Wise Transfer [
RFC 7959], to avoid IP fragmentation. The use of blocks for the transfer of larger EST messages is specified in
Section 4.6.
Figure 1 shows the layered EST-coaps architecture.
The EST-coaps protocol design follows closely the EST design. The supported message types in EST-coaps are:
-
CA certificate retrieval needed to receive the complete set of CA certificates.
-
Simple enroll and re-enroll for a CA to sign client identity public keys.
-
Certificate Signing Request (CSR) attribute messages that informs the client of the fields to include in a CSR.
-
Server-side key generation messages to provide a client identity private key when the client chooses so.
While [
RFC 7030] permits a number of the EST functions to be used without authentication, this specification requires that the client
MUST be authenticated for all functions.
EST-coaps is targeted for low-resource networks with small packets. Two types of installations are possible: (1) a rigid one, where the address and the supported functions of the EST server(s) are known, and (2) a flexible one, where the EST server and its supported functions need to be discovered.
For both types of installations, saving header space is important and short EST-coaps URIs are specified in this document. These URIs are shorter than the ones in [
RFC 7030]. Two example EST-coaps resource path names are:
coaps://example.com:<port>/.well-known/est/<short-est>
coaps://example.com:<port>/.well-known/est/ArbitraryLabel/<short-est>
The short-est strings are defined in
Table 1. Arbitrary Labels are usually defined and used by EST CAs in order to route client requests to the appropriate certificate profile. Implementers should consider using short labels to minimize transmission overhead.
The EST-coaps server URIs, obtained through discovery of the EST-coaps resource(s) as shown below, are of the form:
coaps://example.com:<port>/<root-resource>/<short-est>
coaps://example.com:<port>/<root-resource>/ArbitraryLabel/<short-est>
Figure 5 in
Section 3.2.2 of
RFC 7030 enumerates the operations and corresponding paths that are supported by EST.
Table 1 provides the mapping from the EST URI path to the shorter EST-coaps URI path.
EST |
EST-coaps |
/cacerts |
/crts |
/simpleenroll |
/sen |
/simplereenroll |
/sren |
/serverkeygen |
/skg (PKCS #7) |
/serverkeygen |
/skc (application/pkix-cert) |
/csrattrs |
/att |
Table 1: Short EST-coaps URI Path
The /skg message is the EST /serverkeygen equivalent where the client requests a certificate in PKCS #7 format and a private key. If the client prefers a single application/pkix-cert certificate instead of PKCS #7, it will make an /skc request. In both cases (i.e., /skg, /skc), a private key
MUST be returned.
Clients and servers
MUST support the short resource EST-coaps URIs.
In the context of CoAP, the presence and location of (path to) the EST resources are discovered by sending a GET request to "/.well-known/core" including a resource type (RT) parameter with the value "ace.est*" [
RFC 6690]. The example below shows the discovery over CoAPS of the presence and location of EST-coaps resources. Linefeeds are included only for readability.
REQ: GET /.well-known/core?rt=ace.est*
RES: 2.05 Content
</est/crts>;rt="ace.est.crts";ct="281 287",
</est/sen>;rt="ace.est.sen";ct="281 287",
</est/sren>;rt="ace.est.sren";ct="281 287",
</est/att>;rt="ace.est.att";ct=285,
</est/skg>;rt="ace.est.skg";ct=62,
</est/skc>;rt="ace.est.skc";ct=62
The first three lines, describing ace.est.crts, ace.est.sen, and ace.est.sren, of the discovery response above
MUST be returned if the server supports resource discovery. The last three lines are only included if the corresponding EST functions are implemented (see
Table 2). The Content-Formats in the response allow the client to request one that is supported by the server. These are the values that would be sent in the client request with an Accept Option.
Discoverable port numbers can be returned in the response payload. An example response payload for non-default CoAPS server port 61617 follows below. Linefeeds are included only for readability.
REQ: GET /.well-known/core?rt=ace.est*
RES: 2.05 Content
<coaps://[2001:db8:3::123]:61617/est/crts>;rt="ace.est.crts";
ct="281 287",
<coaps://[2001:db8:3::123]:61617/est/sen>;rt="ace.est.sen";
ct="281 287",
<coaps://[2001:db8:3::123]:61617/est/sren>;rt="ace.est.sren";
ct="281 287",
<coaps://[2001:db8:3::123]:61617/est/att>;rt="ace.est.att";
ct=285,
<coaps://[2001:db8:3::123]:61617/est/skg>;rt="ace.est.skg";
ct=62,
<coaps://[2001:db8:3::123]:61617/est/skc>;rt="ace.est.skc";
ct=62
The server
MUST support the default /.well-known/est root resource. The server
SHOULD support resource discovery when it supports non-default URIs (like /est or /est/ArbitraryLabel) or ports. The client
SHOULD use resource discovery when it is unaware of the available EST-coaps resources.
Throughout this document, the example root resource of /est is used.
This specification contains a set of required-to-implement functions, optional functions, and not-specified functions. The unspecified functions are deemed too expensive for low-resource devices in payload and calculation times.
Table 2 specifies the mandatory-to-implement or optional implementation of the EST-coaps functions. Discovery of the existence of optional functions is described in
Section 4.1.
EST Functions |
EST-coaps Implementation |
/cacerts |
MUST
|
/simpleenroll |
MUST
|
/simplereenroll |
MUST
|
/fullcmc |
Not specified |
/serverkeygen |
OPTIONAL
|
/csrattrs |
OPTIONAL
|
Table 2: List of EST-coaps Functions
EST-coaps is designed for low-resource devices; hence, it does not need to send Base64-encoded data. Simple binary is more efficient (30% smaller payload for DER-encoded ASN.1) and well supported by CoAP. Thus, the payload for a given media type follows the ASN.1 structure of the media type and is transported in binary format.
The Content-Format (HTTP Content-Type equivalent) of the CoAP message determines which EST message is transported in the CoAP payload. The media types specified in the HTTP Content-Type header field (
Section 3.2.4 of
RFC 7030) are specified by the Content-Format Option (12) of CoAP. The combination of URI-Path and Content-Format in EST-coaps
MUST map to an allowed combination of URI and media type in EST. The required Content-Formats for these requests and response messages are defined in
Section 8.1. The CoAP response codes are defined in
Section 4.5.
Content-Format 287 can be used in place of 281 to carry a single certificate instead of a PKCS #7 container in a /crts, /sen, /sren, or /skg response. Content-Format 281
MUST be supported by EST-coaps servers. Servers
MAY also support Content-Format 287. It is up to the client to support only Content-Format 281, 287 or both. The client will use a CoAP Accept Option in the request to express the preferred response Content-Format. If an Accept Option is not included in the request, the client is not expressing any preference and the server
SHOULD choose format 281.
Content-Format 286 is used in /sen, /sren, and /skg requests and 285 in /att responses.
A representation with Content-Format identifier 62 contains a collection of representations along with their respective Content-Format. The Content-Format identifies the media type application/multipart-core specified in [
RFC 8710]. For example, a collection, containing two representations in response to an EST-coaps server-side key generation /skg request, could include a private key in PKCS #8 [
RFC 5958] with Content-Format identifier 284 (0x011C) and a single certificate in a PKCS #7 container with Content-Format identifier 281 (0x0119). Such a collection would look like [284,h'0123456789abcdef', 281,h'fedcba9876543210'] in diagnostic Concise Binary Object Representation (CBOR) notation. The serialization of such CBOR content would be:
84 # array(4)
19 011C # unsigned(284)
48 # bytes(8)
0123456789ABCDEF # "\x01#Eg\x89\xAB\xCD\xEF"
19 0119 # unsigned(281)
48 # bytes(8)
FEDCBA9876543210 # "\xFE\xDC\xBA\x98vT2\x10"
When the client makes an /skc request, the certificate returned with the private key is a single X.509 certificate (not a PKCS #7 container) with Content-Format identifier 287 (0x011F) instead of 281. In cases where the private key is encrypted with Cryptographic Message Syntax (CMS) (as explained in
Section 4.8), the Content-Format identifier is 280 (0x0118) instead of 284. The Content-Format used in the response is summarized in
Table 3.
Function |
Response, Part 1 |
Response, Part 2 |
/skg |
284 |
281 |
/skc |
280 |
287 |
Table 3: Response Content-Formats for /skg and /skc
The key and certificate representations are DER-encoded ASN.1, in its binary form. An example is shown in
Appendix A.3.
The general EST-coaps message characteristics are:
-
EST-coaps servers sometimes need to provide delayed responses, which are preceded by an immediately returned empty ACK or an ACK containing response code 5.03 as explained in Section 4.7. Thus, it is RECOMMENDED for implementers to send EST-coaps requests in Confirmable (CON) CoAP messages.
-
The CoAP Options used are Uri-Host, Uri-Path, Uri-Port, Content-Format, Block1, Block2, and Accept. These CoAP Options are used to communicate the HTTP fields specified in the EST REST messages. The Uri-host and Uri-Port Options can be omitted from the CoAP message sent on the wire. When omitted, they are logically assumed to be the transport protocol destination address and port, respectively. Explicit Uri-Host and Uri-Port Options are typically used when an endpoint hosts multiple virtual servers and uses the Options to route the requests accordingly. Other CoAP Options should be handled in accordance with [RFC 7252].
-
EST URLs are HTTPS based (https://); in CoAP, these are assumed to be translated to CoAPS (coaps://).
Table 1 provides the mapping from the EST URI path to the EST-coaps URI path.
Appendix A includes some practical examples of EST messages translated to CoAP.
Section 5.9 of
RFC 7252 and
Section 7 of
RFC 8075 specify the mapping of HTTP response codes to CoAP response codes. The success code in response to an EST-coaps GET request (/crts, /att) is 2.05. Similarly, 2.04 is used in successful response to EST-coaps POST requests (/sen, /sren, /skg, /skc).
EST makes use of HTTP 204 or 404 responses when a resource is not available for the client. In EST-coaps, 2.04 is used in response to a POST (/sen, /sren, /skg, /skc). 4.04 is used when the resource is not available for the client.
HTTP response code 202 with a Retry-After header field in [
RFC 7030] has no equivalent in CoAP. HTTP 202 with Retry-After is used in EST for delayed server responses.
Section 4.7 specifies how EST-coaps handles delayed messages with 5.03 responses with a Max-Age Option.
Additionally, EST's HTTP 400, 401, 403, 404, and 503 status codes have their equivalent CoAP 4.00, 4.01, 4.03, 4.04, and 5.03 response codes in EST-coaps.
Table 4 summarizes the EST-coaps response codes.
Operation |
EST-coaps Response Code |
Description |
/crts, /att |
2.05 |
Success. Certs included in the response payload. |
|
4.xx / 5.xx |
Failure. |
/sen, /skg, /sren, /skc |
2.04
|
Success. Cert included in the response payload. |
|
5.03 |
Retry in Max-Age Option time. |
|
4.xx / 5.xx |
Failure. |
Table 4: EST-coaps Response Codes
DTLS defines fragmentation only for the handshake and not for secure data exchange (DTLS records). [
RFC 6347] states that to avoid using IP fragmentation, which involves error-prone datagram reconstitution, invokers of the DTLS record layer should size DTLS records so that they fit within any Path MTU estimates obtained from the record layer. In addition, invokers residing on 6LoWPAN (IPv6 over Low-Power Wireless Personal Area Networks) over IEEE 802.15.4 networks [
IEEE802.15.4] are recommended to size CoAP messages such that each DTLS record will fit within one or two IEEE 802.15.4 frames.
That is not always possible in EST-coaps. Even though ECC certificates are small in size, they can vary greatly based on signature algorithms, key sizes, and Object Identifier (OID) fields used. For 256-bit curves, common Elliptic Curve Digital Signature Algorithm (ECDSA) cert sizes are 500-1000 bytes, which could fluctuate further based on the algorithms, OIDs, Subject Alternative Names (SANs), and cert fields. For 384-bit curves, ECDSA certificates increase in size and can sometimes reach 1.5KB. Additionally, there are times when the EST cacerts response from the server can include multiple certificates that amount to large payloads.
Section 4.6 of
RFC 7252 (CoAP) describes the possible payload sizes: "if nothing is known about the size of the headers, good upper bounds are 1152 bytes for the message size and 1024 bytes for the payload size".
Section 4.6 of
RFC 7252 also suggests that IPv4 implementations may want to limit themselves to more conservative IPv4 datagram sizes such as 576 bytes. Even with ECC, EST-coaps messages can still exceed MTU sizes on the Internet or 6LoWPAN [
RFC 4919] (
Section 2 of
RFC 7959). EST-coaps needs to be able to fragment messages into multiple DTLS datagrams.
To perform fragmentation in CoAP, [
RFC 7959] specifies the Block1 Option for fragmentation of the request payload and the Block2 Option for fragmentation of the return payload of a CoAP flow. As explained in
Section 1 of
RFC 7959, block-wise transfers should be used in Confirmable CoAP messages to avoid the exacerbation of lost blocks. EST-coaps servers
MUST implement Block1 and Block2. EST-coaps clients
MUST implement Block2. EST-coaps clients
MUST implement Block1 only if they are expecting to send EST-coaps requests with a packet size that exceeds the path MTU.
[
RFC 7959] also defines Size1 and Size2 Options to provide size information about the resource representation in a request and response. The EST-coaps client and server
MAY support Size1 and Size2 Options.
Examples of fragmented EST-coaps messages are shown in
Appendix B.
Server responses can sometimes be delayed. According to
Section 5.2.2 of
RFC 7252, a slow server can acknowledge the request and respond later with the requested resource representation. In particular, a slow server can respond to an EST-coaps enrollment request with an empty ACK with code 0.00 before sending the certificate to the client after a short delay. If the certificate response is large, the server will need more than one Block2 block to transfer it.
This situation is shown in
Figure 3. The client sends an enrollment request that uses N1+1 Block1 blocks. The server uses an empty 0.00 ACK to announce the delayed response, which is provided later with 2.04 messages containing N2+1 Block2 Options. The first 2.04 is a Confirmable message that is acknowledged by the client. Onwards, the client acknowledges all subsequent Block2 blocks. The notation of
Figure 3 is explained in
Appendix B.1.
POST [2001:db8::2:1]:61616/est/sen (CON)(1:0/1/256)
{CSR (frag# 1)} -->
<-- (ACK) (1:0/1/256) (2.31 Continue)
POST [2001:db8::2:1]:61616/est/sen (CON)(1:1/1/256)
{CSR (frag# 2)} -->
<-- (ACK) (1:1/1/256) (2.31 Continue)
.
.
.
POST [2001:db8::2:1]:61616/est/sen(CON)(1:N1/0/256)
{CSR (frag# N1+1)}-->
<-- (0.00 empty ACK)
|
... Short delay before the certificate is ready ...
|
<-- (CON) (1:N1/0/256)(2:0/1/256)(2.04 Changed)
{Cert resp (frag# 1)}
(ACK) -->
POST [2001:db8::2:1]:61616/est/sen (CON)(2:1/0/256) -->
<-- (ACK) (2:1/1/256) (2.04 Changed) {Cert resp (frag# 2)}
.
.
.
POST [2001:db8::2:1]:61616/est/sen (CON)(2:N2/0/256) -->
<-- (ACK) (2:N2/0/256) (2.04 Changed) {Cert resp (frag# N2+1)}
If the server is very slow (for example, manual intervention is required, which would take minutes), it
SHOULD respond with an ACK containing response code 5.03 (Service unavailable) and a Max-Age Option to indicate the time the client
SHOULD wait before sending another request to obtain the content. After a delay of Max-Age, the client
SHOULD resend the identical CSR to the server. As long as the server continues to respond with response code 5.03 (Service Unavailable) with a Max-Age Option, the client will continue to delay for Max-Age and then resend the enrollment request until the server responds with the certificate or the client abandons the request due to policy or other reasons.
To demonstrate this scenario,
Figure 4 shows a client sending an enrollment request that uses N1+1 Block1 blocks to send the CSR to the server. The server needs N2+1 Block2 blocks to respond but also needs to take a long delay (minutes) to provide the response. Consequently, the server uses a 5.03 ACK response with a Max-Age Option. The client waits for a period of Max-Age as many times as it receives the same 5.03 response and retransmits the enrollment request until it receives a certificate in a fragmented 2.04 response.
POST [2001:db8::2:1]:61616/est/sen (CON)(1:0/1/256)
{CSR (frag# 1)} -->
<-- (ACK) (1:0/1/256) (2.31 Continue)
POST [2001:db8::2:1]:61616/est/sen (CON)(1:1/1/256)
{CSR (frag# 2)} -->
<-- (ACK) (1:1/1/256) (2.31 Continue)
.
.
.
POST [2001:db8::2:1]:61616/est/sen(CON)(1:N1/0/256)
{CSR (frag# N1+1)}-->
<-- (ACK) (1:N1/0/256) (5.03 Service Unavailable) (Max-Age)
|
|
... Client tries again after Max-Age with identical payload ...
|
|
POST [2001:db8::2:1]:61616/est/sen(CON)(1:0/1/256)
{CSR (frag# 1)}-->
<-- (ACK) (1:0/1/256) (2.31 Continue)
POST [2001:db8::2:1]:61616/est/sen (CON)(1:1/1/256)
{CSR (frag# 2)} -->
<-- (ACK) (1:1/1/256) (2.31 Continue)
.
.
.
POST [2001:db8::2:1]:61616/est/sen(CON)(1:N1/0/256)
{CSR (frag# N1+1)}-->
|
... Immediate response when certificate is ready ...
|
<-- (ACK) (1:N1/0/256) (2:0/1/256) (2.04 Changed)
{Cert resp (frag# 1)}
POST [2001:db8::2:1]:61616/est/sen (CON)(2:1/0/256) -->
<-- (ACK) (2:1/1/256) (2.04 Changed) {Cert resp (frag# 2)}
.
.
.
POST [2001:db8::2:1]:61616/est/sen (CON)(2:N2/0/256) -->
<-- (ACK) (2:N2/0/256) (2.04 Changed) {Cert resp (frag# N2+1)}
Private keys can be generated on the server to support scenarios where server-side key generation is needed. Such scenarios include those where it is considered more secure to generate the long-lived, random private key that identifies the client at the server, or where the resources spent to generate a random private key at the client are considered scarce, or where the security policy requires that the certificate public and corresponding private keys are centrally generated and controlled. As always, it is necessary to use proper random numbers in various protocols such as (D)TLS (
Section 9.1).
When requesting server-side key generation, the client asks for the server or proxy to generate the private key and the certificate, which are transferred back to the client in the server-side key generation response. In all respects, the server treats the CSR as it would treat any enroll or re-enroll CSR; the only distinction here is that the server
MUST ignore the public key values and signature in the CSR. These are included in the request only to allow reuse of existing codebases for generating and parsing such requests.
The client /skg request is for a certificate in a PKCS #7 container and private key in two application/multipart-core elements. Respectively, an /skc request is for a single application/pkix-cert certificate and a private key. The private key Content-Format requested by the client is indicated in the PKCS #10 CSR request. If the request contains SMIMECapabilities and DecryptKeyIdentifier or AsymmetricDecryptKeyIdentifier, the client is expecting Content-Format 280 for the private key. Then, this private key is encrypted symmetrically or asymmetrically per [
RFC 7030]. The symmetric key or the asymmetric keypair establishment method is out of scope of this specification. An /skg or /skc request with a CSR without SMIMECapabilities expects an application/multipart-core with an unencrypted PKCS #8 private key with Content-Format 284.
The EST-coaps server-side key generation response is returned with Content-Format application/multipart-core [
RFC 8710] containing a CBOR array with four items (
Section 4.3). The two representations (each consisting of two CBOR array items) do not have to be in a particular order since each representation is preceded by its Content-Format ID. Depending on the request, the private key can be in unprotected PKCS #8 format [
RFC 5958] (Content-Format 284) or protected inside of CMS SignedData (Content-Format 280). The SignedData, placed in the outermost container, is signed by the party that generated the private key, which may be the EST server or the EST CA. SignedData placed within the Enveloped Data does not need additional signing as explained in
Section 4.4.2 of
RFC 7030. In summary, the symmetrically encrypted key is included in the encryptedKey attribute in a KEKRecipientInfo structure. In the case where the asymmetric encryption key is suitable for transport key operations, the generated private key is encrypted with a symmetric key. The symmetric key itself is encrypted by the client-defined (in the CSR) asymmetric public key and is carried in an encryptedKey attribute in a KeyTransRecipientInfo structure. Finally, if the asymmetric encryption key is suitable for key agreement, the generated private key is encrypted with a symmetric key. The symmetric key itself is encrypted by the client defined (in the CSR) asymmetric public key and is carried in a recipientEncryptedKeys attribute in a KeyAgreeRecipientInfo.
[
RFC 7030] recommends the use of additional encryption of the returned private key. For the context of this specification, clients and servers that choose to support server-side key generation
MUST support unprotected (PKCS #8) private keys (Content-Format 284). Symmetric or asymmetric encryption of the private key (CMS EnvelopedData, Content-Format 280)
SHOULD be supported for deployments where end-to-end encryption is needed between the client and a server. Such cases could include architectures where an entity between the client and the CA terminates the DTLS connection (Registrar in
Figure 5). Though [
RFC 7030] strongly recommends that clients request the use of CMS encryption on top of the TLS channel's protection, this document does not make such a recommendation; CMS encryption can still be used when mandated by the use case.