ASN1
ASN1
该文主要介绍 ASN1。
ASN1
1. ASN1
ASN.1
(Abstract Syntax Notation One) 是 ISO
和 ITU-T
的联合标准,最初是 1984 年的 CCITT X.409:1984
的一部分。由于其广泛应用,1988 年 ASN.1
移到独立标准 X.208
,1995 年进行全面修订后变成 X.680
系列标准。
ASN.1
本身只定义了表示信息的抽象句法,但是没有限定其编码的方法。各种 ASN.1
的编码规则提供了由 ASN.1
描述其抽象句法的数据的值的传送语法(具体表达)。标准的 ASN.1
编码规则有:
- 基本编码规则(BER,Basic Encoding Rules)
- 规范编码规则(CER,Canonical Encoding Rules)
- 唯一编码规则(DER,Distinguished Encoding Rules)
- 压缩编码规则(PER,Packed Encoding Rules)
- XML编码规则(XER,XML Encoding Rules)
1.1. TLV编码
TLV (Tag-Length-Value)
1.1.1. Tag (标签)
- 目的:标识数据类型。
- 格式:通常为一个字节或多个字节。
- 结构:
- Class:2 位,用于表示数据类型的类别。有四种类别:
- 00: Universal (通用类型)
- 01: Application (应用类型)
- 10: Context-specific (上下文特定类型)
- 11: Private (私有类型)
- PC (Primitive/Constructed):1 位,表示数据是原始类型还是构造类型。
- 0: Primitive (原始类型)
- 1: Constructed (构造类型)
- Tag Number:5 位或更多位,用于表示具体的数据类型。标准类型为 5 位,扩展类型可以使用更多位。
- Class:2 位,用于表示数据类型的类别。有四种类别:
1.1.2. Length (长度)
- 目的:表示数据值部分的长度。
- 格式:一个字节或多个字节。
- 结构:
- 如果第一个字节的最高位为 0,表示短格式,用 7 位表示长度(0-127)。
- 如果第一个字节的最高位为 1,表示长格式,低 7 位表示后续字节数。后续字节表示的值为数据值的实际长度。即
0x81
表示 1 字节,0x82
表示 2 字节,0x83
表示 3 字节,0x84
表示 4 字节
1.1.3. Value (值)
- 目的:存储实际的数据。
- 格式:任意长度,由
Length
字段定义。 - 结构:具体的数据,根据
Tag
字段定义的类型进行编码。
1.2. Tag类型
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
/* ASN.1 tag values */
#define EASY_ASN1_EOC 0x0
#define EASY_ASN1_BOOLEAN 0x1
#define EASY_ASN1_INTEGER 0x2
#define EASY_ASN1_BIT_STRING 0x3
#define EASY_ASN1_OCTET_STRING 0x4
#define EASY_ASN1_NULL 0x5
#define EASY_ASN1_OBJECT 0x6
#define EASY_ASN1_OBJECT_DESCRIPTOR 0x7
#define EASY_ASN1_EXTERNAL 0x8
#define EASY_ASN1_REAL 0x9
#define EASY_ASN1_ENUMERATED 0xA
#define EASY_ASN1_EMBEDDED_PDV 0xB
#define EASY_ASN1_UTF8STRING 0xC
#define EASY_ASN1_RELATIVE_OID 0xD
#define EASY_ASN1_TIME 0xE
#define EASY_ASN1_SEQUENCE 0x10
#define EASY_ASN1_SET 0x11
#define EASY_ASN1_NUMERICSTRING 0x12
#define EASY_ASN1_PRINTABLESTRING 0x13 /* printable subset of ascii */
#define EASY_ASN1_T61STRING 0x14
#define EASY_ASN1_TELETEXSTRING 0x14 /* alias */
#define EASY_ASN1_VIDEOTEXSTRING 0x15
#define EASY_ASN1_IA5STRING 0x16 /* 7-bit ascii */
#define EASY_ASN1_UTCTIME 0x17
#define EASY_ASN1_GENERALIZEDTIME 0x18
#define EASY_ASN1_GRAPHICSTRING 0x19
#define EASY_ASN1_ISO64STRING 0x1A
#define EASY_ASN1_VISIBLESTRING 0x1A /* alias */
#define EASY_ASN1_GENERALSTRING 0x1B
#define EASY_ASN1_UNIVERSALSTRING 0x1C
#define EASY_ASN1_CHARACTER_STRING 0x1D
#define EASY_ASN1_BMPSTRING 0x1E /* 2-byte unicode with zeros */
2. 代码实现
https://github.com/august295/EnDeCode
参考
本文由作者按照 CC BY 4.0 进行授权