1.详细描述
在arm64平台上,通过libvirt设置虚拟机CPU的占用率限额时,存在以下问题:
1.将虚拟机配置单核,并将CPU占用率限额(即cpu.cfs_quota_us)配置为100000(限制为100%)时,观察虚拟机vCPU线程的物理机CPU占用率,实际可达到100%;
2.将虚拟机配置为4核,并将每个核的限额均设置为100%时,实际总占用率只能达到350%左右,无法达到400%。另外,若将限额设置200000(限制为200%)或-1(无限制)时,总占用率可达到400%。
1.在宿主机的/sys/fs/cgroup/cpu,cpuacct/目录下新建一个目录test
cd test
mkdir t1 t2 t3 t4
echo 100000 >t1/cpu.cfs_quota_us
echo 100000 >t2/cpu.cfs_quota_us
echo 100000 >t3/cpu.cfs_quota_us
echo 100000 >t4/cpu.cfs_quota_us
2.编写测试程序,内容如下:
#include <pthread.h>
#include <stdio.h>
void cpu100(void)
{
while(1);
}
void main(void)
{
pthread_t tid;
pthread_create(&tid,NULL,cpu100,NULL);
pthread_create(&tid,NULL,cpu100,NULL);
pthread_create(&tid,NULL,cpu100,NULL);
pthread_create(&tid,NULL,cpu100,NULL);
sleep(10000000);
}
3.编译上述程序并运行;
4.找到该程序的PID,通过top -Hp <pid>,查询其4个CPU占用率为100%的子线程的PID;
5.将4个子线程的PID分别写入步骤1中test文件夹下的的t1/tasks, t2/tasks, t3/tasks, t4/tasks文件中;
6.继续观察top命令的输出信息,可发现有一个子线程的CPU占用率明显下降,如下图:
该问题由cgroup和完全公平调度器(CFS)的时间片分配逻辑中存在竞争窗口导致。
在调度实体受限时,及时将其记录到受限队列中,以便函数distribute_cfs_runtime()在分发时间片时,可以发现该调度实体,并为其分配新的时间片额度。
目前,社区已在v5.8-rc1版本中修复了该问题,相关补丁为“sched/fair: Eliminate bandwidth race between throttling and distribution“,将该补丁进行移植即可解决问题。