umount usb drive after using openrsync

classic Classic list List threaded Threaded
4 messages Options
Reply | Threaded
Open this post in threaded view
|

umount usb drive after using openrsync

myportslist20190323
Synopsis: umount says device busy after having used openrsync
Category: user
Environment:
        System      : OpenBSD 6.5
        Details     : OpenBSD 6.5-current (GENERIC.MP) #158: Tue Jul 30 15:25:51 MDT 2019
                         [hidden email]:/usr/src/sys/arch/amd64/compile/GENERIC.MP

        Architecture: OpenBSD.amd64
        Machine     : amd64
Description:
        After using openrsync to sync files from a mounted USB drive to a local directory, I then
always see a device busy error when trying to unmount the USB drive. This has been happening
on several machines on amd64 for the last few snapshots (maybe a month or so.)

Sometimes fuser will show nothing; other times it shows lots of processes including 1, so a reboot
is necessary in order to unmount.

This happens for me with any USB drive I try and from three different OpenBSD machines with
different hardware running snapshots.

I've checked ps, fstat -v, fuser, pstat -s, looked for symbolic links, exited all programs and terminals,
logged and and back in, but only a reboot helps. I'm running cwm and haven't tried when booting
to console instead of enabling xenodm.

I'm definitely not in /mnt from any terminal when trying to umount.

/sbin/umount -f does work.

I haven't had this problem on 6.5-release.

How-To-Repeat:
        mount a USB drive, use openrsync to sync files to a local directory, then try to unmount the USB drive.
I'm including a script below. It shows that unmounting works before running openrsync, but fails after syncing.
(The syncing itself is great though -- I thank everyone who worked on it and of course all of OpenBSD!!!)

