"rm -r DIR" would mistakenly prompt about very long names
[platform/upstream/coreutils.git] / src / remove.c
1 /* remove.c -- core functions for removing files and directories
2    Copyright (C) 88, 90, 91, 1994-2008 Free Software Foundation, Inc.
3
4    This program is free software: you can redistribute it and/or modify
5    it under the terms of the GNU General Public License as published by
6    the Free Software Foundation, either version 3 of the License, or
7    (at your option) any later version.
8
9    This program is distributed in the hope that it will be useful,
10    but WITHOUT ANY WARRANTY; without even the implied warranty of
11    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12    GNU General Public License for more details.
13
14    You should have received a copy of the GNU General Public License
15    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
16
17 /* Extracted from rm.c and librarified, then rewritten by Jim Meyering.  */
18
19 #include <config.h>
20 #include <stdio.h>
21 #include <sys/types.h>
22 #include <setjmp.h>
23 #include <assert.h>
24
25 #include "system.h"
26 #include "cycle-check.h"
27 #include "dirfd.h"
28 #include "error.h"
29 #include "euidaccess.h"
30 #include "euidaccess-stat.h"
31 #include "file-type.h"
32 #include "hash.h"
33 #include "hash-pjw.h"
34 #include "lstat.h"
35 #include "obstack.h"
36 #include "quote.h"
37 #include "remove.h"
38 #include "root-dev-ino.h"
39 #include "unlinkdir.h"
40 #include "write-any-file.h"
41 #include "yesno.h"
42
43 /* Avoid shadowing warnings because these are functions declared
44    in dirname.h as well as locals used below.  */
45 #define dir_name rm_dir_name
46 #define dir_len rm_dir_len
47
48 #define obstack_chunk_alloc malloc
49 #define obstack_chunk_free free
50
51 /* This is the maximum number of consecutive readdir/unlink calls that
52    can be made (with no intervening rewinddir or closedir/opendir) before
53    triggering a bug that makes readdir return NULL even though some
54    directory entries have not been processed.  The bug afflicts SunOS's
55    readdir when applied to ufs file systems and Darwin 6.5's (and OSX
56    v.10.3.8's) HFS+.  This maximum is conservative in that demonstrating
57    the problem requires a directory containing at least 16 deletable
58    entries (which doesn't count . and ..).
59    This problem also affects Darwin 7.9.0 (aka MacOS X 10.3.9) on HFS+
60    and NFS-mounted file systems, but not vfat ones.  */
61 enum
62   {
63     CONSECUTIVE_READDIR_UNLINK_THRESHOLD = 10
64   };
65
66 /* FIXME: in 2009, or whenever Darwin 7.9.0 (aka MacOS X 10.3.9) is no
67    longer relevant, remove this work-around code.  Then, there will be
68    no need to perform the extra rewinddir call, ever.  */
69 #define NEED_REWIND(readdir_unlink_count) \
70   (CONSECUTIVE_READDIR_UNLINK_THRESHOLD <= (readdir_unlink_count))
71
72 enum Ternary
73   {
74     T_UNKNOWN = 2,
75     T_NO,
76     T_YES
77   };
78 typedef enum Ternary Ternary;
79
80 /* The prompt function may be called twice for a given directory.
81    The first time, we ask whether to descend into it, and the
82    second time, we ask whether to remove it.  */
83 enum Prompt_action
84   {
85     PA_DESCEND_INTO_DIR = 2,
86     PA_REMOVE_DIR
87   };
88
89 /* Initial capacity of per-directory hash table of entries that have
90    been processed but not been deleted.  */
91 enum { HT_UNREMOVABLE_INITIAL_CAPACITY = 13 };
92
93 /* An entry in the active directory stack.
94    Each entry corresponds to an `active' directory.  */
95 struct AD_ent
96 {
97   /* For a given active directory, this is the set of names of
98      entries in that directory that could/should not be removed.
99      For example, `.' and `..', as well as files/dirs for which
100      unlink/rmdir failed e.g., due to access restrictions.  */
101   Hash_table *unremovable;
102
103   /* Record the status for a given active directory; we need to know
104      whether an entry was not removed, either because of an error or
105      because the user declined.  */
106   enum RM_status status;
107
108   /* The directory's dev/ino.  Used to ensure that a malicious user does
109      not replace a directory we're about to process with a symlink to
110      some other directory.  */
111   struct dev_ino dev_ino;
112 };
113
114 /* D_TYPE(D) is the type of directory entry D if known, DT_UNKNOWN
115    otherwise.  */
116 #if HAVE_STRUCT_DIRENT_D_TYPE
117 # define D_TYPE(d) ((d)->d_type)
118 #else
119 # define D_TYPE(d) DT_UNKNOWN
120
121 /* Any int values will do here, so long as they're distinct.
122    Undef any existing macros out of the way.  */
123 # undef DT_UNKNOWN
124 # undef DT_DIR
125 # undef DT_LNK
126 # define DT_UNKNOWN 0
127 # define DT_DIR 1
128 # define DT_LNK 2
129 #endif
130
131 extern char *program_name;
132
133 struct dirstack_state
134 {
135   /* The name of the directory (starting with and relative to a command
136      line argument) being processed.  When a subdirectory is entered, a new
137      component is appended (pushed).  Remove (pop) the top component
138      upon chdir'ing out of a directory.  This is used to form the full
139      name of the current directory or a file therein, when necessary.  */
140   struct obstack dir_stack;
141
142   /* Stack of lengths of directory names (including trailing slash)
143      appended to dir_stack.  We have to have a separate stack of lengths
144      (rather than just popping back to previous slash) because the first
145      element pushed onto the dir stack may contain slashes.  */
146   struct obstack len_stack;
147
148   /* Stack of active directory entries.
149      The first `active' directory is the initial working directory.
150      Additional active dirs are pushed onto the stack as we `chdir'
151      into each directory to be processed.  When finished with the
152      hierarchy under a directory, pop the active dir stack.  */
153   struct obstack Active_dir;
154
155   /* Used to detect cycles.  */
156   struct cycle_check_state cycle_check_state;
157
158   /* Target of a longjmp in case rm has to stop processing the current
159      command-line argument.  This happens 1) when rm detects a directory
160      cycle or 2) when it has processed one or more directories, but then
161      is unable to return to the initial working directory to process
162      additional `.'-relative command-line arguments.  */
163   jmp_buf current_arg_jumpbuf;
164 };
165 typedef struct dirstack_state Dirstack_state;
166
167 /* A static buffer and its allocated size, these variables are used by
168    xfull_filename and full_filename to form full, relative file names.  */
169 static char *g_buf;
170 static size_t g_n_allocated;
171
172 /* Like fstatat, but cache the result.  If ST->st_size is -1, the
173    status has not been gotten yet.  If less than -1, fstatat failed
174    with errno == ST->st_ino.  Otherwise, the status has already
175    been gotten, so return 0.  */
176 static int
177 cache_fstatat (int fd, char const *file, struct stat *st, int flag)
178 {
179   if (st->st_size == -1 && fstatat (fd, file, st, flag) != 0)
180     {
181       st->st_size = -2;
182       st->st_ino = errno;
183     }
184   if (0 <= st->st_size)
185     return 0;
186   errno = (int) st->st_ino;
187   return -1;
188 }
189
190 /* Initialize a fstatat cache *ST.  Return ST for convenience.  */
191 static inline struct stat *
192 cache_stat_init (struct stat *st)
193 {
194   st->st_size = -1;
195   return st;
196 }
197
198 /* Return true if *ST has been statted.  */
199 static inline bool
200 cache_statted (struct stat *st)
201 {
202   return (st->st_size != -1);
203 }
204
205 /* Return true if *ST has been statted successfully.  */
206 static inline bool
207 cache_stat_ok (struct stat *st)
208 {
209   return (0 <= st->st_size);
210 }
211
212
213 static void
214 hash_freer (void *x)
215 {
216   free (x);
217 }
218
219 static bool
220 hash_compare_strings (void const *x, void const *y)
221 {
222   return STREQ (x, y) ? true : false;
223 }
224
225 static inline void
226 push_dir (Dirstack_state *ds, const char *dir_name)
227 {
228   size_t len = strlen (dir_name);
229
230   /* Don't copy trailing slashes.  */
231   while (1 < len && dir_name[len - 1] == '/')
232     --len;
233
234   /* Append the string onto the stack.  */
235   obstack_grow (&ds->dir_stack, dir_name, len);
236
237   /* Append a trailing slash.  */
238   obstack_1grow (&ds->dir_stack, '/');
239
240   /* Add one for the slash.  */
241   ++len;
242
243   /* Push the length (including slash) onto its stack.  */
244   obstack_grow (&ds->len_stack, &len, sizeof (len));
245 }
246
247 /* Return the entry name of the directory on the top of the stack
248    in malloc'd storage.  */
249 static inline char *
250 top_dir (Dirstack_state const *ds)
251 {
252   size_t n_lengths = obstack_object_size (&ds->len_stack) / sizeof (size_t);
253   size_t *length = obstack_base (&ds->len_stack);
254   size_t top_len = length[n_lengths - 1];
255   char const *p = obstack_next_free (&ds->dir_stack) - top_len;
256   char *q = xmalloc (top_len);
257   memcpy (q, p, top_len - 1);
258   q[top_len - 1] = 0;
259   return q;
260 }
261
262 static inline void
263 pop_dir (Dirstack_state *ds)
264 {
265   size_t n_lengths = obstack_object_size (&ds->len_stack) / sizeof (size_t);
266   size_t *length = obstack_base (&ds->len_stack);
267
268   assert (n_lengths > 0);
269   size_t top_len = length[n_lengths - 1];
270   assert (top_len >= 2);
271
272   /* Pop the specified length of file name.  */
273   assert (obstack_object_size (&ds->dir_stack) >= top_len);
274   obstack_blank (&ds->dir_stack, -top_len);
275
276   /* Pop the length stack, too.  */
277   assert (obstack_object_size (&ds->len_stack) >= sizeof (size_t));
278   obstack_blank (&ds->len_stack, -(int) sizeof (size_t));
279 }
280
281 /* Copy the SRC_LEN bytes of data beginning at SRC into the DST_LEN-byte
282    buffer, DST, so that the last source byte is at the end of the destination
283    buffer.  If SRC_LEN is longer than DST_LEN, then set *TRUNCATED.
284    Set *RESULT to point to the beginning of (the portion of) the source data
285    in DST.  Return the number of bytes remaining in the destination buffer.  */
286
287 static size_t
288 right_justify (char *dst, size_t dst_len, const char *src, size_t src_len,
289                char **result, bool *truncated)
290 {
291   const char *sp;
292   char *dp;
293
294   if (src_len <= dst_len)
295     {
296       sp = src;
297       dp = dst + (dst_len - src_len);
298       *truncated = false;
299     }
300   else
301     {
302       sp = src + (src_len - dst_len);
303       dp = dst;
304       src_len = dst_len;
305       *truncated = true;
306     }
307
308   *result = memcpy (dp, sp, src_len);
309   return dst_len - src_len;
310 }
311
312 /* Using the global directory name obstack, create the full name of FILENAME.
313    Return it in sometimes-realloc'd space that should not be freed by the
314    caller.  Realloc as necessary.  If realloc fails, return NULL.  */
315
316 static char *
317 full_filename0 (Dirstack_state const *ds, const char *filename)
318 {
319   size_t dir_len = obstack_object_size (&ds->dir_stack);
320   char *dir_name = obstack_base (&ds->dir_stack);
321   size_t filename_len = strlen (filename);
322   size_t n_bytes_needed = dir_len + filename_len + 1;
323
324   if (g_n_allocated < n_bytes_needed)
325     {
326       char *new_buf = realloc (g_buf, n_bytes_needed);
327       if (new_buf == NULL)
328         return NULL;
329
330       g_buf = new_buf;
331       g_n_allocated = n_bytes_needed;
332     }
333
334   if (STREQ (filename, ".") && dir_len)
335     {
336       /* FILENAME is just `.' and dir_len is nonzero.
337          Copy the directory part, omitting the trailing slash,
338          and append a trailing zero byte.  */
339       char *p = mempcpy (g_buf, dir_name, dir_len - 1);
340       *p = 0;
341     }
342   else
343     {
344       /* Copy the directory part, including trailing slash, and then
345          append the filename part, including a trailing zero byte.  */
346       memcpy (mempcpy (g_buf, dir_name, dir_len), filename, filename_len + 1);
347       assert (strlen (g_buf) + 1 == n_bytes_needed);
348     }
349
350   return g_buf;
351 }
352
353 /* Using the global directory name obstack, create the full name of FILENAME.
354    Return it in sometimes-realloc'd space that should not be freed by the
355    caller.  Realloc as necessary.  If realloc fails, die.  */
356
357 static char *
358 xfull_filename (Dirstack_state const *ds, const char *filename)
359 {
360   char *buf = full_filename0 (ds, filename);
361   if (buf == NULL)
362     xalloc_die ();
363   return buf;
364 }
365
366 /* Using the global directory name obstack, create the full name FILENAME.
367    Return it in sometimes-realloc'd space that should not be freed by the
368    caller.  Realloc as necessary.  If realloc fails, use a static buffer
369    and put as long a suffix in that buffer as possible.  Be careful not
370    to change errno.  */
371
372 #define full_filename(Filename) full_filename_ (ds, Filename)
373 static char *
374 full_filename_ (Dirstack_state const *ds, const char *filename)
375 {
376   int saved_errno = errno;
377   char *full_name = full_filename0 (ds, filename);
378   if (full_name)
379     {
380       errno = saved_errno;
381       return full_name;
382     }
383
384   {
385 #define SBUF_SIZE 512
386 #define ELLIPSES_PREFIX "[...]"
387     static char static_buf[SBUF_SIZE];
388     bool file_truncated;
389     bool dir_truncated;
390     size_t n_bytes_remaining;
391     char *p;
392     char *dir_name = obstack_base (&ds->dir_stack);
393     size_t dir_len = obstack_object_size (&ds->dir_stack);
394
395     free (g_buf);
396     n_bytes_remaining = right_justify (static_buf, SBUF_SIZE, filename,
397                                        strlen (filename) + 1, &p,
398                                        &file_truncated);
399     right_justify (static_buf, n_bytes_remaining, dir_name, dir_len,
400                    &p, &dir_truncated);
401     if (file_truncated || dir_truncated)
402       {
403         memcpy (static_buf, ELLIPSES_PREFIX,
404                 sizeof (ELLIPSES_PREFIX) - 1);
405       }
406     errno = saved_errno;
407     return p;
408   }
409 }
410
411 static inline size_t
412 AD_stack_height (Dirstack_state const *ds)
413 {
414   return obstack_object_size (&ds->Active_dir) / sizeof (struct AD_ent);
415 }
416
417 static inline struct AD_ent *
418 AD_stack_top (Dirstack_state const *ds)
419 {
420   return (struct AD_ent *)
421     ((char *) obstack_next_free (&ds->Active_dir) - sizeof (struct AD_ent));
422 }
423
424 static void
425 AD_stack_pop (Dirstack_state *ds)
426 {
427   assert (0 < AD_stack_height (ds));
428
429   /* operate on Active_dir.  pop and free top entry */
430   struct AD_ent *top = AD_stack_top (ds);
431   if (top->unremovable)
432     hash_free (top->unremovable);
433   obstack_blank (&ds->Active_dir, -(int) sizeof (struct AD_ent));
434 }
435
436 static void
437 AD_stack_clear (Dirstack_state *ds)
438 {
439   while (0 < AD_stack_height (ds))
440     {
441       AD_stack_pop (ds);
442     }
443 }
444
445 static Dirstack_state *
446 ds_init (void)
447 {
448   Dirstack_state *ds = xmalloc (sizeof *ds);
449   obstack_init (&ds->dir_stack);
450   obstack_init (&ds->len_stack);
451   obstack_init (&ds->Active_dir);
452   return ds;
453 }
454
455 static void
456 ds_clear (Dirstack_state *ds)
457 {
458   obstack_free (&ds->dir_stack, obstack_finish (&ds->dir_stack));
459   obstack_free (&ds->len_stack, obstack_finish (&ds->len_stack));
460   while (0 < AD_stack_height (ds))
461     AD_stack_pop (ds);
462   obstack_free (&ds->Active_dir, obstack_finish (&ds->Active_dir));
463 }
464
465 static void
466 ds_free (Dirstack_state *ds)
467 {
468   obstack_free (&ds->dir_stack, NULL);
469   obstack_free (&ds->len_stack, NULL);
470   obstack_free (&ds->Active_dir, NULL);
471   free (ds);
472 }
473
474 /* Pop the active directory (AD) stack and prepare to move `up' one level,
475    safely.  Moving `up' usually means opening `..', but when we've just
476    finished recursively processing a command-line directory argument,
477    there's nothing left on the stack, so set *FDP to AT_FDCWD in that case.
478    The idea is to return with *FDP opened on the parent directory,
479    assuming there are entries in that directory that we need to remove.
480
481    Note that we must not call opendir (or fdopendir) just yet, since
482    the caller must first remove the directory we're coming from.
483    That is because some file system implementations cache readdir
484    results at opendir time; so calling opendir, rmdir, readdir would
485    return an entry for the just-removed directory.
486
487    Whenever using chdir '..' (virtually, now, via openat), verify
488    that the post-chdir dev/ino numbers for `.' match the saved ones.
489    If any system call fails or if dev/ino don't match, then give a
490    diagnostic and longjump out.
491    Return the name (in malloc'd storage) of the
492    directory (usually now empty) from which we're coming, and which
493    corresponds to the input value of DIRP.
494
495    Finally, note that while this function's name is no longer as
496    accurate as it once was (it no longer calls chdir), it does open
497    the destination directory.  */
498 static char *
499 AD_pop_and_chdir (DIR *dirp, int *fdp, Dirstack_state *ds)
500 {
501   struct AD_ent *leaf_dir_ent = AD_stack_top(ds);
502   struct dev_ino leaf_dev_ino = leaf_dir_ent->dev_ino;
503   enum RM_status old_status = leaf_dir_ent->status;
504   struct AD_ent *top;
505
506   /* Get the name of the current (but soon to be `previous') directory
507      from the top of the stack.  */
508   char *prev_dir = top_dir (ds);
509
510   AD_stack_pop (ds);
511   pop_dir (ds);
512   top = AD_stack_top (ds);
513
514   /* If the directory we're about to leave (and try to rmdir)
515      is the one whose dev_ino is being used to detect a cycle,
516      reset cycle_check_state.dev_ino to that of the parent.
517      Otherwise, once that directory is removed, its dev_ino
518      could be reused in the creation (by some other process)
519      of a directory that this rm process would encounter,
520      which would result in a false-positive cycle indication.  */
521   CYCLE_CHECK_REFLECT_CHDIR_UP (&ds->cycle_check_state,
522                                 top->dev_ino, leaf_dev_ino);
523
524   /* Propagate any failure to parent.  */
525   UPDATE_STATUS (top->status, old_status);
526
527   assert (AD_stack_height (ds));
528
529   if (1 < AD_stack_height (ds))
530     {
531       struct stat sb;
532       int fd = openat (dirfd (dirp), "..", O_RDONLY);
533       if (closedir (dirp) != 0)
534         {
535           error (0, errno, _("FATAL: failed to close directory %s"),
536                  quote (full_filename (prev_dir)));
537           goto next_cmdline_arg;
538         }
539
540       /* The above fails with EACCES when DIRP is readable but not
541          searchable, when using Solaris' openat.  Without this openat
542          call, tests/rm2 would fail to remove directories a/2 and a/3.  */
543       if (fd < 0)
544         fd = openat (AT_FDCWD, xfull_filename (ds, "."), O_RDONLY);
545
546       if (fd < 0)
547         {
548           error (0, errno, _("FATAL: cannot open .. from %s"),
549                  quote (full_filename (prev_dir)));
550           goto next_cmdline_arg;
551         }
552
553       if (fstat (fd, &sb))
554         {
555           error (0, errno,
556                  _("FATAL: cannot ensure %s (returned to via ..) is safe"),
557                  quote (full_filename (".")));
558           goto close_and_next;
559         }
560
561       /*  Ensure that post-chdir dev/ino match the stored ones.  */
562       if ( ! SAME_INODE (sb, top->dev_ino))
563         {
564           error (0, 0, _("FATAL: directory %s changed dev/ino"),
565                  quote (full_filename (".")));
566         close_and_next:;
567           close (fd);
568
569         next_cmdline_arg:;
570           free (prev_dir);
571           longjmp (ds->current_arg_jumpbuf, 1);
572         }
573       *fdp = fd;
574     }
575   else
576     {
577       if (closedir (dirp) != 0)
578         {
579           error (0, errno, _("FATAL: failed to close directory %s"),
580                  quote (full_filename (prev_dir)));
581           goto next_cmdline_arg;
582         }
583       *fdp = AT_FDCWD;
584     }
585
586   return prev_dir;
587 }
588
589 /* Initialize *HT if it is NULL.  Return *HT.  */
590 static Hash_table *
591 AD_ensure_initialized (Hash_table **ht)
592 {
593   if (*ht == NULL)
594     {
595       *ht = hash_initialize (HT_UNREMOVABLE_INITIAL_CAPACITY, NULL, hash_pjw,
596                              hash_compare_strings, hash_freer);
597       if (*ht == NULL)
598         xalloc_die ();
599     }
600
601   return *ht;
602 }
603
604 /* Initialize *HT if it is NULL.
605    Insert FILENAME into HT.  */
606 static void
607 AD_mark_helper (Hash_table **ht, char *filename)
608 {
609   void *ent = hash_insert (AD_ensure_initialized (ht), filename);
610   if (ent == NULL)
611     xalloc_die ();
612   else
613     {
614       if (ent != filename)
615         free (filename);
616     }
617 }
618
619 /* Mark FILENAME (in current directory) as unremovable.  */
620 static void
621 AD_mark_as_unremovable (Dirstack_state *ds, char const *filename)
622 {
623   AD_mark_helper (&AD_stack_top(ds)->unremovable, xstrdup (filename));
624 }
625
626 /* Mark the current directory as unremovable.  I.e., mark the entry
627    in the parent directory corresponding to `.'.
628    This happens e.g., when an opendir fails and the only name
629    the caller has conveniently at hand is `.'.  */
630 static void
631 AD_mark_current_as_unremovable (Dirstack_state *ds)
632 {
633   struct AD_ent *top = AD_stack_top (ds);
634   char *curr = top_dir (ds);
635
636   assert (1 < AD_stack_height (ds));
637
638   --top;
639   AD_mark_helper (&top->unremovable, curr);
640 }
641
642 /* Push an initial dummy entry onto the stack.
643    This will always be the bottommost entry on the stack.  */
644 static void
645 AD_push_initial (Dirstack_state *ds)
646 {
647   struct AD_ent *top;
648
649   /* Extend the stack.  */
650   obstack_blank (&ds->Active_dir, sizeof (struct AD_ent));
651
652   /* Fill in the new values.  */
653   top = AD_stack_top (ds);
654   top->unremovable = NULL;
655
656   /* These should never be used.
657      Give them values that might look suspicious
658      in a debugger or in a diagnostic.  */
659   top->dev_ino.st_dev = TYPE_MAXIMUM (dev_t);
660   top->dev_ino.st_ino = TYPE_MAXIMUM (ino_t);
661 }
662
663 /* Push info about the current working directory (".") onto the
664    active directory stack.  DIR is the ./-relative name through
665    which we've just `chdir'd to this directory.  DIR_SB_FROM_PARENT
666    is the result of calling lstat on DIR from the parent of DIR.
667    Longjump out (skipping the entire command line argument we're
668    dealing with) if `fstat (FD_CWD, ...' fails or if someone has
669    replaced DIR with e.g., a symlink to some other directory.  */
670 static void
671 AD_push (int fd_cwd, Dirstack_state *ds, char const *dir,
672          struct stat const *dir_sb_from_parent)
673 {
674   struct AD_ent *top;
675
676   push_dir (ds, dir);
677
678   /* If our uses of openat are guaranteed not to
679      follow a symlink, then we can skip this check.  */
680   if (! HAVE_WORKING_O_NOFOLLOW)
681     {
682       struct stat sb;
683       if (fstat (fd_cwd, &sb) != 0)
684         {
685           error (0, errno, _("FATAL: cannot enter directory %s"),
686                  quote (full_filename (".")));
687           longjmp (ds->current_arg_jumpbuf, 1);
688         }
689
690       if ( ! SAME_INODE (sb, *dir_sb_from_parent))
691         {
692           error (0, 0,
693                  _("FATAL: just-changed-to directory %s changed dev/ino"),
694                  quote (full_filename (".")));
695           longjmp (ds->current_arg_jumpbuf, 1);
696         }
697     }
698
699   if (cycle_check (&ds->cycle_check_state, dir_sb_from_parent))
700     {
701       error (0, 0, _("\
702 WARNING: Circular directory structure.\n\
703 This almost certainly means that you have a corrupted file system.\n\
704 NOTIFY YOUR SYSTEM MANAGER.\n\
705 The following directory is part of the cycle:\n  %s\n"),
706              quote (full_filename (".")));
707       longjmp (ds->current_arg_jumpbuf, 1);
708     }
709
710   /* Extend the stack.  */
711   obstack_blank (&ds->Active_dir, sizeof (struct AD_ent));
712
713   /* The active directory stack must be one larger than the length stack.  */
714   assert (AD_stack_height (ds) ==
715           1 + obstack_object_size (&ds->len_stack) / sizeof (size_t));
716
717   /* Fill in the new values.  */
718   top = AD_stack_top (ds);
719   top->dev_ino.st_dev = dir_sb_from_parent->st_dev;
720   top->dev_ino.st_ino = dir_sb_from_parent->st_ino;
721   top->unremovable = NULL;
722 }
723
724 static inline bool
725 AD_is_removable (Dirstack_state const *ds, char const *file)
726 {
727   struct AD_ent *top = AD_stack_top (ds);
728   return ! (top->unremovable && hash_lookup (top->unremovable, file));
729 }
730
731 /* Return -1 if FILE is an unwritable non-symlink,
732    0 if it is writable or some other type of file,
733    a positive error number if there is some problem in determining the answer.
734    Set *BUF to the file status.
735    This is to avoid calling euidaccess when FILE is a symlink.  */
736 static int
737 write_protected_non_symlink (int fd_cwd,
738                              char const *file,
739                              Dirstack_state const *ds,
740                              struct stat *buf)
741 {
742   if (can_write_any_file ())
743     return 0;
744   if (cache_fstatat (fd_cwd, file, buf, AT_SYMLINK_NOFOLLOW) != 0)
745     return errno;
746   if (S_ISLNK (buf->st_mode))
747     return 0;
748   /* Here, we know FILE is not a symbolic link.  */
749
750   /* In order to be reentrant -- i.e., to avoid changing the working
751      directory, and at the same time to be able to deal with alternate
752      access control mechanisms (ACLs, xattr-style attributes) and
753      arbitrarily deep trees -- we need a function like eaccessat, i.e.,
754      like Solaris' eaccess, but fd-relative, in the spirit of openat.  */
755
756   /* In the absence of a native eaccessat function, here are some of
757      the implementation choices [#4 and #5 were suggested by Paul Eggert]:
758      1) call openat with O_WRONLY|O_NOCTTY
759         Disadvantage: may create the file and doesn't work for directory,
760         may mistakenly report `unwritable' for EROFS or ACLs even though
761         perm bits say the file is writable.
762
763      2) fake eaccessat (save_cwd, fchdir, call euidaccess, restore_cwd)
764         Disadvantage: changes working directory (not reentrant) and can't
765         work if save_cwd fails.
766
767      3) if (euidaccess (xfull_filename (file), W_OK) == 0)
768         Disadvantage: doesn't work if xfull_filename is too long.
769         Inefficient for very deep trees (O(Depth^2)).
770
771      4) If the full pathname is sufficiently short (say, less than
772         PATH_MAX or 8192 bytes, whichever is shorter):
773         use method (3) (i.e., euidaccess (xfull_filename (file), W_OK));
774         Otherwise: vfork, fchdir in the child, run euidaccess in the
775         child, then the child exits with a status that tells the parent
776         whether euidaccess succeeded.
777
778         This avoids the O(N**2) algorithm of method (3), and it also avoids
779         the failure-due-to-too-long-file-names of method (3), but it's fast
780         in the normal shallow case.  It also avoids the lack-of-reentrancy
781         and the save_cwd problems.
782         Disadvantage; it uses a process slot for very-long file names,
783         and would be very slow for hierarchies with many such files.
784
785      5) If the full file name is sufficiently short (say, less than
786         PATH_MAX or 8192 bytes, whichever is shorter):
787         use method (3) (i.e., euidaccess (xfull_filename (file), W_OK));
788         Otherwise: look just at the file bits.  Perhaps issue a warning
789         the first time this occurs.
790
791         This is like (4), except for the "Otherwise" case where it isn't as
792         "perfect" as (4) but is considerably faster.  It conforms to current
793         POSIX, and is uniformly better than what Solaris and FreeBSD do (they
794         mess up with long file names). */
795
796   {
797     /* This implements #5: */
798     size_t file_name_len
799       = obstack_object_size (&ds->dir_stack) + strlen (file);
800
801     if (MIN (PATH_MAX, 8192) <= file_name_len)
802       return euidaccess_stat (buf, W_OK) ? 0 : -1;
803     if (euidaccess (xfull_filename (ds, file), W_OK) == 0)
804       return 0;
805     if (errno == EACCES)
806       return -1;
807
808     /* Perhaps some other process has removed the file, or perhaps this
809        is a buggy NFS client.  */
810     return errno;
811   }
812 }
813
814 /* Prompt whether to remove FILENAME, if required via a combination of
815    the options specified by X and/or file attributes.  If the file may
816    be removed, return RM_OK.  If the user declines to remove the file,
817    return RM_USER_DECLINED.  If not ignoring missing files and we
818    cannot lstat FILENAME, then return RM_ERROR.
819
820    *PDIRENT_TYPE is the type of the directory entry; update it to DT_DIR
821    or DT_LNK as needed.  *SBUF is the file's status.
822
823    Depending on MODE, ask whether to `descend into' or to `remove' the
824    directory FILENAME.  MODE is ignored when FILENAME is not a directory.
825    Set *IS_EMPTY to T_YES if FILENAME is an empty directory, and it is
826    appropriate to try to remove it with rmdir (e.g. recursive mode).
827    Don't even try to set *IS_EMPTY when MODE == PA_REMOVE_DIR.  */
828 static enum RM_status
829 prompt (int fd_cwd, Dirstack_state const *ds, char const *filename,
830         int *pdirent_type, struct stat *sbuf,
831         struct rm_options const *x, enum Prompt_action mode,
832         Ternary *is_empty)
833 {
834   int write_protected = 0;
835   int dirent_type = *pdirent_type;
836
837   *is_empty = T_UNKNOWN;
838
839   if (x->interactive == RMI_NEVER)
840     return RM_OK;
841
842   if (!x->ignore_missing_files
843       && ((x->interactive == RMI_ALWAYS) || x->stdin_tty)
844       && dirent_type != DT_LNK)
845     write_protected = write_protected_non_symlink (fd_cwd, filename, ds, sbuf);
846
847   if (write_protected || x->interactive == RMI_ALWAYS)
848     {
849       if (write_protected <= 0 && dirent_type == DT_UNKNOWN)
850         {
851           if (cache_fstatat (fd_cwd, filename, sbuf, AT_SYMLINK_NOFOLLOW) == 0)
852             {
853               if (S_ISLNK (sbuf->st_mode))
854                 dirent_type = DT_LNK;
855               else if (S_ISDIR (sbuf->st_mode))
856                 dirent_type = DT_DIR;
857               /* Otherwise it doesn't matter, so leave it DT_UNKNOWN.  */
858               *pdirent_type = dirent_type;
859             }
860           else
861             {
862               /* This happens, e.g., with `rm '''.  */
863               write_protected = errno;
864             }
865         }
866
867       if (write_protected <= 0)
868         switch (dirent_type)
869           {
870           case DT_LNK:
871             /* Using permissions doesn't make sense for symlinks.  */
872             if (x->interactive != RMI_ALWAYS)
873               return RM_OK;
874             break;
875
876           case DT_DIR:
877             if (!x->recursive)
878               write_protected = EISDIR;
879             break;
880           }
881
882       char const *quoted_name = quote (full_filename (filename));
883
884       if (0 < write_protected)
885         {
886           error (0, write_protected, _("cannot remove %s"), quoted_name);
887           return RM_ERROR;
888         }
889
890       /* Issue the prompt.  */
891       /* FIXME: use a variant of error (instead of fprintf) that doesn't
892          append a newline.  Then we won't have to declare program_name in
893          this file.  */
894       if (dirent_type == DT_DIR
895           && mode == PA_DESCEND_INTO_DIR
896           && ((*is_empty = (is_empty_dir (fd_cwd, filename) ? T_YES : T_NO))
897               == T_NO))
898         fprintf (stderr,
899                  (write_protected
900                   ? _("%s: descend into write-protected directory %s? ")
901                   : _("%s: descend into directory %s? ")),
902                  program_name, quoted_name);
903       else
904         {
905           if (cache_fstatat (fd_cwd, filename, sbuf, AT_SYMLINK_NOFOLLOW) != 0)
906             {
907               error (0, errno, _("cannot remove %s"), quoted_name);
908               return RM_ERROR;
909             }
910
911           /* TRANSLATORS: You may find it more convenient to translate
912              the equivalent of _("%s: remove %s (write-protected) %s? ").
913              It should avoid grammatical problems with the output
914              of file_type.  */
915           fprintf (stderr,
916                    (write_protected
917                     ? _("%s: remove write-protected %s %s? ")
918                     : _("%s: remove %s %s? ")),
919                    program_name, file_type (sbuf), quoted_name);
920         }
921
922       if (!yesno ())
923         return RM_USER_DECLINED;
924     }
925   return RM_OK;
926 }
927
928 /* Return true if FILENAME is a directory (and not a symlink to a directory).
929    Otherwise, including the case in which lstat fails, return false.
930    *ST is FILENAME's tstatus.
931    Do not modify errno.  */
932 static inline bool
933 is_dir_lstat (int fd_cwd, char const *filename, struct stat *st)
934 {
935   int saved_errno = errno;
936   bool is_dir =
937     (cache_fstatat (fd_cwd, filename, st, AT_SYMLINK_NOFOLLOW) == 0
938      && S_ISDIR (st->st_mode));
939   errno = saved_errno;
940   return is_dir;
941 }
942
943 /* Return true if FILENAME is a non-directory.
944    Otherwise, including the case in which lstat fails, return false.
945    *ST is FILENAME's tstatus.
946    Do not modify errno.  */
947 static inline bool
948 is_nondir_lstat (int fd_cwd, char const *filename, struct stat *st)
949 {
950   int saved_errno = errno;
951   bool is_non_dir =
952     (cache_fstatat (fd_cwd, filename, st, AT_SYMLINK_NOFOLLOW) == 0
953      && !S_ISDIR (st->st_mode));
954   errno = saved_errno;
955   return is_non_dir;
956 }
957
958 #define DO_UNLINK(Fd_cwd, Filename, X)                                  \
959   do                                                                    \
960     {                                                                   \
961       if (unlinkat (Fd_cwd, Filename, 0) == 0)                          \
962         {                                                               \
963           if ((X)->verbose)                                             \
964             printf (_("removed %s\n"), quote (full_filename (Filename))); \
965           return RM_OK;                                                 \
966         }                                                               \
967                                                                         \
968       if (ignorable_missing (X, errno))                                 \
969         return RM_OK;                                                   \
970     }                                                                   \
971   while (0)
972
973 #define DO_RMDIR(Fd_cwd, Filename, X)                   \
974   do                                                    \
975     {                                                   \
976       if (unlinkat (Fd_cwd, Filename, AT_REMOVEDIR) == 0) /* rmdir */ \
977         {                                               \
978           if ((X)->verbose)                             \
979             printf (_("removed directory: %s\n"),       \
980                     quote (full_filename (Filename)));  \
981           return RM_OK;                                 \
982         }                                               \
983                                                         \
984       if (ignorable_missing (X, errno))                 \
985         return RM_OK;                                   \
986                                                         \
987       if (errno == ENOTEMPTY || errno == EEXIST)        \
988         return RM_NONEMPTY_DIR;                         \
989     }                                                   \
990   while (0)
991
992 /* When a function like unlink, rmdir, or fstatat fails with an errno
993    value of ERRNUM, return true if the specified file system object
994    is guaranteed not to exist;  otherwise, return false.  */
995 static inline bool
996 nonexistent_file_errno (int errnum)
997 {
998   /* Do not include ELOOP here, since the specified file may indeed
999      exist, but be (in)accessible only via too long a symlink chain.
1000      Likewise for ENAMETOOLONG, since rm -f ./././.../foo may fail
1001      if the "..." part expands to a long enough sequence of "./"s,
1002      even though ./foo does indeed exist.  */
1003
1004   switch (errnum)
1005     {
1006     case ENOENT:
1007     case ENOTDIR:
1008       return true;
1009     default:
1010       return false;
1011     }
1012 }
1013
1014 /* Encapsulate the test for whether the errno value, ERRNUM, is ignorable.  */
1015 static inline bool
1016 ignorable_missing (struct rm_options const *x, int errnum)
1017 {
1018   return x->ignore_missing_files && nonexistent_file_errno (errnum);
1019 }
1020
1021 /* Remove the file or directory specified by FILENAME.
1022    Return RM_OK if it is removed, and RM_ERROR or RM_USER_DECLINED if not.
1023    But if FILENAME specifies a non-empty directory, return RM_NONEMPTY_DIR. */
1024
1025 static enum RM_status
1026 remove_entry (int fd_cwd, Dirstack_state const *ds, char const *filename,
1027               int dirent_type_arg, struct stat *st,
1028               struct rm_options const *x)
1029 {
1030   Ternary is_empty_directory;
1031   enum RM_status s = prompt (fd_cwd, ds, filename, &dirent_type_arg, st, x,
1032                              PA_DESCEND_INTO_DIR,
1033                              &is_empty_directory);
1034   int dirent_type = dirent_type_arg;
1035   if (s != RM_OK)
1036     return s;
1037
1038   /* Why bother with the following if/else block?  Because on systems with
1039      an unlink function that *can* unlink directories, we must determine the
1040      type of each entry before removing it.  Otherwise, we'd risk unlinking
1041      an entire directory tree simply by unlinking a single directory;  then
1042      all the storage associated with that hierarchy would not be freed until
1043      the next fsck.  Not nice.  To avoid that, on such slightly losing
1044      systems, we need to call lstat to determine the type of each entry,
1045      and that represents extra overhead that -- it turns out -- we can
1046      avoid on non-losing systems, since there, unlink will never remove
1047      a directory.  Also, on systems where unlink may unlink directories,
1048      we're forced to allow a race condition: we lstat a non-directory, then
1049      go to unlink it, but in the mean time, a malicious someone could have
1050      replaced it with a directory.  */
1051
1052   if (cannot_unlink_dir ())
1053     {
1054       if (dirent_type == DT_DIR && ! x->recursive)
1055         {
1056           error (0, EISDIR, _("cannot remove %s"),
1057                  quote (full_filename (filename)));
1058           return RM_ERROR;
1059         }
1060
1061       /* is_empty_directory is set iff it's ok to use rmdir.
1062          Note that it's set only in interactive mode -- in which case it's
1063          an optimization that arranges so that the user is asked just
1064          once whether to remove the directory.  */
1065       if (is_empty_directory == T_YES)
1066         DO_RMDIR (fd_cwd, filename, x);
1067
1068       /* If we happen to know that FILENAME is a directory, return now
1069          and let the caller remove it -- this saves the overhead of a failed
1070          unlink call.  If FILENAME is a command-line argument, then
1071          DIRENT_TYPE is DT_UNKNOWN so we'll first try to unlink it.
1072          Using unlink here is ok, because it cannot remove a
1073          directory.  */
1074       if (dirent_type == DT_DIR)
1075         return RM_NONEMPTY_DIR;
1076
1077       DO_UNLINK (fd_cwd, filename, x);
1078
1079       /* Upon a failed attempt to unlink a directory, most non-Linux systems
1080          set errno to the POSIX-required value EPERM.  In that case, change
1081          errno to EISDIR so that we emit a better diagnostic.  */
1082       if (! x->recursive && errno == EPERM && is_dir_lstat (fd_cwd,
1083                                                             filename, st))
1084         errno = EISDIR;
1085
1086       if (! x->recursive
1087           || (cache_stat_ok (st) && !S_ISDIR (st->st_mode))
1088           || ((errno == EACCES || errno == EPERM)
1089               && is_nondir_lstat (fd_cwd, filename, st))
1090           )
1091         {
1092           if (ignorable_missing (x, errno))
1093             return RM_OK;
1094
1095           /* Either --recursive is not in effect, or the file cannot be a
1096              directory.  Report the unlink problem and fail.  */
1097           error (0, errno, _("cannot remove %s"),
1098                  quote (full_filename (filename)));
1099           return RM_ERROR;
1100         }
1101       assert (!cache_stat_ok (st) || S_ISDIR (st->st_mode));
1102     }
1103   else
1104     {
1105       /* If we don't already know whether FILENAME is a directory,
1106          find out now.  Then, if it's a non-directory, we can use
1107          unlink on it.  */
1108
1109       if (dirent_type == DT_UNKNOWN)
1110         {
1111           if (fstatat (fd_cwd, filename, st, AT_SYMLINK_NOFOLLOW))
1112             {
1113               if (ignorable_missing (x, errno))
1114                 return RM_OK;
1115
1116               error (0, errno, _("cannot remove %s"),
1117                      quote (full_filename (filename)));
1118               return RM_ERROR;
1119             }
1120
1121           if (S_ISDIR (st->st_mode))
1122             dirent_type = DT_DIR;
1123         }
1124
1125       if (dirent_type != DT_DIR)
1126         {
1127           /* At this point, barring race conditions, FILENAME is known
1128              to be a non-directory, so it's ok to try to unlink it.  */
1129           DO_UNLINK (fd_cwd, filename, x);
1130
1131           /* unlink failed with some other error code.  report it.  */
1132           error (0, errno, _("cannot remove %s"),
1133                  quote (full_filename (filename)));
1134           return RM_ERROR;
1135         }
1136
1137       if (! x->recursive)
1138         {
1139           error (0, EISDIR, _("cannot remove %s"),
1140                  quote (full_filename (filename)));
1141           return RM_ERROR;
1142         }
1143
1144       if (is_empty_directory == T_YES)
1145         {
1146           DO_RMDIR (fd_cwd, filename, x);
1147           /* Don't diagnose any failure here.
1148              It'll be detected when the caller tries another way.  */
1149         }
1150     }
1151
1152   return RM_NONEMPTY_DIR;
1153 }
1154
1155 /* Given FD_CWD, the file descriptor for an open directory,
1156    open its subdirectory F (F is already `known' to be a directory,
1157    so if it is no longer one, someone is playing games), return a DIR*
1158    pointer for F, and put F's `stat' data in *SUBDIR_SB.
1159    Upon failure give a diagnostic and return NULL.
1160    If PREV_ERRNO is nonzero, it is the errno value from a preceding failed
1161    unlink- or rmdir-like system call -- use that value instead of ENOTDIR
1162    if an opened file turns out not to be a directory.  This is important
1163    when the preceding non-dir-unlink failed due to e.g., EPERM or EACCES.
1164    The caller must use a nonnnull CWD_ERRNO the first
1165    time this function is called for each command-line-specified directory.
1166    If CWD_ERRNO is not null, set *CWD_ERRNO to the appropriate error number
1167    if this function fails to restore the initial working directory.
1168    If it is null, report an error and exit if the working directory
1169    isn't restored.  */
1170 static DIR *
1171 fd_to_subdirp (int fd_cwd, char const *f,
1172                int prev_errno,
1173                struct stat *subdir_sb,
1174                int *cwd_errno ATTRIBUTE_UNUSED)
1175 {
1176   int open_flags = O_RDONLY | O_NOCTTY | O_NOFOLLOW | O_NONBLOCK;
1177   int fd_sub = openat_permissive (fd_cwd, f, open_flags, 0, cwd_errno);
1178   int saved_errno;
1179
1180   /* Record dev/ino of F.  We may compare them against saved values
1181      to thwart any attempt to subvert the traversal.  They are also used
1182      to detect directory cycles.  */
1183   if (fd_sub < 0)
1184     return NULL;
1185   else if (fstat (fd_sub, subdir_sb) != 0)
1186     saved_errno = errno;
1187   else if (S_ISDIR (subdir_sb->st_mode))
1188     {
1189       DIR *subdir_dirp = fdopendir (fd_sub);
1190       if (subdir_dirp)
1191         return subdir_dirp;
1192       saved_errno = errno;
1193     }
1194   else
1195     saved_errno = (prev_errno ? prev_errno : ENOTDIR);
1196
1197   close (fd_sub);
1198   errno = saved_errno;
1199   return NULL;
1200 }
1201
1202 /* Remove entries in the directory open on DIRP
1203    Upon finding a directory that is both non-empty and that can be chdir'd
1204    into, return RM_OK and set *SUBDIR and fill in SUBDIR_SB, where
1205    SUBDIR is the malloc'd name of the subdirectory if the chdir succeeded,
1206    NULL otherwise (e.g., if opendir failed or if there was no subdirectory).
1207    Likewise, SUBDIR_SB is the result of calling lstat on SUBDIR.
1208    Return RM_OK if all entries are removed.  Return RM_ERROR if any
1209    entry cannot be removed.  Otherwise, return RM_USER_DECLINED if
1210    the user declines to remove at least one entry.  Remove as much as
1211    possible, continuing even if we fail to remove some entries.  */
1212 static enum RM_status
1213 remove_cwd_entries (DIR **dirp,
1214                     Dirstack_state *ds, char **subdir, struct stat *subdir_sb,
1215                     struct rm_options const *x)
1216 {
1217   struct AD_ent *top = AD_stack_top (ds);
1218   enum RM_status status = top->status;
1219   size_t n_unlinked_since_opendir_or_last_rewind = 0;
1220
1221   assert (VALID_STATUS (status));
1222   *subdir = NULL;
1223
1224   while (1)
1225     {
1226       struct dirent const *dp;
1227       enum RM_status tmp_status;
1228       const char *f;
1229
1230       /* Set errno to zero so we can distinguish between a readdir failure
1231          and when readdir simply finds that there are no more entries.  */
1232       errno = 0;
1233       dp = readdir_ignoring_dot_and_dotdot (*dirp);
1234       if (dp == NULL)
1235         {
1236           if (errno)
1237             {
1238               /* fall through */
1239             }
1240           else if (NEED_REWIND (n_unlinked_since_opendir_or_last_rewind))
1241             {
1242               /* Call rewinddir if we've called unlink or rmdir so many times
1243                  (since the opendir or the previous rewinddir) that this
1244                  NULL-return may be the symptom of a buggy readdir.  */
1245               rewinddir (*dirp);
1246               n_unlinked_since_opendir_or_last_rewind = 0;
1247               continue;
1248             }
1249           break;
1250         }
1251
1252       f = dp->d_name;
1253
1254       /* Skip files we've already tried/failed to remove.  */
1255       if ( ! AD_is_removable (ds, f))
1256         continue;
1257
1258       /* Pass dp->d_type info to remove_entry so the non-glibc
1259          case can decide whether to use unlink or chdir.
1260          Systems without the d_type member will have to endure
1261          the performance hit of first calling lstat F. */
1262       cache_stat_init (subdir_sb);
1263       tmp_status = remove_entry (dirfd (*dirp), ds, f,
1264                                  D_TYPE (dp), subdir_sb, x);
1265       switch (tmp_status)
1266         {
1267         case RM_OK:
1268           /* Count how many files we've unlinked since the initial
1269              opendir or the last rewinddir.  On buggy systems, if you
1270              remove too many, readdir returns NULL even though there
1271              remain unprocessed directory entries.  */
1272           ++n_unlinked_since_opendir_or_last_rewind;
1273           break;
1274
1275         case RM_ERROR:
1276         case RM_USER_DECLINED:
1277           AD_mark_as_unremovable (ds, f);
1278           UPDATE_STATUS (status, tmp_status);
1279           break;
1280
1281         case RM_NONEMPTY_DIR:
1282           {
1283             DIR *subdir_dirp = fd_to_subdirp (dirfd (*dirp), f,
1284                                               errno, subdir_sb, NULL);
1285             if (subdir_dirp == NULL)
1286               {
1287                 status = RM_ERROR;
1288
1289                 /* CAUTION: this test and diagnostic are identical to
1290                    those following the other use of fd_to_subdirp.  */
1291                 if (ignorable_missing (x, errno))
1292                   {
1293                     /* With -f, don't report "file not found".  */
1294                   }
1295                 else
1296                   {
1297                     /* Upon fd_to_subdirp failure, try to remove F directly,
1298                        in case it's just an empty directory.  */
1299                     int saved_errno = errno;
1300                     if (unlinkat (dirfd (*dirp), f, AT_REMOVEDIR) == 0)
1301                       status = RM_OK;
1302                     else
1303                       error (0, saved_errno,
1304                              _("cannot remove %s"), quote (full_filename (f)));
1305                   }
1306
1307                 if (status == RM_ERROR)
1308                   AD_mark_as_unremovable (ds, f);
1309                 break;
1310               }
1311
1312             *subdir = xstrdup (f);
1313             if (closedir (*dirp) != 0)
1314               {
1315                 error (0, 0, _("failed to close directory %s"),
1316                        quote (full_filename (".")));
1317                 status = RM_ERROR;
1318               }
1319             *dirp = subdir_dirp;
1320
1321             break;
1322           }
1323         }
1324
1325       /* Record status for this directory.  */
1326       UPDATE_STATUS (top->status, status);
1327
1328       if (*subdir)
1329         break;
1330     }
1331
1332   /* Ensure that *dirp is not NULL and that its file descriptor is valid.  */
1333   assert (*dirp != NULL);
1334   assert (0 <= fcntl (dirfd (*dirp), F_GETFD));
1335
1336   return status;
1337 }
1338
1339 /* Do this after each call to AD_push or AD_push_initial.
1340    Because the status = RM_OK bit is too remove-specific to
1341    go into the general-purpose AD_* package.  */
1342 #define AD_INIT_OTHER_MEMBERS()                 \
1343   do                                            \
1344     {                                           \
1345       AD_stack_top(ds)->status = RM_OK;         \
1346     }                                           \
1347   while (0)
1348
1349 /*  Remove the hierarchy rooted at DIR.
1350     Do that by changing into DIR, then removing its contents, then
1351     returning to the original working directory and removing DIR itself.
1352     Don't use recursion.  Be careful when using chdir ".." that we
1353     return to the same directory from which we came, if necessary.
1354     Return an RM_status value to indicate success or failure.  */
1355
1356 static enum RM_status
1357 remove_dir (int fd_cwd, Dirstack_state *ds, char const *dir,
1358             struct stat *dir_st,
1359             struct rm_options const *x, int *cwd_errno)
1360 {
1361   enum RM_status status;
1362   dev_t current_dev = dir_st->st_dev;
1363
1364   /* There is a race condition in that an attacker could replace the nonempty
1365      directory, DIR, with a symlink between the preceding call to rmdir
1366      (unlinkat, in our caller) and fd_to_subdirp's openat call.  But on most
1367      systems, even those without openat, this isn't a problem, since we ensure
1368      that opening a symlink will fail, when that is possible.  Otherwise,
1369      fd_to_subdirp's fstat, along with the `fstat' and the dev/ino
1370      comparison in AD_push ensure that we detect it and fail.  */
1371
1372   DIR *dirp = fd_to_subdirp (fd_cwd, dir, 0, dir_st, cwd_errno);
1373
1374   if (dirp == NULL)
1375     {
1376       /* CAUTION: this test and diagnostic are identical to
1377          those following the other use of fd_to_subdirp.  */
1378       if (ignorable_missing (x, errno))
1379         {
1380           /* With -f, don't report "file not found".  */
1381         }
1382       else
1383         {
1384           /* Upon fd_to_subdirp failure, try to remove DIR directly,
1385              in case it's just an empty directory.  */
1386           int saved_errno = errno;
1387           if (unlinkat (fd_cwd, dir, AT_REMOVEDIR) == 0)
1388             return RM_OK;
1389
1390           error (0, saved_errno,
1391                  _("cannot remove %s"), quote (full_filename (dir)));
1392         }
1393
1394       return RM_ERROR;
1395     }
1396
1397   if (ROOT_DEV_INO_CHECK (x->root_dev_ino, dir_st))
1398     {
1399       ROOT_DEV_INO_WARN (full_filename (dir));
1400       status = RM_ERROR;
1401       goto closedir_and_return;
1402     }
1403
1404   AD_push (dirfd (dirp), ds, dir, dir_st);
1405   AD_INIT_OTHER_MEMBERS ();
1406
1407   status = RM_OK;
1408
1409   while (1)
1410     {
1411       char *subdir = NULL;
1412       struct stat subdir_sb;
1413       enum RM_status tmp_status;
1414
1415       tmp_status = remove_cwd_entries (&dirp, ds, &subdir, &subdir_sb, x);
1416
1417       if (tmp_status != RM_OK)
1418         {
1419           UPDATE_STATUS (status, tmp_status);
1420           AD_mark_current_as_unremovable (ds);
1421         }
1422       if (subdir)
1423         {
1424           if ( ! x->one_file_system
1425                || subdir_sb.st_dev == current_dev)
1426             {
1427               AD_push (dirfd (dirp), ds, subdir, &subdir_sb);
1428               AD_INIT_OTHER_MEMBERS ();
1429               free (subdir);
1430               continue;
1431             }
1432
1433           /* Here, --one-file-system is in effect, and with remove_cwd_entries'
1434              traversal into the current directory, (known as SUBDIR, from ..),
1435              DIRP's device number is different from CURRENT_DEV.  Arrange not
1436              to do anything more with this hierarchy.  */
1437           error (0, 0, _("skipping %s, since it's on a different device"),
1438                  quote (full_filename (subdir)));
1439           free (subdir);
1440           AD_mark_current_as_unremovable (ds);
1441           tmp_status = RM_ERROR;
1442           UPDATE_STATUS (status, tmp_status);
1443         }
1444
1445       /* Execution reaches this point when we've removed the last
1446          removable entry from the current directory -- or, with
1447          --one-file-system, when the current directory is on a
1448          different file system.  */
1449       {
1450         int fd;
1451         /* The name of the directory that we have just processed,
1452            nominally removing all of its contents.  */
1453         char *empty_dir = AD_pop_and_chdir (dirp, &fd, ds);
1454         dirp = NULL;
1455         assert (fd != AT_FDCWD || AD_stack_height (ds) == 1);
1456
1457         /* Try to remove EMPTY_DIR only if remove_cwd_entries succeeded.  */
1458         if (tmp_status == RM_OK)
1459           {
1460             struct stat empty_st;
1461             Ternary is_empty;
1462             int dirent_type = DT_DIR;
1463             enum RM_status s = prompt (fd, ds, empty_dir, &dirent_type,
1464                                        cache_stat_init (&empty_st), x,
1465                                        PA_REMOVE_DIR, &is_empty);
1466
1467             if (s != RM_OK)
1468               {
1469                 free (empty_dir);
1470                 status = s;
1471                 if (fd != AT_FDCWD)
1472                   close (fd);
1473                 goto closedir_and_return;
1474               }
1475
1476             if (unlinkat (fd, empty_dir, AT_REMOVEDIR) == 0)
1477               {
1478                 if (x->verbose)
1479                   printf (_("removed directory: %s\n"),
1480                           quote (full_filename (empty_dir)));
1481               }
1482             else
1483               {
1484                 error (0, errno, _("cannot remove directory %s"),
1485                        quote (full_filename (empty_dir)));
1486                 AD_mark_as_unremovable (ds, empty_dir);
1487                 status = RM_ERROR;
1488                 UPDATE_STATUS (AD_stack_top(ds)->status, status);
1489               }
1490           }
1491
1492         free (empty_dir);
1493
1494         if (fd == AT_FDCWD)
1495           break;
1496
1497         dirp = fdopendir (fd);
1498         if (dirp == NULL)
1499           {
1500             error (0, errno, _("FATAL: cannot return to .. from %s"),
1501                    quote (full_filename (".")));
1502             close (fd);
1503             longjmp (ds->current_arg_jumpbuf, 1);
1504           }
1505       }
1506     }
1507
1508   /* If the first/final hash table of unremovable entries was used,
1509      free it here.  */
1510   AD_stack_pop (ds);
1511
1512  closedir_and_return:;
1513   if (dirp != NULL && closedir (dirp) != 0)
1514     {
1515       error (0, 0, _("failed to close directory %s"),
1516              quote (full_filename (".")));
1517       status = RM_ERROR;
1518     }
1519
1520   return status;
1521 }
1522
1523 /* Remove the file or directory specified by FILENAME.
1524    Return RM_OK if it is removed, and RM_ERROR or RM_USER_DECLINED if not.  */
1525
1526 static enum RM_status
1527 rm_1 (Dirstack_state *ds, char const *filename,
1528       struct rm_options const *x, int *cwd_errno)
1529 {
1530   char const *base = last_component (filename);
1531   if (dot_or_dotdot (base))
1532     {
1533       error (0, 0, _(base == filename
1534                      ? "cannot remove directory %s"
1535                      : "cannot remove %s directory %s"),
1536              quote_n (0, base), quote_n (1, filename));
1537       return RM_ERROR;
1538     }
1539
1540   struct stat st;
1541   cache_stat_init (&st);
1542   cycle_check_init (&ds->cycle_check_state);
1543   if (x->root_dev_ino)
1544     {
1545       if (cache_fstatat (AT_FDCWD, filename, &st, AT_SYMLINK_NOFOLLOW) != 0)
1546         {
1547           if (ignorable_missing (x, errno))
1548             return RM_OK;
1549           error (0, errno, _("cannot remove %s"), quote (filename));
1550           return RM_ERROR;
1551         }
1552       if (SAME_INODE (st, *(x->root_dev_ino)))
1553         {
1554           error (0, 0, _("cannot remove root directory %s"), quote (filename));
1555           return RM_ERROR;
1556         }
1557     }
1558
1559   AD_push_initial (ds);
1560   AD_INIT_OTHER_MEMBERS ();
1561
1562   enum RM_status status = remove_entry (AT_FDCWD, ds, filename,
1563                                         DT_UNKNOWN, &st, x);
1564   if (status == RM_NONEMPTY_DIR)
1565     {
1566       /* In the event that remove_dir->remove_cwd_entries detects
1567          a directory cycle, arrange to fail, give up on this FILE, but
1568          continue on with any other arguments.  */
1569       if (setjmp (ds->current_arg_jumpbuf))
1570         status = RM_ERROR;
1571       else
1572         status = remove_dir (AT_FDCWD, ds, filename, &st, x, cwd_errno);
1573
1574       AD_stack_clear (ds);
1575     }
1576
1577   ds_clear (ds);
1578   return status;
1579 }
1580
1581 /* Remove all files and/or directories specified by N_FILES and FILE.
1582    Apply the options in X.  */
1583 extern enum RM_status
1584 rm (size_t n_files, char const *const *file, struct rm_options const *x)
1585 {
1586   enum RM_status status = RM_OK;
1587   Dirstack_state *ds = ds_init ();
1588   int cwd_errno = 0;
1589   size_t i;
1590
1591   for (i = 0; i < n_files; i++)
1592     {
1593       if (cwd_errno && IS_RELATIVE_FILE_NAME (file[i]))
1594         {
1595           error (0, 0, _("cannot remove relative-named %s"), quote (file[i]));
1596           status = RM_ERROR;
1597         }
1598       else
1599         {
1600           enum RM_status s = rm_1 (ds, file[i], x, &cwd_errno);
1601           assert (VALID_STATUS (s));
1602           UPDATE_STATUS (status, s);
1603         }
1604     }
1605
1606   if (x->require_restore_cwd && cwd_errno)
1607     {
1608       error (0, cwd_errno,
1609              _("cannot restore current working directory"));
1610       status = RM_ERROR;
1611     }
1612
1613   ds_free (ds);
1614
1615   return status;
1616 }