学习进阶 利用Linux提升休眠复活技术


黄瀛:大家好,我是来自英特尔科研技术中心上海的黄瀛,今天我给大家介绍一下,我最近做的一点工作。今天先对相关的背景做一个简单的介绍。接下来介绍一下对怎么样增强休眠工作,包括怎么样增加内存的内容,怎么样从休眠的内核中跳回到原内核中去,怎么样恢复状态,包括写出内存镜像,怎么样通过Kexec实现唤醒的功能,接下来我们介绍一下简单的结论。

  首先简单介绍一下Kexec,它的功能基本上是把Linux内核变成一个能力,它能够在一个正在执行的Linux系统之中载入另一个内核。它的实现通过两个部分,首先是一个载入的过程,在这个过程当中,要载入内核的内容,会被载入到软件里面去。这个可能和最终的目标配制不一样的,因为这可能当前正在使用中,会设置一些启动的参数,不同的操作系统有不同的需求。另外一个部分就是真正的去执行。这个时候它要做的工作包括首先会准备设备,基本上准备设备的方式和做关机的方式是差不多的,就是把设备的工作都停下来。

  接下来会转换到物理模式,把分页给关掉,然后执行新的内核。我们从这个图中可以看到,无论是原来的内核,还是说用Kexec重新执行的内核,它们都是使用了整个的内存,就是所有的内存,这样的话新的内核就是完全把过去内核的内容全部覆盖掉了,但是对实现Kexec来讲是没有问题的。

  接下来我们介绍一下Kdump,它可以在系统发生崩溃的时候,用Kexec方式把内存内容写到磁盘里去,这样可以将来对它进行分析,来分析出现问题的原因。它是基于Kexec来做的实现。它首先在原内核中启动的时候,启动过程中会保留一部分内存,专为做Domp内核使用。就像这个图中蓝色的部分。被启动的内核也和Kexec不同,它仅在这一部分指定的内存中运行,而不破坏其他的内核,这可以通过内核的一些启动命令行参数模式来达到这样一个功能。
  
  这样的话当我们做Kexec的时候,载入的时候,我们就把Sotf配制载入就可以了。然后再跳转,执行一个Kexec就完成这样一个功能。这样大家可以看到因为原内核没有使用这一块,目标内核只使用这样一块内存,所以说原内核的内存的内容就保留下来了,这样我们就可以在Damp内核里面把原来的内容保存下来。这个保存的接口,为了实现这个保存的功能,内核提供了一个叫VMCall虚拟的文件,用它来访问原内核内存的内容。

  接下来我们介绍一下休眠,休眠是一种电源管理的方式,它基本的内容就是把设备和CPU的状态保存到内存里面去,然后再把内核里面内存的内容存到磁盘里,然后就关机,或者是待机的状态,这样来达到省电的目的。等到重启之后再把相应的内容恢复回来。现在的实现有一些细节,首先休眠过程中会去冻结所有的进程,这主要是因为当前的休眠的实现要把这个写出,写出内核,写出这个内存镜像的内核,和原内核是同一个内核,所以说它就是要把其他的进程全部停掉,这样的话让他们不去在这个写出的过程,再往磁盘上写东西,因为这个时候会造成不一致,磁盘内容的不一致。

  接下来会再一些准备设备,包括把设备安静下来,保存状态,保存一些CPU的状态,然后把它们写出去,启动的时候把它载入进来,然后拷到目标位置上去,把它恢复回来,基本上是这样一个过程。现有的休眠的实现呢有一些问题,其中第一个就是跟现有一些实现重复,主要是和Kexec有一些重复,我们可以看到它在休眠实现里面包含写出内存镜像到磁盘的过程,其实在休眠当中也有这样一个过程,一个内核里面对于相似的一件事情提供了两个实现。

  那么另一个就是唤醒的时候,把磁盘中的内存镜像载入进来的时候,其实和KESC的load有一些重复的。第二个比较大问题,就是对于冻结程序的依赖,这个冻结主要是有一些问题,所以很多人有不满。接下来还有一个问题就是内存镜像的大小问题,因为原来休眠的实现中是在把使用的内存拷贝到空闲中,用这种方式准备这样一个内存镜像,所以这个内存镜像大小,很难超过整个大小的一半,这是比较大的一个限制。虽然说另外有一个实现解决了这个问题,但是还有很多人认为这个方法不够好。

  接下来我们介绍一下基于Kexec休眠实现。它基本上就是使用Kexec和Keepdamp,来实现原来休眠的部分。它实现基本的方法首先就像现有的休眠实现一样,去满足CPU状态的保存和恢复这样一些功能。然后再把这个内存镜像写出磁盘的时候,是用Keep domp的方式,唤醒是用Kexec load功能,然后再恢复CPU和设备的状态。基本上就对现有的Kexec和Keepdomp做了一些增强,然后再结合一些休眠的实现,所以相对来说是比较简单的。
  • 1
  • 2
  • 下一页

相关内容