[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
bug#36818: mv fails to clobber target if it's a hardlink of a source
From: |
Sergei Trofimovich |
Subject: |
bug#36818: mv fails to clobber target if it's a hardlink of a source |
Date: |
Fri, 26 Jul 2019 19:23:22 +0100 |
On Fri, 26 Jul 2019 13:01:44 -0500
Eric Blake <address@hidden> wrote:
> On 7/26/19 12:43 PM, Sergei Trofimovich wrote:
>
> > Is it an 'mv's bug or a feature to prevent hardlinked file clobbering?
> > If feels like an unnecessary restriction.
>
> It's a POSIX (mis-)feature that for hard links, rename("file1", "file2")
> is a mandatory no-op (no error, but also no change to the existence or
> contents of either file1 or file2). Back under POSIX 2001, mv was
> required to behave identically to the rename() syscall. But this was
> confusing enough that POSIX 2008 relaxed the wording as follows,
> inspired in part by complaint from GNU coreutils:
>
> https://pubs.opengroup.org/onlinepubs/9699919799/utilities/mv.html
>
> "If the source_file operand and destination path resolve to either the
> same existing directory entry or different directory entries for the
> same existing file, then the destination path shall not be removed, and
> one of the following shall occur:
>
> No change is made to source_file, no error occurs, and no diagnostic
> is issued.
>
> No change is made to source_file, a diagnostic is issued to standard
> error identifying the two names, and the exit status is affected.
>
> If the source_file operand and destination path name distinct
> directory entries, then the source_file operand is removed, no error
> occurs, and no diagnostic is issued."
>
> The difference between GNU coreutils and busybox both appear to be
> compliant behaviors (you didn't actually show after the 'mv' command
> whether a.aa still exists, so I can't tell whether busybox implemented
> option 1 or option 3;
Oh, I did not realize source file did not disappear.
Looks like busybox's behaviour is an 'option 1':
$ ls -i a.aa b.bb
208636260 a.aa 208636260 b.bb
$ strace -f busybox mv a.aa b.bb
...
stat("b.bb", {st_mode=S_IFREG|0644, st_size=0, ...}) = 0
access("b.bb", W_OK) = 0
rename("a.aa", "b.bb") = 0
exit_group(0) = ?
+++ exited with 0 +++
$ ls -i a.aa b.bb
208636260 a.aa 208636260 b.bb
> but it appears GNU implemented option 2). Option
> 1 is probably the least intuitive but is the historical behavior when
> you use rename() without any checking. Option 2 at least points out the
> issue that your usage is not going to be universally portable. Option 3
> is closest to what happens when there are no hard links.
Thank you for the quick response. The bug can be closed as WAI then.
--
Sergei
pgpmRRIfD1skC.pgp
Description: Цифровая подпись OpenPGP