class OpenSSL::ASN1::ASN1Data

代表任何 ASN.1 对象的顶级类。当被 ASN1.decode 解析时,带标签的值总是由 ASN1Data 的实例表示。

ASN1Data 在解析带标签值中的作用

当编码 ASN.1 类型时,无论其标签如何,此值具有的原始类型(例如 INTEGER、OCTET STRING 等)都是固有明确的。但是,与编码 ASN.1 类型的时间相反,在解析它们时,无法推断出带标签值的“真实类型”。这就是为什么带标签的值通常被解析为 ASN1Data 实例的原因,但是隐式和显式标签的结果不同。

解析隐式标签值的示例

一个隐式 1 标签的 INTEGER 值将被解析为一个 ASN1Data,其中

这意味着需要一个后续的解码步骤才能完全解码隐式标签的值。

解析显式标签值的示例

一个显式 1 标签的 INTEGER 值将被解析为一个 ASN1Data,其中

示例 - 解码隐式标签的 INTEGER

int = OpenSSL::ASN1::Integer.new(1, 0, :IMPLICIT) # implicit 0-tagged
seq = OpenSSL::ASN1::Sequence.new( [int] )
der = seq.to_der
asn1 = OpenSSL::ASN1.decode(der)
# pp asn1 => #<OpenSSL::ASN1::Sequence:0x87326e0
#              @indefinite_length=false,
#              @tag=16,
#              @tag_class=:UNIVERSAL,
#              @tagging=nil,
#              @value=
#                [#<OpenSSL::ASN1::ASN1Data:0x87326f4
#                   @indefinite_length=false,
#                   @tag=0,
#                   @tag_class=:CONTEXT_SPECIFIC,
#                   @value="\x01">]>
raw_int = asn1.value[0]
# manually rewrite tag and tag class to make it an UNIVERSAL value
raw_int.tag = OpenSSL::ASN1::INTEGER
raw_int.tag_class = :UNIVERSAL
int2 = OpenSSL::ASN1.decode(raw_int)
puts int2.value # => 1

示例 - 解码显式标签的 INTEGER

int = OpenSSL::ASN1::Integer.new(1, 0, :EXPLICIT) # explicit 0-tagged
seq = OpenSSL::ASN1::Sequence.new( [int] )
der = seq.to_der
asn1 = OpenSSL::ASN1.decode(der)
# pp asn1 => #<OpenSSL::ASN1::Sequence:0x87326e0
#              @indefinite_length=false,
#              @tag=16,
#              @tag_class=:UNIVERSAL,
#              @tagging=nil,
#              @value=
#                [#<OpenSSL::ASN1::ASN1Data:0x87326f4
#                   @indefinite_length=false,
#                   @tag=0,
#                   @tag_class=:CONTEXT_SPECIFIC,
#                   @value=
#                     [#<OpenSSL::ASN1::Integer:0x85bf308
#                        @indefinite_length=false,
#                        @tag=2,
#                        @tag_class=:UNIVERSAL
#                        @tagging=nil,
#                        @value=1>]>]>
int2 = asn1.value[0].value[0]
puts int2.value # => 1