ASN.1 BER解码器输入中未声明的标签

时间:2010-02-26 19:21:44

标签: asn.1

我有一个ASN.1语法的规范,我希望通过添加一些字段来修改它。如果我使用带有新字段的BER创建编码字符串,然后尝试使用不知道这些附加字段的解码器解码该字符串,那么结果应该是什么?解码是否会因解码器无法识别的字段而失败?解码器是否只解码它能识别的字段并完全忽略它不能识别的字段?这完全是一个解码器实现问题,所以要么结果是可能的,这取决于解码器的实现方式?

现在,我正在使用一个开源ASN.1编译器/解码器,它似乎完全失败但我不确定这是因为实现还是因为ASN.1规则规定了那种导致?

2 个答案:

答案 0 :(得分:3)

它当然不依赖于实施。也就是说,如果不同的实现以不同的方式处理它,其中一个实际上是错误地执行它。 如果您使用不期望未知字段的解码器来解码未知字段,则解码将失败。它不会跳过未知领域。

然而,有一种方法可以在知道之前提供额外的字段。它是采用扩展标记(“......”)。假设我们开发了各种版本的ASN.1规范。我们称它们为V1,V2,V3等.V1是原始规格,但我们在设计V1时理解,我们可能需要在某些时候修改它。允许这样做,而不是像

那样的东西
Z ::= SEQUENCE { a INTEGER,
                 b OCTET STRING,
                 c Message1
}

我们会声明Z像这样可扩展

Z ::= SEQUENCE { a INTEGER,
                 b OCTET STRING,
                 c Message1,
                 ...
}

扩展标记表示,在c之后,可能还有更多字段尚未知。解码器应该将包含这些字段的消息视为有效,只要它们遵循c即可。解码器无法解码它们,因为它不知道它们应该是什么,但它知道它们是允许的。

假设我们通过插入两个像这样的

新字段来将V1更新为V2
Z ::= SEQUENCE { a INTEGER,            -- V1
                 b OCTET STRING,       -- V1
                 c Message1,           -- V1
                 ...,
             [[  d PrintableString,    -- V2
                 e BOOLEAN          ]] -- V2
}

在这种情况下,V1版本可以与V2版本互操作。 V1编码器不包括d或e,而V2编码器将包括它们。从解码器的角度来看,V1解码器将接受(但不解码)d和e,而V2解码器将解码d和e(如果找到它们)。所以V1解码器会接受V1和V2编码,无论何时找到它们都会忽略d和e; V2解码器也接受V1和V2编码,注意V1编码不包括d或e,但它仍然有效。

我们可以通过其他版本继续这样做,例如,

Z ::= SEQUENCE { a INTEGER,            -- V1
                 b OCTET STRING,       -- V1
                 c Message1,           -- V1
                 ...,
             [[  d PrintableString,    -- V2
                 e BOOLEAN         ]], -- V2
             [[  f PrintableString,    -- V3
                 g ExtensionMessage]]  -- V3
}

其中V1,V2和V3都可以互操作。

但请注意,由于我们正在处理SEQUENCE,因此必须保留订单。没有d就没有e,没有d,e和f就没有g。

因此,结论是,如果您的类型定义包含扩展标记,则可以添加新字段,但如果不包含,则可能不会。

答案 1 :(得分:0)

这将取决于规范和实现。简而言之 - 没有办法说出来。这取决于实施。使用asn.1的任何给定协议/格式的一些规范将明确声明要忽略未知元素,在这种情况下解码不应该失败。

更常见的是,解码器将拒绝任何不严格符合它应该解码的ASN.1语法的输入。