Date: Tue, 6 Aug 2019 15:31:27 +0300 From: Slawa Olhovchenkov <slw@zxy.spb.ru> To: Baptiste Daroussin <bapt@FreeBSD.org> Cc: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-11@freebsd.org Subject: Re: svn commit: r350402 - stable/11/cddl/contrib/opensolaris/lib/libzfs/common Message-ID: <20190806123127.GM47119@zxy.spb.ru> In-Reply-To: <201907290823.x6T8NFAu064976@repo.freebsd.org> References: <201907290823.x6T8NFAu064976@repo.freebsd.org>
next in thread | previous in thread | raw e-mail | index | archive | help
On Mon, Jul 29, 2019 at 08:23:15AM +0000, Baptiste Daroussin wrote: still broken: # ls -l /poudriere/ports/default ls: /poudriere/ports/default: No such file or directory # zfs list NAME USED AVAIL REFER MOUNTPOINT DB 256G 643G 96K /DB DB/var 255G 643G 96K /DB/var DB/var/db 255G 643G 96K /DB/var/db DB/var/db/mysql 255G 643G 255G /var/db/mysql DB/var/db/mysql/MyISAM 96K 643G 96K /var/db/mysql/MyISAM DB/var/db/mysql/innodb-logs 128M 643G 128M /var/db/mysql/innodb-logs zroot 2.94T 551G 112K /ZROOT zroot/ROOT 352M 551G 352M / zroot/home 144K 551G 144K legacy zroot/poudriere 5.41G 551G 128K /poudriere zroot/poudriere/data 608M 551G 608M /poudriere/data zroot/poudriere/jails 2.71G 551G 128K /poudriere/jails zroot/poudriere/jails/10amd64 2.71G 551G 2.71G /poudriere/jails/10amd64 zroot/poudriere/ports 2.10G 551G 96K /poudriere/ports zroot/poudriere/ports/default 2.10G 551G 2.10G /poudriere/ports/default zroot/tmp 6.94G 551G 6.94G /tmp zroot/usr 630G 551G 57.0G /usr zroot/usr/local 543G 551G 543G /usr/local zroot/usr/obj 19.2G 551G 19.2G /usr/obj zroot/usr/ports 4.80G 551G 1.07G /usr/ports zroot/usr/ports/distfiles 3.72G 551G 3.72G /usr/ports/distfiles zroot/usr/ports/packages 7.04M 551G 7.04M /usr/ports/packages zroot/usr/src 5.51G 551G 5.51G /usr/src zroot/var 345G 551G 1.10G /var zroot/var/crash 148K 551G 148K /var/crash zroot/var/db 58.4G 551G 3.92G /var/db zroot/var/db/mysql 54.4G 551G 54.2G /var/db/mysql zroot/var/db/mysql/MyISAM 144K 551G 144K /var/db/mysql/MyISAM zroot/var/db/mysql/innodb-logs 128M 551G 128M /var/db/mysql/innodb-logs zroot/var/db/pkg 69.6M 551G 69.6M /var/db/pkg zroot/var/empty 144K 551G 144K /var/empty zroot/var/log 248G 551G 248G /var/log zroot/var/mail 148K 551G 148K /var/mail zroot/var/run 444K 551G 444K /var/run zroot/var/spool 37.3G 551G 37.3G /var/spool zroot/var/tmp 548K 551G 548K /var/tmp zroot/www 1.98T 551G 160K /www zroot/www/dev0 1.59G 551G 1.59G /www/dev0 zroot/www/dev1 1.48G 551G 1.48G /www/dev1 zroot/www/dev2 1.48G 551G 1.48G /www/dev2 zroot/www/dev3 1.59G 551G 1.59G /www/dev3 zroot/www/dev4 1.49G 551G 1.49G /www/dev4 zroot/www/dev5 1.47G 551G 1.47G /www/dev5 zroot/www/komandirovka 186G 551G 30.9G /www/komandirovka zroot/www/komandirovka_old 1.79T 551G 1.79T /www/komandirovka_old > Author: bapt > Date: Mon Jul 29 08:23:15 2019 > New Revision: 350402 > URL: https://svnweb.freebsd.org/changeset/base/350402 > > Log: > MFC r350358: > > Fix a bug introduced with parallel mounting of zfs > > Incorporate a fix from zol: > https://github.com/zfsonlinux/zfs/commit/ab5036df1ccbe1b18c1ce6160b5829e8039d94ce > > commit log from upstream: > Fix race in parallel mount's thread dispatching algorithm > > Strategy of parallel mount is as follows. > > 1) Initial thread dispatching is to select sets of mount points that > don't have dependencies on other sets, hence threads can/should run > lock-less and shouldn't race with other threads for other sets. Each > thread dispatched corresponds to top level directory which may or may > not have datasets to be mounted on sub directories. > > 2) Subsequent recursive thread dispatching for each thread from 1) > is to mount datasets for each set of mount points. The mount points > within each set have dependencies (i.e. child directories), so child > directories are processed only after parent directory completes. > > The problem is that the initial thread dispatching in > zfs_foreach_mountpoint() can be multi-threaded when it needs to be > single-threaded, and this puts threads under race condition. This race > appeared as mount/unmount issues on ZoL for ZoL having different > timing regarding mount(2) execution due to fork(2)/exec(2) of mount(8). > `zfs unmount -a` which expects proper mount order can't unmount if the > mounts were reordered by the race condition. > > There are currently two known patterns of input list `handles` in > `zfs_foreach_mountpoint(..,handles,..)` which cause the race condition. > > 1) #8833 case where input is `/a /a /a/b` after sorting. > The problem is that libzfs_path_contains() can't correctly handle an > input list with two same top level directories. > There is a race between two POSIX threads A and B, > * ThreadA for "/a" for test1 and "/a/b" > * ThreadB for "/a" for test0/a > and in case of #8833, ThreadA won the race. Two threads were created > because "/a" wasn't considered as `"/a" contains "/a"`. > > 2) #8450 case where input is `/ /var/data /var/data/test` after sorting. > The problem is that libzfs_path_contains() can't correctly handle an > input list containing "/". > There is a race between two POSIX threads A and B, > * ThreadA for "/" and "/var/data/test" > * ThreadB for "/var/data" > and in case of #8450, ThreadA won the race. Two threads were created > because "/var/data" wasn't considered as `"/" contains "/var/data"`. > In other words, if there is (at least one) "/" in the input list, > the initial thread dispatching must be single-threaded since every > directory is a child of "/", meaning they all directly or indirectly > depend on "/". > > In both cases, the first non_descendant_idx() call fails to correctly > determine "path1-contains-path2", and as a result the initial thread > dispatching creates another thread when it needs to be single-threaded. > Fix a conditional in libzfs_path_contains() to consider above two. > > Reviewed-by: Brian Behlendorf <behlendorf1@llnl.gov> > Reviewed by: Sebastien Roy <sebastien.roy@delphix.com> > Signed-off-by: Tomohiro Kusumi <kusumi.tomohiro@gmail.com> > > PR: 237517, 237397, 239243 > Submitted by: Matthew D. Fuller <fullermd@over-yonder.net> (by email) > > Modified: > stable/11/cddl/contrib/opensolaris/lib/libzfs/common/libzfs_mount.c > Directory Properties: > stable/11/ (props changed) > > Modified: stable/11/cddl/contrib/opensolaris/lib/libzfs/common/libzfs_mount.c > ============================================================================== > --- stable/11/cddl/contrib/opensolaris/lib/libzfs/common/libzfs_mount.c Mon Jul 29 08:14:35 2019 (r350401) > +++ stable/11/cddl/contrib/opensolaris/lib/libzfs/common/libzfs_mount.c Mon Jul 29 08:23:15 2019 (r350402) > @@ -1281,12 +1281,14 @@ mountpoint_cmp(const void *arga, const void *argb) > } > > /* > - * Reutrn true if path2 is a child of path1 > + * Return true if path2 is a child of path1 or path2 equals path1 or > + * path1 is "/" (path2 is always a child of "/"). > */ > static boolean_t > libzfs_path_contains(const char *path1, const char *path2) > { > - return (strstr(path2, path1) == path2 && path2[strlen(path1)] == '/'); > + return (strcmp(path1, path2) == 0 || strcmp(path1, "/") == 0 || > + (strstr(path2, path1) == path2 && path2[strlen(path1)] == '/')); > } > > > _______________________________________________ > svn-src-all@freebsd.org mailing list > https://lists.freebsd.org/mailman/listinfo/svn-src-all > To unsubscribe, send any mail to "svn-src-all-unsubscribe@freebsd.org"
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20190806123127.GM47119>