From nobody Thu Jan 20 14:58:44 2022 X-Original-To: dev-commits-src-all@mlmmj.nyi.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2610:1c1:1:606c::19:1]) by mlmmj.nyi.freebsd.org (Postfix) with ESMTP id 9287A195B810; Thu, 20 Jan 2022 14:58:46 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from mxrelay.nyi.freebsd.org (mxrelay.nyi.freebsd.org [IPv6:2610:1c1:1:606c::19:3]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256 client-signature RSA-PSS (4096 bits) client-digest SHA256) (Client CN "mxrelay.nyi.freebsd.org", Issuer "R3" (verified OK)) by mx1.freebsd.org (Postfix) with ESMTPS id 4JflyF6bxJz3lfP; Thu, 20 Jan 2022 14:58:45 +0000 (UTC) (envelope-from git@FreeBSD.org) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=freebsd.org; s=dkim; t=1642690726; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=fFDaGkGaLhuzFGNsHCRXXg82ktQd0B1ZlcN8sEmcJKU=; b=yVLslzSFMApa+4Fs7KlAnzGzwUJOu4cPGPNo3cm9gTvJlhDW9aKuOn6W28ySfs99qAfSUM DLOpEe07pOyhcQDnO9h1YyaMrp5dyQeraDQU77BeUIqbVfciqjYBHpdiopDZJFlSGHDMTY iMWUDXNEhXHXkrvZzkMwemmoQGkOlSN8VutMMKwZQxjlgnFIfWIoJNB+kgbAUvdlPU1EtQ yUBGUMvActZSJ4iMThbEULAM4dI6Yd8vDL1iID6qwfXy/UMd40XjUWTHMvJEamC3vi3MiH JavlrmATJ4TqAbGO0g2fNC3bFZXSMat9BrqrZI07TxGQ/Kl/SSsL0XEvx9pqmA== Received: from gitrepo.freebsd.org (gitrepo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:5]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (Client did not present a certificate) by mxrelay.nyi.freebsd.org (Postfix) with ESMTPS id E2BF82368; Thu, 20 Jan 2022 14:58:44 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from gitrepo.freebsd.org ([127.0.1.44]) by gitrepo.freebsd.org (8.16.1/8.16.1) with ESMTP id 20KEwih2078618; Thu, 20 Jan 2022 14:58:44 GMT (envelope-from git@gitrepo.freebsd.org) Received: (from git@localhost) by gitrepo.freebsd.org (8.16.1/8.16.1/Submit) id 20KEwiv4078617; Thu, 20 Jan 2022 14:58:44 GMT (envelope-from git) Date: Thu, 20 Jan 2022 14:58:44 GMT Message-Id: <202201201458.20KEwiv4078617@gitrepo.freebsd.org> To: src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org, dev-commits-src-main@FreeBSD.org From: Mark Johnston Subject: git: d91d2b513eb3 - main - geom: Handle partial I/O in g_{read,write,delete}_data() List-Id: Commit messages for all branches of the src repository List-Archive: https://lists.freebsd.org/archives/dev-commits-src-all List-Help: List-Post: List-Subscribe: List-Unsubscribe: Sender: owner-dev-commits-src-all@freebsd.org X-BeenThere: dev-commits-src-all@freebsd.org MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 8bit X-Git-Committer: markj X-Git-Repository: src X-Git-Refname: refs/heads/main X-Git-Reftype: branch X-Git-Commit: d91d2b513eb30a226e87f0e52e2f9f232a2e1ca3 Auto-Submitted: auto-generated ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=freebsd.org; s=dkim; t=1642690726; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=fFDaGkGaLhuzFGNsHCRXXg82ktQd0B1ZlcN8sEmcJKU=; b=CdEW80PHwcqldOULV3vryBC9mf8iuIkTQ/OFMq+bwttlDF9lZbAqYjBPVnZQA/MXTeoX+j cKSXzBN7Pms7qbj4JcZKhFymGLIEHXLjAAUzndtTsceEc3QIQLuKKVHVOQMJFW3ViXIB+d B3h4AsFsU/R3mFhbFF1yfVH0ink146QC/JiD4FuHmOjMEw9Quvsxk5KpiliE34d8/cgaa/ IUtCIbnH1uNwOVPHvyqXOm5rVTzWBPhm02/mnmzng7z/0kHc7/de4KCP6spAVyCSZ11TZ6 4PTR2v+NoZXAvSp4ZMg2/XkKdEI+1V95XhlWzyCMnS8inFOx3dzn6+6BdXg9Lw== ARC-Seal: i=1; s=dkim; d=freebsd.org; t=1642690726; a=rsa-sha256; cv=none; b=Vllz7NLCQR4we/O9E3M+GF5pUUzS/BJTqFCgLYScBn2/QKzxYHt5zuwW+HBLFm91V4CPAk uRlvyp4N571kjYJJd7abYWkS8l3ZyrzXbDHeezNEwG9C/sZtoq2kwYEn/aocYO3JcxYnsZ spJ1LkZmNORl70p7LpIFnX29GVo76G83NFEZRp7dnKnEkaotO4jBKF2HcTpudzAgLZXjMq 0i4zsAQ5GJJUUhGQjVs5DvxqIHeJ8+iao/PRys1R6hMyM19TyP/8TXFZilDrUCT6G/wOw0 uynYm/r08b4DLNZjiouWfg0RvGYn/Me2bF60hUW9pbFXZtb3xxASmfKOGyyFeA== ARC-Authentication-Results: i=1; mx1.freebsd.org; none X-ThisMailContainsUnwantedMimeParts: N The branch main has been updated by markj: URL: https://cgit.FreeBSD.org/src/commit/?id=d91d2b513eb30a226e87f0e52e2f9f232a2e1ca3 commit d91d2b513eb30a226e87f0e52e2f9f232a2e1ca3 Author: Mark Johnston AuthorDate: 2022-01-20 13:25:27 +0000 Commit: Mark Johnston CommitDate: 2022-01-20 13:29:39 +0000 geom: Handle partial I/O in g_{read,write,delete}_data() These routines are used internally by GEOM to dispatch I/O requests to a provider, typically for tasting or for updating GEOM class metadata blocks. These routines assumed that partial I/O did not occur without setting BIO_ERROR, but this is possible in at least two cases: - Some or all of the I/O range is beyond the provider's mediasize. In this scenario g_io_check() truncates the bounds of the request before it is handed to the target provider. - A read from vnode-backed md(4) device returns EOF (the backing vnode is allowed to be smaller than the device itself) or partial vnode I/O occurs. In these scenarios g_read_data() could return a partially uninitialized buffer. Many consumers are not affected by the first case, since the offsets used for provider metadata or tasting are relative to the provider's mediasize, but in some cases metadata is read at fixed offsets, such as when searching for a UFS superblock using the offsets defined by SBLOCKSEARCH. Thus, modify the routines to explicitly check for a non-zero residual and return EIO in that case. Remove a related check from the DIOCGDELETE ioctl handler, it is handled within g_delete_data() now. Reviewed by: mav, imp, kib Reported by: KMSAN MFC after: 2 weeks Sponsored by: The FreeBSD Foundation Differential Revision: https://reviews.freebsd.org/D31293 --- sys/geom/geom_dev.c | 13 ------------- sys/geom/geom_io.c | 6 ++++++ 2 files changed, 6 insertions(+), 13 deletions(-) diff --git a/sys/geom/geom_dev.c b/sys/geom/geom_dev.c index fedd9df96274..b94df9fcda67 100644 --- a/sys/geom/geom_dev.c +++ b/sys/geom/geom_dev.c @@ -654,19 +654,6 @@ g_dev_ioctl(struct cdev *dev, u_long cmd, caddr_t data, int fflag, struct thread error = EINVAL; break; } - if ((pp->mediasize > 0) && (offset >= pp->mediasize)) { - /* - * Catch out-of-bounds requests here. The problem is - * that due to historical GEOM I/O implementation - * peculatities, g_delete_data() would always return - * success for requests starting just the next byte - * after providers media boundary. Condition check on - * non-zero media size, since that condition would - * (most likely) cause ENXIO instead. - */ - error = EIO; - break; - } while (length > 0) { chunk = length; if (g_dev_del_max_sectors != 0 && diff --git a/sys/geom/geom_io.c b/sys/geom/geom_io.c index ce7f6c867388..6ec90741a7e2 100644 --- a/sys/geom/geom_io.c +++ b/sys/geom/geom_io.c @@ -886,6 +886,8 @@ g_read_data(struct g_consumer *cp, off_t offset, off_t length, int *error) bp->bio_data = ptr; g_io_request(bp, cp); errorc = biowait(bp, "gread"); + if (errorc == 0 && bp->bio_completed != length) + errorc = EIO; if (error != NULL) *error = errorc; g_destroy_bio(bp); @@ -940,6 +942,8 @@ g_write_data(struct g_consumer *cp, off_t offset, void *ptr, off_t length) bp->bio_data = ptr; g_io_request(bp, cp); error = biowait(bp, "gwrite"); + if (error == 0 && bp->bio_completed != length) + error = EIO; g_destroy_bio(bp); return (error); } @@ -971,6 +975,8 @@ g_delete_data(struct g_consumer *cp, off_t offset, off_t length) bp->bio_data = NULL; g_io_request(bp, cp); error = biowait(bp, "gdelete"); + if (error == 0 && bp->bio_completed != length) + error = EIO; g_destroy_bio(bp); return (error); }