[PATCH v2 0/5] bhyve: TCP console support

Changes since v1: I misunderstood semantics of the 'mode' attribute of the <source> element, and used 'connect' while I should have used 'bind', because bhyve listens on the TCP socket and client connects to using using netcat (or any other similar tool). Now it's using the 'bind' value. Other changes: added validation to bhyve_domain.c, and unified error messages used in bhyve_command.c and bhyve_domain.c Roman Bogorodskiy (5): bhyve: support serial type 'tcp' bhyve: increase number of supported consoles to 4 docs: drvbhyve: document TCP console support bhyve: validate serial devices validation bhyve: sync error messages docs/drvbhyve.rst | 19 ++++++ src/bhyve/bhyve_capabilities.c | 3 +- src/bhyve/bhyve_command.c | 42 +++++++++----- src/bhyve/bhyve_domain.c | 27 +++++++++ .../bhyvexml2argv-4-consoles.args | 15 +++++ .../bhyvexml2argv-4-consoles.ldargs | 4 ++ .../bhyvexml2argv-4-consoles.xml | 35 +++++++++++ .../bhyvexml2argv-serial-invalid-port.args | 12 ++++ .../bhyvexml2argv-serial-invalid-port.ldargs | 4 ++ .../bhyvexml2argv-serial-invalid-port.xml | 28 +++++++++ .../bhyvexml2argv-serial-tcp.args | 12 ++++ .../bhyvexml2argv-serial-tcp.ldargs | 4 ++ .../bhyvexml2argv-serial-tcp.xml | 27 +++++++++ tests/bhyvexml2argvtest.c | 3 + .../bhyvexml2xmlout-4-consoles.xml | 58 +++++++++++++++++++ .../bhyvexml2xmlout-serial-tcp.xml | 46 +++++++++++++++ tests/bhyvexml2xmltest.c | 2 + tests/domaincapsdata/bhyve_basic.x86_64.xml | 1 + tests/domaincapsdata/bhyve_fbuf.x86_64.xml | 1 + tests/domaincapsdata/bhyve_uefi.x86_64.xml | 1 + 20 files changed, 328 insertions(+), 16 deletions(-) create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.args create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.ldargs create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.xml create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.args create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.ldargs create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.xml create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.args create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.ldargs create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.xml create mode 100644 tests/bhyvexml2xmloutdata/bhyvexml2xmlout-4-consoles.xml create mode 100644 tests/bhyvexml2xmloutdata/bhyvexml2xmlout-serial-tcp.xml -- 2.49.0