Script started on Wed Jul 31 09:25:35 2019
root@joe$ /sbin/mount
/dev/sd3a on / type ffs (local)
/dev/sd3d on /tmp type ffs (local, nodev, nosuid)
/dev/sd3f on /usr type ffs (local, nodev)
/dev/sd3g on /usr/X11R6 type ffs (local, nodev)
/dev/sd3h on /usr/local type ffs (local, nodev, wxallowed)
/dev/sd3k on /usr/obj type ffs (local, nodev, nosuid)
/dev/sd3j on /usr/src type ffs (local, nodev, nosuid)
/dev/sd3e on /var type ffs (local, nodev, nosuid)
/dev/sd3l on /home type ffs (local, nodev, nosuid)
/dev/sd4a on /mnt type ffs (local)
root@joe$ /sbin/umount /mnt
root@joe$ /sbin/mount /dev/sd4a /mnt
root@joe$ /bin/ls /mnt
root@joe$ /sbin/umount /mnt
root@joe$ /sbin/mount /dev/sd4a /mnt
root@joe$ /usr/bin/touch /mnt/a /mnt/b /mnt/c
root@joe$ /bin/mkdir /tmp/testbak
root@joe$ cd /mnt
root@joe$ /usr/bin/openrsync --rsync-path=/usr/bin/openrsync -vvv -r -t. /tmp/testbak/
/usr/src/usr.bin/rsync/main.c:466: exec[0] = /usr/bin/openrsync
/usr/src/usr.bin/rsync/main.c:466: exec[1] = --server
/usr/src/usr.bin/rsync/main.c:466: exec[2] = -r
/usr/src/usr.bin/rsync/main.c:466: exec[3] = -t
/usr/src/usr.bin/rsync/main.c:466: exec[4] = -v
/usr/src/usr.bin/rsync/main.c:466: exec[5] = -v
/usr/src/usr.bin/rsync/main.c:466: exec[6] = -v
/usr/src/usr.bin/rsync/main.c:466: exec[7] = .
/usr/src/usr.bin/rsync/main.c:466: exec[8] = /tmp/testbak/
/usr/src/usr.bin/rsync/client.c:71: client detected client version 27, server version 27, seed -2038779841
/usr/src/usr.bin/rsync/server.c:99: server detected client version 27, server version 27, seed -2038779841
/usr/src/usr.bin/rsync/client.c:82: client starting sender: (local)
/usr/src/usr.bin/rsync/server.c:128: server starting receiver
/usr/src/usr.bin/rsync/flist.c:1002: generated 4 filenames: .
/usr/src/usr.bin/rsync/flist.c:1028: recursively generated 4 filenames
/usr/src/usr.bin/rsync/flist.c:268: sending file metadata list: 4
/usr/src/usr.bin/rsync/flist.c:305: .: sending file metadata: size 512, mtime 1564583177, mode 40755
/usr/src/usr.bin/rsync/flist.c:305: ./a: sending file metadata: size 0, mtime 1564583177, mode 100644
/usr/src/usr.bin/rsync/flist.c:305: ./b: sending file metadata: size 0, mtime 1564583177, mode 100644
/usr/src/usr.bin/rsync/flist.c:305: ./c: sending file metadata: size 0, mtime 1564583177, mode 100644
/usr/src/usr.bin/rsync/flist.c:739: .: received file metadata: size 512, mtime 1564583177, mode 40755, rdev (0, 0)
Transfer starting: 4 files
/usr/src/usr.bin/rsync/flist.c:739: ./a: received file metadata: size 0, mtime 1564583177, mode 100644, rdev (0, 0)
/usr/src/usr.bin/rsync/flist.c:739: ./b: received file metadata: size 0, mtime 1564583177, mode 100644, rdev (0, 0)
/usr/src/usr.bin/rsync/flist.c:739: ./c: received file metadata: size 0, mtime 1564583177, mode 100644, rdev (0, 0)
/usr/src/usr.bin/rsync/flist.c:765: received file metadata list: 4
/usr/src/usr.bin/rsync/receiver.c:233: /tmp/testbak/: receiver destination
/usr/src/usr.bin/rsync/receiver.c:329: /tmp/testbak/: ready for phase 1 data
/usr/src/usr.bin/rsync/uploader.c:544: .: updating directory
/usr/src/usr.bin/rsync/uploader.c:952: ./a: not mapped
/usr/src/usr.bin/rsync/uploader.c:952: ./b: not mapped
/usr/src/usr.bin/rsync/uploader.c:952: ./c: not mapped
/usr/src/usr.bin/rsync/blocks.c:392: ./a: read block prologue: 0 blocks of 32768 B, 0 B remainder, 2 B checksum
/usr/src/usr.bin/rsync/blocks.c:439: ./a: read blocks: 0 blocks, 0 B total blocked data
/usr/src/usr.bin/rsync/blocks.c:392: ./b: read block prologue: 0 blocks of 32768 B, 0 B remainder, 2 B checksum
/usr/src/usr.bin/rsync/blocks.c:439: ./b: read blocks: 0 blocks, 0 B total blocked data
/usr/src/usr.bin/rsync/blocks.c:392: ./c: read block prologue: 0 blocks of 32768 B, 0 B remainder, 2 B checksum
/usr/src/usr.bin/rsync/blocks.c:439: ./c: read blocks: 0 blocks, 0 B total blocked data
./a
/usr/src/usr.bin/rsync/sender.c:267: ./a: primed for 0 B total
/usr/src/usr.bin/rsync/sender.c:181: ./a: flushed 0 KB total, -nan% uploaded
./b
/usr/src/usr.bin/rsync/sender.c:267: ./b: primed for 0 B total
/usr/src/usr.bin/rsync/sender.c:181: ./b: flushed 0 KB total, -nan% uploaded
./c
/usr/src/usr.bin/rsync/sender.c:267: ./c: primed for 0 B total
/usr/src/usr.bin/rsync/downloader.c:435: ./a: temporary: ./.a.N4Nx6ktKx2
/usr/src/usr.bin/rsync/sender.c:181: ./c: flushed 0 KB total, -nan% uploaded
/usr/src/usr.bin/rsync/downloader.c:435: ./b: temporary: ./.b.Jmi0w0Amnz
/usr/src/usr.bin/rsync/downloader.c:435: ./c: temporary: ./.c.em1CErjiiJ
/usr/src/usr.bin/rsync/downloader.c:321: downloader: phase complete
/usr/src/usr.bin/rsync/receiver.c:404: /tmp/testbak/: receiver ready for phase 2 data
Transfer complete: 76 B sent, 215 B read, 0 B file size
/usr/src/usr.bin/rsync/uploader.c:1018: fixing up directory times and permissions
/usr/src/usr.bin/rsync/receiver.c:453: receiver finished updating
/usr/src/usr.bin/rsync/sender.c:679: sender finished updating
root@joe$ /bin/ls -l /mnt /tmp/testbak
/mnt:
total 0
-rw-r--r--  1 root  wheel  0 Jul 31 09:26 a
-rw-r--r--  1 root  wheel  0 Jul 31 09:26 b
-rw-r--r--  1 root  wheel  0 Jul 31 09:26 c

