From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54474) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1a4NLo-00064L-TG for qemu-devel@nongnu.org; Thu, 03 Dec 2015 01:26:47 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1a4NLk-0001dB-Hk for qemu-devel@nongnu.org; Thu, 03 Dec 2015 01:26:44 -0500 Received: from [59.151.112.132] (port=44281 helo=heian.cn.fujitsu.com) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1a4NLj-0001ct-Ik for qemu-devel@nongnu.org; Thu, 03 Dec 2015 01:26:40 -0500 References: <1448357149-17572-1-git-send-email-zhang.zhanghailiang@huawei.com> <1448357149-17572-35-git-send-email-zhang.zhanghailiang@huawei.com> <565F9836.7070106@cn.fujitsu.com> <565FBCBD.2040101@huawei.com> From: Wen Congyang Message-ID: <565FE071.9090102@cn.fujitsu.com> Date: Thu, 3 Dec 2015 14:25:53 +0800 MIME-Version: 1.0 In-Reply-To: <565FBCBD.2040101@huawei.com> Content-Type: text/plain; charset="windows-1252" Content-Transfer-Encoding: 7bit Subject: Re: [Qemu-devel] [PATCH COLO-Frame v11 34/39] net/filter-buffer: Add default filter-buffer for each netdev List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: Hailiang Zhang , qemu-devel@nongnu.org Cc: lizhijian@cn.fujitsu.com, quintela@redhat.com, Jason Wang , yunhong.jiang@intel.com, eddie.dong@intel.com, peter.huangpeng@huawei.com, dgilbert@redhat.com, arei.gonglei@huawei.com, stefanha@redhat.com, amit.shah@redhat.com, hongyang.yang@easystack.cn On 12/03/2015 11:53 AM, Hailiang Zhang wrote: > On 2015/12/3 9:17, Wen Congyang wrote: >> On 11/24/2015 05:25 PM, zhanghailiang wrote: >>> We add each netdev a default filter-buffer, which will be used for COLO >>> or Micro-checkpoint to buffer VM's packets. The name of default filter-buffer >>> is 'nop'. >>> For the default filter-buffer, it will not buffer any packets in default. >>> So it has no side effect for the netdev. >> >> No, filter-buffer doesn't support vhost, so if you add default filter-buffer >> for each netdev, you can't use vhost. >> > > Have you tested it ? Did the default filter-buffer break vhost ? > It's not supposed to break vhost, I will look into it. Thanks. Yes, I have tested it. When I want to start a normal vm with vhost, I get the following error messages: qemu-system-x86_64: -netdev tap,id=hn0,queues=1,vhost=on: Vhost is not supported Thanks Wen Congyang > >> Thanks >> Wen Congyang >> >>> >>> Signed-off-by: zhanghailiang >>> Cc: Jason Wang >>> Cc: Yang Hongyang >>> --- >>> v11: >>> - New patch >>> --- >>> include/net/filter.h | 3 +++ >>> net/filter-buffer.c | 74 ++++++++++++++++++++++++++++++++++++++++++++++++++++ >>> net/net.c | 8 ++++++ >>> 3 files changed, 85 insertions(+) >>> >>> diff --git a/include/net/filter.h b/include/net/filter.h >>> index 2deda36..01a7e90 100644 >>> --- a/include/net/filter.h >>> +++ b/include/net/filter.h >>> @@ -74,4 +74,7 @@ ssize_t qemu_netfilter_pass_to_next(NetClientState *sender, >>> int iovcnt, >>> void *opaque); >>> >>> +void netdev_add_default_filter_buffer(const char *netdev_id, >>> + NetFilterDirection direction, >>> + Error **errp); >>> #endif /* QEMU_NET_FILTER_H */ >>> diff --git a/net/filter-buffer.c b/net/filter-buffer.c >>> index 57be149..195af68 100644 >>> --- a/net/filter-buffer.c >>> +++ b/net/filter-buffer.c >>> @@ -14,6 +14,12 @@ >>> #include "qapi/qmp/qerror.h" >>> #include "qapi-visit.h" >>> #include "qom/object.h" >>> +#include "net/net.h" >>> +#include "qapi/qmp/qdict.h" >>> +#include "qapi/qmp-output-visitor.h" >>> +#include "qapi/qmp-input-visitor.h" >>> +#include "monitor/monitor.h" >>> +#include "qmp-commands.h" >>> >>> #define TYPE_FILTER_BUFFER "filter-buffer" >>> >>> @@ -26,6 +32,8 @@ typedef struct FilterBufferState { >>> NetQueue *incoming_queue; >>> uint32_t interval; >>> QEMUTimer release_timer; >>> + bool is_default; >>> + bool enable_buffer; >>> } FilterBufferState; >>> >>> static void filter_buffer_flush(NetFilterState *nf) >>> @@ -65,6 +73,10 @@ static ssize_t filter_buffer_receive_iov(NetFilterState *nf, >>> { >>> FilterBufferState *s = FILTER_BUFFER(nf); >>> >>> + /* Don't buffer any packets if the filter is not enabled */ >>> + if (!s->enable_buffer) { >>> + return 0; >>> + } >>> /* >>> * We return size when buffer a packet, the sender will take it as >>> * a already sent packet, so sent_cb should not be called later. >>> @@ -102,6 +114,7 @@ static void filter_buffer_cleanup(NetFilterState *nf) >>> static void filter_buffer_setup(NetFilterState *nf, Error **errp) >>> { >>> FilterBufferState *s = FILTER_BUFFER(nf); >>> + char *path = object_get_canonical_path_component(OBJECT(nf)); >>> >>> /* >>> * We may want to accept zero interval when VM FT solutions like MC >>> @@ -114,6 +127,7 @@ static void filter_buffer_setup(NetFilterState *nf, Error **errp) >>> } >>> >>> s->incoming_queue = qemu_new_net_queue(qemu_netfilter_pass_to_next, nf); >>> + s->is_default = !strcmp(path, "nop"); >>> if (s->interval) { >>> timer_init_us(&s->release_timer, QEMU_CLOCK_VIRTUAL, >>> filter_buffer_release_timer, nf); >>> @@ -163,6 +177,66 @@ out: >>> error_propagate(errp, local_err); >>> } >>> >>> +/* >>> +* This will be used by COLO or MC FT, for which they will need >>> +* to buffer the packets of VM's net devices, Here we add a default >>> +* buffer filter for each netdev. The name of default buffer filter is >>> +* 'nop' >>> +*/ >>> +void netdev_add_default_filter_buffer(const char *netdev_id, >>> + NetFilterDirection direction, >>> + Error **errp) >>> +{ >>> + QmpOutputVisitor *qov; >>> + QmpInputVisitor *qiv; >>> + Visitor *ov, *iv; >>> + QObject *obj = NULL; >>> + QDict *qdict; >>> + void *dummy = NULL; >>> + const char *id = "nop"; >>> + char *queue = g_strdup(NetFilterDirection_lookup[direction]); >>> + NetClientState *nc = qemu_find_netdev(netdev_id); >>> + Error *err = NULL; >>> + >>> + /* FIXME: Not support multiple queues */ >>> + if (!nc || nc->queue_index > 1) { >>> + return; >>> + } >>> + qov = qmp_output_visitor_new(); >>> + ov = qmp_output_get_visitor(qov); >>> + visit_start_struct(ov, &dummy, NULL, NULL, 0, &err); >>> + if (err) { >>> + goto out; >>> + } >>> + visit_type_str(ov, &nc->name, "netdev", &err); >>> + if (err) { >>> + goto out; >>> + } >>> + visit_type_str(ov, &queue, "queue", &err); >>> + if (err) { >>> + goto out; >>> + } >>> + visit_end_struct(ov, &err); >>> + if (err) { >>> + goto out; >>> + } >>> + obj = qmp_output_get_qobject(qov); >>> + g_assert(obj != NULL); >>> + qdict = qobject_to_qdict(obj); >>> + qmp_output_visitor_cleanup(qov); >>> + >>> + qiv = qmp_input_visitor_new(obj); >>> + iv = qmp_input_get_visitor(qiv); >>> + object_add(TYPE_FILTER_BUFFER, id, qdict, iv, &err); >>> + qmp_input_visitor_cleanup(qiv); >>> + qobject_decref(obj); >>> +out: >>> + g_free(queue); >>> + if (err) { >>> + error_propagate(errp, err); >>> + } >>> +} >>> + >>> static void filter_buffer_init(Object *obj) >>> { >>> object_property_add(obj, "interval", "int", >>> diff --git a/net/net.c b/net/net.c >>> index ade6051..b36d49f 100644 >>> --- a/net/net.c >>> +++ b/net/net.c >>> @@ -1028,6 +1028,14 @@ static int net_client_init1(const void *object, int is_netdev, Error **errp) >>> } >>> return -1; >>> } >>> + >>> + if (is_netdev) { >>> + const Netdev *netdev = object; >>> + >>> + netdev_add_default_filter_buffer(netdev->id, >>> + NET_FILTER_DIRECTION_RX, >>> + errp); >>> + } >>> return 0; >>> } >>> >>> >> >> >> >> >> . >> > > > > > . >