In addition to the nmdm consoles, bhyve also supports a tcp console. It's configured with: .. -l com1,tcp=127.0.0.1:12345 Then a user could connect to the guest console port 0 by making a tcp connection to the host's 127.0.0.1:12345. In the domain XML this configuration is represented as: <serial type='tcp'> <source mode='bind' host='127.0.0.1' service='12345'/> <target type='serial' port='0'/> </serial> Also, update domain capabilities to include the TCP console support. Unfortunately, there's no way to detect that from the bhyve binary before trying to start a VM, so there's no capability probing for this feature. Signed-off-by: Roman Bogorodskiy <bogorodskiy@gmail.com> Reviewed-by: Daniel P. Berrangé <berrange@redhat.com> --- src/bhyve/bhyve_capabilities.c | 3 +- src/bhyve/bhyve_command.c | 42 +++++++++++------ .../bhyvexml2argv-serial-tcp.args | 12 +++++ .../bhyvexml2argv-serial-tcp.ldargs | 4 ++ .../bhyvexml2argv-serial-tcp.xml | 27 +++++++++++ tests/bhyvexml2argvtest.c | 1 + .../bhyvexml2xmlout-serial-tcp.xml | 46 +++++++++++++++++++ tests/bhyvexml2xmltest.c | 1 + tests/domaincapsdata/bhyve_basic.x86_64.xml | 1 + tests/domaincapsdata/bhyve_fbuf.x86_64.xml | 1 + tests/domaincapsdata/bhyve_uefi.x86_64.xml | 1 + 11 files changed, 123 insertions(+), 16 deletions(-) create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.args create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.ldargs create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.xml create mode 100644 tests/bhyvexml2xmloutdata/bhyvexml2xmlout-serial-tcp.xml diff --git a/src/bhyve/bhyve_capabilities.c b/src/bhyve/bhyve_capabilities.c index 59fc81d26c..04a5a4cf29 100644 --- a/src/bhyve/bhyve_capabilities.c +++ b/src/bhyve/bhyve_capabilities.c @@ -128,7 +128,8 @@ virBhyveDomainCapsFill(virDomainCaps *caps, caps->console.supported = VIR_TRISTATE_BOOL_YES; caps->console.type.report = true; VIR_DOMAIN_CAPS_ENUM_SET(caps->console.type, - VIR_DOMAIN_CHR_TYPE_NMDM); + VIR_DOMAIN_CHR_TYPE_NMDM, + VIR_DOMAIN_CHR_TYPE_TCP); return 0; } diff --git a/src/bhyve/bhyve_command.c b/src/bhyve/bhyve_command.c index c82a07c2eb..89648f76cb 100644 --- a/src/bhyve/bhyve_command.c +++ b/src/bhyve/bhyve_command.c @@ -159,29 +159,41 @@ bhyveBuildNetArgStr(const virDomainDef *def, static int bhyveBuildConsoleArgStr(const virDomainDef *def, virCommand *cmd) { + size_t i = 0; virDomainChrDef *chr = NULL; if (!def->nserials) return 0; - chr = def->serials[0]; + for (i = 0; i < def->nserials; i++) { + chr = def->serials[i]; - if (chr->source->type != VIR_DOMAIN_CHR_TYPE_NMDM) { - virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", - _("only nmdm console types are supported")); - return -1; - } + /* bhyve supports only two ports: com1 and com2 */ + if (chr->target.port > 2) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", + _("only two serial ports are supported")); + return -1; + } - /* bhyve supports only two ports: com1 and com2 */ - if (chr->target.port > 2) { - virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", - _("only two serial ports are supported")); - return -1; - } + virCommandAddArg(cmd, "-l"); - virCommandAddArg(cmd, "-l"); - virCommandAddArgFormat(cmd, "com%d,%s", - chr->target.port + 1, chr->source->data.file.path); + switch (chr->source->type) { + case VIR_DOMAIN_CHR_TYPE_NMDM: + virCommandAddArgFormat(cmd, "com%d,%s", + chr->target.port + 1, chr->source->data.file.path); + break; + case VIR_DOMAIN_CHR_TYPE_TCP: + virCommandAddArgFormat(cmd, "com%d,tcp=%s:%s", + chr->target.port + 1, + chr->source->data.tcp.host, + chr->source->data.tcp.service); + break; + default: + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", + _("only nmdm and tcp console types are supported")); + return -1; + } + } return 0; } diff --git a/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.args b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.args new file mode 100644 index 0000000000..8e4072d897 --- /dev/null +++ b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.args @@ -0,0 +1,12 @@ +bhyve \ +-c 1 \ +-m 214 \ +-u \ +-H \ +-P \ +-s 0:0,hostbridge \ +-s 1:0,lpc \ +-s 2:0,ahci,hd:/tmp/freebsd.img \ +-s 3:0,virtio-net,faketapdev,mac=52:54:00:b1:42:eb \ +-l com1,tcp=127.0.0.1:12345 \ +bhyve diff --git a/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.ldargs b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.ldargs new file mode 100644 index 0000000000..5905f4b3e6 --- /dev/null +++ b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.ldargs @@ -0,0 +1,4 @@ +bhyveload \ +-m 214 \ +-d /tmp/freebsd.img \ +bhyve diff --git a/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.xml b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.xml new file mode 100644 index 0000000000..61c9440e44 --- /dev/null +++ b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.xml @@ -0,0 +1,27 @@ +<domain type='bhyve'> + <name>bhyve</name> + <uuid>df3be7e7-a104-11e3-aeb0-50e5492bd3dc</uuid> + <memory>219136</memory> + <vcpu>1</vcpu> + <os> + <type>hvm</type> + </os> + <devices> + <disk type='file'> + <driver name='file' type='raw'/> + <source file='/tmp/freebsd.img'/> + <target dev='hda' bus='sata'/> + <address type='drive' controller='0' bus='0' target='2' unit='0'/> + </disk> + <interface type='bridge'> + <mac address='52:54:00:b1:42:eb'/> + <model type='virtio'/> + <source bridge="virbr0"/> + <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> + </interface> + <serial type='tcp'> + <source mode='connect' host='127.0.0.1' service='12345'/> + <protocol type="raw"/> + </serial> + </devices> +</domain> diff --git a/tests/bhyvexml2argvtest.c b/tests/bhyvexml2argvtest.c index 58b404ca7d..d1786ff165 100644 --- a/tests/bhyvexml2argvtest.c +++ b/tests/bhyvexml2argvtest.c @@ -254,6 +254,7 @@ mymain(void) DO_TEST_FAILURE("virtio-rnd-transitional"); driver.bhyvecaps &= ~BHYVE_CAP_VIRTIO_RND; DO_TEST_FAILURE("virtio-rnd"); + DO_TEST("serial-tcp"); /* Address allocation tests */ DO_TEST("addr-single-sata-disk"); diff --git a/tests/bhyvexml2xmloutdata/bhyvexml2xmlout-serial-tcp.xml b/tests/bhyvexml2xmloutdata/bhyvexml2xmlout-serial-tcp.xml new file mode 100644 index 0000000000..641efcd602 --- /dev/null +++ b/tests/bhyvexml2xmloutdata/bhyvexml2xmlout-serial-tcp.xml @@ -0,0 +1,46 @@ +<domain type='bhyve'> + <name>bhyve</name> + <uuid>df3be7e7-a104-11e3-aeb0-50e5492bd3dc</uuid> + <memory unit='KiB'>219136</memory> + <currentMemory unit='KiB'>219136</currentMemory> + <vcpu placement='static'>1</vcpu> + <os> + <type arch='x86_64'>hvm</type> + <boot dev='hd'/> + </os> + <clock offset='utc'/> + <on_poweroff>destroy</on_poweroff> + <on_reboot>restart</on_reboot> + <on_crash>destroy</on_crash> + <devices> + <disk type='file' device='disk'> + <driver name='file' type='raw'/> + <source file='/tmp/freebsd.img'/> + <target dev='hda' bus='sata'/> + <address type='drive' controller='0' bus='0' target='2' unit='0'/> + </disk> + <controller type='pci' index='0' model='pci-root'/> + <controller type='isa' index='0'> + <address type='pci' domain='0x0000' bus='0x00' slot='0x01' function='0x0'/> + </controller> + <controller type='sata' index='0'> + <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/> + </controller> + <interface type='bridge'> + <mac address='52:54:00:b1:42:eb'/> + <source bridge='virbr0'/> + <model type='virtio'/> + <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> + </interface> + <serial type='tcp'> + <source mode='connect' host='127.0.0.1' service='12345'/> + <protocol type='raw'/> + <target port='0'/> + </serial> + <console type='tcp'> + <source mode='connect' host='127.0.0.1' service='12345'/> + <protocol type='raw'/> + <target type='serial' port='0'/> + </console> + </devices> +</domain> diff --git a/tests/bhyvexml2xmltest.c b/tests/bhyvexml2xmltest.c index 98006dac04..0b858731a6 100644 --- a/tests/bhyvexml2xmltest.c +++ b/tests/bhyvexml2xmltest.c @@ -115,6 +115,7 @@ mymain(void) DO_TEST_DIFFERENT("isa-controller"); DO_TEST_DIFFERENT("fs-9p"); DO_TEST_DIFFERENT("virtio-rnd"); + DO_TEST_DIFFERENT("serial-tcp"); /* Address allocation tests */ DO_TEST_DIFFERENT("addr-single-sata-disk"); diff --git a/tests/domaincapsdata/bhyve_basic.x86_64.xml b/tests/domaincapsdata/bhyve_basic.x86_64.xml index d1211a5b5e..0c386c79d2 100644 --- a/tests/domaincapsdata/bhyve_basic.x86_64.xml +++ b/tests/domaincapsdata/bhyve_basic.x86_64.xml @@ -29,6 +29,7 @@ <hostdev supported='no'/> <console supported='yes'> <enum name='type'> + <value>tcp</value> <value>nmdm</value> </enum> </console> diff --git a/tests/domaincapsdata/bhyve_fbuf.x86_64.xml b/tests/domaincapsdata/bhyve_fbuf.x86_64.xml index 8d5e42dd82..2936281857 100644 --- a/tests/domaincapsdata/bhyve_fbuf.x86_64.xml +++ b/tests/domaincapsdata/bhyve_fbuf.x86_64.xml @@ -46,6 +46,7 @@ <hostdev supported='no'/> <console supported='yes'> <enum name='type'> + <value>tcp</value> <value>nmdm</value> </enum> </console> diff --git a/tests/domaincapsdata/bhyve_uefi.x86_64.xml b/tests/domaincapsdata/bhyve_uefi.x86_64.xml index 3a6f178dd4..fa87fd3640 100644 --- a/tests/domaincapsdata/bhyve_uefi.x86_64.xml +++ b/tests/domaincapsdata/bhyve_uefi.x86_64.xml @@ -38,6 +38,7 @@ <hostdev supported='no'/> <console supported='yes'> <enum name='type'> + <value>tcp</value> <value>nmdm</value> </enum> </console> -- 2.49.0

