qemu创建vm和vcpu进入kvm的流程
kvm是一个内核模块,它实现了一个/dev/kvm的字符设备来与用户进行交互,通过调用一系列ioctl函数可以实现qemu和kvm之间的切换。

1、qemu发起KVM_CREATE_VM的ioctl创建虚拟机
qemu从vl.c/main开始,通过configure_accelerator根据当前current_machine调用对应的accel_init_machine,如果是kvm则具体是kvm_init。当要创建虚拟机,kvm_init函数中会s->fd = qemu_open("/dev/kvm", O_RDWR);打开/dev/kvm设备,获取虚拟机句柄fd,在该fd上ret = kvm_ioctl(s, KVM_CREATE_VM, type); s->vmfd = ret;此ioctl函数在kvm中的实现为kvm_main.c中kvm_dev_ioctl函数。当传入的参数为KVM_CREATE_VM时,该函数会创建一个VM,并且返回一个vm_fd,通过该vm_fd可以操作虚拟机。
2、qemu中创建虚拟机的vcpu和qemu线程关系,并切换到kvm中
在vl.c/main的最开始会module_call_init(MODULE_INIT_MACHINE)本质就是把pc_init1赋值给了mc->init。在kvm_init创建完虚拟机后,会返回到main中,调用machine_class->init(current_machine);即会调用之前注册的pc_init1,该函数中有两个重要的pc_cpus_init和pc_memory_init,即CPU和内存的初始化,在pc_cpus_init-》pc_new_cpu-》(1)cpu_x86_create主要就是把CPUX86State填充了一下,涉及到CPUID和其他的feature。(2)object_property_set_bool-》object_property_set_qobject-》object_property_set-》property_set_bool-》device_set_realized-》dc->realize此即为X86_cpu_common_class_init设置了处理函数dc->realize = x86_cpu_realizefn;
执行x86_cpu_realizefn调用qemu_init_vcpu-》qemu_kvm_start_vcpu-》qemu_thread_create该函数创建VCPU对应的qemu线程,线程函数是qemu_kvm_cpu_thread_fn,该线程函数中:
(1)kvm_init_vcpu(1.1)通过ret = kvm_vm_ioctl(s, KVM_CREATE_VCPU, (void *)kvm_arch_vcpu_id(cpu));创建虚拟机的vcpu。对应到kvm的kvm_main.c中kvm_vm_ioctl函数,当传入的参数为VM_CREATE_VCPU时,与KVM_CREATE_VM过程类似,它创建一个vcpu并且返回可以操作该vcpu的vcpu_fd;(1.2)mmap_size = kvm_ioctl(s, KVM_GET_VCPU_MMAP_SIZE, 0);cpu->kvm_run = mmap(NULL, mmap_size, PROT_READ | PROT_WRITE, MAP_SHARED, cpu->kvm_fd, 0);获取kvm_run对应的内存映射(1.3)kvm_arch_init_vcpu则填充对应的kvm_arch内容。
(2)在kvm_init_vcpu返回后会先设置开关qemu_cond_signal(&qemu_cpu_cond);打开这个开关(貌似再经过pc_memory_init设置好内存后,pc_init1完成,即可运行)才会while循环kvm_cpu_exec,该函数会run_ret = kvm_vcpu_ioctl(cpu, KVM_RUN, 0);切换到kvm中运行。对应到kvm的:kvm_main.c中kvm_vcpu_ioctl函数,若传入的参数为KVM_RUN,它最终会调用vcpu_enter_guest函数进入guest vm。
关于开关:
qemu-kvm线程工作过程:
1)启动一个子线程,创建初始化vcpu,主线程等待
2)子线程创建初始化vcpu完毕,子线程等待,并等候通知主线程运行
3)主线程继续初始化虚拟机工作,初始化完成,通知子线程继续运行
4)子线程继续启动虚拟机kvm_run,主线程执行select交互处理
3、主线程main_loop
Thread1:主线程,这个线程loop循环,循环操作select.实际就是查看有无读写文件描述符,有的话进行读写操作
Thread2:子线程,异步进行i/o操作,主要针对磁盘映像操作(block drive)
Thread3:子线程,VCPU线程, kvm_run启动和运行虚拟机
ps –ef|grep qemu
gdb –p $pid

