diff options
author | Pádraig Brady <P@draigBrady.com> | 2010-12-30 01:36:59 +0000 |
---|---|---|
committer | Pádraig Brady <P@draigBrady.com> | 2010-12-30 16:26:20 +0000 |
commit | 44dbcae6b98700617d4d3cb8d799ce83d538e3e7 (patch) | |
tree | ffeea8e1488a96e5d3baa713d2b29e9afa3c0566 | |
parent | b0097f3d2180352896a4434fb8eaeb076f12794c (diff) | |
download | coreutils-44dbcae6b98700617d4d3cb8d799ce83d538e3e7.tar.xz |
split: fix the suffix length calculation
* src/split.c (set_suffix_length): Only auto-calculate
the suffix length when the number of files is specified.
* tests/misc/split-a: Add a case to trigger the bug,
and exercise the suffix length auto-calculation.
* NEWS: Mention the fix.
Reported by Dmitry V. Levin and Sergey Vlasov at
https://bugzilla.altlinux.org/show_bug.cgi?id=24841
-rw-r--r-- | NEWS | 6 | ||||
-rw-r--r-- | THANKS | 1 | ||||
-rw-r--r-- | src/split.c | 33 | ||||
-rwxr-xr-x | tests/misc/split-a | 10 |
4 files changed, 38 insertions, 12 deletions
@@ -2,6 +2,12 @@ GNU coreutils NEWS -*- outline -*- * Noteworthy changes in release ?.? (????-??-??) [?] +** Bug fixes + + split no longer creates files with a suffix length that + is dependent on the number of bytes or lines per file. + [bug introduced in coreutils-8.8] + * Noteworthy changes in release 8.8 (2010-12-22) [stable] @@ -553,6 +553,7 @@ Scott Harrison scott.gnu.2009@scottrix.co.uk Scott Lurndal slurn@griffin.engr.sgi.com Sébastien Maret smaret@umich.edu Sergei Steshenko sergstesh@yahoo.com +Sergey Vlasov vsu@altlinux.org Shing-Shong Shei shei@cs.indiana.edu Soeren Sonnenburg sonnenburg@informatik.hu-berlin.de Solar Designer solar@owl.openwall.com diff --git a/src/split.c b/src/split.c index ae98bc76a..a5eda153d 100644 --- a/src/split.c +++ b/src/split.c @@ -78,6 +78,13 @@ static bool elide_empty_files; input to output, which is much slower, so disabled by default. */ static bool unbuffered; +/* The split mode to use. */ +enum Split_type +{ + type_undef, type_bytes, type_byteslines, type_lines, type_digits, + type_chunk_bytes, type_chunk_lines, type_rr +}; + /* For long options that have no equivalent short option, use a non-character as a pseudo short option, starting with CHAR_MAX + 1. */ enum @@ -105,16 +112,22 @@ static struct option const longopts[] = }; static void -set_suffix_length (uintmax_t n_units) +set_suffix_length (uintmax_t n_units, enum Split_type split_type) { #define DEFAULT_SUFFIX_LENGTH 2 size_t suffix_needed = 0; - size_t alphabet_len = strlen (suffix_alphabet); - bool alphabet_slop = (n_units % alphabet_len) != 0; - while (n_units /= alphabet_len) - suffix_needed++; - suffix_needed += alphabet_slop; + + /* Auto-calculate the suffix length if the number of files is given. */ + if (split_type == type_chunk_bytes || split_type == type_chunk_lines + || split_type == type_rr) + { + size_t alphabet_len = strlen (suffix_alphabet); + bool alphabet_slop = (n_units % alphabet_len) != 0; + while (n_units /= alphabet_len) + suffix_needed++; + suffix_needed += alphabet_slop; + } if (suffix_length) /* set by user */ { @@ -780,11 +793,7 @@ int main (int argc, char **argv) { struct stat stat_buf; - enum - { - type_undef, type_bytes, type_byteslines, type_lines, type_digits, - type_chunk_bytes, type_chunk_lines, type_rr - } split_type = type_undef; + enum Split_type split_type = type_undef; size_t in_blk_size = 0; /* optimal block size of input file device */ char *buf; /* file i/o buffer */ size_t page_size = getpagesize (); @@ -984,7 +993,7 @@ main (int argc, char **argv) usage (EXIT_FAILURE); } - set_suffix_length (n_units); + set_suffix_length (n_units, split_type); /* Get out the filename arguments. */ diff --git a/tests/misc/split-a b/tests/misc/split-a index d861b9291..08d313efd 100755 --- a/tests/misc/split-a +++ b/tests/misc/split-a @@ -63,4 +63,14 @@ for f in $files; do n=$(expr $n + 1) done +# Ensure that -a is independent of -[bCl] +split -a2 -b1000 < /dev/null || fail=1 +split -a2 -l1000 < /dev/null || fail=1 +split -a2 -C1000 < /dev/null || fail=1 + +# Ensure that -a fails early with a -n that is too large +rm -f x* +split -a2 -n1000 < /dev/null && fail=1 +test -f xaa && fail=1 + Exit $fail |