From 54cf511ce1286ce46f04e4cead085b4af829f179 Mon Sep 17 00:00:00 2001 From: Denis Vlasenko Date: Sat, 17 Feb 2007 18:11:45 +0000 Subject: [PATCH] sort: fix multiple -k (was ignoring all except last) --- archival/tar.c | 2 +- coreutils/od_bloaty.c | 2 +- coreutils/sort.c | 14 ++++++++++---- include/libbb.h | 2 +- libbb/llist.c | 2 +- networking/wget.c | 2 +- procps/ps.c | 2 +- testsuite/sort.tests | 10 ++++++++++ 8 files changed, 26 insertions(+), 10 deletions(-) diff --git a/archival/tar.c b/archival/tar.c index 57da0b6b8..1cdae296d 100644 --- a/archival/tar.c +++ b/archival/tar.c @@ -864,7 +864,7 @@ int tar_main(int argc, char **argv) llist_add_to(&tar_handle->accept, argv[optind]); optind++; } - tar_handle->accept = rev_llist(tar_handle->accept); + tar_handle->accept = llist_rev(tar_handle->accept); if (tar_handle->accept || tar_handle->reject) tar_handle->filter = filter_accept_reject_list; diff --git a/coreutils/od_bloaty.c b/coreutils/od_bloaty.c index f060c0ace..c69470a14 100644 --- a/coreutils/od_bloaty.c +++ b/coreutils/od_bloaty.c @@ -1312,7 +1312,7 @@ int od_main(int argc, char **argv) if (opt & OPT_l) decode_format_string("d4"); if (opt & OPT_o) decode_format_string("o2"); //if (opt & OPT_t)... - lst_t = rev_llist(lst_t); + lst_t = llist_rev(lst_t); while (lst_t) { decode_format_string(lst_t->data); lst_t = lst_t->link; diff --git a/coreutils/sort.c b/coreutils/sort.c index e2c7b1dbf..311d0cb9c 100644 --- a/coreutils/sort.c +++ b/coreutils/sort.c @@ -276,7 +276,8 @@ int sort_main(int argc, char **argv) { FILE *fp, *outfile = stdout; char *line, **lines = NULL; - char *str_ignored, *str_o, *str_k, *str_t; + char *str_ignored, *str_o, *str_t; + llist_t *lst_k = NULL; int i, flag; int linecount = 0; @@ -284,8 +285,9 @@ int sort_main(int argc, char **argv) /* Parse command line options */ /* -o and -t can be given at most once */ - opt_complementary = "?:o--o:t--t"; - getopt32(argc, argv, OPT_STR, &str_ignored, &str_ignored, &str_o, &str_k, &str_t); + opt_complementary = "?:o--o:t--t:" /* -t, -o: maximum one of each */ + "k::"; /* -k takes list */ + getopt32(argc, argv, OPT_STR, &str_ignored, &str_ignored, &str_o, &lst_k, &str_t); #if ENABLE_FEATURE_SORT_BIG if (option_mask32 & FLAG_o) outfile = xfopen(str_o, "w"); if (option_mask32 & FLAG_t) { @@ -294,7 +296,8 @@ int sort_main(int argc, char **argv) key_separator = str_t[0]; } /* parse sort key */ - if (option_mask32 & FLAG_k) { + lst_k = llist_rev(lst_k); + while (lst_k) { enum { FLAG_allowed_for_k = FLAG_n | /* Numeric sort */ @@ -308,6 +311,7 @@ int sort_main(int argc, char **argv) 0 }; struct sort_key *key = add_key(); + char *str_k = lst_k->data; const char *temp2; i = 0; /* i==0 before comma, 1 after (-k3,6) */ @@ -337,6 +341,8 @@ int sort_main(int argc, char **argv) str_k++; } } + /* leaking lst_k... */ + lst_k = lst_k->link; } #endif /* global b strips leading and trailing spaces */ diff --git a/include/libbb.h b/include/libbb.h index 09e8a57d2..a32e6154c 100644 --- a/include/libbb.h +++ b/include/libbb.h @@ -473,7 +473,7 @@ extern void llist_add_to(llist_t **old_head, void *data); extern void llist_add_to_end(llist_t **list_head, void *data); extern void *llist_pop(llist_t **elm); extern void llist_free(llist_t *elm, void (*freeit)(void *data)); -extern llist_t* rev_llist(llist_t *list); +extern llist_t* llist_rev(llist_t *list); enum { LOGMODE_NONE = 0, diff --git a/libbb/llist.c b/libbb/llist.c index 63c77fa9e..0a5978a26 100644 --- a/libbb/llist.c +++ b/libbb/llist.c @@ -74,7 +74,7 @@ void llist_free(llist_t * elm, void (*freeit) (void *data)) /* Reverse list order. Useful since getopt32 saves option params * in reverse order */ -llist_t *rev_llist(llist_t * list) +llist_t *llist_rev(llist_t * list) { llist_t *new = NULL; diff --git a/networking/wget.c b/networking/wget.c index e649ccdda..db222156b 100644 --- a/networking/wget.c +++ b/networking/wget.c @@ -157,7 +157,7 @@ int wget_main(int argc, char **argv) if (headers_llist) { int size = 1; char *cp; - llist_t *ll = headers_llist = rev_llist(headers_llist); + llist_t *ll = headers_llist = llist_rev(headers_llist); while (ll) { size += strlen(ll->data) + 2; ll = ll->link; diff --git a/procps/ps.c b/procps/ps.c index a9da807a5..c06d333cd 100644 --- a/procps/ps.c +++ b/procps/ps.c @@ -253,7 +253,7 @@ int ps_main(int argc, char **argv) opt_complementary = "o::"; getopt32(argc, argv, "o:aAdefl", &opt_o); if (opt_o) { - opt_o = rev_llist(opt_o); + opt_o = llist_rev(opt_o); do { parse_o(opt_o->data); opt_o = opt_o->link; diff --git a/testsuite/sort.tests b/testsuite/sort.tests index df5f7c7dd..1db7870d4 100755 --- a/testsuite/sort.tests +++ b/testsuite/sort.tests @@ -66,6 +66,16 @@ testing "sort key range with multiple options" "sort -k2,3rn input" \ egg 1 2 papyrus " "$data" "" +testing "sort key range with two -k options" "sort -k 2,2n -k 1,1r input" "\ +d 2 +b 2 +c 3 +" "\ +c 3 +b 2 +d 2 +" "" + testing "sort with non-default leading delim 1" "sort -n -k2 -t/ input" "\ /a/2 /b/1 -- 2.25.1