libcareplus多补丁管理

Posted rtoax

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了libcareplus多补丁管理相关的知识,希望对你有一定的参考价值。

libcareplus多补丁管理

荣涛
2021年10月13日

文档修改日志

日期修改内容修改人备注
2021年10月13日创建文档荣涛
2021年10月15日AARch64多补丁支持荣涛

1. 研发背景

OpenEuler上的libcareplus代码陈旧,多补丁管理功能目前没有开源,经过和华为Libcareplus的研发人员沟通,版本发布时间不确定。所以,只能自己编写多补丁管理功能。我在gitee上fork的repo中进行了开发,目前(2021年10月13日)多补丁管理功能在分支multi-patches中进行开发,后续将合并到主分支上。

本文将讲解我在libcareplus基础上开发的多补丁管理功能。

2. 研发

在OpenEuler社区视频中演示的功能,是支持多补丁管理的。但是在Gitee上libcareplus并没有此功能。为了尽可能与视频中保持一直,添加了与视频中相同的命令行参数,一如补丁ID。

例如,视频中演示的多补丁查看功能:

其中的PatchID是在便一过程中添加的-i参数:

为了与其保持一致,我添加了同样的参数(OpenEuler中patchid可能是字符串,我选择使用32位整形表示)。我所添加的功能性参数如下:

  1. --new-patch:首先,为了支持多补丁编译功能,在libcareplus编译脚本中添加了--new-patch选项,当编译基于上次编译生成的可执行文件时,需要使用这个选项。需要注意的是,该选项在OpenEuler的libcareplus是没有的。
  2. -i:然后,为了支持多补丁加载功能,在编译脚本的参数中添加了-i选项,这与OpenEuler的libcareplus是一致的,只是我认为OpenEuler是用字符串处理的,而我是使用32位整形处理的。

3. 多补丁

多补丁有多种情况,如不相关的补丁、叠加补丁,他们的关系可以总结为下图:

通常认为,多补丁是代码上互不相关的补丁;叠加补丁是代码上有交集的补丁。

4. 测试例

4.1. 单补丁

4.1.1. 说明

用一个简单的图例,从上图中的补丁,单补丁可能的情况有:

4.1.2. 补丁生成

按照上面的测示场景编写测示例代码,分别创建三个源文件补丁(如上图),在main函数中创建两个线程,分别打印hello -Banana-或者hello -Apple-,创建的两个补丁中,其中的一个线程的打印变为hello FOO1,另一个为hello FOO2,第三个补丁是前两个补丁之和,创建命令为:

libcare-patch-make --clean -i 1 foo1.patch
libcare-patch-make --clean --new-patch -i 2 foo2.patch
libcare-patch-make --clean --new-patch -i 3 foo1.patch foo2.patch

其中:

  1. foo1.patchhello -Apple-改为hello FOO1
  2. foo2.patchhello -Banana-改为hello FOO2

本测示例的代码可以从libcareplus/test查看。

分别生成三个补丁二进制文件:

  1. 1.kpatch:对应foo1.patch;
  2. 2.kpatch:对应foo2.patch;
  3. 3.kpatch:对应foo1.patch+foo2.patch;

生成补丁后,就可以开始打补丁了:

4.1.3. 加载补丁

$ libcare-ctl patch -p $(pidof foo) 1.kpatch
1 patch hunk(s) have been successfully applied to PID '10155'

可以同步看到的是,打印信息同步的发生变化。

4.1.4. 查看补丁信息

$ libcare-ctl info -p $(pidof foo)
 Process Information.
PID                 : 10155
COMM                : foo
BuildID             : 9f43563e4d74202f84da73d0d8831bdbfc48af31
NAME                : foo
PatchVL             : 0

	PatchID  TotalSize  ULv  FLAGs  BuildTime         
	1        5448       0    0      20211013/09:58:36 

	Total 1 patches.

4.1.5. 卸载补丁

$ libcare-ctl unpatch -p $(pidof foo) -i 1
1 patch hunk(s) were successfully cancelled from PID '10155'

对于补丁2.kpatch3.kpatch重复以上步骤即可。

