乐趣区

关于linux:eBPF的发展演进从石器时代到成为神四

5.eBPF 的意义

BPF 最后来源于解决网络报文过滤的问题,实现灵便的过滤规定。网络报文的过滤规定,最后只须要正则语言就能表白,但起初就不够了。而 BPF 提供了更弱小的表达能力,BPF 具备近似图灵齐备性,必将成为问题合成、解决简单问题的神级工具。

5.1. 图灵齐备性

探讨 BPF 的计算能力,波及到图灵齐备。BPF 目前的根本设计中,有限性是根本设计准则,这是保障内核不被扩大逻辑挂死的根本要求。而有限性,是 BPF 和图灵机的基本差别,因而它不是图灵齐备的。这个论断诚然没错,但如果探讨仅止于此的话,那么这一论断过于毛糙,换个乏味一点的说法,这样的探讨不是图灵齐备的,因而还须要具体分析。

齐备性,不是评估工具优劣的齐全准则。个别认为,C 语言是图灵齐备的。然而 C 语言的所有数据类型都是有界的,其实是弱于图灵机的。但不障碍人们认为 C 是图灵齐备的,因为它的能力边界间隔理论利用的需要很远,咱们感触不到。尽管 C 语言图灵不齐备,然而不障碍它的发展潜力,在它的成长过程中,也在一直的改版、丰盛。是因为它的齐备性有余吗?显然不是。一种工具,在工程实际中,齐备性是主要的,因为他被抉择,就阐明它是够用的。其余方面才是当下更应该关注的问题。

图灵机是一种有限的自动机,人们穷尽方法也只能迫近,即便全世界所有计算机加在一起的总和,也弱于图灵机。所以图灵齐备事实中基本不存在,探讨迫近图灵机的能力可能更事实。在理论的语境中,人们实际上把有限靠近图灵机的迫近能力,等同于图灵齐备性。一个很好的例子就是 C 语言,它显然不是图灵齐备的,但人们个别认为它是图灵齐备。从这点说,BPF 语言同样是图灵齐备的。

排除语言的问题,那么 BPF 是图灵齐备的吗?依然不是,BPF 的图灵不齐备,并不次要来源于 BPF 语言自身,而是来源于运行环境。从这点说,BPF 语言是图灵齐备的,BPF 虚拟机不是。从这点也能够说,只有有须要,通过革新运行环境,BPF 能够有限迫近图灵机的计算能力。

因而,从图灵齐备这一点,咱们既不能适度的否定 BPF,认为它的能力无限。但同时,也不能认为它的能力能够有限扩张,因为须要满足特定的条件。总之,BPF 还在疾速倒退过程中,所有可能性皆在其中,任何定论皆言之过早。

从另一个角度,就 BPF 目前的应用领域来说,输出是无限的、状态空间是无限的,因而在无限的输出下,图灵齐备并不是必须。这是从事实的需要来说,BPF 足以实现指定语境下的任何计算。

但显然 BPF 的计算能力还有很大的晋升空间。

语言方面,BPF 的指令集的提出,在计算能力上,它就是超配的。当初的问题是,如何平安地开释他的能力。运行时零碎和工具链的设计,是目前的焦点问题。曾经呈现出思维一致,基于运行时环境的思路和间接凋谢的思路同时存在。将来这两个思路应该都会有肯定水平的倒退,造成面向不同畛域的高下搭配的解决方案。

因而,我认为运行时的改良可能更加迫切。这须要咱们及早确定问题边界,提供面向问题的运行环境,能力更无效的提出均衡平安和可计算性的问题的计划,即:运行环境 + 必要的计算能力,形成齐备的面向问题域的解决方案。定义一个平安的虚拟机,保障操作不逃逸,一个平安的运行时库,导出或者链接内核对象(Helper),在这个汇合上,定义平安的操作,这样语言自身就能够不再受具体逻辑和拜访对象的限度,做到语言自身的图灵齐备。

5.2. 编程模型的倒退

