From b03f5162ac239c3743cfac246b3760b0020f4d23 Mon Sep 17 00:00:00 2001 From: Denys Vlasenko Date: Fri, 20 Dec 2024 22:12:33 +0100 Subject: cut: fix up -D/-s behavior with -F function old new delta cut_main 1388 1402 +14 packed_usage 34934 34933 -1 ------------------------------------------------------------------------------ (add/remove: 0/0 grow/shrink: 1/1 up/down: 14/-1) Total: 13 bytes Signed-off-by: Denys Vlasenko --- coreutils/cut.c | 6 +++--- testsuite/cut.tests | 35 +++++++++++++++++++++++++++++++++-- 2 files changed, 36 insertions(+), 5 deletions(-) diff --git a/coreutils/cut.c b/coreutils/cut.c index a766db40f..65e0e5c30 100644 --- a/coreutils/cut.c +++ b/coreutils/cut.c @@ -43,7 +43,7 @@ //usage: "\n -F LIST Print only these fields (-d is regex)" //usage: ) //usage: "\n -s Drop lines with no delimiter (else print them in full)" -//usage: "\n -D Don't sort/collate sections or match -f"IF_FEATURE_CUT_REGEX("F")" lines without delimeter" +//usage: "\n -D Don't sort ranges; line without delimiters has one field" //usage: IF_LONG_OPTS( //usage: "\n --output-delimiter SEP Output field delimeter" //usage: ) IF_NOT_LONG_OPTS( @@ -202,8 +202,8 @@ static void cut_file(FILE *file, const char *delim, const char *odelim, /* End of current line? */ if (next == linelen) { end = linelen; /* print up to end */ - /* If we've seen no delimiters, check -s */ - if (cl_pos == 0 && dcount == 0 && !opt_REGEX) { + /* If we've seen no delimiters, and no -D, check -s */ + if (!(option_mask32 & OPT_NOSORT) && cl_pos == 0 && dcount == 0) { if (option_mask32 & OPT_SUPPRESS) goto next_line; /* else: will print entire line */ diff --git a/testsuite/cut.tests b/testsuite/cut.tests index e57b028ac..21cfea809 100755 --- a/testsuite/cut.tests +++ b/testsuite/cut.tests @@ -95,8 +95,16 @@ testing "cut with -d -s omits blank lines" "cut -d' ' -f2 -s input" "bar\nbong\n # substitute for awk optional FEATURE_CUT_REGEX -testing "cut -DF" "cut -DF 2,7,5" \ - "said and your\nare\nis demand. supply\nforecast :\nyou you better,\n\nEm: Took hate\n" "" \ +testing "cut -DF unordered" "cut -DF 2,7,5" \ + "\ +said and your +are +is demand. supply +forecast : +you you better, + +Em: Took hate +" "" \ "Bother, said Pooh. It's your husband, and he has a gun. Cheerios are donut seeds. Talk is cheap because supply exceeds demand. @@ -105,6 +113,29 @@ Apple: you can buy better, but you can't pay more. Subcalifragilisticexpialidocious. Auntie Em: Hate you, hate Kansas. Took the dog. Dorothy." +# No delimiter found: print entire line regardless of -F RANGES +testing "cut -F1" "cut -d: -F1" \ + "the_only_field\n" "" \ + "the_only_field\n" +testing "cut -F2" "cut -d: -F2" \ + "the_only_field\n" "" \ + "the_only_field\n" +# No delimiter found and -s: skip entire line +testing "cut -sF1" "cut -d: -sF1" \ + "" "" \ + "the_only_field\n" +#^^^ the above is probably mishandled by toybox, it prints the line +testing "cut -sF2" "cut -d: -sF2" \ + "" "" \ + "the_only_field\n" +# -D disables special handling of lines with no delimiters, the line is treated as the 1st field +testing "cut -DF1" "cut -d: -DF1" \ + "the_only_field\n" "" \ + "the_only_field\n" +testing "cut -DF2" "cut -d: -DF2" \ + "\n" "" \ + "the_only_field\n" + optional FEATURE_CUT_REGEX LONG_OPTS testing "cut -F preserves intermediate delimiters" \ "cut --output-delimiter=: -F2,4-6,7" \ -- cgit v1.2.3-55-g6feb