Date: Wed, 20 Sep 2017 08:27:21 +0000 (UTC) From: Andriy Gapon <avg@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r323796 - head/sys/cddl/contrib/opensolaris/uts/common/fs/zfs Message-ID: <201709200827.v8K8RLiK032316@repo.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: avg Date: Wed Sep 20 08:27:21 2017 New Revision: 323796 URL: https://svnweb.freebsd.org/changeset/base/323796 Log: fix memory leak in g_bio zone introduced in r320452, another ABD fallout I overlooked the fact that that ZIO_IOCTL_PIPELINE does not include ZIO_STAGE_VDEV_IO_DONE stage. We do allocate a struct bio for an ioctl zio (a disk cache flush), but we never freed it. This change splits bio handling into two groups, one for normal read/write i/o that passes data around and, thus, needs the abd data tranform; the other group is for "data-less" i/o such as trim and cache flush. PR: 222288 Reported by: Dan Nelson <dnelson@allantgroup.com> Tested by: Borja Marcos <borjam@sarenet.es> MFC after: 10 days Modified: head/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_geom.c Modified: head/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_geom.c ============================================================================== --- head/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_geom.c Wed Sep 20 07:28:18 2017 (r323795) +++ head/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_geom.c Wed Sep 20 08:27:21 2017 (r323796) @@ -989,6 +989,15 @@ vdev_geom_io_intr(struct bio *bp) break; } + /* + * We have to split bio freeing into two parts, because the ABD code + * cannot be called in this context and vdev_op_io_done is not called + * for ZIO_TYPE_IOCTL zio-s. + */ + if (zio->io_type != ZIO_TYPE_READ && zio->io_type != ZIO_TYPE_WRITE) { + g_destroy_bio(bp); + zio->io_bio = NULL; + } zio_delay_interrupt(zio); } @@ -1090,21 +1099,23 @@ vdev_geom_io_done(zio_t *zio) { struct bio *bp = zio->io_bio; + if (zio->io_type != ZIO_TYPE_READ && zio->io_type != ZIO_TYPE_WRITE) { + ASSERT(bp == NULL); + return; + } + if (bp == NULL) { - ASSERT3S(zio->io_error, !=, 0); - IMPLY(zio->io_type == ZIO_TYPE_READ || - zio->io_type == ZIO_TYPE_WRITE, - zio->io_error == ENXIO); + ASSERT3S(zio->io_error, ==, ENXIO); return; } - if (zio->io_type == ZIO_TYPE_READ) { + if (zio->io_type == ZIO_TYPE_READ) abd_return_buf_copy(zio->io_abd, bp->bio_data, zio->io_size); - } else if (zio->io_type == ZIO_TYPE_WRITE) { + else abd_return_buf(zio->io_abd, bp->bio_data, zio->io_size); - } g_destroy_bio(bp); + zio->io_bio = NULL; } static void
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201709200827.v8K8RLiK032316>