在 BPF 之前,Linux 开发的编程模型,能够分为内核编程和用户态编程两种。别离应用不同的编程接口和编程标准,是两者最大的区别。

BPF 呈现之后,呈现了新的编程模型,既不能称之为内核编程,也不能称之为用户态编程。

这是一种全新的编程模型。它运行于内核态,然而不应用任何传统的内核接口(5.13 能够调用通过筛选和解决的内核函数。至今,它依然受限于特定函数和指定的上下文,还不是一种通用的机制。且这种机制进一步通用化之前,它的安全性依然值得先进一步的探讨),不通过符号与内核进行链接。它应用利用编程逻辑和范式,然而不应用利用编程传统的接口,而是应用 BPF 提供的帮忙函数。它所能拜访的数据对象还在一直倒退过程中,远未定型。

因而,笔者称这种编程模型为:临界编程。兴许它将来会有更好的名字,但这个名字一方面,表明它的跨界个性,一方面外表它突飞猛进的倒退。也表明对它将来的期待。

5.3. 用户态比重的加大

因为虚拟化和软件工程的起因,网络报文解决和文件系统,呈现出往用户态迁徙的趋势。

BPF 和用户态化的共通点和差别点在于,都将更多的内核扩展性放在了用户态,但 BPF 的逻辑依然从属于内核。

他们都和传统内核通过一层良好定义的接口进行了隔离。用户态驱动和文件系统,使内核的性能更容易扩大。而 BPF 则是对内核自身的扩大。两者存在基本差别,因而也存在互相联合的可能,从而造成更加弱小的软件架构。

而这种架构会用于什么中央呢?

咱们曾经做了初步尝试,FUSE 和 BPF 进行联合。能够实现用户态文件系统和内核更加高效的交互(这一话题,咱们在后续的篇章中再具体探讨)。

推而广之,内核的网络、平安、文件系统、驱动,都能够放在用户态来实现,通过 BPF 来优化交互。

5.4. 微内核

BPF 的运行根底是运行时环境,随着 BPF 利用的减少,肯定会促使内核子系统的更进一步的形象和解偶,这在逻辑上为微内核化筹备了条件。

BPF 真正防止了纯正用户态编程的性能问题,为利用开发人员开发特色性能提供了一种临界编程工具。这或者是微内核的另一种实现门路。

5.5. 观测代码与业务代码合一

BPF 呈现的时候,最后是观测工具,但起初它也能用于实现更简单的性能,影响网络子系统的报文转发逻辑。

BPF 计算能力的弱小、性能的劣势,使它不仅能用于观测还能够做更多简单的事件。

通过高度抽象化的设计,咱们能够设计出简单、通用的业务零碎,然而咱们设计不出“最佳”的业务零碎。最佳的业务零碎肯定是在实在的利用场景中,通过一直的观测、剖析、优化,能力达成的。

将一个简单系统优化到“最佳”同样是一个简单问题,多指标的一致性、动静零碎的不稳定性、微小的状态空间等等,都可能导致这个问题没有最终答案,只有采纳动静反馈机制。因而,将观测代码和优化代码(业务代码的策略优化局部)合一,是使这一优化模式可能更加精确、高效、稳固的必然选择。

5.6. 编译器和内核合一

从实质上讲,计算问题、语言问题其实是一个问题。最后咱们解决计算问题,是在纸带上打孔,起初有了编译器。解决计算问题的效率大大晋升,然而解决计算问题的能力其实没有变动。

起初有了操作系统,软件的分层模型逐步成型,开发应用程序的效率大大晋升,但其实通过编程解决计算问题的能力并没有晋升,反而是在降落。因为软件的每一个分层,在带来工程化效率的同时,也导致了能力的损耗。API 的设计是一个大命题,然而没有完满的 API 设计。

开发效率的晋升,带来了利用的高度倒退,当初计算能力的问题呈现了。回归本原,将编译器和内核合一,构建更加弱小的计算能力,是将来倒退的根底。

退出移动版