[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PATCH v6 05/13] monitor: suspend monitor instead of send C
From: |
Peter Xu |
Subject: |
[Qemu-devel] [PATCH v6 05/13] monitor: suspend monitor instead of send CMD_DROP |
Date: |
Wed, 15 Aug 2018 21:37:39 +0800 |
When we received too many qmp commands, previously we'll send
COMMAND_DROPPED events to monitors, then we'll drop the requests. It
can only solve the flow control of the request queue, however it'll not
really work since we might queue unlimited events in the response queue
which is a potential risk.
Now instead of sending such an event, we stop consuming the client input
when we noticed that the queue is reaching its limitation before hand.
Then after we handled commands, we'll try to resume the monitor when
needed.
Signed-off-by: Peter Xu <address@hidden>
---
monitor.c | 46 ++++++++++++++++++++++++++++++----------------
1 file changed, 30 insertions(+), 16 deletions(-)
diff --git a/monitor.c b/monitor.c
index d31de95141..2fc480d75b 100644
--- a/monitor.c
+++ b/monitor.c
@@ -165,6 +165,8 @@ struct MonFdset {
QLIST_ENTRY(MonFdset) next;
};
+#define QMP_REQ_QUEUE_LEN_MAX (8)
+
typedef struct {
JSONMessageParser parser;
/*
@@ -397,10 +399,21 @@ static void monitor_qmp_try_resume(Monitor *mon)
{
assert(monitor_is_qmp(mon));
qemu_mutex_lock(&mon->qmp.qmp_lock);
+
+ if (mon->qmp.qmp_requests->length >= QMP_REQ_QUEUE_LEN_MAX) {
+ /*
+ * This should not happen, but in case if it happens, we
+ * should still keep the monitor in suspend state
+ */
+ qemu_mutex_unlock(&mon->qmp.qmp_lock);
+ return;
+ }
+
if (mon->qmp.need_resume) {
monitor_resume(mon);
mon->qmp.need_resume = false;
}
+
qemu_mutex_unlock(&mon->qmp.qmp_lock);
}
@@ -4254,7 +4267,14 @@ static void monitor_qmp_bh_dispatcher(void *data)
qemu_bh_schedule(qmp_dispatcher_bh);
}
-#define QMP_REQ_QUEUE_LEN_MAX (8)
+/* Called with Monitor.qmp.qmp_lock held. */
+static void monitor_qmp_suspend_locked(Monitor *mon)
+{
+ assert(monitor_is_qmp(mon));
+ assert(mon->qmp.need_resume == false);
+ monitor_suspend(mon);
+ mon->qmp.need_resume = true;
+}
static void handle_qmp_command(JSONMessageParser *parser, GQueue *tokens)
{
@@ -4307,22 +4327,16 @@ static void handle_qmp_command(JSONMessageParser
*parser, GQueue *tokens)
* OOB is not enabled, the server will never drop any command.
*/
if (!qmp_oob_enabled(mon)) {
- monitor_suspend(mon);
- mon->qmp.need_resume = true;
+ monitor_qmp_suspend_locked(mon);
} else {
- /* Drop the request if queue is full. */
- if (mon->qmp.qmp_requests->length >= QMP_REQ_QUEUE_LEN_MAX) {
- qemu_mutex_unlock(&mon->qmp.qmp_lock);
- /*
- * FIXME @id's scope is just @mon, and broadcasting it is
- * wrong. If another monitor's client has a command with
- * the same ID in flight, the event will incorrectly claim
- * that command was dropped.
- */
- qapi_event_send_command_dropped(id,
- COMMAND_DROP_REASON_QUEUE_FULL);
- qmp_request_free(req_obj);
- return;
+ /*
+ * If the queue is reaching the length limitation, we queue
+ * this command, meanwhile we suspend the monitor to block new
+ * commands. We'll resume ourselves until the queue has more
+ * space.
+ */
+ if (mon->qmp.qmp_requests->length >= QMP_REQ_QUEUE_LEN_MAX - 1) {
+ monitor_qmp_suspend_locked(mon);
}
}
--
2.17.1
- Re: [Qemu-devel] [PATCH v6 01/13] monitor: simplify monitor_qmp_setup_handlers_bh, (continued)
- [Qemu-devel] [PATCH v6 02/13] qapi: Fix build_params() for empty parameter list, Peter Xu, 2018/08/15
- [Qemu-devel] [PATCH v6 03/13] qapi: remove error checks for event emission, Peter Xu, 2018/08/15
- [Qemu-devel] [PATCH v6 04/13] monitor: move need_resume flag into monitor struct, Peter Xu, 2018/08/15
- [Qemu-devel] [PATCH v6 06/13] qapi: remove COMMAND_DROPPED event, Peter Xu, 2018/08/15
- [Qemu-devel] [PATCH v6 05/13] monitor: suspend monitor instead of send CMD_DROP,
Peter Xu <=
- [Qemu-devel] [PATCH v6 07/13] monitor: restrict response queue length too, Peter Xu, 2018/08/15
- [Qemu-devel] [PATCH v6 08/13] monitor: remove "x-oob", turn oob on by default, Peter Xu, 2018/08/15
- [Qemu-devel] [PATCH v6 10/13] monitor: add traces for qmp queues, Peter Xu, 2018/08/15
- [Qemu-devel] [PATCH v6 09/13] Revert "tests: Add parameter to qtest_init_without_qmp_handshake", Peter Xu, 2018/08/15
- [Qemu-devel] [PATCH v6 11/13] tests: remove "0.15" prefix for test-qmp-cmds, Peter Xu, 2018/08/15