你好,我是 yes。

在之前的文章已经提到了 RPC 的核心,想必一个 RPC 通信大致的流程和基本原理已经清晰了。

这篇文章借着 Dubbo 来说说微内核这种设计思想,不会扯到 Dubbo 某个具体细节实现上,和 Dubbo 强相关的内容会在之后的文章写到。

所以今天的重点在微内核,而这个概念我最早是从操作系统那里得知,不过操作系统的微内核和 Dubbo 相关的微内核又不太一样。

Dubbo 的微内核广义上的微内核,而操作系统只是针对内核实现。

这么说你肯定不清楚,别急,听我慢慢道来。

我们先看看操作系统的微内核。

操作系统中的微内核

在维基百科上搜索微内核出现的就是:

在计算机科学中,微内核(英语:Microkernel,μ-kernel),是一种内核的设计架构,由尽可能精简的程序所组成,以实现一个操作系统所需要的最基本功能,包括了底层的寻址空间管理、线程管理、与进程间通信。

这个词条归类在操作系统技术下,所以这里的微内核指的就是操作系统的内核设计,与之对应的是宏内核架构。

Linux 就是宏内核架构。

操作系统我们都知道它是一个中间层,为我们管理底层的硬件资源,为上层服务提供接口。

提供进程管理、内存管理、文件系统、进程通信等功能。

像 Linux 这样的宏内核设计是把这些功能都作为内核来实现,而微内核则仅保留最基础的功能。

比如就留下进程的管理、内存管理等,把文件管理等功能剥离出去,变成用户空间的独立进程来提供服务。

来看下这个维基百科上的这个图应该就很清晰了。

宏内核中的一些功能在微内核架构上都被独立到用户态中,这样内核代码量就少了,代码少了潜在的 bug 就少,出了问题也更容易排查。

系统也就更加稳定,不易奔溃,因为那些服务从内核中移除,在用户空间运行着,如果出了故障,内核重启这个服务就好了,不会像之前那样整个内核 GG。

拿显卡驱动来说,出问题就蓝屏,这要是微内核设计就可以重启显卡驱动。

听起来好像微内核很好啊?并不是,接下来就说说微内核的缺点。

首先是性能问题,因为很多功能作为独立进程放到用户空间运行了,所以宏内核时的函数调用就变成了进程间调用,涉及进程间的通信,还会伴随着内核态和用户态的来回切换,我们知道这种上下文切换时比较耗时的。

这性能的问题就有点大了。

然后微内核设计没那么简单,想要灵巧、减少耦合、提高可移植性就需要好好的设计,按照林纳斯的话来说:“如果 GNU 内核(微内核架构)早在去年春天完成了,我压根不会开始我的项目(Lniux)。”

GNU Hurd 采用微内核架构,设计过于精巧,研发速度缓慢,性能长期无法提升。

当年林纳斯还和 Minix 的作者安德鲁,对操作系统的宏内核和微内核的好坏进行了一波网络口水战。

我们来回顾一下那段历史,挺有意思的。

因为 AT&T 把 Unix 商业化了,大学不能免费使用 Unix,身为大学教授的安德鲁为了教学自己搞了个操作系统,即 Minix。

当时的学术风潮是微内核架构,把核心功能模块化,划分为几个独立的进程,运行在不同的地址空间提高了代码的可移植和系统的安全性。

所以 Minix 就是按微内核架构编写的,当然还有上述提到的 GNU Hurd。

而林纳斯那时候读大学,他祖父送了他一台 Intel 80386,林纳斯也看到了安德鲁的教科书,根据书上的内容写出了 Linux。

不过没有按照微内核的设计,而是跟 Unix 一样采用了宏内核架构。

安德鲁教授看到了 Linux ,然后在 comp.os.Minix 上批评道:宏内核的设计有害的,Linux 内核耦合度太高,完全是为了 Intel 80386 而设计的,处理器架构进化很快的,操作系统应该都具备可移植性。

安德鲁还提到:都1991年了还用宏内核来设计操作系统,这是一种巨大的退步。

