summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--fileio.c3
-rw-r--r--flist.c6
-rw-r--r--generator.c24
-rw-r--r--hlink.c3
-rw-r--r--ifuncs.h40
-rw-r--r--io.c2
-rw-r--r--lib/compat.c114
-rw-r--r--log.c12
-rw-r--r--main.c38
-rw-r--r--match.c13
-rw-r--r--options.c14
-rwxr-xr-xpackaging/var-checker7
-rw-r--r--progress.c8
-rw-r--r--receiver.c11
-rw-r--r--rsync.yo22
-rw-r--r--sender.c7
-rw-r--r--t_stub.c2
-rw-r--r--testsuite/daemon.test7
-rw-r--r--tls.c10
-rw-r--r--trimslash.c1
-rw-r--r--util.c18
-rw-r--r--wildtest.c1
-rw-r--r--xattrs.c2
23 files changed, 254 insertions, 111 deletions
diff --git a/fileio.c b/fileio.c
index 93cf5737..38f9eb4b 100644
--- a/fileio.c
+++ b/fileio.c
@@ -20,6 +20,7 @@
*/
#include "rsync.h"
+#include "ifuncs.h"
#ifndef ENODATA
#define ENODATA EAGAIN
@@ -233,7 +234,7 @@ char *map_ptr(struct map_struct *map, OFF_T offset, int32 len)
OFF_T ret = do_lseek(map->fd, read_start, SEEK_SET);
if (ret != read_start) {
rsyserr(FERROR, errno, "lseek returned %s, not %s",
- big_num(ret, 0), big_num(read_start, 0));
+ big_num(ret), big_num(read_start));
exit_cleanup(RERR_FILEIO);
}
map->p_fd_offset = read_start;
diff --git a/flist.c b/flist.c
index 92e89a26..7c64d86d 100644
--- a/flist.c
+++ b/flist.c
@@ -321,7 +321,7 @@ static void flist_expand(struct file_list *flist, int extra)
if (DEBUG_GTE(FLIST, 1) && flist->malloced != FLIST_START) {
rprintf(FCLIENT, "[%s] expand file_list pointer array to %s bytes, did%s move\n",
who_am_i(),
- big_num(sizeof flist->files[0] * flist->malloced, 0),
+ big_num(sizeof flist->files[0] * flist->malloced),
(new_ptr == flist->files) ? " not" : "");
}
@@ -488,7 +488,7 @@ static void send_file_entry(int f, const char *fname, struct file_struct *file,
} else if (DEBUG_GTE(HLINK, 3)) {
rprintf(FINFO, "[%s] dev:inode for #%d is %s:%s\n",
who_am_i(), first_ndx + ndx,
- big_num(tmp_dev, 0), big_num(tmp_ino, 0));
+ big_num(tmp_dev), big_num(tmp_ino));
}
}
} else {
@@ -2819,7 +2819,7 @@ static void output_flist(struct file_list *flist)
"[%s] i=%d %s %s%s%s%s mode=0%o len=%s%s%s flags=%x\n",
who, i + flist->ndx_start,
root, dir, slash, name, trail,
- (int)file->mode, big_num(F_LENGTH(file), 0),
+ (int)file->mode, comma_num(F_LENGTH(file)),
uidbuf, gidbuf, file->flags);
}
}
diff --git a/generator.c b/generator.c
index 80e9826d..af6f22a2 100644
--- a/generator.c
+++ b/generator.c
@@ -21,6 +21,7 @@
*/
#include "rsync.h"
+#include "ifuncs.h"
extern int dry_run;
extern int do_xfers;
@@ -53,6 +54,7 @@ extern int ignore_errors;
extern int remove_source_files;
extern int delay_updates;
extern int update_only;
+extern int human_readable;
extern int ignore_existing;
extern int ignore_non_existing;
extern int inplace;
@@ -806,8 +808,8 @@ static void sum_sizes_sqroot(struct sum_struct *sum, int64 len)
if (sum->count && DEBUG_GTE(DELTASUM, 2)) {
rprintf(FINFO,
"count=%s rem=%ld blength=%ld s2length=%d flength=%s\n",
- big_num(sum->count, 0), (long)sum->remainder, (long)sum->blength,
- sum->s2length, big_num(sum->flength, 0));
+ big_num(sum->count), (long)sum->remainder, (long)sum->blength,
+ sum->s2length, big_num(sum->flength));
}
}
@@ -858,7 +860,7 @@ static int generate_and_send_sums(int fd, OFF_T len, int f_out, int f_copy)
if (DEBUG_GTE(DELTASUM, 3)) {
rprintf(FINFO,
"chunk[%s] offset=%s len=%ld sum1=%08lx\n",
- big_num(i, 0), big_num(offset - n1, 0), (long)n1,
+ big_num(i), big_num(offset - n1), (long)n1,
(unsigned long)sum1);
}
write_int(f_out, sum1);
@@ -1199,6 +1201,7 @@ static void list_file_entry(struct file_struct *f)
{
char permbuf[PERMSTRING_SIZE];
int64 len;
+ int colwidth = human_readable ? 14 : 11;
if (!F_IS_ACTIVE(f)) {
/* this can happen if duplicate names were removed */
@@ -1212,15 +1215,16 @@ static void list_file_entry(struct file_struct *f)
#ifdef SUPPORT_LINKS
if (preserve_links && S_ISLNK(f->mode)) {
- rprintf(FINFO, "%s %11s %s %s -> %s\n",
- permbuf, big_num(len, 0), timestring(f->modtime),
- f_name(f, NULL), F_SYMLINK(f));
+ rprintf(FINFO, "%s %*s %s %s -> %s\n",
+ permbuf, colwidth, comma_num(len),
+ timestring(f->modtime), f_name(f, NULL),
+ F_SYMLINK(f));
} else
#endif
{
- rprintf(FINFO, "%s %11s %s %s\n",
- permbuf, big_num(len, 0), timestring(f->modtime),
- f_name(f, NULL));
+ rprintf(FINFO, "%s %*s %s %s\n",
+ permbuf, colwidth, comma_num(len),
+ timestring(f->modtime), f_name(f, NULL));
}
}
@@ -1905,7 +1909,7 @@ static void recv_generator(char *fname, struct file_struct *file, int ndx,
if (DEBUG_GTE(DELTASUM, 3)) {
rprintf(FINFO, "gen mapped %s of size %s\n",
- fnamecmp, big_num(sx.st.st_size, 0));
+ fnamecmp, big_num(sx.st.st_size));
}
if (DEBUG_GTE(DELTASUM, 2))
diff --git a/hlink.c b/hlink.c
index cdafa9fa..212f5153 100644
--- a/hlink.c
+++ b/hlink.c
@@ -21,6 +21,7 @@
*/
#include "rsync.h"
+#include "ifuncs.h"
extern int dry_run;
extern int list_only;
@@ -73,7 +74,7 @@ struct ht_int64_node *idev_find(int64 dev, int64 ino)
if (DEBUG_GTE(HLINK, 3)) {
rprintf(FINFO,
"[%s] created hashtable for dev %s\n",
- who_am_i(), big_num(dev, 0));
+ who_am_i(), big_num(dev));
}
}
} else
diff --git a/ifuncs.h b/ifuncs.h
index e032c67f..6562764e 100644
--- a/ifuncs.h
+++ b/ifuncs.h
@@ -67,6 +67,46 @@ d_name(struct dirent *di)
#endif
}
+static inline char *
+big_num(int64 num)
+{
+ return do_big_num(num, 0, NULL);
+}
+
+static inline char *
+comma_num(int64 num)
+{
+ extern int human_readable;
+ return do_big_num(num, human_readable != 0, NULL);
+}
+
+static inline char *
+human_num(int64 num)
+{
+ extern int human_readable;
+ return do_big_num(num, human_readable, NULL);
+}
+
+static inline char *
+big_dnum(double dnum, int decimal_digits)
+{
+ return do_big_dnum(dnum, 0, decimal_digits);
+}
+
+static inline char *
+comma_dnum(double dnum, int decimal_digits)
+{
+ extern int human_readable;
+ return do_big_dnum(dnum, human_readable != 0, decimal_digits);
+}
+
+static inline char *
+human_dnum(double dnum, int decimal_digits)
+{
+ extern int human_readable;
+ return do_big_dnum(dnum, human_readable, decimal_digits);
+}
+
static inline int
isDigit(const char *ptr)
{
diff --git a/io.c b/io.c
index 1752d86f..d3ae5368 100644
--- a/io.c
+++ b/io.c
@@ -626,7 +626,7 @@ static void whine_about_eof(int fd)
rprintf(FERROR, RSYNC_NAME ": connection unexpectedly closed "
"(%s bytes received so far) [%s]\n",
- big_num(stats.total_read, 0), who_am_i());
+ big_num(stats.total_read), who_am_i());
exit_cleanup(RERR_STREAMIO);
}
diff --git a/lib/compat.c b/lib/compat.c
index 494b64fc..20beeca3 100644
--- a/lib/compat.c
+++ b/lib/compat.c
@@ -20,6 +20,9 @@
*/
#include "rsync.h"
+#include "ifuncs.h"
+
+extern char number_separator;
#ifndef HAVE_STRDUP
char *strdup(char *s)
@@ -152,45 +155,112 @@ int sys_gettimeofday(struct timeval *tv)
#endif
}
+#define HUMANIFY(mult) \
+ do { \
+ if (num >= mult || num <= -mult) { \
+ double dnum = (double)num / mult; \
+ char units; \
+ if (num < 0) \
+ dnum = -dnum; \
+ if (dnum < mult) \
+ units = 'K'; \
+ else if ((dnum /= mult) < mult) \
+ units = 'M'; \
+ else if ((dnum /= mult) < mult) \
+ units = 'G'; \
+ else { \
+ dnum /= mult; \
+ units = 'T'; \
+ } \
+ if (num < 0) \
+ dnum = -dnum; \
+ snprintf(bufs[n], sizeof bufs[0], "%.2f%c", dnum, units); \
+ return bufs[n]; \
+ } \
+ } while (0)
+
/* Return the int64 number as a string. If the human_flag arg is non-zero,
- * we may output the number in K, M, or G units. We can return up to 4
- * buffers at a time. */
-char *big_num(int64 num, int human_flag)
+ * we may output the number in K, M, G, or T units. If we don't add a unit
+ * suffix, we will append the fract string, if it is non-NULL. We can
+ * return up to 4 buffers at a time. */
+char *do_big_num(int64 num, int human_flag, const char *fract)
{
static char bufs[4][128]; /* more than enough room */
static unsigned int n;
char *s;
+ int len, negated;
n = (n + 1) % (sizeof bufs / sizeof bufs[0]);
- if (human_flag) {
- char units = '\0';
- int mult = human_flag == 1 ? 1000 : 1024;
- double dnum = 0;
- if (num > mult*mult*mult) {
- dnum = (double)num / (mult*mult*mult);
- units = 'G';
- } else if (num > mult*mult) {
- dnum = (double)num / (mult*mult);
- units = 'M';
- } else if (num > mult) {
- dnum = (double)num / mult;
- units = 'K';
- }
- if (units) {
- snprintf(bufs[n], sizeof bufs[0], "%.2f%c", dnum, units);
- return bufs[n];
- }
+ if (human_flag > 1) {
+ if (human_flag == 2)
+ HUMANIFY(1000);
+ else
+ HUMANIFY(1024);
}
s = bufs[n] + sizeof bufs[0] - 1;
- *s = '\0';
+ if (fract) {
+ len = strlen(fract);
+ s -= len;
+ strlcpy(s, fract, len + 1);
+ } else
+ *s = '\0';
+
+ len = 0;
if (!num)
*--s = '0';
+ if (num < 0) {
+ /* A maximum-size negated number can't fit as a positive,
+ * so do one digit in negated form to start us off. */
+ *--s = (char)(-(num % 10)) + '0';
+ num = -(num / 10);
+ len++;
+ negated = 1;
+ } else
+ negated = 0;
+
while (num) {
+ if (human_flag) {
+ if (len == 3) {
+ *--s = number_separator;
+ len = 1;
+ } else
+ len++;
+ }
*--s = (char)(num % 10) + '0';
num /= 10;
}
+
+ if (negated)
+ *--s = '-';
+
return s;
}
+
+/* Return the double number as a string. If the human_flag option is > 1,
+ * we may output the number in K, M, G, or T units. The buffer we use for
+ * our result is either a single static buffer defined here, or a buffer
+ * we get from do_big_num(). */
+char *do_big_dnum(double dnum, int human_flag, int decimal_digits)
+{
+ static char tmp_buf[128];
+#if SIZEOF_INT64 >= 8
+ char *fract;
+
+ snprintf(tmp_buf, sizeof tmp_buf, "%.*f", decimal_digits, dnum);
+
+ if (!human_flag || (dnum < 1000.0 && dnum > -1000.0))
+ return tmp_buf;
+
+ for (fract = tmp_buf+1; isDigit(fract); fract++) {}
+
+ return do_big_num((int64)dnum, human_flag, fract);
+#else
+ /* A big number might lose digits converting to a too-short int64,
+ * so let's just return the raw double conversion. */
+ snprintf(tmp_buf, sizeof tmp_buf, "%.*f", decimal_digits, dnum);
+ return tmp_buf;
+#endif
+}
diff --git a/log.c b/log.c
index 6d66e20a..adf3a4ad 100644
--- a/log.c
+++ b/log.c
@@ -514,7 +514,7 @@ static void log_formatted(enum logcode code, const char *format, const char *op,
case 'l':
strlcat(fmt, "s", sizeof fmt);
snprintf(buf2, sizeof buf2, fmt,
- big_num(F_LENGTH(file), 0));
+ comma_num(F_LENGTH(file)));
n = buf2;
break;
case 'U':
@@ -631,7 +631,7 @@ static void log_formatted(enum logcode code, const char *format, const char *op,
initial_stats->total_read;
}
strlcat(fmt, "s", sizeof fmt);
- snprintf(buf2, sizeof buf2, fmt, big_num(b, 0));
+ snprintf(buf2, sizeof buf2, fmt, comma_num(b));
n = buf2;
break;
case 'c':
@@ -643,7 +643,7 @@ static void log_formatted(enum logcode code, const char *format, const char *op,
initial_stats->total_read;
}
strlcat(fmt, "s", sizeof fmt);
- snprintf(buf2, sizeof buf2, fmt, big_num(b, 0));
+ snprintf(buf2, sizeof buf2, fmt, comma_num(b));
n = buf2;
break;
case 'C':
@@ -854,9 +854,9 @@ void log_exit(int code, const char *file, int line)
{
if (code == 0) {
rprintf(FLOG,"sent %s bytes received %s bytes total size %s\n",
- big_num(stats.total_written, 0),
- big_num(stats.total_read, 0),
- big_num(stats.total_size, 0));
+ comma_num(stats.total_written),
+ comma_num(stats.total_read),
+ comma_num(stats.total_size));
} else if (am_server != 2) {
const char *name;
diff --git a/main.c b/main.c
index c32457d4..942fec36 100644
--- a/main.c
+++ b/main.c
@@ -35,7 +35,6 @@ extern int am_sender;
extern int am_daemon;
extern int inc_recurse;
extern int blocking_io;
-extern int human_readable;
extern int always_checksum;
extern int remove_source_files;
extern int output_needs_newline;
@@ -246,43 +245,42 @@ static void output_summary(void)
{
if (INFO_GTE(STATS, 2)) {
rprintf(FCLIENT, "\n");
- rprintf(FINFO,"Number of files: %d\n", stats.num_files);
- rprintf(FINFO,"Number of files transferred: %d\n",
- stats.num_transferred_files);
+ rprintf(FINFO,"Number of files: %s\n", comma_num(stats.num_files));
+ rprintf(FINFO,"Number of files transferred: %s\n",
+ comma_num(stats.num_transferred_files));
rprintf(FINFO,"Total file size: %s bytes\n",
- big_num(stats.total_size, human_readable));
+ human_num(stats.total_size));
rprintf(FINFO,"Total transferred file size: %s bytes\n",
- big_num(stats.total_transferred_size, human_readable));
+ human_num(stats.total_transferred_size));
rprintf(FINFO,"Literal data: %s bytes\n",
- big_num(stats.literal_data, human_readable));
+ human_num(stats.literal_data));
rprintf(FINFO,"Matched data: %s bytes\n",
- big_num(stats.matched_data, human_readable));
+ human_num(stats.matched_data));
rprintf(FINFO,"File list size: %s\n",
- big_num(stats.flist_size, human_readable));
+ human_num(stats.flist_size));
if (stats.flist_buildtime) {
rprintf(FINFO,
- "File list generation time: %.3f seconds\n",
- (double)stats.flist_buildtime / 1000);
+ "File list generation time: %s seconds\n",
+ comma_dnum((double)stats.flist_buildtime / 1000, 3));
rprintf(FINFO,
- "File list transfer time: %.3f seconds\n",
- (double)stats.flist_xfertime / 1000);
+ "File list transfer time: %s seconds\n",
+ comma_dnum((double)stats.flist_xfertime / 1000, 3));
}
rprintf(FINFO,"Total bytes sent: %s\n",
- big_num(total_written, human_readable));
+ human_num(total_written));
rprintf(FINFO,"Total bytes received: %s\n",
- big_num(total_read, human_readable));
+ human_num(total_read));
}
if (INFO_GTE(STATS, 1)) {
rprintf(FCLIENT, "\n");
rprintf(FINFO,
"sent %s bytes received %s bytes %s bytes/sec\n",
- big_num(total_written, human_readable),
- big_num(total_read, human_readable),
+ human_num(total_written), human_num(total_read),
human_dnum((total_written + total_read)/(0.5 + (endtime - starttime)), 2));
- rprintf(FINFO, "total size is %s speedup is %.2f%s\n",
- big_num(stats.total_size, human_readable),
- (double)stats.total_size / (total_written+total_read),
+ rprintf(FINFO, "total size is %s speedup is %s%s\n",
+ human_num(stats.total_size),
+ comma_dnum((double)stats.total_size / (total_written+total_read), 2),
write_batch < 0 ? " (BATCH ONLY)" : dry_run ? " (DRY RUN)" : "");
}
diff --git a/match.c b/match.c
index 7e9b611e..c459af84 100644
--- a/match.c
+++ b/match.c
@@ -20,6 +20,7 @@
*/
#include "rsync.h"
+#include "ifuncs.h"
extern int checksum_seed;
extern int append_mode;
@@ -111,7 +112,7 @@ static void matched(int f, struct sum_struct *s, struct map_struct *buf,
if (DEBUG_GTE(DELTASUM, 2) && i >= 0) {
rprintf(FINFO,
"match at %s last_match=%s j=%d len=%ld n=%ld\n",
- big_num(offset, 0), big_num(last_match, 0), i,
+ big_num(offset), big_num(last_match), i,
(long)s->sums[i].len, (long)n);
}
@@ -154,7 +155,7 @@ static void hash_search(int f,struct sum_struct *s,
if (DEBUG_GTE(DELTASUM, 2)) {
rprintf(FINFO, "hash search b=%ld len=%s\n",
- (long)s->blength, big_num(len, 0));
+ (long)s->blength, big_num(len));
}
k = (int32)MIN(len, (OFF_T)s->blength);
@@ -173,7 +174,7 @@ static void hash_search(int f,struct sum_struct *s,
if (DEBUG_GTE(DELTASUM, 3)) {
rprintf(FINFO, "hash search s->blength=%ld len=%s count=%s\n",
- (long)s->blength, big_num(len, 0), big_num(s->count, 0));
+ (long)s->blength, big_num(len), big_num(s->count));
}
do {
@@ -182,7 +183,7 @@ static void hash_search(int f,struct sum_struct *s,
if (DEBUG_GTE(DELTASUM, 4)) {
rprintf(FINFO, "offset=%s sum=%04x%04x\n",
- big_num(offset, 0), s2 & 0xFFFF, s1 & 0xFFFF);
+ big_num(offset), s2 & 0xFFFF, s1 & 0xFFFF);
}
if (tablesize == TRADITIONAL_TABLESIZE) {
@@ -216,7 +217,7 @@ static void hash_search(int f,struct sum_struct *s,
if (DEBUG_GTE(DELTASUM, 3)) {
rprintf(FINFO,
"potential match at %s i=%ld sum=%08x\n",
- big_num(offset, 0), (long)i, sum);
+ big_num(offset), (long)i, sum);
}
if (!done_csum2) {
@@ -413,5 +414,5 @@ void match_report(void)
rprintf(FINFO,
"total: matches=%d hash_hits=%d false_alarms=%d data=%s\n",
total_matches, total_hash_hits, total_false_alarms,
- big_num(stats.literal_data, 0));
+ big_num(stats.literal_data));
}
diff --git a/options.c b/options.c
index 11860cbc..e0a84017 100644
--- a/options.c
+++ b/options.c
@@ -93,7 +93,7 @@ int filesfrom_fd = -1;
char *filesfrom_host = NULL;
int eol_nulls = 0;
int protect_args = 0;
-int human_readable = 0;
+int human_readable = 1;
int recurse = 0;
int allow_inc_recurse = 1;
int xfer_dirs = -1;
@@ -121,6 +121,7 @@ int checksum_seed = 0;
int inplace = 0;
int delay_updates = 0;
long block_size = 0; /* "long" because popt can't set an int32. */
+char number_separator;
char *skip_compress = NULL;
item_list dparam_list = EMPTY_ITEM_LIST;
@@ -1669,7 +1670,7 @@ int parse_arguments(int *argc_p, const char ***argv_p)
}
}
- if (human_readable && argc == 2 && !am_server) {
+ if (human_readable > 1 && argc == 2 && !am_server) {
/* Allow the old meaning of 'h' (--help) on its own. */
usage(FINFO);
exit_cleanup(0);
@@ -1682,6 +1683,15 @@ int parse_arguments(int *argc_p, const char ***argv_p)
verbose > 1 ? "stats3" : "stats2", DEFAULT_PRIORITY);
}
+ if (human_readable) {
+ char buf[32];
+ snprintf(buf, sizeof buf, "%f", 3.14);
+ if (strchr(buf, '.') != NULL)
+ number_separator = ',';
+ else
+ number_separator = '.';
+ }
+
#ifdef ICONV_OPTION
if (iconv_opt && protect_args != 2) {
if (!am_server && strcmp(iconv_opt, "-") == 0)
diff --git a/packaging/var-checker b/packaging/var-checker
index b63428b7..445bea0e 100755
--- a/packaging/var-checker
+++ b/packaging/var-checker
@@ -6,6 +6,7 @@
use strict;
my %add_syscall_c = map { $_ => 1 } qw( t_stub.c t_unsafe.c tls.c trimslash.c );
+my %add_compat_c = map { $_ => 1 } qw( t_stub.c tls.c trimslash.c wildtest.c );
my %add_util_c = map { $_ => 1 } qw( t_stub.c t_unsafe.c );
my %sizes;
@@ -14,6 +15,11 @@ undef $/; my $syscall_c = <IN>; $/ = "\n";
close IN;
$syscall_c =~ s/^extern\s.*//mg;
+open(IN, '<', 'lib/compat.c') or die $!;
+undef $/; my $compat_c = <IN>; $/ = "\n";
+close IN;
+$compat_c =~ s/^extern\s.*//mg;
+
open(IN, '<', 'util.c') or die $!;
undef $/; my $util_c = <IN>; $/ = "\n";
close IN;
@@ -30,6 +36,7 @@ foreach my $fn (@files) {
my @externs = /^extern\s+(.*);/mg;
$_ .= $syscall_c if $add_syscall_c{$fn};
+ $_ .= $compat_c if $add_compat_c{$fn};
$_ .= $util_c if $add_util_c{$fn};
s/INFO_GTE/info_levels/g;
s/DEBUG_GTE/debug_levels/g;
diff --git a/progress.c b/progress.c
index b09ca118..5d445a13 100644
--- a/progress.c
+++ b/progress.c
@@ -21,11 +21,11 @@
*/
#include "rsync.h"
+#include "ifuncs.h"
extern int am_server;
extern int need_unsorted_flist;
extern int output_needs_newline;
-extern int human_readable;
extern struct stats stats;
extern struct file_list *cur_flist;
@@ -72,7 +72,7 @@ static void rprint_progress(OFF_T ofs, OFF_T size, struct timeval *now,
if (is_last) {
int len = snprintf(eol, sizeof eol,
- " (xfer#%d, to-check=%d/%d)\n",
+ " (xfr#%d, to-chk=%d/%d)\n",
stats.num_transferred_files,
stats.num_files - current_file_index - 1,
stats.num_files);
@@ -124,8 +124,8 @@ static void rprint_progress(OFF_T ofs, OFF_T size, struct timeval *now,
output_needs_newline = 0;
pct = ofs == size ? 100 : (int) (100.0 * ofs / size);
- rprintf(FCLIENT, "\r%12s %3d%% %7.2f%s %s%s",
- big_num(ofs, human_readable), pct, rate, units, rembuf, eol);
+ rprintf(FCLIENT, "\r%15s %3d%% %7.2f%s %s%s",
+ human_num(ofs), pct, rate, units, rembuf, eol);
if (!is_last) {
output_needs_newline = 1;
rflush(FCLIENT);
diff --git a/receiver.c b/receiver.c
index 4f5463a9..9b353f56 100644
--- a/receiver.c
+++ b/receiver.c
@@ -20,6 +20,7 @@
*/
#include "rsync.h"
+#include "ifuncs.h"
extern int dry_run;
extern int do_xfers;
@@ -181,7 +182,7 @@ static int receive_data(int f_in, char *fname_r, int fd_r, OFF_T size_r,
mapbuf = map_file(fd_r, size_r, read_size, sum.blength);
if (DEBUG_GTE(DELTASUM, 2)) {
rprintf(FINFO, "recv mapped %s of size %s\n",
- fname_r, big_num(size_r, 0));
+ fname_r, big_num(size_r));
}
} else
mapbuf = NULL;
@@ -211,7 +212,7 @@ static int receive_data(int f_in, char *fname_r, int fd_r, OFF_T size_r,
offset = sum.flength;
if (fd != -1 && (j = do_lseek(fd, offset, SEEK_SET)) != offset) {
rsyserr(FERROR_XFER, errno, "lseek of %s returned %s, not %s",
- full_fname(fname), big_num(j, 0), big_num(offset, 0));
+ full_fname(fname), big_num(j), big_num(offset));
exit_cleanup(RERR_FILEIO);
}
}
@@ -223,7 +224,7 @@ static int receive_data(int f_in, char *fname_r, int fd_r, OFF_T size_r,
if (i > 0) {
if (DEBUG_GTE(DELTASUM, 3)) {
rprintf(FINFO,"data recv %d at %s\n",
- i, big_num(offset, 0));
+ i, big_num(offset));
}
stats.literal_data += i;
@@ -248,7 +249,7 @@ static int receive_data(int f_in, char *fname_r, int fd_r, OFF_T size_r,
if (DEBUG_GTE(DELTASUM, 3)) {
rprintf(FINFO,
"chunk[%d] of size %ld at %s offset=%s\n",
- i, (long)len, big_num(offset2, 0), big_num(offset, 0));
+ i, (long)len, big_num(offset2), big_num(offset));
}
if (mapbuf) {
@@ -268,7 +269,7 @@ static int receive_data(int f_in, char *fname_r, int fd_r, OFF_T size_r,
rsyserr(FERROR_XFER, errno,
"lseek of %s returned %s, not %s",
full_fname(fname),
- big_num(pos, 0), big_num(offset, 0));
+ big_num(pos), big_num(offset));
exit_cleanup(RERR_FILEIO);
}
continue;
diff --git a/rsync.yo b/rsync.yo
index efa99904..79cbf07d 100644
--- a/rsync.yo
+++ b/rsync.yo
@@ -1918,10 +1918,24 @@ would output as "\#012". A literal backslash that is in a filename is not
escaped unless it is followed by a hash and 3 digits (0-9).
dit(bf(-h, --human-readable)) Output numbers in a more human-readable format.
-This makes big numbers output using larger units, with a K, M, or G suffix. If
-this option was specified once, these units are K (1000), M (1000*1000), and
-G (1000*1000*1000); if the option is repeated, the units are powers of 1024
-instead of 1000.
+There are 3 possible levels: (1) output numbers with a separator between each
+set of 3 digits (either a comma or a period, depending on if the decimal point
+is represented by a period or a comma); (2) output numbers in units of 1000
+(with a character suffix for larger units -- see below); (3) output numbers in
+units of 1024.
+
+The default is human-readable level 1. Each bf(-h) option increases the level
+by one. You can take the level down to 0 (to output numbers as pure digits) by
+specifing the bf(--no-human-readable) (bf(--no-h)) option.
+
+The unit letters that are appended in levels 2 and 3 are: K (kilo), M (mega),
+G (giga), or T (tera). For example, a 1234567-byte file would output as 1.23M
+in level-2 (assuming that a period is your local decimal point).
+
+Backward compatibility note: versions of rsync prior to 3.1.0 do not support
+human-readable level 1, and they default to level 0. Thus, specifying one or
+two bf(-h) options behaves the same in old and new versions as long as you
+didn't specify a bf(--no-h) option prior to one or more bf(-h) options.
dit(bf(--partial)) By default, rsync will delete any partially
transferred file if the transfer is interrupted. In some circumstances
diff --git a/sender.c b/sender.c
index ba1d6ffa..2919e553 100644
--- a/sender.c
+++ b/sender.c
@@ -20,6 +20,7 @@
*/
#include "rsync.h"
+#include "ifuncs.h"
extern int dry_run;
extern int do_xfers;
@@ -71,7 +72,7 @@ static struct sum_struct *receive_sums(int f)
if (DEBUG_GTE(DELTASUM, 3)) {
rprintf(FINFO, "count=%s n=%ld rem=%ld\n",
- big_num(s->count, 0), (long)s->blength, (long)s->remainder);
+ big_num(s->count), (long)s->blength, (long)s->remainder);
}
if (append_mode > 0) {
@@ -106,7 +107,7 @@ static struct sum_struct *receive_sums(int f)
if (DEBUG_GTE(DELTASUM, 3)) {
rprintf(FINFO,
"chunk[%d] len=%d offset=%s sum1=%08x\n",
- i, s->sums[i].len, big_num(s->sums[i].offset, 0),
+ i, s->sums[i].len, big_num(s->sums[i].offset),
s->sums[i].sum1);
}
}
@@ -319,7 +320,7 @@ void send_files(int f_in, int f_out)
if (DEBUG_GTE(DELTASUM, 2)) {
rprintf(FINFO, "send_files mapped %s%s%s of size %s\n",
- path,slash,fname, big_num(st.st_size, 0));
+ path,slash,fname, big_num(st.st_size));
}
write_ndx_and_attrs(f_out, ndx, iflags, fname, file,
diff --git a/t_stub.c b/t_stub.c
index 6a205fa3..d00d4374 100644
--- a/t_stub.c
+++ b/t_stub.c
@@ -24,10 +24,10 @@
int modify_window = 0;
int module_id = -1;
int relative_paths = 0;
-int human_readable = 0;
int module_dirlen = 0;
int preserve_xattrs = 0;
mode_t orig_umask = 002;
+char number_separator = ',';
char *partial_dir;
char *module_dir;
struct filter_list_struct daemon_filter_list;
diff --git a/testsuite/daemon.test b/testsuite/daemon.test
index 113d6a59..2d003530 100644
--- a/testsuite/daemon.test
+++ b/testsuite/daemon.test
@@ -25,7 +25,8 @@ chkfile="$scratchdir/rsync.chk"
outfile="$scratchdir/rsync.out"
SSH="src/support/lsh --no-cd"
-DIR_REPL='s/^\(d[^ ]*\) *[0-9][0-9]* /\1 DIR /'
+FILE_REPL='s/^\([^d][^ ]*\) *\(..........[0-9]\) /\1 \2 /'
+DIR_REPL='s/^\(d[^ ]*\) *[0-9][.,0-9]* /\1 DIR /'
LS_REPL='s;[0-9][0-9][0-9][0-9]/[0-9][0-9]/[0-9][0-9] [0-9][0-9]:[0-9][0-9]:[0-9][0-9];####/##/## ##:##:##;'
build_rsyncd_conf
@@ -65,7 +66,7 @@ EOT
diff $diffopt "$chkfile" "$outfile" || test_fail "test 1 failed"
$RSYNC -r localhost::test-hidden \
- | sed "$DIR_REPL" | sed "$LS_REPL" \
+ | sed "$FILE_REPL" | sed "$DIR_REPL" | sed "$LS_REPL" \
| tee "$outfile"
cat <<EOT >"$chkfile"
drwxr-xr-x DIR ####/##/## ##:##:## .
@@ -79,7 +80,7 @@ EOT
diff $diffopt "$chkfile" "$outfile" || test_fail "test 2 failed"
$RSYNC -r localhost::test-from/f* \
- | sed "$DIR_REPL" | sed "$LS_REPL" \
+ | sed "$FILE_REPL" | sed "$DIR_REPL" | sed "$LS_REPL" \
| tee "$outfile"
cat <<EOT >"$chkfile"
drwxr-xr-x DIR ####/##/## ##:##:## foo
diff --git a/tls.c b/tls.c
index c01bdc88..501a9326 100644
--- a/tls.c
+++ b/tls.c
@@ -49,6 +49,7 @@ int link_times = 0;
int link_owner = 0;
int preserve_perms = 0;
int preserve_executability = 0;
+char number_separator;
#ifdef SUPPORT_XATTRS
@@ -180,7 +181,7 @@ static void list_file(const char *fname)
(long)major(buf.st_rdev),
(long)minor(buf.st_rdev));
} else
- printf("%12s", big_num(buf.st_size, 0));
+ printf("%15s", do_big_num(buf.st_size, 1, NULL));
printf(" %6ld.%-6ld %6ld %s %s%s\n",
(long)buf.st_uid, (long)buf.st_gid, (long)buf.st_nlink,
datebuf, fname, linkbuf);
@@ -217,6 +218,7 @@ main(int argc, char *argv[])
{
poptContext pc;
const char **extra_args;
+ char buf[32];
int opt;
pc = poptGetContext(PROGRAM, argc, (const char **)argv,
@@ -238,6 +240,12 @@ main(int argc, char *argv[])
if (!extra_args || *extra_args == NULL)
tls_usage(1);
+ snprintf(buf, sizeof buf, "%f", 3.14);
+ if (strchr(buf, '.') != NULL)
+ number_separator = ',';
+ else
+ number_separator = '.';
+
for (; *extra_args; extra_args++)
list_file(*extra_args);
poptFreeContext(pc);
diff --git a/trimslash.c b/trimslash.c
index e5cf2f4c..40f2eb9b 100644
--- a/trimslash.c
+++ b/trimslash.c
@@ -27,6 +27,7 @@ int read_only = 1;
int list_only = 0;
int preserve_perms = 0;
int preserve_executability = 0;
+char number_separator = ',';
int
main(int argc, char **argv)
diff --git a/util.c b/util.c
index 4b6c11fd..e3402845 100644
--- a/util.c
+++ b/util.c
@@ -27,7 +27,6 @@ extern int dry_run;
extern int module_id;
extern int modify_window;
extern int relative_paths;
-extern int human_readable;
extern int preserve_xattrs;
extern char *module_dir;
extern unsigned int module_dirlen;
@@ -1192,21 +1191,6 @@ int unsafe_symlink(const char *dest, const char *src)
return (depth < 0);
}
-/* Return the double number as a string. If the --human-readable option was
- * specified, we may output the number in K, M, or G units. We use a buffer
- * from big_num() to return our result. */
-char *human_dnum(double dnum, int decimal_digits)
-{
- char *buf = big_num(dnum, human_readable);
- int len = strlen(buf);
- if (isDigit(buf + len - 1)) {
- /* There's extra room in buf prior to the start of the num. */
- buf -= decimal_digits + 1;
- snprintf(buf, len + decimal_digits + 2, "%.*f", decimal_digits, dnum);
- }
- return buf;
-}
-
/* Return the date and time as a string. Some callers tweak returned buf. */
char *timestring(time_t t)
{
@@ -1545,7 +1529,7 @@ void *expand_item_list(item_list *lp, size_t item_size,
new_ptr = _realloc_array(lp->items, item_size, new_size);
if (DEBUG_GTE(FLIST, 3)) {
rprintf(FINFO, "[%s] expand %s to %s bytes, did%s move\n",
- who_am_i(), desc, big_num(new_size * item_size, 0),
+ who_am_i(), desc, big_num(new_size * item_size),
new_ptr == lp->items ? " not" : "");
}
if (!new_ptr)
diff --git a/wildtest.c b/wildtest.c
index efda5d6e..1692efe9 100644
--- a/wildtest.c
+++ b/wildtest.c
@@ -31,6 +31,7 @@ int fnmatch_errors = 0;
#endif
int wildmatch_errors = 0;
+char number_separator = ',';
typedef char bool;
diff --git a/xattrs.c b/xattrs.c
index 051c08d9..2855e583 100644
--- a/xattrs.c
+++ b/xattrs.c
@@ -136,7 +136,7 @@ static ssize_t get_xattr_names(const char *fname)
got_error:
rsyserr(FERROR_XFER, errno,
"get_xattr_names: llistxattr(\"%s\",%s) failed",
- fname, big_num(arg, 0));
+ fname, big_num(arg));
return -1;
}
list_len = sys_llistxattr(fname, NULL, 0);