[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-devel] [PATCH v3 3/3] xl: add support for channels
This adds support for channel declarations of the form: channel = [ "name=...,kind=...[,path=...][,backend=...]" ] where 'name' is a label to identify the channel to the frontend. If 'kind = pty' then the channel is connected to a pty in the backend domain If 'kind = socket' then the channel is connected to a Unix domain socket given by 'path = ...' in the backend domain. This patch also adds the command: xl channel-list <domain> which allows the state of channels to be queried. In particular if 'kind=pty' this will show the path of the pty slave device. Signed-off-by: David Scott <dave.scott@xxxxxxxxxx> --- docs/man/xl.cfg.pod.5 | 51 ++++++++++++++++++++++++ docs/man/xl.pod.1 | 10 +++++ tools/libxl/xl.h | 1 + tools/libxl/xl_cmdimpl.c | 97 ++++++++++++++++++++++++++++++++++++++++++++- tools/libxl/xl_cmdtable.c | 5 +++ 5 files changed, 163 insertions(+), 1 deletion(-) diff --git a/docs/man/xl.cfg.pod.5 b/docs/man/xl.cfg.pod.5 index a94d037..5069049 100644 --- a/docs/man/xl.cfg.pod.5 +++ b/docs/man/xl.cfg.pod.5 @@ -470,6 +470,57 @@ L<qemu(1)> manpage. The default is B<en-us>. =back +=item B<channel=[ "CHANNEL_SPEC_STRING", "CHANNEL_SPEC_STRING", ...]> + +Specifies the virtual channels to be provided to the guest. A +channel is a low-bandwidth, bidirectional byte stream, which resembles +a serial link. Typical uses for channels include transmitting VM +configuration after boot and signalling to in-guest agents. Please see +F<docs/misc/channels.txt> for more details. + +Each B<CHANNEL_SPEC_STRING> is a comma-separated list of C<KEY=VALUE> +settings, from the following list: + +=over 4 + +=item C<backend=DOMAIN> + +Specify the backend domain name or id. This parameter is optional. If +this parameter is omitted then the toolstack domain will be assumed. + +=item C<name=NAME> + +Specify the string name for this device. This parameter is mandatory. +This should be a well-known name for the specific application (e.g. +guest agent) and should be used by the frontend to connect the +application to the right channel device. There is no formal registry +of channel names, so application authors are encouraged to make their +names unique by including domain name and version number in the string +(e.g. org.mydomain.guestagent.1). + +=item C<kind=KIND> + +Specify how the backend will be implemented. This following options are +available: + +=over 4 + +=item B<kind=SOCKET>: + +The backend will bind a Unix domain socket (at the path given by +B<path=PATH>), call listen and accept connections. The backend will proxy +data between the channel and the connected socket. + +=item B<kind=PTY>: + +The backend will create a pty and proxy data between the channel and the +master device. The command B<xl channel-list> can be used to discover the +assigned slave device. + +=back + +=back + =item B<pci=[ "PCI_SPEC_STRING", "PCI_SPEC_STRING", ... ]> Specifies the host PCI devices to passthrough to this guest. Each B<PCI_SPEC_STRING> diff --git a/docs/man/xl.pod.1 b/docs/man/xl.pod.1 index 30bd4bf..827f5a5 100644 --- a/docs/man/xl.pod.1 +++ b/docs/man/xl.pod.1 @@ -1194,6 +1194,16 @@ List virtual network interfaces for a domain. =back +=head2 CHANNEL DEVICES + +=over 4 + +=item B<channel-list> I<domain-id> + +List virtual channel interfaces for a domain. + +=back + =head2 VTPM DEVICES =over 4 diff --git a/tools/libxl/xl.h b/tools/libxl/xl.h index 10a2e66..afc5f8b 100644 --- a/tools/libxl/xl.h +++ b/tools/libxl/xl.h @@ -78,6 +78,7 @@ int main_top(int argc, char **argv); int main_networkattach(int argc, char **argv); int main_networklist(int argc, char **argv); int main_networkdetach(int argc, char **argv); +int main_channellist(int argc, char **argv); int main_blockattach(int argc, char **argv); int main_blocklist(int argc, char **argv); int main_blockdetach(int argc, char **argv); diff --git a/tools/libxl/xl_cmdimpl.c b/tools/libxl/xl_cmdimpl.c index 5195914..a5697ef 100644 --- a/tools/libxl/xl_cmdimpl.c +++ b/tools/libxl/xl_cmdimpl.c @@ -736,7 +736,7 @@ static void parse_config_data(const char *config_source, long l; XLU_Config *config; XLU_ConfigList *cpus, *vbds, *nics, *pcis, *cvfbs, *cpuids, *vtpms; - XLU_ConfigList *ioports, *irqs, *iomem; + XLU_ConfigList *channels, *ioports, *irqs, *iomem; int num_ioports, num_irqs, num_iomem; int pci_power_mgmt = 0; int pci_msitranslate = 0; @@ -1289,6 +1289,58 @@ static void parse_config_data(const char *config_source, } } + if (!xlu_cfg_get_list (config, "channel", &channels, 0, 0)) { + d_config->num_channels = 0; + d_config->channels = NULL; + while ((buf = xlu_cfg_get_listitem (channels, + d_config->num_channels)) != NULL) { + libxl_device_channel *chn; + char *buf2 = strdup(buf); + char *p, *p2; + chn = ARRAY_EXTEND_INIT(d_config->channels, d_config->num_channels, + libxl_device_channel_init); + + p = strtok(buf2, ","); + if (!p) + goto skip_channel; + do { + while (*p == ' ') + p++; + if ((p2 = strchr(p, '=')) == NULL) + break; + *p2 = '\0'; + if (!strcmp(p, "backend")) { + free(chn->backend_domname); + chn->backend_domname = strdup(p2 + 1); + } else if (!strcmp(p, "name")) { + free(chn->name); + chn->name = strdup(p2 + 1); + } else if (!strcmp(p, "kind")) { + if (chn->kind != LIBXL_CHANNEL_KIND_UNKNOWN) { + fprintf(stderr, "a channel may have only one kind\n"); + exit(1); + } + if (!strcmp(p2 + 1, "pty")) { + chn->kind = LIBXL_CHANNEL_KIND_PTY; + } else if (!strcmp(p2 + 1, "socket")) { + chn->kind = LIBXL_CHANNEL_KIND_SOCKET; + } else { + fprintf(stderr, "unknown channel kind '%s'\n", p2 + 1); + exit(1); + } + } else if (!strcmp(p, "path")) { + free(chn->u.socket.path); + chn->u.socket.path = strdup(p2 + 1); + } else { + fprintf(stderr, "unknown channel parameter '%s'," + " ignoring\n", p); + } + } while ((p = strtok(NULL, ",")) != NULL); +skip_channel: + free(buf2); + } + } + if (!xlu_cfg_get_list (config, "vif", &nics, 0, 0)) { d_config->num_nics = 0; d_config->nics = NULL; @@ -5921,6 +5973,49 @@ int main_networkdetach(int argc, char **argv) return 0; } +int main_channellist(int argc, char **argv) +{ + int opt; + libxl_device_channel *channels; + libxl_channelinfo channelinfo; + int nb, i; + + SWITCH_FOREACH_OPT(opt, "", NULL, "channel-list", 1) { + /* No options */ + } + + /* Idx BE MAC Hdl Sta evch txr/rxr BE-path */ + printf("%-3s %-2s %-5s %-6s %8s %-10s %-30s\n", + "Idx", "BE", "state", "evt-ch", "ring-ref", "kind", ""); + for (argv += optind, argc -= optind; argc > 0; --argc, ++argv) { + uint32_t domid = find_domain(*argv); + channels = libxl_device_channel_list(ctx, domid, &nb); + if (!channels) { + continue; + } + for (i = 0; i < nb; ++i) { + if (!libxl_device_channel_getinfo(ctx, domid, &channels[i], &channelinfo)) { + printf("%-3d %-2d ", channels[i].devid, channelinfo.backend_id); + printf("%-5d ", channelinfo.state); + printf("%-6d %-8d ", channelinfo.evtch, channelinfo.rref); + printf("%-10s ", libxl_channel_kind_to_string(channels[i].kind)); + switch (channels[i].kind) { + case LIBXL_CHANNEL_KIND_PTY: + printf("%-30s ", channelinfo.u.pty.path); + break; + default: + break; + } + printf("\n"); + libxl_channelinfo_dispose(&channelinfo); + } + libxl_device_channel_dispose(&channels[i]); + } + free(channels); + } + return 0; +} + int main_blockattach(int argc, char **argv) { int opt; diff --git a/tools/libxl/xl_cmdtable.c b/tools/libxl/xl_cmdtable.c index 4279b9f..e8d01ae 100644 --- a/tools/libxl/xl_cmdtable.c +++ b/tools/libxl/xl_cmdtable.c @@ -335,6 +335,11 @@ struct cmd_spec cmd_table[] = { "Destroy a domain's virtual network device", "<Domain> <DevId|mac>", }, + { "channel-list", + &main_channellist, 0, 0, + "List virtual channel devices for a domain", + "<Domain(s)>", + }, { "block-attach", &main_blockattach, 1, 1, "Create a new virtual block device", -- 1.7.10.4 _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxx http://lists.xen.org/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |