VirtualBox虚拟机的串口通信机制有两种,一种是通过将虚拟机的串口连接到主机的串口,另外一种是将虚拟机的串口连接到主机上的一个命名管道,第一种方式到现在我还没有实践出来,目前只是对命名管道的方式实践成功。
1.启用串口
新建虚拟机后在设置中会出现串口面板,可以进行串口设置,默认是不起用的,一般端口选择使用COM1对应虚拟机的/dev/ttyS0,端口模式选择Host Pipe,表示将虚拟机的串口连接到主机的一个命名管道,创建通道表示启动虚拟机时VirtualBox会在HostOS中对应地创建一个命名管道,并使它与虚拟机的对应串口相连。端口路径在选择Host Pipe时表示命名管道的路径,在Windows系统上,它是\\.\pipe\xxx的形式,在Linux可以设任何路径,比如我们将它设为/tmp/vbox。注意,如果端口路径对应的命名管道不能创建的话,虚拟机启动会失败;端口路径的命名管道不能重复创建。
你也可以使用命令行启用并创建一个虚拟机到主机命名管道的连接,下面的命令就将虚拟机Ubuntu 8.10 Dev OS的COM1串口和主机的/tmp/vbox命名管道连接起来:
VBoxManage setextradata “Ubuntu8.10DevOS” “VBoxInternal/Devices/serial/0/Config/IRQ” 4
VBoxManage setextradata “Ubuntu8.10DevOS” “VBoxInternal/Devices/serial/0/Config/IOBase” 0x3f8
VBoxManage setextradata “Ubuntu8.10DevOS” “VBoxInternal/Devices/serial/0/LUN#0/Driver” Char
VBoxManage setextradata “Ubuntu8.10DevOS” “VBoxInternal/Devices/serial/0/LUN#0/AttachedDriver/Driver” NamedPipe
VBoxManage setextradata “Ubuntu8.10DevOS” “VBoxInternal/Devices/serial/0/LUN#0/AttachedDriver/Config/Location” “/tmp/vbox”
VBoxManage setextradata “Ubuntu8.10DevOS” “VBoxInternal/Devices/serial/0/LUN#0/AttachedDriver/Config/IsServer” 1
2.虚拟机和主机HostOS间的串口通信
启动虚拟机Ubuntu8.10DevOS,这时会在主机的/tmp/目录下创建vbox新文件,可以用ls -l看到它是一个sock类型的文件,使用来进行通信的。在HostOS中安装minicom,minicom可以用来作为串口测试:
sudo apt-get install minicom
接下来我们可以配置minicom,让它指向/tmp/vbox,执行命令
sudo gedit /etc/minicom/minirc.dfl并修改为
pu port unix#/tmp/vbox
也可以在minicom中通过串口设置来修改。测试前应保证minicom中的串口设置的波特率和虚拟机中的串口一样。虚拟机中的串口波特率设置可以参考下文,minicom的波特率设置可以直接在程序中Ctrl+A, O后修改,或修改配置文件。
测试过程,
1)在HostOS中启动minicom:
sudo minicom
在虚拟机中的终端中执行:
echo is that ok? > /dev/ttyS0
会在HostOS中的minicom中回显对应内容
2)在虚拟机中的终端中执行:
cat /dev/ttyS0
这时主机中的minicom中会出现输入状态,在其中输入的信息也会在虚拟机终端上回显。
3.虚拟机和虚拟机之间的串口通信
两台虚拟机间的通信也可以通过利用主机的命名管道来完成。原理可以简单的这样描述:一台虚拟机在主机中创建的命名管道并其串口相连,另外一台虚拟机也将自己的串口连到主机的命名管道上,这样两个虚拟机的串口就能连起来了。这里两台虚拟机都使用各自的COM1端口,主机的命名管道为同一管道/tmp/vbox,在配置时一台创建通道(假设为Ubuntu8.10DevOS),另一台不创建。启动时先启动创建通道的虚拟机,然后启动另一台虚拟机,分别打开两台虚拟机的终端,通过如下命令将各自的COM1口的输入输出波特率都设为115200
stty ispeed 115200 ospeed 115200 -F /dev/ttyS0
测试过程:
在其中一台虚拟机A终端上执行
cat /dev/ttyS0
在另一台虚拟机B上执行
echo ok > /dev/ttyS0
这时虚拟机A的终端会接受到B发来的ok消息。