1. Introduction
Il existe des centaines de formats standardisés pour la représentation binaire de données structurées (également connus sous le nom de formats de sérialisation binaire). Parmi ceux-ci, certains sont destinés à des domaines d'information spécifiques, tandis que d'autres sont généralisés pour des données arbitraires. Au sein de l'IETF, les formats les plus connus dans cette dernière catégorie sont probablement le BER et le DER d'ASN.1 [ASN.1].
Le format défini ici suit des objectifs de conception spécifiques qui ne sont pas bien satisfaits par les formats actuels. Le modèle de données sous-jacent (Data Model) est une version étendue du modèle de données JSON [RFC8259]. Il est important de noter qu'il ne s'agit pas d'une proposition d'extension générale de la grammaire dans RFC 8259, car cela entraînerait une incompatibilité significative avec les documents JSON déjà déployés. Au lieu de cela, ce document définit simplement son propre modèle de données qui part de JSON.
L'annexe E liste certains formats binaires existants et discute de la mesure dans laquelle ils correspondent ou ne correspondent pas aux objectifs de conception de Concise Binary Object Representation (CBOR, Représentation Concise d'Objet Binaire).
Ce document rend obsolète [RFC7049], en fournissant des améliorations éditoriales, de nouveaux détails et des corrections d'errata tout en maintenant une compatibilité complète avec le format d'échange de RFC 7049. Il ne crée pas une nouvelle version du format.
1.1. Objectives (Objectifs)
Les objectifs de CBOR, approximativement par ordre décroissant d'importance, sont:
-
La représentation doit pouvoir encoder sans ambiguïté la plupart des formats de données courants utilisés dans les standards Internet.
-
Elle doit représenter un ensemble raisonnable de types de données de base et de structures utilisant un encodage binaire. "Raisonnable" ici est largement influencé par les capacités de JSON, avec l'ajout majeur des chaînes d'octets binaires (Byte String). Les structures prises en charge sont limitées aux tableaux (Array) et aux arbres (Tree); les boucles (Loop) et les graphes de type treillis (Lattice-Style Graph) ne sont pas pris en charge.
-
Il n'est pas nécessaire que tous les formats de données soient encodés de manière unique; c'est-à-dire qu'il est acceptable que le nombre "7" puisse être encodé de plusieurs manières différentes.
-
-
Le code d'un encodeur ou décodeur doit pouvoir être compact afin de prendre en charge des systèmes avec une mémoire, une puissance de processeur et des jeux d'instructions très limités.
-
Un encodeur et un décodeur doivent pouvoir être implémentés avec une très petite quantité de code (par exemple, dans des nœuds contraints de classe 1 tels que définis dans [RFC7228]).
-
Le format doit utiliser des représentations de données de machines contemporaines (par exemple, ne nécessitant pas de conversion binaire-décimale).
-
-
Les données doivent pouvoir être décodées sans description de schéma (Schema Description).
- Similaire à JSON, les données encodées doivent être auto-descriptives (Self-Describing) afin qu'un décodeur générique puisse être écrit.
-
La sérialisation doit être raisonnablement compacte, mais la compacité des données est secondaire par rapport à la compacité du code pour l'encodeur et le décodeur.
- "Raisonnable" ici est délimité par JSON comme limite supérieure de taille et par la complexité de l'implémentation, qui limite la quantité d'effort pouvant être consacré à atteindre cette compacité. L'utilisation de schémas de compression généraux ou de manipulations de bits étendues viole les objectifs de complexité.
-
Le format doit être applicable à la fois aux nœuds contraints (Constrained Node) et aux applications à fort volume.
- Cela signifie qu'il doit être raisonnablement économe en utilisation de CPU pour l'encodage et le décodage. Ceci est pertinent à la fois pour les nœuds contraints et pour une utilisation potentielle dans des applications avec un très grand volume de données.
-
Le format doit prendre en charge tous les types de données JSON pour la conversion vers et depuis JSON.
- Il doit prendre en charge un niveau raisonnable de conversion tant que les données représentées sont dans les capacités de JSON. Il doit être possible de définir un mappage unidirectionnel vers JSON pour tous les types de données.
-
Le format doit être extensible, et les données étendues doivent pouvoir être décodées par des décodeurs antérieurs.
-
Le format est conçu pour des décennies d'utilisation.
-
Le format doit prendre en charge une forme d'extensibilité qui permet un repli (Fallback) afin qu'un décodeur qui ne comprend pas une extension puisse quand même décoder le message.
-
Le format doit pouvoir être étendu à l'avenir par des standards IETF ultérieurs.
-
1.2. Terminology (Terminologie)
Les mots-clés "MUST" (DOIT), "MUST NOT" (NE DOIT PAS), "REQUIRED" (REQUIS), "SHALL" (DEVRA), "SHALL NOT" (NE DEVRA PAS), "SHOULD" (DEVRAIT), "SHOULD NOT" (NE DEVRAIT PAS), "RECOMMENDED" (RECOMMANDÉ), "NOT RECOMMENDED" (NON RECOMMANDÉ), "MAY" (PEUT), et "OPTIONAL" (OPTIONNEL) dans ce document doivent être interprétés comme décrit dans BCP 14 [RFC2119] [RFC8174] lorsque, et seulement lorsque, ils apparaissent en majuscules, comme indiqué ici.
Le terme "byte" (octet) est utilisé dans son sens désormais habituel comme synonyme d'"octet". Toutes les valeurs multi-octets sont encodées dans l'ordre des octets réseau (Network Byte Order) (c'est-à-dire, l'octet le plus significatif en premier, également connu sous le nom de "big-endian").
Cette spécification utilise la terminologie suivante:
Data item (élément de données): Un seul élément de données CBOR. La structure d'un élément de données peut contenir zéro, un ou plusieurs éléments de données imbriqués. Le terme est utilisé à la fois pour l'élément de données au format de représentation et pour l'idée abstraite qui peut en être dérivée par un décodeur; le premier peut être spécifiquement désigné en utilisant le terme "encoded data item" (élément de données encodé).
Decoder (décodeur): Un processus qui décode un élément de données CBOR encodé bien formé et le rend disponible pour une application. Formellement, un décodeur contient un analyseur (Parser) pour décomposer l'entrée en utilisant les règles syntaxiques de CBOR, ainsi qu'un processeur sémantique (Semantic Processor) pour préparer les données sous une forme adaptée à l'application.
Encoder (encodeur): Un processus qui génère le format de représentation (bien formé) d'un élément de données CBOR à partir d'informations d'application.
Data Stream (flux de données): Une séquence de zéro ou plusieurs éléments de données, non assemblés en un élément de données contenant plus grand (voir [RFC8742] pour une application). Les éléments de données indépendants qui composent un flux de données sont parfois également appelés "top-level data items" (éléments de données de niveau supérieur).
Well-formed (bien formé): Un élément de données qui suit la structure syntaxique de CBOR. Un élément de données bien formé utilise les octets initiaux et les chaînes d'octets et/ou éléments de données qui sont impliqués par leurs valeurs telles que définies dans CBOR et n'inclut pas de données étrangères suivantes. Les décodeurs CBOR, par définition, ne retournent que du contenu provenant d'éléments de données bien formés.
Valid (valide): Un élément de données qui est bien formé et qui suit également les restrictions sémantiques qui s'appliquent aux éléments de données CBOR (Section 5.3).
Expected (attendu): Outre sa signification anglaise normale, le terme "expected" est utilisé pour décrire les exigences au-delà de la validité CBOR qu'une application a sur ses données d'entrée. Well-formed (traitable), valid (vérifié par un décodeur générique de vérification de validité) et expected (vérifié par l'application) forment une hiérarchie de couches d'acceptabilité.
Stream decoder (décodeur de flux): Un processus qui décode un flux de données et rend chacun des éléments de données de la séquence disponible pour une application au fur et à mesure qu'ils sont reçus.
Les termes et concepts pour les valeurs à virgule flottante tels que Infinity, NaN (pas un nombre, Not a Number), zéro négatif (Negative Zero) et nombres sous-normaux (Subnormal) sont définis dans [IEEE754].
Lorsque l'arithmétique binaire ou les types de données sont expliqués, ce document utilise la notation familière du langage de programmation C [C], sauf que ".." désigne une plage qui inclut les deux extrémités données, et la notation en exposant désigne l'exponentiation. Par exemple, 2 à la puissance 64 est noté: 2^(64). Dans la version en texte brut de cette spécification, la notation en exposant n'est pas disponible et est donc rendue par une notation de substitution. Cette notation n'est pas optimisée pour cette RFC; elle est malheureusement ambiguë avec l'ou exclusif de C (qui n'est utilisé que dans les annexes, qui à leur tour n'utilisent pas l'exponentiation) et nécessite de la circonspection de la part du lecteur de la version en texte brut.
Les exemples et le pseudocode supposent que les entiers signés utilisent la représentation en complément à deux et que les décalages à droite des entiers signés effectuent une extension de signe; ces hypothèses sont également spécifiées dans les sections 6.8.1 (basic.fundamental) et 7.6.7 (expr.shift) de la version 2020 de C++ (actuellement disponible en tant que brouillon final, [Cplusplus20]).
Similaire à la notation "0x" pour les nombres hexadécimaux, les nombres en notation binaire sont préfixés par "0b". Des traits de soulignement peuvent être ajoutés à un nombre uniquement pour la lisibilité, donc 0b00100001 (0x21) pourrait être écrit 0b001_00001 pour mettre en évidence l'interprétation souhaitée des bits dans l'octet; dans ce cas, il est divisé en trois bits et cinq bits. Les éléments de données CBOR encodés sont parfois donnés dans la notation "0x" ou "0b"; ces valeurs sont d'abord interprétées comme des nombres comme en C, puis interprétées comme des chaînes d'octets dans l'ordre des octets réseau, y compris tous les octets zéro initiaux exprimés dans la notation.
Les mots peuvent être en italique pour l'emphase; sous forme de texte brut de cette spécification, ceci est indiqué en entourant les mots de caractères de soulignement. Le texte verbatim (par exemple, les noms d'un langage de programmation) peut être défini en type "monospace"; en texte brut, ceci est approximé de manière quelque peu ambiguë en entourant le texte de guillemets doubles (qui conservent également leur signification habituelle).