Recent versions of bhyve support 4 com ports instead of just 2. Thus, allow to use 4 console devices. Also, there was a bug previously because the condition was "if (chr->target.port > 2)", but as target.port start with 0 and "com" ports start with 1, this condition allows com3 to be used. As bhyve supports 4 com ports already long enough, and all supported FreeBSD versions include this capability, do not introduce driver capability for that. Add a couple of tests for that: - A domain that uses 4 serials, 2 of type 'nmdm' and the other 2 of type 'tcp' - A domain that uses unsupported port, such as target.port=4 which translates into com5. Signed-off-by: Roman Bogorodskiy <bogorodskiy@gmail.com> Reviewed-by: Daniel P. Berrangé <berrange@redhat.com> --- src/bhyve/bhyve_command.c | 4 +- .../bhyvexml2argv-4-consoles.args | 15 +++++ .../bhyvexml2argv-4-consoles.ldargs | 4 ++ .../bhyvexml2argv-4-consoles.xml | 35 +++++++++++ .../bhyvexml2argv-serial-invalid-port.args | 12 ++++ .../bhyvexml2argv-serial-invalid-port.ldargs | 4 ++ .../bhyvexml2argv-serial-invalid-port.xml | 28 +++++++++ .../bhyvexml2argv-serial-tcp.xml | 2 +- tests/bhyvexml2argvtest.c | 2 + .../bhyvexml2xmlout-4-consoles.xml | 58 +++++++++++++++++++ .../bhyvexml2xmlout-serial-tcp.xml | 4 +- tests/bhyvexml2xmltest.c | 1 + 12 files changed, 164 insertions(+), 5 deletions(-) create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.args create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.ldargs create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.xml create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.args create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.ldargs create mode 100644 tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.xml create mode 100644 tests/bhyvexml2xmloutdata/bhyvexml2xmlout-4-consoles.xml diff --git a/src/bhyve/bhyve_command.c b/src/bhyve/bhyve_command.c index 89648f76cb..18f65cf757 100644 --- a/src/bhyve/bhyve_command.c +++ b/src/bhyve/bhyve_command.c @@ -168,8 +168,8 @@ bhyveBuildConsoleArgStr(const virDomainDef *def, virCommand *cmd) for (i = 0; i < def->nserials; i++) { chr = def->serials[i]; - /* bhyve supports only two ports: com1 and com2 */ - if (chr->target.port > 2) { + /* bhyve supports 4 ports: com1, com2, com3, com4 */ + if (chr->target.port > 3) { virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", _("only two serial ports are supported")); return -1; diff --git a/tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.args b/tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.args new file mode 100644 index 0000000000..16c7bd7638 --- /dev/null +++ b/tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.args @@ -0,0 +1,15 @@ +bhyve \ +-c 1 \ +-m 214 \ +-u \ +-H \ +-P \ +-s 0:0,hostbridge \ +-s 1:0,lpc \ +-s 2:0,ahci,hd:/tmp/freebsd.img \ +-s 3:0,virtio-net,faketapdev,mac=52:54:00:b1:42:eb \ +-l com1,/dev/nmdmdf3be7e7-a104-11e3-aeb0-50e5492bd3dcA \ +-l com2,tcp=127.0.0.1:12345 \ +-l com3,tcp=0.0.0.0:54321 \ +-l com4,/dev/nmdm0A \ +bhyve diff --git a/tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.ldargs b/tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.ldargs new file mode 100644 index 0000000000..5905f4b3e6 --- /dev/null +++ b/tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.ldargs @@ -0,0 +1,4 @@ +bhyveload \ +-m 214 \ +-d /tmp/freebsd.img \ +bhyve diff --git a/tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.xml b/tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.xml new file mode 100644 index 0000000000..c32680aa34 --- /dev/null +++ b/tests/bhyvexml2argvdata/bhyvexml2argv-4-consoles.xml @@ -0,0 +1,35 @@ +<domain type='bhyve'> + <name>bhyve</name> + <uuid>df3be7e7-a104-11e3-aeb0-50e5492bd3dc</uuid> + <memory>219136</memory> + <vcpu>1</vcpu> + <os> + <type>hvm</type> + </os> + <devices> + <disk type='file'> + <driver name='file' type='raw'/> + <source file='/tmp/freebsd.img'/> + <target dev='hda' bus='sata'/> + <address type='drive' controller='0' bus='0' target='2' unit='0'/> + </disk> + <interface type='bridge'> + <mac address='52:54:00:b1:42:eb'/> + <model type='virtio'/> + <source bridge="virbr0"/> + <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> + </interface> + <serial type='nmdm'/> + <serial type='tcp'> + <source mode='bind' host='127.0.0.1' service='12345'/> + <protocol type="raw"/> + </serial> + <serial type='tcp'> + <source mode='bind' host='0.0.0.0' service='54321'/> + <protocol type="raw"/> + </serial> + <serial type='nmdm'> + <source master="/dev/nmdm0A" slave="/dev/nmdm0B"/> + </serial> + </devices> +</domain> diff --git a/tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.args b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.args new file mode 100644 index 0000000000..8e4072d897 --- /dev/null +++ b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.args @@ -0,0 +1,12 @@ +bhyve \ +-c 1 \ +-m 214 \ +-u \ +-H \ +-P \ +-s 0:0,hostbridge \ +-s 1:0,lpc \ +-s 2:0,ahci,hd:/tmp/freebsd.img \ +-s 3:0,virtio-net,faketapdev,mac=52:54:00:b1:42:eb \ +-l com1,tcp=127.0.0.1:12345 \ +bhyve diff --git a/tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.ldargs b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.ldargs new file mode 100644 index 0000000000..5905f4b3e6 --- /dev/null +++ b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.ldargs @@ -0,0 +1,4 @@ +bhyveload \ +-m 214 \ +-d /tmp/freebsd.img \ +bhyve diff --git a/tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.xml b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.xml new file mode 100644 index 0000000000..36ecd1a9f1 --- /dev/null +++ b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-invalid-port.xml @@ -0,0 +1,28 @@ +<domain type='bhyve'> + <name>bhyve</name> + <uuid>df3be7e7-a104-11e3-aeb0-50e5492bd3dc</uuid> + <memory>219136</memory> + <vcpu>1</vcpu> + <os> + <type>hvm</type> + </os> + <devices> + <disk type='file'> + <driver name='file' type='raw'/> + <source file='/tmp/freebsd.img'/> + <target dev='hda' bus='sata'/> + <address type='drive' controller='0' bus='0' target='2' unit='0'/> + </disk> + <interface type='bridge'> + <mac address='52:54:00:b1:42:eb'/> + <model type='virtio'/> + <source bridge="virbr0"/> + <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> + </interface> + <serial type='tcp'> + <source mode='connect' host='127.0.0.1' service='12345'/> + <protocol type="raw"/> + <target port="4"/> + </serial> + </devices> +</domain> diff --git a/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.xml b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.xml index 61c9440e44..a52b507dda 100644 --- a/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.xml +++ b/tests/bhyvexml2argvdata/bhyvexml2argv-serial-tcp.xml @@ -20,7 +20,7 @@ <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface> <serial type='tcp'> - <source mode='connect' host='127.0.0.1' service='12345'/> + <source mode='bind' host='127.0.0.1' service='12345'/> <protocol type="raw"/> </serial> </devices> diff --git a/tests/bhyvexml2argvtest.c b/tests/bhyvexml2argvtest.c index d1786ff165..2838b20c29 100644 --- a/tests/bhyvexml2argvtest.c +++ b/tests/bhyvexml2argvtest.c @@ -255,6 +255,8 @@ mymain(void) driver.bhyvecaps &= ~BHYVE_CAP_VIRTIO_RND; DO_TEST_FAILURE("virtio-rnd"); DO_TEST("serial-tcp"); + DO_TEST("4-consoles"); + DO_TEST_FAILURE("serial-invalid-port"); /* Address allocation tests */ DO_TEST("addr-single-sata-disk"); diff --git a/tests/bhyvexml2xmloutdata/bhyvexml2xmlout-4-consoles.xml b/tests/bhyvexml2xmloutdata/bhyvexml2xmlout-4-consoles.xml new file mode 100644 index 0000000000..fba7d37a4b --- /dev/null +++ b/tests/bhyvexml2xmloutdata/bhyvexml2xmlout-4-consoles.xml @@ -0,0 +1,58 @@ +<domain type='bhyve'> + <name>bhyve</name> + <uuid>df3be7e7-a104-11e3-aeb0-50e5492bd3dc</uuid> + <memory unit='KiB'>219136</memory> + <currentMemory unit='KiB'>219136</currentMemory> + <vcpu placement='static'>1</vcpu> + <os> + <type arch='x86_64'>hvm</type> + <boot dev='hd'/> + </os> + <clock offset='utc'/> + <on_poweroff>destroy</on_poweroff> + <on_reboot>restart</on_reboot> + <on_crash>destroy</on_crash> + <devices> + <disk type='file' device='disk'> + <driver name='file' type='raw'/> + <source file='/tmp/freebsd.img'/> + <target dev='hda' bus='sata'/> + <address type='drive' controller='0' bus='0' target='2' unit='0'/> + </disk> + <controller type='pci' index='0' model='pci-root'/> + <controller type='isa' index='0'> + <address type='pci' domain='0x0000' bus='0x00' slot='0x01' function='0x0'/> + </controller> + <controller type='sata' index='0'> + <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/> + </controller> + <interface type='bridge'> + <mac address='52:54:00:b1:42:eb'/> + <source bridge='virbr0'/> + <model type='virtio'/> + <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> + </interface> + <serial type='nmdm'> + <source master='/dev/nmdmdf3be7e7-a104-11e3-aeb0-50e5492bd3dcA' slave='/dev/nmdmdf3be7e7-a104-11e3-aeb0-50e5492bd3dcB'/> + <target port='0'/> + </serial> + <serial type='tcp'> + <source mode='bind' host='127.0.0.1' service='12345'/> + <protocol type='raw'/> + <target port='1'/> + </serial> + <serial type='tcp'> + <source mode='bind' host='0.0.0.0' service='54321'/> + <protocol type='raw'/> + <target port='2'/> + </serial> + <serial type='nmdm'> + <source master='/dev/nmdm0A' slave='/dev/nmdm0B'/> + <target port='3'/> + </serial> + <console type='nmdm'> + <source master='/dev/nmdmdf3be7e7-a104-11e3-aeb0-50e5492bd3dcA' slave='/dev/nmdmdf3be7e7-a104-11e3-aeb0-50e5492bd3dcB'/> + <target type='serial' port='0'/> + </console> + </devices> +</domain> diff --git a/tests/bhyvexml2xmloutdata/bhyvexml2xmlout-serial-tcp.xml b/tests/bhyvexml2xmloutdata/bhyvexml2xmlout-serial-tcp.xml index 641efcd602..529f1e8f02 100644 --- a/tests/bhyvexml2xmloutdata/bhyvexml2xmlout-serial-tcp.xml +++ b/tests/bhyvexml2xmloutdata/bhyvexml2xmlout-serial-tcp.xml @@ -33,12 +33,12 @@ <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/> </interface> <serial type='tcp'> - <source mode='connect' host='127.0.0.1' service='12345'/> + <source mode='bind' host='127.0.0.1' service='12345'/> <protocol type='raw'/> <target port='0'/> </serial> <console type='tcp'> - <source mode='connect' host='127.0.0.1' service='12345'/> + <source mode='bind' host='127.0.0.1' service='12345'/> <protocol type='raw'/> <target type='serial' port='0'/> </console> diff --git a/tests/bhyvexml2xmltest.c b/tests/bhyvexml2xmltest.c index 0b858731a6..df093a5539 100644 --- a/tests/bhyvexml2xmltest.c +++ b/tests/bhyvexml2xmltest.c @@ -116,6 +116,7 @@ mymain(void) DO_TEST_DIFFERENT("fs-9p"); DO_TEST_DIFFERENT("virtio-rnd"); DO_TEST_DIFFERENT("serial-tcp"); + DO_TEST_DIFFERENT("4-consoles"); /* Address allocation tests */ DO_TEST_DIFFERENT("addr-single-sata-disk"); -- 2.49.0

Signed-off-by: Roman Bogorodskiy <bogorodskiy@gmail.com> Reviewed-by: Daniel P. Berrangé <berrange@redhat.com> --- docs/drvbhyve.rst | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/docs/drvbhyve.rst b/docs/drvbhyve.rst index 7eec4a2123..0962bccef4 100644 --- a/docs/drvbhyve.rst +++ b/docs/drvbhyve.rst @@ -619,3 +619,22 @@ Example: <backend model='random'/> </rng> ... + +TCP console +~~~~~~~~~~~ +:since:`Since 11.6.0` it's possible to configure TCP console. + +Example: + +:: + + ... + <serial type='tcp'> + <source mode='bind' host='127.0.0.1' service='12345'/> + <target type='serial' port='0'/> + </serial> + ... + +Note: there's no direct way to check if the actual ``bhyve`` binary supports +the TCP console. Thus, libvirt always assumes it's supported. Please +refer to the ``bhyve(1)`` manual page to make sure. -- 2.49.0

Extend bhyveDomainDeviceDefValidate() to check that: - only 'nmdm' or 'tcp' serial devices are used, - serial device count is not more than supported, - only listening raw TCP sockets are used. Signed-off-by: Roman Bogorodskiy <bogorodskiy@gmail.com> --- src/bhyve/bhyve_domain.c | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) diff --git a/src/bhyve/bhyve_domain.c b/src/bhyve/bhyve_domain.c index c9bbf27d83..9dec300a99 100644 --- a/src/bhyve/bhyve_domain.c +++ b/src/bhyve/bhyve_domain.c @@ -263,6 +263,33 @@ bhyveDomainDeviceDefValidate(const virDomainDeviceDef *dev, _("Only 'virio' RNG device model is supported")); return -1; } + } else if (dev->type == VIR_DOMAIN_DEVICE_CHR && + dev->data.chr->deviceType == VIR_DOMAIN_CHR_DEVICE_TYPE_SERIAL) { + virDomainChrDef *chr = dev->data.chr; + if (chr->source->type != VIR_DOMAIN_CHR_TYPE_NMDM && + chr->source->type != VIR_DOMAIN_CHR_TYPE_TCP) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", + _("Only 'nmdm' and 'tcp' console types are supported")); + return -1; + } + if (chr->target.port > 3) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", + _("Only four serial ports are supported")); + return -1; + } + if (chr->source->type == VIR_DOMAIN_CHR_TYPE_TCP) { + if (chr->source->data.tcp.listen == false) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", + _("Only listening TCP sockets are supported")); + return -1; + } + + if (chr->source->data.tcp.protocol != VIR_DOMAIN_CHR_TCP_PROTOCOL_RAW) { + virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", + _("Only 'raw' protocol is supported for TCP sockets")); + return -1; + } + } } return 0; -- 2.49.0

