3. Message Format
CoAP 基于紧凑 message 的交换, 默认通过 UDP 传输 (即每个 CoAP message 占据一个 UDP datagram 的数据部分). CoAP 也可在 Datagram Transport Layer Security (DTLS) 上使用 (见 Section 9.1). 它还可在 SMS, TCP 或 SCTP 等其他传输上使用, 但这些传输的规范超出本文档范围. (CoAP 不支持 UDP-lite [RFC3828] 和 UDP zero checksum [RFC6936].)
CoAP message 采用简单的二进制格式编码. message format 以固定大小的 4 字节 header 开始. 其后是可变长度 Token 值, 长度可为 0 到 8 字节.
Token 值之后是零个或多个 Type-Length-Value (TLV) 格式的 CoAP Options 序列, 可选地后跟占据 datagram 剩余部分的 payload.
0 1 2 3
0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |Ver| T | TKL | Code | Message ID | +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | Token (if any, TKL bytes) ... +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | Options (if any) ... +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |1 1 1 1 1 1 1 1| Payload (if any) ... +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
Figure 7: Message Format
header 中的字段定义如下:
Version (Ver): 2-bit unsigned integer. 指示 CoAP version number. 本规范的实现 MUST 将此字段设置为 1 (01 binary). 其他值保留给未来版本. 具有未知 version number 的 message MUST 被静默忽略.
Type (T): 2-bit unsigned integer. 指示该 message 类型是 Confirmable (0), Non-confirmable (1), Acknowledgement (2) 还是 Reset (3). 这些 message type 的语义在 Section 4 中定义.
Token Length (TKL): 4-bit unsigned integer. 指示可变长度 Token 字段的长度 (0-8 bytes). 长度 9-15 保留, MUST NOT 发送, 并且 MUST 作为 message format error 处理.
Code: 8-bit unsigned integer, 拆分为 3-bit class (最高有效位) 和 5-bit detail (最低有效位), 记为 "c.dd", 其中 "c" 是 0 到 7 的数字, 表示 3-bit 子字段, "dd" 是 00 到 31 的两位数字, 表示 5-bit 子字段. class 可表示 request (0), success response (2), client error response (4) 或 server error response (5). (所有其他 class 值保留.) 作为特殊情况, Code 0.00 表示 Empty message. 对于 request, Code 字段指示 Request Method; 对于 response, 则指示 Response Code. 可能值维护在 CoAP Code Registries (Section 12.1) 中. request 和 response 的语义在 Section 5 中定义.
Message ID: 16-bit unsigned integer in network byte order. 用于检测 message 重复, 并将 Acknowledgement/Reset 类型的 message 与 Confirmable/Non-confirmable 类型的 message 匹配. Message ID 的生成规则和 message 匹配规则在 Section 4 中定义.
header 后跟 Token 值, 其长度按 Token Length 字段给出, 可为 0 到 8 字节. Token 值用于关联 request 和 response. Token 的生成规则以及 request 与 response 的关联规则在 Section 5.3.1 中定义.
Header 和 Token 后跟零个或多个 Option (Section 3.1). 一个 Option 后面可以是 message 结束, 另一个 Option, 或 Payload Marker 与 payload.
在 header, token 和 option (如果有) 之后, 是可选 payload. 如果存在且长度非零, 它前面带有固定的一字节 Payload Marker (0xFF), 用来指示 option 结束和 payload 开始. payload data 从 marker 之后一直延伸到 UDP datagram 结束, 即 Payload Length 根据 datagram size 计算. Payload Marker 缺失表示零长度 payload. 存在 marker 且后跟零长度 payload MUST 作为 message format error 处理.
Implementation Note: 字节值 0xFF 也可能出现在 option length 或 value 中, 因此简单地按字节扫描 0xFF 不是查找 payload marker 的可行技术. 只有在另一个 option 可能开始的位置, 字节 0xFF 才具有 payload marker 的含义.
3.1. Option Format
CoAP 定义了若干可包含在 message 中的 option. message 中的每个 option 实例指定所定义 CoAP option 的 Option Number, Option Value 的长度以及 Option Value 本身.
实例并不直接指定 Option Number, 而是 MUST 按 Option Number 顺序出现, 并在实例之间使用 delta encoding: 每个实例的 Option Number 计算为其 delta 与 message 中前一个实例的 Option Number 之和. 对 message 中第一个实例, 假定前一个 option 实例的 Option Number 为零. 通过使用 delta 为零, 可包含同一 option 的多个实例.
Option Number 维护在 "CoAP Option Numbers" registry (Section 12.2) 中. 本文档定义的 option 语义见 Section 5.4.
0 1 2 3 4 5 6 7
+---------------+---------------+
| | |
| Option Delta | Option Length | 1 byte
| | |
+---------------+---------------+
\
/ Option Delta / 0-2 bytes
\ (extended)
+-------------------------------+
\
/ Option Length / 0-2 bytes
\ (extended)
+-------------------------------+
\
/ /
\
/ Option Value / 0 or more bytes
\
/ /
\
+-------------------------------+
Figure 8: Option Format
option 中的字段定义如下:
Option Delta: 4-bit unsigned integer. 0 到 12 之间的值表示 Option Delta. 三个值保留用于特殊结构:
13: 初始字节后跟一个 8-bit unsigned integer, 表示 Option Delta minus 13.
14: 初始字节后跟一个 network byte order 的 16-bit unsigned integer, 表示 Option Delta minus 269.
15: 为 Payload Marker 保留. 如果该字段设置为此值但整个字节不是 payload marker, 则 MUST 作为 message format error 处理.
所得 Option Delta 用作此 option 的 Option Number 与前一 option (或第一个 option 时的零) 的 Option Number 之间的差值. 换言之, Option Number 通过简单累加本 option 及其之前所有 option 的 Option Delta 值计算.
Option Length: 4-bit unsigned integer. 0 到 12 之间的值以字节为单位指示 Option Value 的长度. 三个值保留用于特殊结构:
13: Option Value 前有一个 8-bit unsigned integer, 表示 Option Length minus 13.
14: Option Value 前有一个 network byte order 的 16-bit unsigned integer, 表示 Option Length minus 269.
15: 为未来使用保留. 如果该字段设置为此值, 则 MUST 作为 message format error 处理.
Value: 恰好 Option Length 字节的序列. Option Value 的长度和格式取决于相应 option, 该 option MAY 定义可变长度值. 本文档使用的格式见 Section 3.2; 其他文档中定义的 option MAY 使用其他 option value format.
3.2. Option Value Formats
本文档定义的 option 使用以下 option value format.
empty: 零长度字节序列.
opaque: 不透明字节序列.
uint: 非负整数, 使用 Option Length 字段给出的字节数按 network byte order 表示.
option 定义可指定允许的字节数范围; 如果有选择, sender SHOULD 用尽可能少的字节表示该整数, 即不带 leading zero byte. 例如, 数字 0 用 empty option value (零长度字节序列) 表示, 数字 1 用数值为 1 的单字节表示 (按最高有效位优先记法为 bit combination 00000001). recipient MUST 准备处理带 leading zero byte 的值.
Implementation Note: 允许 sender 采用的例外行为, 是为高度受限的模板化实现 (例如硬件实现) 设计的, 这些实现会在模板中使用固定大小 option.
string: Unicode string, 使用 UTF-8 [RFC3629] 以 Net-Unicode form [RFC5198] 编码.
注意, 在此处以及 CoAP 协议中所有使用 UTF-8 编码的其他位置, 其意图都是让编码后的 string 可由 CoAP 协议实现直接作为 opaque byte string 使用和比较. CoAP 实现中不期望也不需要执行 normalization (除非从 CoAP 协议之外的来源导入了未知是否已 normalization 的 Unicode string). 还要注意, ASCII string (不使用特殊 control character) 始终是有效的 UTF-8 Net-Unicode string.