4.2. 多补丁

上节介绍了单补丁的使用,本节介绍多补丁管理。按照上述步骤,生成多个不相关的补丁,如下图。

4.2.1. 生成补丁

libcare-patch-make --clean -i 1 main.patch
libcare-patch-make --clean --new-patch -i 2 foo1.patch 
libcare-patch-make --clean --new-patch -i 3 foo2.patch
libcare-patch-make --clean --new-patch -i 4 main.patch foo1.patch
libcare-patch-make --clean --new-patch -i 5 main.patch foo2.patch
libcare-patch-make --clean --new-patch -i 6 foo1.patch foo2.patch
libcare-patch-make --clean --new-patch -i 7 log.patch 
libcare-patch-make --clean --new-patch -i 8 main.patch foo1.patch foo2.patch log.patch

上述一共生成了8个补丁,分别将他们命名为:

1.kpatch
2.kpatch
3.kpatch
4.kpatch
5.kpatch
6.kpatch
7.kpatch
8.kpatch

4.2.2. 加载补丁

然后使用libcare-ctl patch命令进行加载,为了方便使用一个循环:

for patch in `ls [1-9].kpatch`
do
    libcare-ctl patch -p $(pidof foo) $patch
done

4.2.3. 查看多补丁信息

$ libcare-ctl info -p $(pidof foo)
 Process Information.
PID                 : 10996
COMM                : foo
BuildID             : 92c6c49ee9714ff05fc467b993f1261b544e83f6
NAME                : foo
PatchVL             : 0

	PatchID  TotalSize  ULv  FLAGs  BuildTime         
	1        5672       0    0      20211013/10:19:58 
	2        5448       0    0      20211013/10:20:01 
	3        5448       0    0      20211013/10:20:04 
	4        6024       0    0      20211013/10:20:07 
	5        6024       0    0      20211013/10:20:10 
	6        5800       0    0      20211013/10:20:13 
	7        5656       0    0      20211013/10:20:21 
	8        6744       0    0      20211013/10:20:34 

	Total 8 patches.

========================================

OpenEuler社区视频中演示的功能截图

我在的基础上,添加了补丁创建时间。

4.2.4. 卸载补丁

警告
添加补丁的顺序是1-2-3-4-5-6-7-8,那么卸载补丁的顺序必须是8-7-6-5-4-3-2-1。
目前如果跳过最新加载的补丁,转而卸载较老版本的补丁,将失败。这也是比较合理的(同版本回退类似)。

for patchid in 8 7 6 5 4 3 2 1
do 
    libcare-ctl unpatch -p $(pidof foo) -i $patchid
done

再次查看该进程的补丁信息证明补丁被卸载:

libcare-ctl info -p $(pidof foo)

4.3. 叠加补丁

其实,从上节多补丁中,已经存在叠加补丁的情况,为了阐述叠加补丁情景,给出示例图:

也就是在补丁1的基础上,叠加补丁2,这是支持的,不做详细步骤介绍。

5. AArch64多补丁支持

目前(2021年10月15日)测试结果,AArch64不支持多补丁功能,主线段错误Segmentation fault (core dumped)或者非法指令Illegal instruction (core dumped)错误。后续将进行研发调试。

6. 下一步计划

6.1. 优先级

  1. 多补丁在Qemu-6.1.0中的应用;
  2. arm64架构热补丁:通过测试,目前AArch64平台不支持多补丁;
  3. 热补丁性能和稳定性测试;
  4. Qemu-6.1.0协程的支持;

Copyright (C) CESTC Com.

以上是关于libcareplus多补丁管理的主要内容,如果未能解决你的问题,请参考以下文章

libcareplus支持的补丁类型

LibcarePlus用户态程序热补丁

libcareplus一个Qemu-6.1.0热补丁示例

用户态热补丁

libcareplus应用于Qemu-6.1.0

续:纠正:ubuntu7.04可以安装,而且完美的安装 ! for《Oracle-10.2.0.1,打补丁10.2.0.5:在 debian 版本4不含4以上,及 ubuntu 7.04不含(代码片段