From: Elena Ufimtseva <elena.ufimts...@oracle.com> Signed-off-by: Elena Ufimtseva <elena.ufimts...@oracle.com> Signed-off-by: Jagannathan Raman <jag.ra...@oracle.com> Signed-off-by: John G Johnson <john.g.john...@oracle.com> --- New patch in v3
vl.c | 117 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 117 insertions(+) diff --git a/vl.c b/vl.c index dc2558c..08e9c09 100644 --- a/vl.c +++ b/vl.c @@ -279,6 +279,28 @@ static QemuOptsList qemu_option_rom_opts = { }, }; +static QemuOptsList qemu_remote_opts = { + .name = "remote", + .head = QTAILQ_HEAD_INITIALIZER(qemu_remote_opts.head), + .desc = { + { + .name = "rid", + .type = QEMU_OPT_NUMBER, + .help = "id of the remote process" + },{ + .name = "socket", + .type = QEMU_OPT_NUMBER, + .help = "Socket for remote", + },{ + .name = "command", + .type = QEMU_OPT_STRING, + .help = "command to run", + }, + { /* end of list */ } + }, +}; + + static QemuOptsList qemu_machine_opts = { .name = "machine", .implied_opt_name = "type", @@ -346,6 +368,87 @@ static QemuOptsList qemu_boot_opts = { }, }; +#if defined(CONFIG_MPQEMU) +static int device_remote_add(void *opaque, QemuOpts *opts, Error **errp) +{ + unsigned int rid = *(unsigned int *)opaque; + const char *opt_rid = NULL; + struct remote_process *p = NULL;; + + opt_rid = qemu_opt_get(opts, "rid"); + if (!opt_rid) { + return 0; + } + + p = get_remote_process_rid(rid); + if (!p) { + return -EINVAL; + } + + if (atoi(opt_rid) == rid) { + qemu_opt_set(opts, "command", p->command, errp); + rdevice_init_func(opaque, opts, errp); + qemu_opts_del(opts); + } + return 0; +} + +static int parse_remote(void *opaque, QemuOpts *opts, Error **errp) +{ + int rid; + int socket; + char *c_sock; + const char *command = NULL; + struct remote_process r_proc; + + rid = atoi(qemu_opt_get(opts, "rid")); + if (rid < 0) { + error_setg(errp, "rid is required."); + return -1; + } + if (get_remote_process_rid(rid)) { + error_setg(errp, "There is already process with rid %d", rid); + goto cont_devices; + } + + c_sock = (char *)qemu_opt_get(opts, "socket"); + if (c_sock) { + socket = atoi(c_sock); + } else { + socket = -1; + } + + command = qemu_opt_get(opts, "command"); + + if (socket <= STDERR_FILENO && socket != -1) { + socket = -1; + } + + if (!command && socket < 0) { + error_setg(errp, "No correct socket or command defined for remote."); + return -1; + } + + if (rid < 0) { + error_setg(errp, "id option is required and must be non-negative"); + return -1; + } + r_proc.rid = rid; + r_proc.socket = socket; + r_proc.command = g_strdup(command); + remote_process_register(&r_proc); + + cont_devices: + if (qemu_opts_foreach(qemu_find_opts("device"), device_remote_add, + &rid, NULL)) { + error_setg(errp, "Could not process some of the remote devices."); + } + + return 0; +} + +#endif + static QemuOptsList qemu_add_fd_opts = { .name = "add-fd", .head = QTAILQ_HEAD_INITIALIZER(qemu_add_fd_opts.head), @@ -2861,6 +2964,7 @@ int main(int argc, char **argv, char **envp) qemu_add_opts(&qemu_icount_opts); qemu_add_opts(&qemu_semihosting_config_opts); qemu_add_opts(&qemu_fw_cfg_opts); + qemu_add_opts(&qemu_remote_opts); module_call_init(MODULE_INIT_OPTS); runstate_init(); @@ -3697,6 +3801,14 @@ int main(int argc, char **argv, char **envp) exit(1); #endif break; + case QEMU_OPTION_remote: + opts = qemu_opts_parse_noisily(qemu_find_opts("remote"), + optarg, false); + if (!opts) { + exit(1); + } + break; + case QEMU_OPTION_object: opts = qemu_opts_parse_noisily(qemu_find_opts("object"), optarg, true); @@ -4297,6 +4409,11 @@ int main(int argc, char **argv, char **envp) qemu_opts_foreach(qemu_find_opts("device"), device_init_func, NULL, &error_fatal); +#ifdef CONFIG_MPQEMU + qemu_opts_foreach(qemu_find_opts("remote"), + parse_remote, NULL, &error_fatal); +#endif + cpu_synchronize_all_post_init(); rom_reset_order_override(); -- 1.8.3.1