林纳斯在一天之后进行了反击,他说 Minix 设计上有缺陷,从哲学和美学角度来看微内核确实好,但是你看 GUN Hurd 到现在还没开发出来。

然后操作系统本来就依靠硬件的特性,所以内核本身不需要过度具备可移植性,应用程序的可移植性才重要,Linux 比 Minix 好移植多了。

而且 Linux 本来就是为我自己做的,所以契合 80386,如果要移植到别的平台,代码都是开源的(Minix 源码当时得买),想要的人自己做咯。

安德鲁也做了一波回应:Minix 有局限性是因为我是教授,因为大部分学生都只能在低配的机器上使用,所以系统的硬件需求得足够低,虽然你 Linux 是免费的,但是需要的硬件贵呀。

其实可以看到,两者并没有对宏内核和微内核的技术细节的进行深入探讨,而是抓住对方的:你这 Minix 代码还要收费,你这 Linux 需要的硬件这么贵来进行“攻击”,所以称之为口水战。

反正口水战之后双方都没有改变各自的设计,不过林纳斯有引进微内核的思想来改进代码,也改善了可移植性。

微内核市面上设计成功的有 QNX,黑莓手机就是用这个操作系统,车用市场也几乎都用 QNX 系统。

这手机很多年前我用过,当时觉得有点东西的。

宏内核的话就提个 Linux ,足够了。

两个架构都有成功的产品,所以还是取舍的问题,也没有谁完全压着谁。

再具体的就不深入了,今天的主角其实是广义上的微内核。

Dubbo 中的微内核

Dubbo 的微内核是广义上的,它的思想是:核心系统+插件。

这个微内核说白了就是把不变的功能抽象出来称为核心,把变动的功能作为插件来扩展,符合开闭原则,更容易扩展、维护。

小霸王游戏机大家都应该玩过,就长这样的,它的设计就可以认为是个微内核设计。

机体本身作为核心系统,游戏片就是插件。

我们想玩哪个游戏就插哪个游戏片,简单便捷,不影响机体本身。

假设不把游戏片抽象成插件式,那是不是就难搞了?换个游戏就成为难题了。

所以微内核架构的本质就是将变化的部分抽象成插件,使得可以快速简便地满足各种需求又不影响整体的稳定性。

这就是微内核架构的精髓。

这里再扣个细节,较个真(就是我个人的一点想法)。

Mark Richards 在 《Software Architecture Patterns》的微内核章节里面提到

The core system of the microkernel architecture pattern traditionally contains only the minimal functionality required to make the system operational.

从字面意义来看,Mark 认为核心系统指的是可以独立运行且提供基本功能的最小模块

例如 vscode、idea、chrome 等设计就符合 Mark 认为的核心设计,核心系统提供基础必备的功能,可以独立运行。

像 vscode 核心就是编辑器,没有插件也可以独立运行,然后又有丰富的插件,来满足一些特殊需求,扩展核心系统的功能。

这里可能会让人产生误导,认为核心必须是能让系统运行的最小功能模块。

我认为核心不一定需要独立运行且提供基础功能,能让系统运行的最小组织模块也是核心。

两个说法的差别在于:只有核心的话系统能否正常的运行。

vscode 没有插件照样能运行,能提供基本功能,而小霸王游戏机没有游戏片那运行个寂寞,玩个球。

但是小霸王这种难道就不算微内核了嘛?

就我个人而言,把变与不变区分出来,把变化封装成插件就称为微内核设计。

像 Dubbo 能支持很多协议、各种负载均衡的扩展、集群的扩展等等,它自身的一些功能也是通过扩展点实现的,没有插件也跑不了。

这样的内核就像胶水,把各个插件结合起来最终提供服务,没有插件这个系统就没什么意义。

所以我认为核心系统不一定需要能独立运行,能让系统运行的最小组织模块也是核心。

因此我觉得 Mark 说的不太准确,容易产生误导。

当然这是文字上面的抠细节,核心概念都是一致的:抽象出核心,剥离变化为插件。

