1 Star 0 Fork 120

sdf_2022/qemu

forked from src-openEuler/qemu 
加入 Gitee
与超过 1200万 开发者一起发现、参与优秀开源项目,私有仓库也完全免费 :)
免费加入
该仓库未声明开源许可证文件(LICENSE),使用请关注具体项目描述及其代码上游依赖。
克隆/下载
monitor-qmp-drop-inflight-rsp-if-qmp-client-broken.patch 4.20 KB
一键复制 编辑 原始数据 按行查看 历史
From 7eb28408efe75192a0f976a197f8f1906d9073e8 Mon Sep 17 00:00:00 2001
From: Chuan Zheng <zhengchuan@huawei.com>
Date: Wed, 9 Feb 2022 14:13:05 +0800
Subject: [PATCH 14/15] monitor/qmp: drop inflight rsp if qmp client broken
If libvirt restart while qemu is handle qmp message, libvirt will
reconnect qemu monitor socket, and query status of qemu by qmp.
But qemu may return last qmp respond to new connect socket, and libvirt
recv unexpected respond, So libvirt think qemu is abnormal, and will
kill qemu.
This patch add qmp connect id, while reconnect id will change. While
respond to libvirt, judge if id is same, if not, drop this respond.
---
monitor/monitor-internal.h | 1 +
monitor/qmp.c | 19 +++++++++++--------
2 files changed, 12 insertions(+), 8 deletions(-)
diff --git a/monitor/monitor-internal.h b/monitor/monitor-internal.h
index 3da3f86c6a..5435864add 100644
--- a/monitor/monitor-internal.h
+++ b/monitor/monitor-internal.h
@@ -144,6 +144,7 @@ typedef struct {
const QmpCommandList *commands;
bool capab_offered[QMP_CAPABILITY__MAX]; /* capabilities offered */
bool capab[QMP_CAPABILITY__MAX]; /* offered and accepted */
+ uint64_t qmp_client_id; /*qmp client id, update if peer disconnect */
/*
* Protects qmp request/response queue.
* Take monitor_lock first when you need both.
diff --git a/monitor/qmp.c b/monitor/qmp.c
index 092c527b6f..4d1ac66785 100644
--- a/monitor/qmp.c
+++ b/monitor/qmp.c
@@ -125,18 +125,19 @@ void qmp_send_response(MonitorQMP *mon, const QDict *rsp)
* Null @rsp can only happen for commands with QCO_NO_SUCCESS_RESP.
* Nothing is emitted then.
*/
-static void monitor_qmp_respond(MonitorQMP *mon, QDict *rsp)
+static void monitor_qmp_respond(MonitorQMP *mon, QDict *rsp, uint64_t req_client_id)
{
- if (rsp) {
- qmp_send_response(mon, rsp);
+ if (!rsp || (mon->qmp_client_id != req_client_id)) {
+ return;
}
+ qmp_send_response(mon, rsp);
}
/*
* Runs outside of coroutine context for OOB commands, but in
* coroutine context for everything else.
*/
-static void monitor_qmp_dispatch(MonitorQMP *mon, QObject *req)
+static void monitor_qmp_dispatch(MonitorQMP *mon, QObject *req, uint64_t req_client_id)
{
QDict *rsp;
QDict *error;
@@ -156,7 +157,7 @@ static void monitor_qmp_dispatch(MonitorQMP *mon, QObject *req)
}
}
- monitor_qmp_respond(mon, rsp);
+ monitor_qmp_respond(mon, rsp, req_client_id);
qobject_unref(rsp);
}
@@ -315,13 +316,13 @@ void coroutine_fn monitor_qmp_dispatcher_co(void *data)
trace_monitor_qmp_cmd_in_band(id_json->str);
g_string_free(id_json, true);
}
- monitor_qmp_dispatch(mon, req_obj->req);
+ monitor_qmp_dispatch(mon, req_obj->req, mon->qmp_client_id);
} else {
assert(req_obj->err);
trace_monitor_qmp_err_in_band(error_get_pretty(req_obj->err));
rsp = qmp_error_response(req_obj->err);
req_obj->err = NULL;
- monitor_qmp_respond(mon, rsp);
+ monitor_qmp_respond(mon, rsp, mon->qmp_client_id);
qobject_unref(rsp);
}
@@ -366,7 +367,7 @@ static void handle_qmp_command(void *opaque, QObject *req, Error *err)
trace_monitor_qmp_cmd_out_of_band(id_json->str);
g_string_free(id_json, true);
}
- monitor_qmp_dispatch(mon, req);
+ monitor_qmp_dispatch(mon, req, mon->qmp_client_id);
qobject_unref(req);
return;
}
@@ -452,6 +453,7 @@ static void monitor_qmp_event(void *opaque, QEMUChrEvent event)
mon_refcount++;
break;
case CHR_EVENT_CLOSED:
+ mon->qmp_client_id++;
/*
* Note: this is only useful when the output of the chardev
* backend is still open. For example, when the backend is
@@ -505,6 +507,7 @@ void monitor_init_qmp(Chardev *chr, bool pretty, Error **errp)
}
qemu_chr_fe_set_echo(&mon->common.chr, true);
+ mon->qmp_client_id = 1;
/* Note: we run QMP monitor in I/O thread when @chr supports that */
monitor_data_init(&mon->common, true, false,
qemu_chr_has_feature(chr, QEMU_CHAR_FEATURE_GCONTEXT));
--
2.27.0
马建仓 AI 助手
尝试更多
代码解读
代码找茬
代码优化
1
https://gitee.com/songdf_2022/qemu.git
git@gitee.com:songdf_2022/qemu.git
songdf_2022
qemu
qemu
master

搜索帮助