vz: add tcp and udp serial device support

vz supports only a subset of tcp and udp parameters.

1. tcp type supports only 'raw' protocol.
2. udp type supports only same parameters of 'host' and 'service'
for 'bind' and 'connect'.

Signed-off-by: Nikolay Shirokovskiy <nshirokovskiy@virtuozzo.com>
This commit is contained in:
Nikolay Shirokovskiy 2016-05-31 12:38:33 +03:00 committed by Maxim Nestratov
parent ec8d5ce1ea
commit c62e9d4199

View File

@ -1078,48 +1078,85 @@ prlsdkGetSerialInfo(PRL_HANDLE serialPort, virDomainChrDefPtr chr)
PRL_UINT32 emulatedType;
char *friendlyName = NULL;
PRL_SERIAL_PORT_SOCKET_OPERATION_MODE socket_mode;
char *uristr = NULL;
virURIPtr uri = NULL;
int ret = -1;
chr->deviceType = VIR_DOMAIN_CHR_DEVICE_TYPE_SERIAL;
chr->targetTypeAttr = false;
pret = PrlVmDev_GetIndex(serialPort, &serialPortIndex);
prlsdkCheckRetGoto(pret, error);
prlsdkCheckRetGoto(pret, cleanup);
chr->target.port = serialPortIndex;
pret = PrlVmDev_GetEmulatedType(serialPort, &emulatedType);
prlsdkCheckRetGoto(pret, error);
prlsdkCheckRetGoto(pret, cleanup);
if (!(friendlyName = prlsdkGetStringParamVar(PrlVmDev_GetFriendlyName,
serialPort)))
goto error;
goto cleanup;
pret = PrlVmDevSerial_GetSocketMode(serialPort, &socket_mode);
prlsdkCheckRetGoto(pret, error);
prlsdkCheckRetGoto(pret, cleanup);
switch (emulatedType) {
case PDT_USE_OUTPUT_FILE:
chr->source.type = VIR_DOMAIN_CHR_TYPE_FILE;
chr->source.data.file.path = friendlyName;
friendlyName = NULL;
break;
case PDT_USE_SERIAL_PORT_SOCKET_MODE:
chr->source.type = VIR_DOMAIN_CHR_TYPE_UNIX;
chr->source.data.nix.path = friendlyName;
chr->source.data.nix.listen = socket_mode == PSP_SERIAL_SOCKET_SERVER;
friendlyName = NULL;
break;
case PDT_USE_REAL_DEVICE:
chr->source.type = VIR_DOMAIN_CHR_TYPE_DEV;
chr->source.data.file.path = friendlyName;
friendlyName = NULL;
break;
case PDT_USE_TCP:
chr->source.type = VIR_DOMAIN_CHR_TYPE_TCP;
if (virAsprintf(&uristr, "tcp://%s", friendlyName) < 0)
goto cleanup;
if (!(uri = virURIParse(uristr)))
goto cleanup;
if (VIR_STRDUP(chr->source.data.tcp.host, uri->server) < 0)
goto cleanup;
if (virAsprintf(&chr->source.data.tcp.service, "%d", uri->port) < 0)
goto cleanup;
chr->source.data.tcp.listen = socket_mode == PSP_SERIAL_SOCKET_SERVER;
break;
case PDT_USE_UDP:
chr->source.type = VIR_DOMAIN_CHR_TYPE_UDP;
if (virAsprintf(&uristr, "udp://%s", friendlyName) < 0)
goto cleanup;
if (!(uri = virURIParse(uristr)))
goto cleanup;
if (VIR_STRDUP(chr->source.data.udp.bindHost, uri->server) < 0)
goto cleanup;
if (virAsprintf(&chr->source.data.udp.bindService, "%d", uri->port) < 0)
goto cleanup;
if (VIR_STRDUP(chr->source.data.udp.connectHost, uri->server) < 0)
goto cleanup;
if (virAsprintf(&chr->source.data.udp.connectService, "%d", uri->port) < 0)
goto cleanup;
break;
default:
virReportError(VIR_ERR_INTERNAL_ERROR,
_("Unknown serial type: %X"), emulatedType);
goto error;
goto cleanup;
break;
}
return 0;
error:
ret = 0;
cleanup:
VIR_FREE(friendlyName);
return -1;
VIR_FREE(uristr);
virURIFree(uri);
return ret;
}
@ -2627,7 +2664,9 @@ static int prlsdkCheckSerialUnsupportedParams(virDomainChrDefPtr chr)
if (chr->source.type != VIR_DOMAIN_CHR_TYPE_DEV &&
chr->source.type != VIR_DOMAIN_CHR_TYPE_FILE &&
chr->source.type != VIR_DOMAIN_CHR_TYPE_UNIX) {
chr->source.type != VIR_DOMAIN_CHR_TYPE_UNIX &&
chr->source.type != VIR_DOMAIN_CHR_TYPE_TCP &&
chr->source.type != VIR_DOMAIN_CHR_TYPE_UDP) {
virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
@ -2650,6 +2689,26 @@ static int prlsdkCheckSerialUnsupportedParams(virDomainChrDefPtr chr)
return -1;
}
if (chr->source.type == VIR_DOMAIN_CHR_TYPE_TCP &&
chr->source.data.tcp.protocol != VIR_DOMAIN_CHR_TCP_PROTOCOL_RAW) {
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
_("Protocol '%s' is not supported for "
"tcp character device."),
virDomainChrTcpProtocolTypeToString(chr->source.data.tcp.protocol));
return -1;
}
if (chr->source.type == VIR_DOMAIN_CHR_TYPE_UDP &&
(STRNEQ(chr->source.data.udp.bindHost,
chr->source.data.udp.connectHost) ||
STRNEQ(chr->source.data.udp.bindService,
chr->source.data.udp.connectService))) {
virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
_("Different bind and connect parameters for "
"udp character device is not supported."));
return -1;
}
return 0;
}
@ -2851,6 +2910,7 @@ static int prlsdkAddSerial(PRL_HANDLE sdkdom, virDomainChrDefPtr chr)
PRL_VM_DEV_EMULATION_TYPE emutype;
PRL_SERIAL_PORT_SOCKET_OPERATION_MODE socket_mode = PSP_SERIAL_SOCKET_SERVER;
char *path;
char *url = NULL;
int ret = -1;
if (prlsdkCheckSerialUnsupportedParams(chr) < 0)
@ -2871,11 +2931,27 @@ static int prlsdkAddSerial(PRL_HANDLE sdkdom, virDomainChrDefPtr chr)
case VIR_DOMAIN_CHR_TYPE_UNIX:
emutype = PDT_USE_SERIAL_PORT_SOCKET_MODE;
path = chr->source.data.nix.path;
if (chr->source.data.nix.listen)
socket_mode = PSP_SERIAL_SOCKET_SERVER;
else
if (!chr->source.data.nix.listen)
socket_mode = PSP_SERIAL_SOCKET_CLIENT;
break;
case VIR_DOMAIN_CHR_TYPE_TCP:
emutype = PDT_USE_TCP;
if (virAsprintf(&url, "%s:%s",
chr->source.data.tcp.host,
chr->source.data.tcp.service) < 0)
goto cleanup;
if (!chr->source.data.tcp.listen)
socket_mode = PSP_SERIAL_SOCKET_CLIENT;
path = url;
break;
case VIR_DOMAIN_CHR_TYPE_UDP:
emutype = PDT_USE_UDP;
if (virAsprintf(&url, "%s:%s",
chr->source.data.udp.bindHost,
chr->source.data.udp.bindService) < 0)
goto cleanup;
path = url;
break;
default:
virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
_("vz driver doesn't support "
@ -2892,10 +2968,8 @@ static int prlsdkAddSerial(PRL_HANDLE sdkdom, virDomainChrDefPtr chr)
pret = PrlVmDev_SetFriendlyName(sdkchr, path);
prlsdkCheckRetGoto(pret, cleanup);
if (chr->source.type == VIR_DOMAIN_CHR_TYPE_UNIX) {
pret = PrlVmDevSerial_SetSocketMode(sdkchr, socket_mode);
prlsdkCheckRetGoto(pret, cleanup);
}
pret = PrlVmDevSerial_SetSocketMode(sdkchr, socket_mode);
prlsdkCheckRetGoto(pret, cleanup);
pret = PrlVmDev_SetEnabled(sdkchr, 1);
prlsdkCheckRetGoto(pret, cleanup);
@ -2906,6 +2980,7 @@ static int prlsdkAddSerial(PRL_HANDLE sdkdom, virDomainChrDefPtr chr)
ret = 0;
cleanup:
PrlHandle_Free(sdkchr);
VIR_FREE(url);
return ret;
}