微内核设计的好处

这里的微内核指的是广义的微内核。

作为一个框架或者软件,扩展性非常的重要。

因为一个框架、一个软件的使用者千千万,不同的人有不同的需求。

身为框架的维护者、软件的开发者你有精力和能力满足所有用户的需求?

做梦,不存在的。

有些 idea 你想都想不到。

比如我之前看到的 vscode 里面有个「坤坤鼓励师」插件,默认你代码写一小时之后蔡徐坤来给你跳鸡你太美,让你休息休息......

来感受一下?

所以做一个框架或者软件,想要让更多人使用,不仅自身提供的功能要全、性能要好、使用要简单,让用户 DIY,做各种定制化也非常的关键!

Dubbo 的成功其实就离不开它的微内核设计,定制化开发在很多场景都要用到,毕竟都得稍加改造一番来满足自己公司的一些特殊需求。

当然也不是什么都要微内核

微内核看起来是很方便,但是设计起来就不方便了。

需要精心的设计,抽象出各种扩展点。

除了本身的功能还需要管理插件的生命周期、插件如何连接、如何通信等。

有些还需要做沙箱隔离,防止插件污染整个系统等等,本来的内部函数调用变成了插件间的通信,反正设计起来是复杂了。

一般微内核适合用在框架的设计上,或者一些规则引擎的设计,只有复杂的会有很多变化的需求场景才需要用到微内核。

像一般简单的项目,本来就一条直道走到底的那种就算了,不要瞎操作,等下秀折了腿。

最后

微内核其实就是一种架构思想,可以是框架层面的,也可以细化到某个模块的设计。

归根结底就是把变化封装成插件,可插拔,拥抱变化。

当然今天也提到了操作系统的微内核,这个和广义上的微内核还是不太一样的。

至于 Dubbo 的微内核就离不开它的 SPI,之后文章会深入写一波​,等我哈。​

更多文章可看我的文章汇总:https://github.com/yessimida/yes 欢迎 star !


我是 yes,从一点点到亿点点,欢迎在看、转发、留言,我们下篇见。

巨人的肩膀

https://en.wikipedia.org/wiki/Microkernel

https://en.wikipedia.org/wiki/Tanenbaum–Torvalds_debate

《Software Architecture Patterns》

操作系统微内核和Dubbo微内核,有何不同?的更多相关文章

  1. Dubbo原理和源码解析之“微内核+插件”机制

    github新增仓库 "dubbo-read"(点此查看),集合所有<Dubbo原理和源码解析>系列文章,后续将继续补充该系列,同时将针对Dubbo所做的功能扩展也进行 ...

  2. 微内核架构(Microkernel Architecture)

    微内核架构(Microkernel Architecture) 微内核架构有时也被成为插件架构模式(plug-in architecture pattern),通常用于实现基于产品的应用,如Eclip ...

  3. Atitit 插件机制原理与设计微内核 c# java 的实现attilax总结

    Atitit 插件机制原理与设计微内核 c# java 的实现attilax总结 1. 微内核与插件的优点1 2. 插件的注册与使用2 2.1. Ioc容器中注册插件2 2.2. 启动器微内核启动3 ...

  4. 【Dubbo 源码解析】02_Dubbo SPI

    Dubbo SPI:(version:2.6.*) Dubbo 微内核 + 插件 模式,得益于 Dubbo SPI .其中 ExtentionLoader是 Dubbo SPI 最核心的类,它负责扩展 ...

  5. 理解 Dubbo SPI 扩展机制

    写在前面 最近接触了 gRPC 体会到虽然众多 RPC 框架各有各的特点但是他们提供的特性和功能有很多的相似之处 , 这就说明他们面对同样的分布式系统带来的问题.从 2016 年左右开始接触到 dub ...

  6. [转] 理解 Dubbo SPI 扩展机制

    写在前面 最近接触了 gRPC 体会到虽然众多 RPC 框架各有各的特点但是他们提供的特性和功能有很多的相似之处 , 这就说明他们面对同样的分布式系统带来的问题.从 2016 年左右开始接触到 dub ...

  7. Dubbo 就是靠它崭露头角!(身为开源框架很重要的一点)

    Hola,我是 yes. 经过了 RPC 核心和 Dubbo 微内核两篇文章后,今天终于要稍稍深入一波 Dubbo 了. 作为一个通用的 RPC 框架,性能是很重要的一环,而易用性和扩展性也极为重要. ...

  8. MIT6.828 JOS系统 lab2

    MIT6.828 LAB2:http://pdos.csail.mit.edu/6.828/2014/labs/lab2/ LAB2里面主要讲的是系统的分页过程,还有就是简单的虚拟地址到物理地址的过程 ...

  9. (笔记)Linux内核学习(一)之内核介绍

    内核与操作系统: 内核是操作系统的核心部分,包含了系统运行的核心过程,决定系统的性能,操作系统启动内核被装入到RAM中: 操作系统与底层硬件设备交互和为运行应用程序提供执行环境. Linux内核与微内 ...