On Wed, Jul 16, 2025 at 06:28:46PM +0200, Roman Bogorodskiy wrote:
Extend bhyveDomainDeviceDefValidate() to check that:
- only 'nmdm' or 'tcp' serial devices are used, - serial device count is not more than supported, - only listening raw TCP sockets are used.
Signed-off-by: Roman Bogorodskiy <bogorodskiy@gmail.com> --- src/bhyve/bhyve_domain.c | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+)
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com> With regards, Daniel -- |: https://berrange.com -o- https://www.flickr.com/photos/dberrange :| |: https://libvirt.org -o- https://fstop138.berrange.com :| |: https://entangle-photo.org -o- https://www.instagram.com/dberrange :|

Use the same error messages for serial devices validation which are already used in bhyve_domain.c Signed-off-by: Roman Bogorodskiy <bogorodskiy@gmail.com> --- src/bhyve/bhyve_command.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/bhyve/bhyve_command.c b/src/bhyve/bhyve_command.c index 18f65cf757..5757a41e7e 100644 --- a/src/bhyve/bhyve_command.c +++ b/src/bhyve/bhyve_command.c @@ -171,7 +171,7 @@ bhyveBuildConsoleArgStr(const virDomainDef *def, virCommand *cmd) /* bhyve supports 4 ports: com1, com2, com3, com4 */ if (chr->target.port > 3) { virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", - _("only two serial ports are supported")); + _("Only four serial ports are supported")); return -1; } @@ -190,7 +190,7 @@ bhyveBuildConsoleArgStr(const virDomainDef *def, virCommand *cmd) break; default: virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", - _("only nmdm and tcp console types are supported")); + _("Only 'nmdm' and 'tcp' console types are supported")); return -1; } } -- 2.49.0

