108 lines
3.6 KiB
Diff
108 lines
3.6 KiB
Diff
ChangeLog | 10 ++++++++++
|
|
NEWS | 15 +++++++++++++++
|
|
find/ftsfind.c | 37 +++++++++++++++++++------------------
|
|
3 files changed, 44 insertions(+), 18 deletions(-)
|
|
|
|
diff --git a/ChangeLog b/ChangeLog
|
|
index fefc1b8..98d7962 100644
|
|
--- a/ChangeLog
|
|
+++ b/ChangeLog
|
|
@@ -1,5 +1,15 @@
|
|
2010-04-10 James Youngman <jay@gnu.org>
|
|
|
|
+ Fix Savannah bug #19593, -execdir .... {} + has suboptimal performance
|
|
+ * find/ftsfind.c (consider_visiting): Don't call
|
|
+ complete_pending_execdirs for every file we visit.
|
|
+ (find): Instead, call complete_pending_execdirs every time we
|
|
+ see a file which isn't at the same nesting level as the previous
|
|
+ file we saw. This is an improvement but not optimal (since
|
|
+ descending into a subdirectory will cause us to issue an exec
|
|
+ before we've finished with the current directory).
|
|
+ * NEWS: Mention this change.
|
|
+
|
|
Exec predicates now store which directory they want to run in.
|
|
* lib/dircallback.c (run_in_dirfd): New name for old run_in_dir
|
|
function.
|
|
diff --git a/NEWS b/NEWS
|
|
index 6b8b725..569ff51 100644
|
|
--- a/NEWS
|
|
+++ b/NEWS
|
|
@@ -1,5 +1,20 @@
|
|
GNU findutils NEWS - User visible changes. -*- outline -*- (allout)
|
|
|
|
+* Major changes in release 4.4.3-git, YYYY-MM-DD
|
|
+
|
|
+** Bug Fixes
|
|
+
|
|
+#19593: -execdir .... {} + has suboptimal performance (see below)
|
|
+
|
|
+** Performance changes
|
|
+
|
|
+The find program will once again build argument lists longer than 1
|
|
+with "-execdir ...+". The upper limit of 1 argument for execdir was
|
|
+introduced as a workaround in findutils-4.3.4. The limit is now
|
|
+removed, but find still does not issue the maximum possible number of
|
|
+arguments, since an exec will occur each time find encounters a
|
|
+subdirectory (if at least one argument is pending).
|
|
+
|
|
* Major changes in release 4.4.2, 2009-11-26
|
|
|
|
** Functional Enhancements to find
|
|
diff --git a/find/ftsfind.c b/find/ftsfind.c
|
|
index 9945abd..3c9ae1d 100644
|
|
--- a/find/ftsfind.c
|
|
+++ b/find/ftsfind.c
|
|
@@ -524,24 +524,6 @@ consider_visiting(FTS *p, FTSENT *ent)
|
|
visit(p, ent, &statbuf);
|
|
}
|
|
|
|
- /* XXX: if we allow a build-up of pending arguments for "-execdir foo {} +"
|
|
- * we need to execute them in the same directory as we found the item.
|
|
- * If we are trying to do "find a -execdir echo {} +", we will need to
|
|
- * echo
|
|
- * a while in the original working directory
|
|
- * b while in a
|
|
- * c while in b (just before leaving b)
|
|
- *
|
|
- * These restrictions are hard to satisfy while using fts(). The reason is
|
|
- * that it doesn't tell us just before we leave a directory. For the moment,
|
|
- * we punt and don't allow the arguments to build up.
|
|
- */
|
|
- if (state.execdirs_outstanding)
|
|
- {
|
|
- show_outstanding_execdirs(stderr);
|
|
- complete_pending_execdirs ();
|
|
- }
|
|
-
|
|
if (ent->fts_info == FTS_DP)
|
|
{
|
|
/* we're leaving a directory. */
|
|
@@ -591,8 +573,27 @@ find(char *arg)
|
|
}
|
|
else
|
|
{
|
|
+ int level = INT_MIN;
|
|
+
|
|
while ( (ent=fts_read(p)) != NULL )
|
|
{
|
|
+ if (state.execdirs_outstanding)
|
|
+ {
|
|
+ /* If we changed level, perform any outstanding
|
|
+ * execdirs. If we see a sequence of directory entries
|
|
+ * like this: fffdfffdfff, we could build a command line
|
|
+ * of 9 files, but this simple-minded implementation
|
|
+ * builds a command line for only 3 files at a time
|
|
+ * (since fts descends into the directories).
|
|
+ */
|
|
+ if ((int)ent->fts_level != level)
|
|
+ {
|
|
+ show_outstanding_execdirs (stderr);
|
|
+ complete_pending_execdirs ();
|
|
+ }
|
|
+ }
|
|
+ level = (int)ent->fts_level;
|
|
+
|
|
state.have_stat = false;
|
|
state.have_type = false;
|
|
state.type = 0;
|