qemu创建vm和vcpu进入kvm的流程的更多相关文章
- Qemu创建KVM虚拟机内存初始化流程
转载请注明:[转载自博客xelatex KVM],并附本文链接.谢谢. [注]文章中采用的版本: Linux-3.11,https://www.kernel.org/pub/linux/kernel/ ...
- qemu启动vm后,如何host上使用ssh连接?
qemu启动vm后,如何从host ssh连接vm? qemu启动参数 启动命令: ${cmd_qemu_system} --enable-kvm \ -machine type=q35,accel= ...
- openstack上创建vm实例后,状态为ERROR问题解决
问题说明:在openstack上创建虚拟机,之前已顺利创建了n个centos6.8镜像的vm现在用ubuntu14.04镜像创建vm,发现vm创建后的状态为ERROR! 1)终端命令行操作vm创建 [ ...
- Azure Virtual Machine 之 如何利用Management Class Libraries 创建VM
之前发的blog简单的介绍了如何使用Management Class Libraries 来控制Azure platform. 但由于官方并没有提供文档,所以我们只能够通过自己研究来摸索使用该类库的方 ...
- 从托管映像创建 VM
可以从 Azure 中托管的 VM 映像创建多个 VM. 托管 VM 映像包含创建 VM 所需的信息,包括 OS 和数据磁盘. 构成映像的 VHD(包括 OS 磁盘和任何数据磁盘)存储为托管磁盘. 先 ...
- 由于挂载的nfs存储目录掉下线,导致创建VM时,无法创建
具体错误,如下截图 重新挂载存储后,在创建VM,将成功
- Azure上采用Json Template从已有的VHD创建VM
从已有的VHD创建VM是使用Azure中经常要操作的内容. 本文将介绍如何采用Json Template从已经有的VHD创建VM. 一.准备VHD 在我的Azure账户中选择一台VM,如下图: 查看其 ...
- kvm初体验之八:调整vm的vcpu, memory, disk大小
假设host上创建的vm的名字为vm1. 1. 查看vm1的domain information [root@tanghuimin thm]# virsh dominfo vm1 Id: 10 Nam ...
- opennebula kvm 创建VM oned报错日志
Thu Jul :: [ReM][D]: Req: UID: VirtualMachineDeploy result SUCCESS, Thu Jul :: [TM][D]: Message rece ...
随机推荐
- python文档测试
def average(values): """ compute average value >>> print(average([20, 30, 10 ...
- solr 入门
这个博客写的不错,很详细 https://blog.csdn.net/wzy18210825916/article/details/80946454
- Windows命令行设置dns
管理员运行cmd 1.dns配置成192.168.1.200 netsh interface ip set dns name="以太网" source=static addr=19 ...
- 【Python全栈-CSS】CSS实现网页背景图片自适应全屏
CSS实现网页背景图片自适应全屏 功能:实现能自适应屏幕大小又不会变形的背景大图,而且背景图片不会随着滚动条滚动而滚动. 以下是用CSS实现的方法: <html> <head> ...
- 查看虚拟机里的Centos7的IP
这里之所以是查看下IP ,是我们后面要建一个Centos远程工具Xshell 连接Centos的时候,需要IP地址,所以我们这里先 学会查看虚拟机里的Centos7的IP地址 首先我们登录操作系统 用 ...
- 写一个方法,用于解读 url 后面的请求参数,最终得到 {"a":2,"b":3,"c":4};
function getUrlParams(url){ let searchParam = url.split("?")[1]; let searchItemParams = se ...
- 使用easyui搭建网页架子
使用踩坑: 一.弹出框上datagrid第二次加载数据,必须在显示状态,datagrid加载数据才会渲染,否则是空白 $('#xq_selKs').window('open').window('cen ...
- Python从入坑到放弃!
Python基础 python基础 python基础之 while 逻辑运算符 格式化输出等 python基础之 基本数据类型,str方法和for循环 python基础之 列表,元组,字典 pyth ...
- 3.1.3 Spring之AOP
三.Spring之AOP 1. 代理模式 (1) 什么是代理模式? 代理模式是面向对象编程的23种基础设计模式之一.为其他对象(代理对象)提供一种代理以控制对这个对象(源对象)的访问. 就是说,声明一 ...
- for循环的beak continue用法
continue跳出该循环, for循环后面的都要执行.break直接中段循环 后面不执行了