On Wed, Jul 16, 2025 at 06:28:47PM +0200, Roman Bogorodskiy wrote:
Use the same error messages for serial devices validation which are already used in bhyve_domain.c
Signed-off-by: Roman Bogorodskiy <bogorodskiy@gmail.com> --- src/bhyve/bhyve_command.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
diff --git a/src/bhyve/bhyve_command.c b/src/bhyve/bhyve_command.c index 18f65cf757..5757a41e7e 100644 --- a/src/bhyve/bhyve_command.c +++ b/src/bhyve/bhyve_command.c @@ -171,7 +171,7 @@ bhyveBuildConsoleArgStr(const virDomainDef *def, virCommand *cmd) /* bhyve supports 4 ports: com1, com2, com3, com4 */ if (chr->target.port > 3) { virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", - _("only two serial ports are supported")); + _("Only four serial ports are supported")); return -1; }
@@ -190,7 +190,7 @@ bhyveBuildConsoleArgStr(const virDomainDef *def, virCommand *cmd) break; default: virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", - _("only nmdm and tcp console types are supported")); + _("Only 'nmdm' and 'tcp' console types are supported")); return -1; } }
FWIW, in the QEMU driver, when building the CLI, we make the assumption that the domani validation has been performed, so we wouldn't repeat things like the "chr->target.port > 3" check again. With regards, Daniel -- |: https://berrange.com -o- https://www.flickr.com/photos/dberrange :| |: https://libvirt.org -o- https://fstop138.berrange.com :| |: https://entangle-photo.org -o- https://www.instagram.com/dberrange :|

Daniel P. Berrangé wrote:
On Wed, Jul 16, 2025 at 06:28:47PM +0200, Roman Bogorodskiy wrote:
Use the same error messages for serial devices validation which are already used in bhyve_domain.c
Signed-off-by: Roman Bogorodskiy <bogorodskiy@gmail.com> --- src/bhyve/bhyve_command.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
diff --git a/src/bhyve/bhyve_command.c b/src/bhyve/bhyve_command.c index 18f65cf757..5757a41e7e 100644 --- a/src/bhyve/bhyve_command.c +++ b/src/bhyve/bhyve_command.c @@ -171,7 +171,7 @@ bhyveBuildConsoleArgStr(const virDomainDef *def, virCommand *cmd) /* bhyve supports 4 ports: com1, com2, com3, com4 */ if (chr->target.port > 3) { virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", - _("only two serial ports are supported")); + _("Only four serial ports are supported")); return -1; }
@@ -190,7 +190,7 @@ bhyveBuildConsoleArgStr(const virDomainDef *def, virCommand *cmd) break; default: virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s", - _("only nmdm and tcp console types are supported")); + _("Only 'nmdm' and 'tcp' console types are supported")); return -1; } }
FWIW, in the QEMU driver, when building the CLI, we make the assumption that the domani validation has been performed, so we wouldn't repeat things like the "chr->target.port > 3" check again.
Yes, I think I need to do the same. Not sure if it's better to do in one shot or gradually move validation to bhyve_domain.c when touching related areas. Probably doing in one shot is better for consistency of the codebase.
With regards, Daniel -- |: https://berrange.com -o- https://www.flickr.com/photos/dberrange :| |: https://libvirt.org -o- https://fstop138.berrange.com :| |: https://entangle-photo.org -o- https://www.instagram.com/dberrange :|
participants (2)
-
Daniel P. Berrangé
-
Roman Bogorodskiy