随机推荐

  1. Error response from daemon: driver failed programming external connectivity on endpoint mysql3308 (

    Docker启动容器报错. 1. 错误描述 [root@localhost nginx]# docker start mysql3308 Error response from daemon: dri ...

  2. Golang自学系列

    为什么会有这个系列? 因为我要往架构方向靠拢啊. 关于架构,其实架构的书我看了<架构整洁之道>,也有<实现驱动领域设计>.但是我感觉明显还不够,所以我在极客时间买了一个架构相关 ...

  3. JavaScript使用中的一些小技巧

    任何一门技术在实际中都会有一些属于自己的小技巧.同样的,在使用JavaScript时也有一些自己的小技巧,只不过很多时候有可能容易被大家忽略.而在互联网上,时不时的有很多同行朋友会总结(或收集)一些这 ...

  4. (四)CPU主频与”性能“

    一.什么是性能 CPU的性能就是就是时间的倒数,简单来说:耗时越少,性能越好,主要包含下面两个指标: 响应时间:程序执行耗时 吞吐率:单位时间处理数据或执行程序的量 缩短响应时间,一定时间内可以执行更 ...

  5. 第8.20节 Python中限制动态定义实例属性的白名单:__slots__

    一. 引言 按照<第7.10节 Python类中的实例变量定义与使用>.<第7.14节Python类中的实例方法解析>中的介绍,当定义了一个类,并且创建了该类的实例后,可以给该 ...

  6. 关于Python中中文文本文件使用二进制方式读取后的解码UnicodeDecodeError问题

    最近老猿在进行文件操作的验证测试,发现对于中文文本文件如果使用二进制方式打开,返回的类型是bytes,如果要转换成可读的字符串信息需要进行解码.可是老猿使用decode()或decode(" ...

  7. 第十三章 Python基础篇结束章

    从2019年3月底开始学习Python,4月份开始在CSDN发博客,至今不到半年,老猿认为博客内容中关于Python基础知识的内容已经基本告一段落,本章进入Python基础知识结束章节,对Python ...

  8. PyQt(Python+Qt)学习随笔:Model中项的标记flags取值及枚举类型Qt.ItemFlag

    老猿Python博文目录 专栏:使用PyQt开发图形界面Python应用 老猿Python博客地址 在Model中的项可以通过flags()方法查询对应项是否能被选择.拖拽或其他操作,对应的返回值类型 ...

  9. SpringCloud Alibaba学习笔记

    目录 目录 目录 导学 为什么学 学习目标 进阶目标 思路 Spring Cloud Alibaba的重要组件 环境搭建 Spring Boot必知必会 Spring Boot特性 编写第一个Spri ...

  10. Scrum冲刺_Day01

    一.团队展示: 1.项目:light_note备忘录 2.队名:删库跑路队 3.团队成员 队员(不分先后) 项目角色 黄敦鸿 后端工程师.测试 黄华 后端工程师.测试 黄骏鹏 后端工程师.测试 黄源钦 ...