/tmp/testbak/:
total 0
-rw-r--r--  1 root  wheel  0 Jul 31 09:26 a
-rw-r--r--  1 root  wheel  0 Jul 31 09:26 b
-rw-r--r--  1 root  wheel  0 Jul 31 09:26 c
root@joe$ cd
root@joe$ pwd
/root
root@joe$ /sbin/umount /mnt
umount: /mnt: Device busy
root@joe$ /usr/bin/fuser -c /mnt
/mnt:
root@joe$ /usr/bin/fuser /dev/sd4a
/dev/sd4a:
root@joe$ /usr/bin/fuser -f /dev/sd4a
/dev/sd4a:
root@joe$ /usr/bin/fstat -v |/usr/bin/grep mnt
root@joe$

Reply | Threaded
Open this post in threaded view
|

Re: umount usb drive after using openrsync

Alexander Bluhm
On Wed, Jul 31, 2019 at 10:12:02AM -0500, [hidden email] wrote:
> Synopsis: umount says device busy after having used openrsync

I have seen this behavior in combination with unveil(2) and chroot(2).
Could you test if the same diff helps for your problem?

bluhm

Index: kern/kern_unveil.c
===================================================================
RCS file: /data/mirror/openbsd/cvs/src/sys/kern/kern_unveil.c,v
retrieving revision 1.29
diff -u -p -r1.29 kern_unveil.c
--- kern/kern_unveil.c 29 Jul 2019 23:14:06 -0000 1.29
+++ kern/kern_unveil.c 30 Jul 2019 12:18:52 -0000
@@ -309,8 +309,7 @@ unveil_find_cover(struct vnode *dp, stru
  break;
  }

- if (parent != vp)
- vrele(vp);
+ vrele(vp);
  (void) unveil_lookup(parent, p, &ret);
  vput(parent);

Reply | Threaded
Open this post in threaded view
|

Re: umount usb drive after using openrsync

Alexander Bluhm
On Wed, Jul 31, 2019 at 08:29:31PM +0200, Alexander Bluhm wrote:
> On Wed, Jul 31, 2019 at 10:12:02AM -0500, [hidden email] wrote:
> > Synopsis: umount says device busy after having used openrsync
>
> I have seen this behavior in combination with unveil(2) and chroot(2).
> Could you test if the same diff helps for your problem?

I have commited my fix for unveil(2) and chroot(2).  Unfortunately
there seems to be another bug that is triggert by unveil(2) and
chdir(2).  I have written a test for the latter, but I have not
found the bug yet.

bluhm

> Index: kern/kern_unveil.c
> ===================================================================
> RCS file: /data/mirror/openbsd/cvs/src/sys/kern/kern_unveil.c,v
> retrieving revision 1.29
> diff -u -p -r1.29 kern_unveil.c
> --- kern/kern_unveil.c 29 Jul 2019 23:14:06 -0000 1.29
> +++ kern/kern_unveil.c 30 Jul 2019 12:18:52 -0000
> @@ -309,8 +309,7 @@ unveil_find_cover(struct vnode *dp, stru
>   break;
>   }
>
> - if (parent != vp)
> - vrele(vp);
> + vrele(vp);
>   (void) unveil_lookup(parent, p, &ret);
>   vput(parent);

Reply | Threaded
Open this post in threaded view
|

Re: umount usb drive after using openrsync

Alexander Bluhm
On Thu, Aug 01, 2019 at 06:15:46PM +0200, Alexander Bluhm wrote:
> there seems to be another bug that is triggert by unveil(2) and
> chdir(2).  I have written a test for the latter, but I have not
> found the bug yet.

unveil(2) on "." leaks a vnode.  Even if the parent and the vnode
are equal, both are reference counted.  So we need two vrele().

ok?

bluhm

Index: kern/vfs_syscalls.c
===================================================================
RCS file: /data/mirror/openbsd/cvs/src/sys/kern/vfs_syscalls.c,v
retrieving revision 1.327
diff -u -p -r1.327 vfs_syscalls.c
--- kern/vfs_syscalls.c 25 Jul 2019 01:43:21 -0000 1.327
+++ kern/vfs_syscalls.c 1 Aug 2019 21:21:14 -0000
@@ -1048,7 +1048,7 @@ sys_unveil(struct proc *p, void *v, regi
  /* release vref from namei, but not vref from unveil_add */
  if (nd.ni_vp)
  vrele(nd.ni_vp);
- if (nd.ni_dvp && nd.ni_dvp != nd.ni_vp)
+ if (nd.ni_dvp)
  vrele(nd.ni_dvp);

  pool_put(&namei_pool, nd.ni_cnd.cn_pnbuf);