在kvm虚拟化环境中,我们经常遇到一些需求,如忘记虚拟机密码,使用镜像部署虚拟机不知道初始密码,在不登录虚拟机的情况下如何对虚拟机进行一些简单的操作等等。此篇文章会给你答案,在介绍方法之前,先介绍一个一个概念channel device,如下:
1. channel是主机和虚拟机之前的私有通道,在libvirt的xml中典型的配置如下:
...
<devices>
<channel type='unix'>
<source mode='bind' path='/tmp/guestfwd'/>
<target type='guestfwd' address='10.0.2.1' port='4600'/>
</channel>
<!-- KVM virtio channel -->
<channel type='pty'>
<target type='virtio' name='arbitrary.virtio.serial.port.name'/>
</channel>
<channel type='unix'>
<source mode='bind' path='/var/lib/libvirt/qemu/f16x86_64.agent'/>
<target type='virtio' name='org.qemu.guest_agent.0' state='connected'/>
</channel>
<channel type='spicevmc'>
<target type='virtio' name='com.redhat.spice.0'/>
</channel>
</devices>
...
channel可以通过多种方式实现。通道的具体类型在目标元素的type属性中给出。不同的通道类型具有不同的目标属性。
guestfwd
TCP流量通过制定的IP地址和端口被转发道host的管道设备中,target设备必须要有IP地址和端口
virtio
半虚拟化virtio通道,通道被暴露在/dev/vport*下。
channel的基本实现原理:创建虚机时,需要在xml中配置channel段,写入相关参数,启动虚机时,会在宿主机上生成对应unix socket文件,同时,会在vm里生成一个字符设备,生成的unix socket和字符设备可以理解为一个channel隧道的两端。
2.比较常见的是通过channel使用qemu guest agent(qga)qga实现过程:
虚拟机镜像制作时,安装好qemu-guest-agent守护进程并配置开启自启动,qemu-guest-agent进程会监听字符设备。
宿主机上,将虚机中qga支持的rpc指令,通过channel发送,虚机中的qemu-guest-agent从串口设备收到数据后,执行相关指令。可实现文件读写、密码修改等。使用步骤如下:
1)虚拟机安装agent
#yum install qemu-guest-agent
2)启动服务
#systemctl enable qemu-guest-agent
3)创建虚拟机,xml里面加入:
<channel type='unix'>
<source mode='bind' path='/var/lib/libvirt/qemu/compile.agent'/>
<target type='virtio' name='org.qemu.guest_agent.0'/>
<address type='virtio-serial' controller='0' bus='0' port='1'/>
</channel>
4)启动虚拟机,通道建立就可以通信,如:
# virsh
virsh # set-user-password
error: command 'set-user-password' requires <domain> option
error: command 'set-user-password' requires <user> option
error: command 'set-user-password' requires <password> option
virsh # set-user-password 10 administrator xxxxxx
Password set successfully for administrator in 10
# virsh qemu-agent-command vm01 '{"execute":"guest-info"}'
{"return":{"version":"5.0.0.4","supported_commands":[{"enabled":true,"name":"guest-get-osinfo","success-response":true},{"enabled":true,"name":"guest-get-timezone","success-response":true},{"enabled":true,"name":"guest-get-users","success-response":true},{"enabled":true,"name":"guest-get-host-name","success-response":true},{"enabled":false,"name":"guest-exec","success-response":true},{"enabled":false,"name":"guest-exec-status","success-response":true},{"enabled":true,"name":"guest-get-memory-block-info","success-response":true},{"enabled":true,"name":"guest-set-memory-blocks","success-response":true},{"enabled":true,"name":"guest-get-memory-blocks","success-response":true},{"enabled":true,"name":"guest-set-user-password","success-response":true},{"enabled":true,"name":"guest-get-fsinfo","success-response":true},{"enabled":true,"name":"guest-set-vcpus","success-response":true},{"enabled":true,"name":"guest-get-vcpus","success-response":true},{"enabled":true,"name":"guest-network-get-interfaces","success-response":true},{"enabled":true,"name":"guest-suspend-hybrid","success-response":false},{"enabled":true,"name":"guest-suspend-ram","success-response":false},{"enabled":true,"name":"guest-suspend-disk","success-response":false},{"enabled":true,"name":"guest-fstrim","success-response":true},{"enabled":true,"name":"guest-fsfreeze-thaw","success-response":true},{"enabled":true,"name":"guest-fsfreeze-freeze-list","success-response":true},{"enabled":true,"name":"guest-fsfreeze-freeze","success-response":true},{"enabled":true,"name":"guest-fsfreeze-status","success-response":true},{"enabled":false,"name":"guest-file-flush","success-response":true},{"enabled":false,"name":"guest-file-seek","success-response":true},{"enabled":false,"name":"guest-file-write","success-response":true},{"enabled":false,"name":"guest-file-read","success-response":true},{"enabled":false,"name":"guest-file-close","success-response":true},{"enabled":false,"name":"guest-file-open","success-response":true},{"enabled":true,"name":"guest-shutdown","success-response":false},{"enabled":true,"name":"guest-info","success-response":true},{"enabled":true,"name":"guest-set-time","success-response":true},{"enabled":true,"name":"guest-get-time","success-response":true},{"enabled":true,"name":"guest-ping","success-response":true},{"enabled":true,"name":"guest-sync","success-response":true},{"enabled":true,"name":"guest-sync-delimited","success-response":true}]}}
[root@gzinf-computer-55e235e17e32 tmp]# virsh qemu-agent-command vm02 '{"execute":"guest-info"}'
error: Guest agent is not responding: QEMU guest agent is not connected
其他常用命令如:
'{"execute":"guest-network-get-interfaces"}'
'{"execute":"guest-ping"}'
如此便可以在不登陆虚拟机的情况下对虚拟机进行一些简单的操作。