2004-10-18  Dmitry V. Levin  <ldv@altlinux.org>

	Implement "find -delete" action, based on patch from Douglas Siebert,
	http://marc.theaimsgroup.com/?l=bugtraq&m=87930069226479&w=2
	* find/parser.c (parse_delete): New function.
	(parse_table): Add parse_delete.
	(parse_help): Mention -delete option.
	* find/defs.h: Declare pred_delete.
	* find/pred.c (pred_delete): New function.
	(pred_table): Add pred_delete.
	* doc/find.texi, find/find.1: Document new option.

--- findutils-4.2.1.orig/doc/find.texi	2004-08-08 16:24:01 +0400
+++ findutils-4.2.1/doc/find.texi	2004-10-18 18:45:28 +0400
@@ -991,6 +991,7 @@
 * Print File Name::
 * Print File Information::
 * Run Commands::
+* Delete Files::
 * Adding Tests::
 @end menu
 
@@ -1602,6 +1603,15 @@
 with @samp{y} or @samp{Y}.  Implies @samp{-t}.
 @end table
 
+@node Delete Files
+@section Delete Files
+
+@deffn Action -delete
+Delete files; true if removal succeeded.
+
+The @samp{-delete} option implies @samp{-depth} option.
+@end deffn
+
 @node Adding Tests
 @section Adding Tests
 
--- findutils-4.2.1.orig/find/defs.h	2004-05-03 13:14:36 +0400
+++ findutils-4.2.1/find/defs.h	2004-10-18 18:53:34 +0400
@@ -348,6 +348,7 @@ boolean pred_cmin PARAMS((char *pathname
 boolean pred_cnewer PARAMS((char *pathname, struct stat *stat_buf, struct predicate *pred_ptr));
 boolean pred_comma PARAMS((char *pathname, struct stat *stat_buf, struct predicate *pred_ptr));
 boolean pred_ctime PARAMS((char *pathname, struct stat *stat_buf, struct predicate *pred_ptr));
+boolean pred_delete PARAMS((char *pathname, struct stat *stat_buf, struct predicate *pred_ptr));
 boolean pred_empty PARAMS((char *pathname, struct stat *stat_buf, struct predicate *pred_ptr));
 boolean pred_exec PARAMS((char *pathname, struct stat *stat_buf, struct predicate *pred_ptr));
 boolean pred_false PARAMS((char *pathname, struct stat *stat_buf, struct predicate *pred_ptr));
--- findutils-4.2.1.orig/find/find.1	2004-08-08 16:24:01 +0400
+++ findutils-4.2.1/find/find.1	2004-10-18 18:45:28 +0400
@@ -265,6 +265,8 @@
 `l'.  In other words, for symbolic links, \-xtype checks the type of
 the file that \-type does not check.
 .SS ACTIONS
+.IP "\-delete\fR"
+Delete files; true if removal succeeded.
 .IP "\-exec \fIcommand\fR ;"
 Execute \fIcommand\fR; true if 0 status is returned.  All following
 arguments to
--- findutils-4.2.1.orig/find/parser.c	2004-10-17 18:10:16 +0400
+++ findutils-4.2.1/find/parser.c	2004-10-18 18:53:34 +0400
@@ -67,6 +67,7 @@ static boolean parse_cnewer PARAMS((char
 static boolean parse_comma PARAMS((char *argv[], int *arg_ptr));
 static boolean parse_ctime PARAMS((char *argv[], int *arg_ptr));
 static boolean parse_daystart PARAMS((char *argv[], int *arg_ptr));
+static boolean parse_delete PARAMS((char *argv[], int *arg_ptr));
 static boolean parse_depth PARAMS((char *argv[], int *arg_ptr));
 static boolean parse_empty PARAMS((char *argv[], int *arg_ptr));
 static boolean parse_exec PARAMS((char *argv[], int *arg_ptr));
@@ -169,6 +170,7 @@ static struct parser_table const parse_t
 #endif
   {"ctime", parse_ctime},
   {"daystart", parse_daystart},	/* GNU */
+  {"delete", parse_delete},	/* GNU */
   {"depth", parse_depth},
   {"empty", parse_empty},	/* GNU */
   {"exec", parse_exec},
@@ -412,6 +414,20 @@ parse_daystart (char **argv, int *arg_pt
 }
 
 static boolean
+parse_delete (argv, arg_ptr)
+  char *argv[];
+  int *arg_ptr;
+{
+  struct predicate *our_pred;
+
+  our_pred = insert_primary (pred_delete);
+  our_pred->side_effects = true;
+  /* -delete implies -depth */
+  do_dir_first = false;
+  return (true);
+}
+
+static boolean
 parse_depth (char **argv, int *arg_ptr)
 {
   do_dir_first = false;
@@ -573,7 +589,7 @@ operators (decreasing precedence; -and i
       ( EXPR ) ! EXPR -not EXPR EXPR1 -a EXPR2 EXPR1 -and EXPR2\n"));
   puts (_("\
       EXPR1 -o EXPR2 EXPR1 -or EXPR2 EXPR1 , EXPR2\n\
-options (always true): -daystart -depth -follow --help\n\
+options (always true): -daystart -delete -depth -follow --help\n\
       -maxdepth LEVELS -mindepth LEVELS -mount -noleaf --version -xdev\n\
 tests (N can be +N or -N or N): -amin N -anewer FILE -atime N -cmin N"));
   puts (_("\
--- findutils-4.2.1.orig/find/pred.c	2004-10-02 15:05:38 +0400
+++ findutils-4.2.1/find/pred.c	2004-10-18 18:53:34 +0400
@@ -159,6 +159,7 @@ struct pred_assoc pred_table[] =
   {pred_cnewer, "cnewer  "},
   {pred_comma, ",       "},
   {pred_ctime, "ctime   "},
+  {pred_delete, "delete  "},
   {pred_empty, "empty   "},
   {pred_exec, "exec    "},
   {pred_false, "false   "},
@@ -403,6 +404,17 @@ pred_ctime (char *pathname, struct stat 
 }
 
 boolean
+pred_delete (pathname, stat_buf, pred_ptr)
+     char *pathname;
+     struct stat *stat_buf;
+     struct predicate *pred_ptr;
+{
+  if (strcmp (rel_pathname, "."))
+    return (remove (rel_pathname));
+  return (true);
+}
+
+boolean
 pred_empty (char *pathname, struct stat *stat_buf, struct predicate *pred_ptr)
 {
   if (S_ISDIR (stat_buf->st_mode))
