virtio-serial设备提供了一条虚拟机与物理机进行通信的通道,最常用于qemu-guest-agent和spice。
virtio-serial 与virtio-console设备的关系
在Virtio规范上的 Device ID列表上是没有virtio-serial这个设备的,因为virtio-serial是在virtio-console 上扩展而来的。
下图是virto官网对virtio-serial的解释
virtio-serial设备在guest系统里是被识别成virtio-console 设备。
该设备可以有多个port,port vport1p0固定用作console,其余的port则为serial ports,可以在/dev/virtio-ports目录下查看到。
qemu中virtio-serial的代码实现分析
下面对qemu中virtio-serial的代码实现进行分析。
函数调用链
当在qemu命令行加上以下参数以创建virtio-serial时
-device virtio-serial-pci,id=virtio-serial0
-device virtserialport,bus=virtio-serial0.0,nr=1,id=channel0,name=com.redhat.spice.0
代码执行的大致逻辑流程如下:
a.virtio-serial-pci主要负责接pci总线,创建出virtio-serial-device;
b.virtio-serial-device主要负责创建多个virtio-queue(guest与host数据通道),创建好virtio-serial-bus,维护virtio-queue与virtio-serial-port的对应关系(一个port对两个queue);
c.virtio-serial-bus主要负责接多个virtio-serial-port;
d.virtio-serial-port主要负责对接chardev,在virtio-queue(guest侧数据)和chardev(spice侧数据 )间建立数据中转。
对应的函数调用链如下:
当在qemu命令行加上以下参数以创建virtio-console时
-device virtconsole,bus=virtio-serial0.0,nr=0
代码执行的大致逻辑流程如下:
QOM对象继承关系
QOM 的全称是 QEMU Object Model,是 QEMU 中模拟面向对象的一种规范。开发者借助 QOM 实现面向对象的设备模拟。比如在QEMU中,我们可以将网卡看成是一个类,它的父类是一个 PCI 设备类,这个 PCI 设备类的父类是设备类,这就是用继承的方式来描述它们之间的关系。
QOM 提供给开发者的是 TypeInfo 结构体,TypeInfo 结构体里面包括:
name,指的是类型的名字,
parent,指的是父类型的名字,
instance_size,指的是对象的大小,
instance_init, 指的是对象的初始化函数,
class_size, 指的是类的大小,
class_init 指的是类的初始化函数。
virtio-serial设备涉及的各QOM对象的继承关系如下:
TYPE_VIRTIO_SERIAL_PCI(virtio-serial-pci)的parent 是TYPE_VIRTIO_PCI(virtio-pci)
TYPE_VIRTIO_SERIAL (virtio-serial-device) 的parent 是TYPE_VIRTIO_DEVICE(virtio-device)
TYPE_VIRTIO_SERIAL_BUS(virtio-serial-bus)的parent 是TYPE_BUS (bus)
TYPE_VIRTIO_CONSOLE_SERIAL_PORT (virtserialport)的parent是 TYPE_VIRTIO_SERIAL_PORT (virtio-serial-port)
TYPE_VIRTIO_SERIAL_PORT (virtio-serial-port)的parent是TYPE_DEVICE(device)
virtconsole 的parent 是 TYPE_VIRTIO_CONSOLE_SERIAL_PORT (virtserialport)