From patchwork Tue Mar 4 16:42:10 2014 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Beno=C3=AEt_Canet?= X-Patchwork-Id: 326397 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from lists.gnu.org (lists.gnu.org [IPv6:2001:4830:134:3::11]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id E3B852C00BD for ; Wed, 5 Mar 2014 03:43:39 +1100 (EST) Received: from localhost ([::1]:46272 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1WKsRN-0003yR-NF for incoming@patchwork.ozlabs.org; Tue, 04 Mar 2014 11:43:37 -0500 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54815) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1WKsQ8-0002bh-3K for qemu-devel@nongnu.org; Tue, 04 Mar 2014 11:42:25 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1WKsQ0-0001Db-CO for qemu-devel@nongnu.org; Tue, 04 Mar 2014 11:42:20 -0500 Received: from lnantes-156-75-100-125.w80-12.abo.wanadoo.fr ([80.12.84.125]:55668 helo=paradis.irqsave.net) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1WKsQ0-0001D7-6y for qemu-devel@nongnu.org; Tue, 04 Mar 2014 11:42:12 -0500 Received: from localhost.localdomain (laure.irqsave.net [192.168.77.2]) by paradis.irqsave.net (Postfix) with ESMTP id A78BE7D997; Tue, 4 Mar 2014 18:47:11 +0100 (CET) From: =?UTF-8?q?Beno=C3=AEt=20Canet?= To: qemu-devel@nongnu.org Date: Tue, 4 Mar 2014 17:42:10 +0100 Message-Id: <1393951330-25436-2-git-send-email-benoit.canet@irqsave.net> X-Mailer: git-send-email 1.8.3.2 In-Reply-To: <1393951330-25436-1-git-send-email-benoit.canet@irqsave.net> References: <1393951330-25436-1-git-send-email-benoit.canet@irqsave.net> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 3.x [generic] X-Received-From: 80.12.84.125 Cc: kwolf@redhat.com, =?UTF-8?q?Beno=C3=AEt=20Canet?= , Benoit Canet , stefanha@redhat.com, mreitz@redhat.com Subject: [Qemu-devel] [QEMU 2.0 Fix] block: make bdrv_swap rebuild the bs graph node list field. X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Moving only the node_name one field could lead to some inconsitencies where a node_name was defined on a bs which was not registered in the graph node list. bdrv_swap between a named node bs and a non named node bs would lead to this. bdrv_make_anon would then crash because it would try to remove the bs from the graph node list while it is not in it. This patch remove named node bses from the graph node list before doing the swap then insert them back. Signed-off-by: Benoit Canet Reviewed-by: Max Reitz --- block.c | 24 +++++++++++++++++++----- 1 file changed, 19 insertions(+), 5 deletions(-) diff --git a/block.c b/block.c index 749835c..71349e5 100644 --- a/block.c +++ b/block.c @@ -1846,11 +1846,6 @@ static void bdrv_move_feature_fields(BlockDriverState *bs_dest, pstrcpy(bs_dest->device_name, sizeof(bs_dest->device_name), bs_src->device_name); bs_dest->device_list = bs_src->device_list; - - /* keep the same entry in graph_bdrv_states - * We do want to swap name but don't want to swap linked list entries - */ - bs_dest->node_list = bs_src->node_list; } /* @@ -1869,6 +1864,17 @@ void bdrv_swap(BlockDriverState *bs_new, BlockDriverState *bs_old) { BlockDriverState tmp; + /* The code need to swap the node_name but simply swapping node_list won't + * work so first remove the nodes from the graph list, do the swap then + * insert them back if needed. + */ + if (bs_new->node_name[0] != '\0') { + QTAILQ_REMOVE(&graph_bdrv_states, bs_new, node_list); + } + if (bs_old->node_name[0] != '\0') { + QTAILQ_REMOVE(&graph_bdrv_states, bs_old, node_list); + } + /* bs_new must be anonymous and shouldn't have anything fancy enabled */ assert(bs_new->device_name[0] == '\0'); assert(QLIST_EMPTY(&bs_new->dirty_bitmaps)); @@ -1897,6 +1903,14 @@ void bdrv_swap(BlockDriverState *bs_new, BlockDriverState *bs_old) assert(bs_new->io_limits_enabled == false); assert(!throttle_have_timer(&bs_new->throttle_state)); + /* insert back the nodes in the graph node list if needed */ + if (bs_new->node_name[0] != '\0') { + QTAILQ_INSERT_TAIL(&graph_bdrv_states, bs_new, node_list); + } + if (bs_old->node_name[0] != '\0') { + QTAILQ_INSERT_TAIL(&graph_bdrv_states, bs_old, node_list); + } + bdrv_rebind(bs_new); bdrv_rebind(bs_old); }