I just fatfingered a ';' into a ',':

$ rm a.out, cc mind.c
rm: a.out,: No such file or directory
rm: cc: No such file or directory

In full POSIX-conformance I lost my mind.  Coincidentally I had an idea.
What do you think?


Index: bin/rm/rm.1
===================================================================
RCS file: /cvs/src/bin/rm/rm.1,v
retrieving revision 1.37
diff -u -p -r1.37 rm.1
--- bin/rm/rm.1 25 May 2014 19:07:36 -0000      1.37
+++ bin/rm/rm.1 17 Oct 2014 18:37:18 -0000
@@ -41,7 +41,7 @@
 .Nd remove directory entries
 .Sh SYNOPSIS
 .Nm rm
-.Op Fl dfiPRr
+.Op Fl dfxiPRr
 .Ar
 .Sh DESCRIPTION
 The
@@ -65,6 +65,17 @@ The
 .Fl f
 option overrides any previous
 .Fl i
+or
+.Fl x
+options.
+.It Fl x
+Exit immediately on error, instead of processing any remaining arguments.
+The
+.Fl x
+option overrides any previous
+.Fl f
+or
+.Fl i
 options.
 .It Fl i
 Request confirmation before attempting to remove each file, regardless of
@@ -74,6 +85,8 @@ The
 .Fl i
 option overrides any previous
 .Fl f
+or
+.Fl x
 options.
 .It Fl P
 Overwrite regular files before deleting them.
@@ -148,7 +161,7 @@ utility is compliant with the
 specification.
 .Pp
 The flags
-.Op Fl dP
+.Op Fl dxP
 are extensions to that specification.
 .Sh HISTORY
 An
Index: bin/rm/rm.c
===================================================================
RCS file: /cvs/src/bin/rm/rm.c,v
retrieving revision 1.29
diff -u -p -r1.29 rm.c
--- bin/rm/rm.c 21 May 2014 06:23:02 -0000      1.29
+++ bin/rm/rm.c 17 Oct 2014 18:37:18 -0000
@@ -40,6 +40,7 @@
 #include <errno.h>
 #include <fcntl.h>
 #include <fts.h>
+#include <stdarg.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
@@ -49,7 +50,7 @@
 
 extern char *__progname;
 
-int dflag, eval, fflag, iflag, Pflag, stdin_ok;
+int dflag, eval, fflag, xflag, iflag, Pflag, stdin_ok;
 
 int    check(char *, char *, struct stat *);
 void   checkdot(char **);
@@ -58,6 +59,8 @@ int   rm_overwrite(char *, struct stat *);
 int    pass(int, off_t, char *, size_t);
 void   rm_tree(char **);
 void   usage(void);
+void   warnerr(const char * fmt, ...);
+void   warnerrx(const char * fmt, ...);
 
 /*
  * rm --
@@ -74,7 +77,7 @@ main(int argc, char *argv[])
        setlocale(LC_ALL, "");
 
        Pflag = rflag = 0;
-       while ((ch = getopt(argc, argv, "dfiPRr")) != -1)
+       while ((ch = getopt(argc, argv, "dfxiPRr")) != -1)
                switch(ch) {
                case 'd':
                        dflag = 1;
@@ -82,10 +85,17 @@ main(int argc, char *argv[])
                case 'f':
                        fflag = 1;
                        iflag = 0;
+                       xflag = 0;
+                       break;
+               case 'x':
+                       fflag = 0;
+                       iflag = 0;
+                       xflag = 1;
                        break;
                case 'i':
                        fflag = 0;
                        iflag = 1;
+                       xflag = 0;
                        break;
                case 'P':
                        Pflag = 1;
@@ -146,7 +156,7 @@ rm_tree(char **argv)
                switch (p->fts_info) {
                case FTS_DNR:
                        if (!fflag || p->fts_errno != ENOENT) {
-                               warnx("%s: %s",
+                               warnerrx("%s: %s",
                                    p->fts_path, strerror(p->fts_errno));
                                eval = 1;
                        }
@@ -161,7 +171,7 @@ rm_tree(char **argv)
                        if (!needstat)
                                break;
                        if (!fflag || p->fts_errno != ENOENT) {
-                               warnx("%s: %s",
+                               warnerrx("%s: %s",
                                    p->fts_path, strerror(p->fts_errno));
                                eval = 1;
                        }
@@ -209,7 +219,7 @@ rm_tree(char **argv)
                            (fflag && errno == ENOENT))
                                continue;
                }
-               warn("%s", p->fts_path);
+               warnerr("%s", p->fts_path);
                eval = 1;
        }
        if (errno)
@@ -232,14 +242,14 @@ rm_file(char **argv)
                /* Assume if can't stat the file, can't unlink it. */
                if (lstat(f, &sb)) {
                        if (!fflag || errno != ENOENT) {
-                               warn("%s", f);
+                               warnerr("%s", f);
                                eval = 1;
                        }
                        continue;
                }
 
                if (S_ISDIR(sb.st_mode) && !dflag) {
-                       warnx("%s: is a directory", f);
+                       warnerrx("%s: is a directory", f);
                        eval = 1;
                        continue;
                }
@@ -253,7 +263,7 @@ rm_file(char **argv)
                        rval = unlink(f);
                }
                if (rval && (!fflag || errno != ENOENT)) {
-                       warn("%s", f);
+                       warnerr("%s", f);
                        eval = 1;
                }
        }
@@ -289,7 +299,8 @@ rm_overwrite(char *file, struct stat *sb
        if (!S_ISREG(sbp->st_mode))
                return (1);
        if (sbp->st_nlink > 1) {
-               warnx("%s (inode %llu): not overwritten due to multiple links",
+               warnerrx(
+                   "%s (inode %llu): not overwritten due to multiple links",
                    file, (unsigned long long)sbp->st_ino);
                return (0);
        }
@@ -317,7 +328,7 @@ rm_overwrite(char *file, struct stat *sb
        return (1);
 
 err:
-       warn("%s", file);
+       warnerr("%s", file);
        close(fd);
        eval = 1;
        free(buf);
@@ -401,7 +412,7 @@ checkdot(char **argv)
 
                if (ISDOT(p)) {
                        if (!complained++)
-                               warnx("\".\" and \"..\" may not be removed");
+                               warnerrx("\".\" and \"..\" may not be removed");
                        eval = 1;
                        for (save = t; (t[0] = t[1]) != NULL; ++t)
                                continue;
@@ -414,6 +425,32 @@ checkdot(char **argv)
 void
 usage(void)
 {
-       (void)fprintf(stderr, "usage: %s [-dfiPRr] file ...\n", __progname);
+       (void)fprintf(stderr, "usage: %s [-dfxiPRr] file ...\n", __progname);
        exit(1);
+}
+
+void
+warnerr(const char * fmt, ...)
+{
+       va_list ap;
+
+       va_start(ap, fmt);
+       if (xflag)
+               verr(EXIT_FAILURE, fmt, ap);
+       else
+               vwarn(fmt, ap);
+       va_end(ap);
+}
+
+void
+warnerrx(const char * fmt, ...)
+{
+       va_list ap;
+
+       va_start(ap, fmt);
+       if (xflag)
+               verrx(EXIT_FAILURE, fmt, ap);
+       else
+               vwarnx(fmt, ap);
+       va_end(ap);
 }

Reply via email to