X-Git-Url: https://mattmccutchen.net/rsync/rsync.git/blobdiff_plain/736a6a291cf0fc9ab9410f300174a70e868e4122..e03dfae507d291785d65f454b50a358a79113cfe:/flist.c diff --git a/flist.c b/flist.c index fcc6a53a..843cf9e4 100644 --- a/flist.c +++ b/flist.c @@ -66,6 +66,35 @@ static struct file_struct null_file; static void clean_flist(struct file_list *flist, int strip_root); + +static int show_build_progress_p(void) +{ + extern int do_progress; + + return do_progress && verbose && recurse && !am_server; +} + +/** + * True if we're local, etc, and should emit progress emssages. + **/ +static void emit_build_progress(const struct file_list *flist) +{ + rprintf(FINFO, + " %d files...\r", + flist->count); +} + + +static void finish_build_progress(const struct file_list *flist) +{ + if (verbose && recurse && !am_server) { + /* This overwrites the progress line, if any. */ + rprintf(FINFO, RSYNC_NAME ": %d files to consider.\n", + flist->count); + } +} + + static struct string_area *string_area_new(int size) { struct string_area *a; @@ -310,8 +339,8 @@ static void send_file_entry(struct file_struct *file,int f,unsigned base_flags) write_int(f,(int)file->inode); } else { /* 64-bit dev_t and ino_t */ - write_longint(f, (int64) file->dev); - write_longint(f, (int64) file->inode); + write_longint(f, file->dev); + write_longint(f, file->inode); } } #endif @@ -626,7 +655,10 @@ void send_file_name(int f,struct file_list *flist,char *fname, file = make_file(f,fname, &flist->string_area, 0); - if (!file) return; + if (!file) return; + + if (show_build_progress_p() & !(flist->count % 100)) + emit_build_progress(flist); if (flist->count >= flist->malloced) { if (flist->malloced < 1000) @@ -717,6 +749,11 @@ static void send_directory(int f,struct file_list *flist,char *dir) } +/* + * + * I *think* f==-1 means that the list should just be built in memory + * and not transmitted. But who can tell? -- mbp + */ struct file_list *send_file_list(int f,int argc,char *argv[]) { int i,l; @@ -727,7 +764,7 @@ struct file_list *send_file_list(int f,int argc,char *argv[]) int64 start_write; if (verbose && recurse && !am_server && f != -1) { - rprintf(FINFO,"building file list ... "); + rprintf(FINFO, RSYNC_NAME ": building file list...\n"); if (verbose > 1) rprintf(FINFO, "\n"); rflush(FINFO); @@ -850,8 +887,7 @@ struct file_list *send_file_list(int f,int argc,char *argv[]) send_file_entry(NULL,f,0); } - if (verbose && recurse && !am_server && f != -1) - rprintf(FINFO,"done\n"); + finish_build_progress(flist); clean_flist(flist, 0); @@ -982,6 +1018,10 @@ oom: } +/* + * XXX: This is currently the hottest function while building the file + * list, because building f_name()s every time is expensive. + **/ int file_compare(struct file_struct **f1,struct file_struct **f2) { if (!(*f1)->basename && !(*f2)->basename) return 0; @@ -1143,6 +1183,10 @@ static void clean_flist(struct file_list *flist, int strip_root) /* * return the full filename of a flist entry + * + * This function is too expensive at the moment, because it copies + * strings when often we only want to compare them. In any case, + * using strlcat is silly because it will walk the string repeatedly. */ char *f_name(struct file_struct *f) { @@ -1155,9 +1199,11 @@ char *f_name(struct file_struct *f) n = (n+1)%10; if (f->dirname) { - strlcpy(p, f->dirname, MAXPATHLEN); - strlcat(p, "/", MAXPATHLEN); - strlcat(p, f->basename, MAXPATHLEN); + int off; + + off = strlcpy(p, f->dirname, MAXPATHLEN); + off += strlcpy(p+off, "/", MAXPATHLEN-off); + off += strlcpy(p+off, f->basename, MAXPATHLEN-off); } else { strlcpy(p, f->basename, MAXPATHLEN); }