4

解析应用程序协议的常规方法是什么?

给定来自已设计协议(例如 SMTP)的套接字的流,处理协议的常用方法是什么。它是基于 yacc 的解析器、基于正则表达式的方法还是其他方式?

4

1 回答 1

2

应用层协议有很多,但我认为主要区别在于它是基于二进制还是基于文本的。两者都被广泛使用。

对于基于文本的协议,通常对输入进行标记,然后使用yacc. 一些基于文本的协议甚至比这更容易解析,因此您可能只需拆分输入并检查它是否有意义。应该考虑编码,但它必须是您已经通过内置方法或库(例如UTF-8. 例如,HTTP 是一个文本协议,并且很容易解析(示例来自这里):

要求:

GET /path/file.html HTTP/1.0
From: someuser@jmarshall.com
User-Agent: HTTPTool/1.0
[blank line here]

回复:

HTTP/1.0 200 OK
Date: Fri, 31 Dec 1999 23:59:59 GMT
Content-Type: text/html
Content-Length: 1354

<html>
<body>
<h1>Happy New Millennium!</h1>
(more file contents)
  .
  .
  .
</body>
</html>

大多数程序员都可以为此编写解析器,即使您最好依赖经过良好测试和完整的库实现。

二进制协议虽然有些不同。第一件事是使用例如ASN.1(在电信中经常使用)、协议缓冲区或类似的东西对消息进行编码/解码。如果可能的话,不要发明自己的二进制格式,依赖经过测试和尝试的库——这很难做到,难怪ASN.1大多数工具都很昂贵。

这是ASN.1 UPER,您定义了一个简单的元素,例如(此处的示例):

myQuestion FooQuestion ::= {
    trackingNumber     5,
    question           "Anybody there?"
}

它被编码如下:

01 05 0e 83 bb ce 2d f9 3c a0 e9 a3 2f 2c af c0

有了所有的位移和掩码,实现起来并不容易——这就是为什么支持的开源ASN.1PER如此罕见的原因。

两种方法都有其优点/缺点。基于文本的协议更容易正确、调试和理解。不过,他们通常很健谈,在某些情况下,这很重要。这是选择 eg 的时候ASN.1 PER,这很难实现或调试,但非常紧凑。

于 2013-02-18T11:11:22.530 回答