From patchwork Sun Aug 26 10:23:11 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ilya Dryomov X-Patchwork-Id: 10576259 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 2C25A1805 for ; Sun, 26 Aug 2018 10:23:49 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 1832829C73 for ; Sun, 26 Aug 2018 10:23:49 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 0C89429C7A; Sun, 26 Aug 2018 10:23:49 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 3DB6029C77 for ; Sun, 26 Aug 2018 10:23:47 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726604AbeHZOFr (ORCPT ); Sun, 26 Aug 2018 10:05:47 -0400 Received: from mail-wm0-f66.google.com ([74.125.82.66]:36059 "EHLO mail-wm0-f66.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726433AbeHZOFr (ORCPT ); Sun, 26 Aug 2018 10:05:47 -0400 Received: by mail-wm0-f66.google.com with SMTP id j192-v6so5575282wmj.1 for ; Sun, 26 Aug 2018 03:23:37 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references; bh=5bprgxI3U3YORL6WGHukNSDfFnsEb24yTLFNpHM3To4=; b=sJLGs0un4qVpTzfoNBGtDygQzM5kiGUfxS+1K+X6K12d1umoqUnjQ8Vp2s/KtbTKNm 0E2eY2XvRkG5bpXFapHXdwwHd+8w9pn2tInJlje1GexaA+9Rdx6F2e1whHmur5Ut87JC LqCbMwyJ0Udqx+jy7DClvSv/Hzb7B8tQQGEksDIHmndiyVEPVrFg2fowijiV9saa0c7Q Cd81idtomCqkufzw6YUnXeIqn2v9yuZgH3u7cnyGnbAUj+MY4kqW470Ad0o9SWpSnmeb W2fcst8WQsS9sITwGMWE/t8dUuMufHUnjMbqKNz3J3zPnLEGwizRNJI0thE68p8uv960 XBVQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references; bh=5bprgxI3U3YORL6WGHukNSDfFnsEb24yTLFNpHM3To4=; b=uKMTM/lpjJ7rVULWxYdNDi8MLIkmzGd7G5gehj0eXovSWClr/ZsuRhnK5A+v1t8/D5 GCQgcecp1txMbKQUPqtST0tole5qmk9+fd183ZBq3boc7mw+FJWT8Vsf/vSV37LSn3Ku /SWHGILdmX1wegpZZT71wSkIDW9jqW85933dXDwEN9dz62CGDc5isOr4Us0pHqnYAw6Q B0NTzRS0ZsSPcMkp3k2H1Ebm+vKB1K8mk8wQ2biWLRiXQ7cStStVV0k3rmG05VWByLUl cD2CMuV/AD7M1+hfQ/ORofQvZr0dG8YU+f04PPXY2ADzl5jZ2kCjFvddvhcFglYaaeQV xn+g== X-Gm-Message-State: APzg51BzLrJK2vaLc+f0ZiKePRg8OLfo6BX4Vct+rYXZiS9KfBtopJi4 xpg6RYehDduTluvabR6kAKItse06 X-Google-Smtp-Source: ANB0VdZlJtNBe/5RtsN8gThhAoE4u+aDFqOjZwGGumv3VqMaQhg29bKnDozYjrqKyIN/1ViIdShcPQ== X-Received: by 2002:a1c:d98a:: with SMTP id q132-v6mr3123449wmg.78.1535279016356; Sun, 26 Aug 2018 03:23:36 -0700 (PDT) Received: from orange.local (ip-86-49-115-215.net.upcbroadband.cz. [86.49.115.215]) by smtp.gmail.com with ESMTPSA id r17-v6sm14510061wmb.11.2018.08.26.03.23.35 for (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Sun, 26 Aug 2018 03:23:35 -0700 (PDT) From: Ilya Dryomov To: ceph-devel@vger.kernel.org Subject: [PATCH 1/2] rbd: factor out get_parent_info_legacy() Date: Sun, 26 Aug 2018 12:23:11 +0200 Message-Id: <20180826102312.19180-2-idryomov@gmail.com> X-Mailer: git-send-email 2.14.4 In-Reply-To: <20180826102312.19180-1-idryomov@gmail.com> References: <20180826102312.19180-1-idryomov@gmail.com> Sender: ceph-devel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: ceph-devel@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP In preparation for the new parent_get and parent_overlap_get class methods, factor out the fetching and decoding of parent data. As a side effect, we now decode all four fields in the "no parent" case. Signed-off-by: Ilya Dryomov --- drivers/block/rbd.c | 120 ++++++++++++++++++++++++++++++++-------------------- 1 file changed, 73 insertions(+), 47 deletions(-) diff --git a/drivers/block/rbd.c b/drivers/block/rbd.c index d4d2e2ed4bd5..e86ed5ee7337 100644 --- a/drivers/block/rbd.c +++ b/drivers/block/rbd.c @@ -4584,47 +4584,83 @@ static int rbd_dev_v2_features(struct rbd_device *rbd_dev) &rbd_dev->header.features); } +struct parent_image_spec { + u64 pool_id; + const char *image_id; + u64 snap_id; +}; + +/* + * The caller is responsible for @pis. + */ +static int get_parent_info_legacy(struct rbd_device *rbd_dev, + struct parent_image_spec *pis, u64 *overlap) +{ + struct ceph_osd_client *osdc = &rbd_dev->rbd_client->client->osdc; + struct page *req_page, *reply_page; + size_t reply_len = PAGE_SIZE; + void *p, *end; + int ret; + + req_page = alloc_page(GFP_KERNEL); + if (!req_page) + return -ENOMEM; + + reply_page = alloc_page(GFP_KERNEL); + if (!reply_page) { + __free_page(req_page); + return -ENOMEM; + } + + p = page_address(req_page); + ceph_encode_64(&p, rbd_dev->spec->snap_id); + ret = ceph_osdc_call(osdc, &rbd_dev->header_oid, &rbd_dev->header_oloc, + "rbd", "get_parent", CEPH_OSD_FLAG_READ, + req_page, sizeof(u64), reply_page, &reply_len); + if (ret) + goto out; + + p = page_address(reply_page); + end = p + reply_len; + ceph_decode_64_safe(&p, end, pis->pool_id, e_inval); + pis->image_id = ceph_extract_encoded_string(&p, end, NULL, GFP_KERNEL); + if (IS_ERR(pis->image_id)) { + ret = PTR_ERR(pis->image_id); + pis->image_id = NULL; + goto out; + } + ceph_decode_64_safe(&p, end, pis->snap_id, e_inval); + ceph_decode_64_safe(&p, end, *overlap, e_inval); + +out: + __free_page(req_page); + __free_page(reply_page); + return ret; + +e_inval: + ret = -EINVAL; + goto out; +} + static int rbd_dev_v2_parent_info(struct rbd_device *rbd_dev) { struct rbd_spec *parent_spec; - size_t size; - void *reply_buf = NULL; - __le64 snapid; - void *p; - void *end; - u64 pool_id; - char *image_id; - u64 snap_id; - u64 overlap; + struct parent_image_spec pis = { 0 }; + u64 uninitialized_var(overlap); int ret; parent_spec = rbd_spec_alloc(); if (!parent_spec) return -ENOMEM; - size = sizeof (__le64) + /* pool_id */ - sizeof (__le32) + RBD_IMAGE_ID_LEN_MAX + /* image_id */ - sizeof (__le64) + /* snap_id */ - sizeof (__le64); /* overlap */ - reply_buf = kmalloc(size, GFP_KERNEL); - if (!reply_buf) { - ret = -ENOMEM; - goto out_err; - } - - snapid = cpu_to_le64(rbd_dev->spec->snap_id); - ret = rbd_obj_method_sync(rbd_dev, &rbd_dev->header_oid, - &rbd_dev->header_oloc, "get_parent", - &snapid, sizeof(snapid), reply_buf, size); - dout("%s: rbd_obj_method_sync returned %d\n", __func__, ret); - if (ret < 0) + ret = get_parent_info_legacy(rbd_dev, &pis, &overlap); + if (ret) goto out_err; + dout("%s pool_id %llu image_id %s snap_id %llu overlap %llu\n", + __func__, pis.pool_id, pis.image_id, pis.snap_id, + overlap); - p = reply_buf; - end = reply_buf + ret; - ret = -ERANGE; - ceph_decode_64_safe(&p, end, pool_id, out_err); - if (pool_id == CEPH_NOPOOL) { + if (pis.pool_id == CEPH_NOPOOL) { /* * Either the parent never existed, or we have * record of it but the image got flattened so it no @@ -4647,19 +4683,11 @@ static int rbd_dev_v2_parent_info(struct rbd_device *rbd_dev) /* The ceph file layout needs to fit pool id in 32 bits */ ret = -EIO; - if (pool_id > (u64)U32_MAX) { + if (pis.pool_id > (u64)U32_MAX) { rbd_warn(NULL, "parent pool id too large (%llu > %u)", - (unsigned long long)pool_id, U32_MAX); - goto out_err; - } - - image_id = ceph_extract_encoded_string(&p, end, NULL, GFP_KERNEL); - if (IS_ERR(image_id)) { - ret = PTR_ERR(image_id); + (unsigned long long)pis.pool_id, U32_MAX); goto out_err; } - ceph_decode_64_safe(&p, end, snap_id, out_err); - ceph_decode_64_safe(&p, end, overlap, out_err); /* * The parent won't change (except when the clone is @@ -4667,9 +4695,10 @@ static int rbd_dev_v2_parent_info(struct rbd_device *rbd_dev) * record the parent spec we have not already done so. */ if (!rbd_dev->parent_spec) { - parent_spec->pool_id = pool_id; - parent_spec->image_id = image_id; - parent_spec->snap_id = snap_id; + parent_spec->pool_id = pis.pool_id; + parent_spec->image_id = pis.image_id; + pis.image_id = NULL; + parent_spec->snap_id = pis.snap_id; /* TODO: support cloning across namespaces */ if (rbd_dev->spec->pool_ns) { @@ -4683,8 +4712,6 @@ static int rbd_dev_v2_parent_info(struct rbd_device *rbd_dev) rbd_dev->parent_spec = parent_spec; parent_spec = NULL; /* rbd_dev now owns this */ - } else { - kfree(image_id); } /* @@ -4707,9 +4734,8 @@ static int rbd_dev_v2_parent_info(struct rbd_device *rbd_dev) out: ret = 0; out_err: - kfree(reply_buf); + kfree(pis.image_id); rbd_spec_put(parent_spec); - return ret; } From patchwork Sun Aug 26 10:23:12 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ilya Dryomov X-Patchwork-Id: 10576257 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id B878E15A7 for ; Sun, 26 Aug 2018 10:23:48 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id A493B29C73 for ; Sun, 26 Aug 2018 10:23:48 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 98D8F29C7A; Sun, 26 Aug 2018 10:23:48 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 67F5C29C7B for ; Sun, 26 Aug 2018 10:23:47 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726643AbeHZOFs (ORCPT ); Sun, 26 Aug 2018 10:05:48 -0400 Received: from mail-wm0-f68.google.com ([74.125.82.68]:35478 "EHLO mail-wm0-f68.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726415AbeHZOFs (ORCPT ); Sun, 26 Aug 2018 10:05:48 -0400 Received: by mail-wm0-f68.google.com with SMTP id o18-v6so5574742wmc.0 for ; Sun, 26 Aug 2018 03:23:38 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references; bh=19N8LgN8+tQm1Fz2WMV21z9+SO0+/lt7msnlu7Cqj6A=; b=lSyEuGTWT+ui1fW5GlH1VsKvBv+njI4SVFgu8VC+4/L3B+3KoRZyQuyv0CHD7wJRYw lsOxM2fBmEvWJAfrAYveuOthsfQbhpatOs8KiL2SgWcaomlewItrpW3Fzw8yLOTKzPcc Uxf145HMk0voYwjXAh8MgKIuw15OXdSzKIy+huhHWonhKms/0/NnNaAiOwUVpAZW+cSz BzNztpdwJs9vfa2whNTeRtLz+gJOeKMFu6zh89EsODkjPE5VEIjxha06xzabByw7oUMx gBgIT8JmXYF0eY4zH6MVOCuWCBArxV++BGEKHBtmBPU81OKjGj3M9moEVGAXOlZ95pvf Bntg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references; bh=19N8LgN8+tQm1Fz2WMV21z9+SO0+/lt7msnlu7Cqj6A=; b=aUGK3CUWUApzJhj32pp9BJpA5/bCDfUsmEPvjeHAPfVF/v6X/USBxg7ENLg7bwlAwA 0H3ehpIhCmKhZMtNSTmS4VE+hkXME/2ST7UNeESJGcAedPBqhULzxWVftGEDSVG0vVbj X3QU3Atu0XZdyqoDDQhxv+jsz9pivjSnEpTn5dWVUZR3w+RSbl+X2rRxD78a4VCelZNo XmX+1Jrlkp6w2wzohLVSCbJmAwOr6MxkFaVGucEzGZDrCAxOqsNOogMKQGowlkJ+XltE t2Lcb/rFWFgd7pfDVx+9FB09wnQqDWujL+PK93LCjfVheKk6xj1yJEEBBkr7OABBCl/7 btGg== X-Gm-Message-State: APzg51DKiAZrVEaBatVZM4RV6aGM6wtjaGkWXpK3d5Mzl7inJRqWyI/5 jrvzXuypnEzcqdYTGiSfOkwHJOD+ X-Google-Smtp-Source: ANB0VdZWi1ZzwbjPg6pDbNMMUmu7lij0fBOq25f9P9ZNUPwgpI6Im3Oun1UigG5PgpC9millcHU3Uw== X-Received: by 2002:a1c:8e81:: with SMTP id q123-v6mr2934889wmd.56.1535279017215; Sun, 26 Aug 2018 03:23:37 -0700 (PDT) Received: from orange.local (ip-86-49-115-215.net.upcbroadband.cz. [86.49.115.215]) by smtp.gmail.com with ESMTPSA id r17-v6sm14510061wmb.11.2018.08.26.03.23.36 for (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Sun, 26 Aug 2018 03:23:36 -0700 (PDT) From: Ilya Dryomov To: ceph-devel@vger.kernel.org Subject: [PATCH 2/2] rbd: support cloning across namespaces Date: Sun, 26 Aug 2018 12:23:12 +0200 Message-Id: <20180826102312.19180-3-idryomov@gmail.com> X-Mailer: git-send-email 2.14.4 In-Reply-To: <20180826102312.19180-1-idryomov@gmail.com> References: <20180826102312.19180-1-idryomov@gmail.com> Sender: ceph-devel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: ceph-devel@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP If parent_get class method is not supported by the OSDs, fall back to the legacy class method and assume that the parent is in the default (i.e. "") namespace. The "use the child's image namespace" workaround is no longer needed because creating images within namespaces will require parent_get aware OSDs. Signed-off-by: Ilya Dryomov Reviewed-by: Jason Dillaman --- drivers/block/rbd.c | 112 ++++++++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 99 insertions(+), 13 deletions(-) diff --git a/drivers/block/rbd.c b/drivers/block/rbd.c index e86ed5ee7337..45e20af8efb6 100644 --- a/drivers/block/rbd.c +++ b/drivers/block/rbd.c @@ -4586,10 +4586,99 @@ static int rbd_dev_v2_features(struct rbd_device *rbd_dev) struct parent_image_spec { u64 pool_id; + const char *pool_ns; const char *image_id; u64 snap_id; }; +/* + * The caller is responsible for @pis. + */ +static int decode_parent_image_spec(void **p, void *end, + struct parent_image_spec *pis) +{ + u8 struct_v; + u32 struct_len; + int ret; + + ret = ceph_start_decoding(p, end, 1, "ParentImageSpec", + &struct_v, &struct_len); + if (ret) + return ret; + + ceph_decode_64_safe(p, end, pis->pool_id, e_inval); + pis->pool_ns = ceph_extract_encoded_string(p, end, NULL, GFP_KERNEL); + if (IS_ERR(pis->pool_ns)) { + ret = PTR_ERR(pis->pool_ns); + pis->pool_ns = NULL; + return ret; + } + pis->image_id = ceph_extract_encoded_string(p, end, NULL, GFP_KERNEL); + if (IS_ERR(pis->image_id)) { + ret = PTR_ERR(pis->image_id); + pis->image_id = NULL; + return ret; + } + ceph_decode_64_safe(p, end, pis->snap_id, e_inval); + return 0; + +e_inval: + return -EINVAL; +} + +static int get_parent_info(struct rbd_device *rbd_dev, + struct parent_image_spec *pis, u64 *overlap) +{ + struct ceph_osd_client *osdc = &rbd_dev->rbd_client->client->osdc; + struct page *req_page, *reply_page; + size_t reply_len = PAGE_SIZE; + void *p, *end; + int ret; + + req_page = alloc_page(GFP_KERNEL); + if (!req_page) + return -ENOMEM; + + reply_page = alloc_page(GFP_KERNEL); + if (!reply_page) { + __free_page(req_page); + return -ENOMEM; + } + + p = page_address(req_page); + ceph_encode_64(&p, rbd_dev->spec->snap_id); + ret = ceph_osdc_call(osdc, &rbd_dev->header_oid, &rbd_dev->header_oloc, + "rbd", "parent_get", CEPH_OSD_FLAG_READ, + req_page, sizeof(u64), reply_page, &reply_len); + if (ret) + goto out; + + p = page_address(reply_page); + end = p + reply_len; + ret = decode_parent_image_spec(&p, end, pis); + if (ret) + goto out; + + ret = ceph_osdc_call(osdc, &rbd_dev->header_oid, &rbd_dev->header_oloc, + "rbd", "parent_overlap_get", CEPH_OSD_FLAG_READ, + req_page, sizeof(u64), reply_page, &reply_len); + if (ret) + goto out; + + p = page_address(reply_page); + end = p + reply_len; + ceph_decode_64_safe(&p, end, *overlap, e_inval); + +out: + __free_page(req_page); + __free_page(reply_page); + return ret; + +e_inval: + ret = -EINVAL; + goto out; +} + /* * The caller is responsible for @pis. */ @@ -4653,11 +4742,13 @@ static int rbd_dev_v2_parent_info(struct rbd_device *rbd_dev) if (!parent_spec) return -ENOMEM; - ret = get_parent_info_legacy(rbd_dev, &pis, &overlap); + ret = get_parent_info(rbd_dev, &pis, &overlap); + if (ret == -EOPNOTSUPP) + ret = get_parent_info_legacy(rbd_dev, &pis, &overlap); if (ret) goto out_err; - dout("%s pool_id %llu image_id %s snap_id %llu overlap %llu\n", - __func__, pis.pool_id, pis.image_id, pis.snap_id, + dout("%s pool_id %llu pool_ns %s image_id %s snap_id %llu overlap %llu\n", + __func__, pis.pool_id, pis.pool_ns, pis.image_id, pis.snap_id, overlap); if (pis.pool_id == CEPH_NOPOOL) { @@ -4696,20 +4787,14 @@ static int rbd_dev_v2_parent_info(struct rbd_device *rbd_dev) */ if (!rbd_dev->parent_spec) { parent_spec->pool_id = pis.pool_id; + if (pis.pool_ns && *pis.pool_ns) { + parent_spec->pool_ns = pis.pool_ns; + pis.pool_ns = NULL; + } parent_spec->image_id = pis.image_id; pis.image_id = NULL; parent_spec->snap_id = pis.snap_id; - /* TODO: support cloning across namespaces */ - if (rbd_dev->spec->pool_ns) { - parent_spec->pool_ns = kstrdup(rbd_dev->spec->pool_ns, - GFP_KERNEL); - if (!parent_spec->pool_ns) { - ret = -ENOMEM; - goto out_err; - } - } - rbd_dev->parent_spec = parent_spec; parent_spec = NULL; /* rbd_dev now owns this */ } @@ -4734,6 +4819,7 @@ static int rbd_dev_v2_parent_info(struct rbd_device *rbd_dev) out: ret = 0; out_err: + kfree(pis.pool_ns); kfree(pis.image_id); rbd_spec_put(parent_spec); return ret;