提交 caa97225 编写于 作者: A Anthony Liguori

Merge remote branch 'qmp/for-anthony' into staging

......@@ -1017,7 +1017,8 @@ static void do_info_cpu_stats(Monitor *mon)
*/
static int do_quit(Monitor *mon, const QDict *qdict, QObject **ret_data)
{
exit(0);
monitor_suspend(mon);
qemu_system_exit_request();
return 0;
}
......@@ -2414,15 +2415,6 @@ static int do_getfd(Monitor *mon, const QDict *qdict, QObject **ret_data)
return -1;
}
fd = dup(fd);
if (fd == -1) {
if (errno == EMFILE)
qerror_report(QERR_TOO_MANY_FILES);
else
qerror_report(QERR_UNDEFINED_ERROR);
return -1;
}
QLIST_FOREACH(monfd, &mon->fds, next) {
if (strcmp(monfd->name, fdname) != 0) {
continue;
......@@ -4404,7 +4396,7 @@ static void handle_qmp_command(JSONMessageParser *parser, QList *tokens)
qerror_report(QERR_QMP_BAD_INPUT_OBJECT, "execute");
goto err_input;
} else if (qobject_type(obj) != QTYPE_QSTRING) {
qerror_report(QERR_QMP_BAD_INPUT_OBJECT, "string");
qerror_report(QERR_QMP_BAD_INPUT_OBJECT_MEMBER, "execute", "string");
goto err_input;
}
......@@ -4437,6 +4429,9 @@ static void handle_qmp_command(JSONMessageParser *parser, QList *tokens)
obj = qdict_get(input, "arguments");
if (!obj) {
args = qdict_new();
} else if (qobject_type(obj) != QTYPE_QDICT) {
qerror_report(QERR_QMP_BAD_INPUT_OBJECT_MEMBER, "arguments", "object");
goto err_input;
} else {
args = qobject_to_qdict(obj);
QINCREF(args);
......
......@@ -2000,8 +2000,9 @@ static void tcp_chr_process_IAC_bytes(CharDriverState *chr,
static int tcp_get_msgfd(CharDriverState *chr)
{
TCPCharDriver *s = chr->opaque;
return s->msgfd;
int fd = s->msgfd;
s->msgfd = -1;
return fd;
}
#ifndef _WIN32
......@@ -2089,10 +2090,6 @@ static void tcp_chr_read(void *opaque)
tcp_chr_process_IAC_bytes(chr, s, buf, &size);
if (size > 0)
qemu_chr_read(chr, buf, size);
if (s->msgfd != -1) {
close(s->msgfd);
s->msgfd = -1;
}
}
}
......
......@@ -1175,32 +1175,33 @@ DEFHEADING()
DEFHEADING(Character device options:)
DEF("chardev", HAS_ARG, QEMU_OPTION_chardev,
"-chardev null,id=id\n"
"-chardev null,id=id[,mux=on|off]\n"
"-chardev socket,id=id[,host=host],port=host[,to=to][,ipv4][,ipv6][,nodelay]\n"
" [,server][,nowait][,telnet] (tcp)\n"
"-chardev socket,id=id,path=path[,server][,nowait][,telnet] (unix)\n"
" [,server][,nowait][,telnet][,mux=on|off] (tcp)\n"
"-chardev socket,id=id,path=path[,server][,nowait][,telnet],[mux=on|off] (unix)\n"
"-chardev udp,id=id[,host=host],port=port[,localaddr=localaddr]\n"
" [,localport=localport][,ipv4][,ipv6]\n"
"-chardev msmouse,id=id\n"
" [,localport=localport][,ipv4][,ipv6][,mux=on|off]\n"
"-chardev msmouse,id=id[,mux=on|off]\n"
"-chardev vc,id=id[[,width=width][,height=height]][[,cols=cols][,rows=rows]]\n"
"-chardev file,id=id,path=path\n"
"-chardev pipe,id=id,path=path\n"
" [,mux=on|off]\n"
"-chardev file,id=id,path=path[,mux=on|off]\n"
"-chardev pipe,id=id,path=path[,mux=on|off]\n"
#ifdef _WIN32
"-chardev console,id=id\n"
"-chardev serial,id=id,path=path\n"
"-chardev console,id=id[,mux=on|off]\n"
"-chardev serial,id=id,path=path[,mux=on|off]\n"
#else
"-chardev pty,id=id\n"
"-chardev stdio,id=id\n"
"-chardev pty,id=id[,mux=on|off]\n"
"-chardev stdio,id=id[,mux=on|off]\n"
#endif
#ifdef CONFIG_BRLAPI
"-chardev braille,id=id\n"
"-chardev braille,id=id[,mux=on|off]\n"
#endif
#if defined(__linux__) || defined(__sun__) || defined(__FreeBSD__) \
|| defined(__NetBSD__) || defined(__OpenBSD__) || defined(__DragonFly__)
"-chardev tty,id=id,path=path\n"
"-chardev tty,id=id,path=path[,mux=on|off]\n"
#endif
#if defined(__linux__) || defined(__FreeBSD__) || defined(__DragonFly__)
"-chardev parport,id=id,path=path\n"
"-chardev parport,id=id,path=path[,mux=on|off]\n"
#endif
, QEMU_ARCH_ALL
)
......@@ -1210,7 +1211,7 @@ STEXI
The general form of a character device option is:
@table @option
@item -chardev @var{backend} ,id=@var{id} [,@var{options}]
@item -chardev @var{backend} ,id=@var{id} [,mux=on|off] [,@var{options}]
@findex -chardev
Backend is one of:
@option{null},
......@@ -1232,6 +1233,10 @@ The specific backend will determine the applicable options.
All devices must have an id, which can be any string up to 127 characters long.
It is used to uniquely identify this device in other command line directives.
A character device may be used in multiplexing mode by multiple front-ends.
The key sequence of @key{Control-a} and @key{c} will rotate the input focus
between attached front-ends. Specify @option{mux=on} to enable this mode.
Options to each backend are described below.
@item -chardev null ,id=@var{id}
......
......@@ -170,7 +170,11 @@ static const QErrorStringTable qerror_table[] = {
},
{
.error_fmt = QERR_QMP_BAD_INPUT_OBJECT,
.desc = "Bad QMP input object",
.desc = "Expected '%(expected)' in QMP input",
},
{
.error_fmt = QERR_QMP_BAD_INPUT_OBJECT_MEMBER,
.desc = "QMP input object member '%(member)' expects '%(expected)'",
},
{
.error_fmt = QERR_SET_PASSWD_FAILED,
......
......@@ -145,6 +145,9 @@ QError *qobject_to_qerror(const QObject *obj);
#define QERR_QMP_BAD_INPUT_OBJECT \
"{ 'class': 'QMPBadInputObject', 'data': { 'expected': %s } }"
#define QERR_QMP_BAD_INPUT_OBJECT_MEMBER \
"{ 'class': 'QMPBadInputObjectMember', 'data': { 'member': %s, 'expected': %s } }"
#define QERR_SET_PASSWD_FAILED \
"{ 'class': 'SetPasswdFailed', 'data': {} }"
......
......@@ -45,9 +45,11 @@ void cpu_disable_ticks(void);
void qemu_system_reset_request(void);
void qemu_system_shutdown_request(void);
void qemu_system_powerdown_request(void);
void qemu_system_exit_request(void);
int qemu_shutdown_requested(void);
int qemu_reset_requested(void);
int qemu_powerdown_requested(void);
int qemu_exit_requested(void);
extern qemu_irq qemu_system_powerdown;
void qemu_system_reset(void);
......
......@@ -1697,6 +1697,7 @@ static int shutdown_requested;
static int powerdown_requested;
int debug_requested;
int vmstop_requested;
static int exit_requested;
int qemu_shutdown_requested(void)
{
......@@ -1719,6 +1720,12 @@ int qemu_powerdown_requested(void)
return r;
}
int qemu_exit_requested(void)
{
/* just return it, we'll exit() anyway */
return exit_requested;
}
static int qemu_debug_requested(void)
{
int r = debug_requested;
......@@ -1789,6 +1796,12 @@ void qemu_system_powerdown_request(void)
qemu_notify_event();
}
void qemu_system_exit_request(void)
{
exit_requested = 1;
qemu_notify_event();
}
#ifdef _WIN32
static void host_main_loop_wait(int *timeout)
{
......@@ -1925,6 +1938,8 @@ static int vm_can_run(void)
return 0;
if (debug_requested)
return 0;
if (exit_requested)
return 0;
return 1;
}
......@@ -1977,6 +1992,9 @@ static void main_loop(void)
if ((r = qemu_vmstop_requested())) {
vm_stop(r);
}
if (qemu_exit_requested()) {
exit(0);
}
}
pause_all_vcpus();
}
......@@ -2330,11 +2348,9 @@ static void monitor_parse(const char *optarg, const char *mode)
if (strstart(optarg, "chardev:", &p)) {
snprintf(label, sizeof(label), "%s", p);
} else {
if (monitor_device_index) {
snprintf(label, sizeof(label), "monitor%d",
monitor_device_index);
} else {
snprintf(label, sizeof(label), "monitor");
snprintf(label, sizeof(label), "compat_monitor%d",
monitor_device_index);
if (monitor_device_index == 0) {
def = 1;
}
opts = qemu_chr_parse_compat(label, optarg);
......@@ -3602,6 +3618,10 @@ int main(int argc, char **argv, char **envp)
}
}
if (qemu_opts_foreach(&qemu_mon_opts, mon_init_func, NULL, 1) != 0) {
exit(1);
}
if (foreach_device_config(DEV_SERIAL, serial_parse) < 0)
exit(1);
if (foreach_device_config(DEV_PARALLEL, parallel_parse) < 0)
......@@ -3714,9 +3734,6 @@ int main(int argc, char **argv, char **envp)
text_consoles_set_display(ds);
if (qemu_opts_foreach(&qemu_mon_opts, mon_init_func, NULL, 1) != 0)
exit(1);
if (gdbstub_dev && gdbserver_start(gdbstub_dev) < 0) {
fprintf(stderr, "qemu: could not open gdbserver on device '%s'\n",
gdbstub_dev);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册