2009/02/28
当我创造这些代码的时候考虑的第一件事就是线程。当前代码可以以单一线程或者多线程方式运行。我在平时测试的时候,运行大约11个线程,其中10个处理包,剩下1个是管理线程。
关于线程,最基本的原则是一个包同时只被最多一个线程处理。因为这样可以避免许多锁问题。这样,当存在一个以上的线程时,引擎可以同时处理多个包。
所有的功能都在(我称之为)线程模块中产生。这样一个模块运行在一个线程中。线程可以拥有一个或更多个运行的模块。例如,有解码模块、检查模块、警报模块等。我打算在将来实现这些模块插件化,以便在不重新编译代码库的情况下加载第三方模块。
这个线程模型以并行和串行的方式工作。并行可以用于多个线程做一件工作,例如,有两个线程都用于获取包,解码,检查,警报。线程的串行方式则有些不同。比如有这样一种情景,1个线程任务有限(比如只负责解码),当它出力完一个包后将这个包传给下一个线程(比如这个线程只负责检查)。两种方法可以结合,我默认情况下使用1个包获取线程,2个解码线程,2个检查线程,1个判断线程,以及一些警报和实时响应线程。
在串行的各个线程中,使用了队列(queue)这种结构,用于包从一个线程传送给另一个。一个队列可以包含许多个包。在上面那个例子中,nfq包获取线程可以从队列中尽可能快的读入包,并在处理完之后将它们放入自己的队列中。之后,2个解码线程又从这个nfq包获取线程的队列中尽可能快的获取包。处理完之后又把这些包放入下一个队列,以便后面的进程从中获取包。如此往复。
还可以使用队列的代码路径来确定。例如,可以使用不同的线程处理IPv4包,而不是IPv6包。或者使用不同的线程处理有警报的数据包,而不是没有警报的数据包。
目前的主要挑战是配置过于复杂,对于有能力的使用者这可能引起他们的兴趣,但对于正常用户来说这些复杂的配置可能会困扰他们。(对于最新版的suricata,配置功能已经很强大且简单了)
网友评论