From: Jim Meyering Date: Wed, 5 Sep 2012 14:48:50 +0000 (+0200) Subject: rm: be more careful when using a replacement errno value X-Git-Tag: v8.20~66 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=ccbd3f3b290cb1bbed6a91361389bb936446621c;p=thirdparty%2Fcoreutils.git rm: be more careful when using a replacement errno value * src/remove.c (excise): Tighten the test for when we defer to an old errno value: instead of relying solely on an FTS_DNR (unreadable directory) failure, also test current and replacement errno values. This change would also have solved the problem addressed by commit v8.19-106-g57dd067. For more info, see http://bugs.gnu.org/12339#113 --- diff --git a/src/remove.c b/src/remove.c index 847a5cc4a4..a141718c9f 100644 --- a/src/remove.c +++ b/src/remove.c @@ -392,11 +392,13 @@ excise (FTS *fts, FTSENT *ent, struct rm_options const *x, bool is_dir) if (ignorable_missing (x, errno)) return RM_OK; - /* When failing to rmdir an unreadable directory, the typical - errno value is EISDIR, but that is not as useful to the user - as the errno value from the failed open (probably EPERM). - Use the earlier, more descriptive errno value. */ - if (ent->fts_info == FTS_DNR) + /* When failing to rmdir an unreadable directory, we see errno values + like EISDIR or ENOTDIR, but they would be meaningless in a diagnostic. + When that happens and the errno value from the failed open is EPERM + or EACCES, use the earlier, more descriptive errno value. */ + if (ent->fts_info == FTS_DNR + && (errno == ENOTEMPTY || errno == EISDIR || errno == ENOTDIR) + && (ent->fts_errno == EPERM || ent->fts_errno == EACCES)) errno = ent->fts_errno; error (0, errno, _("cannot remove %s"), quote (ent->fts_path)); mark_ancestor_dirs (ent);