From cf809e2f2dbf699035e4841e45070b947374a989 Mon Sep 17 00:00:00 2001 From: YU Jincheng Date: Fri, 7 Jul 2023 16:44:24 +0800 Subject: getfattr: new applet function old new delta getfattr_main - 309 +309 print_attr - 115 +115 packed_usage 34576 34631 +55 .rodata 105349 105395 +46 lgetxattr - 41 +41 getxattr - 41 +41 llistxattr - 35 +35 listxattr - 35 +35 applet_names 2806 2815 +9 applet_main 1620 1624 +4 ------------------------------------------------------------------------------ (add/remove: 7/0 grow/shrink: 4/0 up/down: 690/0) Total: 690 bytes Signed-off-by: YU Jincheng Signed-off-by: Denys Vlasenko --- miscutils/getfattr.c | 131 +++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 131 insertions(+) create mode 100644 miscutils/getfattr.c (limited to 'miscutils') diff --git a/miscutils/getfattr.c b/miscutils/getfattr.c new file mode 100644 index 000000000..59b6f6bca --- /dev/null +++ b/miscutils/getfattr.c @@ -0,0 +1,131 @@ +/* + * getfattr - get extended attributes of filesystem objects. + * + * Copyright (C) 2023 by LoveSy + * + * Licensed under GPLv2, see file LICENSE in this source tree. + */ +//config:config GETFATTR +//config: bool "getfattr (12.3 kb)" +//config: default y +//config: help +//config: Get extended attributes on files + +//applet:IF_GETFATTR(APPLET_NOEXEC(getfattr, getfattr, BB_DIR_USR_BIN, BB_SUID_DROP, getfattr)) + +//kbuild:lib-$(CONFIG_GETFATTR) += getfattr.o + +#include +#include +#include "libbb.h" + +//usage:#define getfattr_trivial_usage +//usage: "[-h] {-d|-n ATTR} FILE...\n" +//usage:#define getfattr_full_usage "\n\n" +//usage: "Get extended attributes" +//usage: "\n" +//usage: "\n -h Do not follow symlinks" +//usage: "\n -d Dump all attributes" +//usage: "\n -n ATTR Get attribute ATTR" + +enum { + OPT_h = (1 << 0), + OPT_d = (1 << 1), +}; + +static int print_attr(const char *file, const char *name, char **buf, size_t *bufsize) +{ + ssize_t len; + + if (*bufsize == 0) + goto grow; + again: + len = ((option_mask32 & OPT_h) ? lgetxattr: getxattr)(file, name, *buf, *bufsize); + if (len < 0) { + if (errno != ERANGE) + return len; + grow: + *bufsize = (*bufsize * 2) + 1024; + *buf = xrealloc(*buf, *bufsize); + goto again; + } + printf("%s=\"%.*s\"\n", name, len, *buf); + return 0; +} + +static ssize_t list_attr(const char *file, char **list, size_t *listsize) +{ + ssize_t len; + + if (*listsize == 0) + goto grow; + again: + len = ((option_mask32 & OPT_h) ? llistxattr : listxattr)(file, *list, *listsize); + if (len < 0) { + if (errno != ERANGE) + return len; + grow: + *listsize = (*listsize * 2) + 1024; + *list = xrealloc(*list, *listsize); + goto again; + } + return len; +} + +int getfattr_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; +int getfattr_main(int argc UNUSED_PARAM, char **argv) +{ + const char *name; + int status; + int opt; + char *buf = NULL; + size_t bufsize = 0; + char *list = NULL; + size_t listsize = 0; + + opt = getopt32(argv, "^" + "hdn:" + /* Min one arg; exactly one of -n or -d is required. */ + "\0" "-1:d:n:n--d:d--n" + , &name + ); + argv += optind; + status = EXIT_SUCCESS; + + do { + int r; + if (opt & OPT_d) { + ssize_t len = list_attr(*argv, &list, &listsize); + if (len > 0) { + char *key; + printf("# file: %s\n", *argv); + key = list; + while (len > 0) { + ssize_t keylen; + r = print_attr(*argv, key, &buf, &bufsize); + if (r) + goto err; + keylen = strlen(key) + 1; + key += keylen; + len -= keylen; + } + bb_putchar('\n'); + } + } else { + printf("# file: %s\n", *argv); + r = print_attr(*argv, name, &buf, &bufsize); + if (r) { + err: + bb_simple_perror_msg(*argv); + status = EXIT_FAILURE; + // continue; maybe? + } + bb_putchar('\n'); + } + } while (*++argv); + + if (ENABLE_FEATURE_CLEAN_UP) + free(buf); + + fflush_stdout_and_exit(status); +} -- cgit v1.2.3-55-g6feb From a6a102ec4c8d96fcfb968c88fbdae80f6142c7bf Mon Sep 17 00:00:00 2001 From: Denys Vlasenko Date: Mon, 17 Jul 2023 09:36:17 +0200 Subject: getfattr: fix "getfattr NOTEXIST" - now prints error msg function old new delta getfattr_main 309 307 -2 .rodata 105395 105391 -4 ------------------------------------------------------------------------------ (add/remove: 0/0 grow/shrink: 0/2 up/down: 0/-6) Total: -6 bytes Signed-off-by: Denys Vlasenko --- miscutils/getfattr.c | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) (limited to 'miscutils') diff --git a/miscutils/getfattr.c b/miscutils/getfattr.c index 59b6f6bca..905aec65f 100644 --- a/miscutils/getfattr.c +++ b/miscutils/getfattr.c @@ -31,6 +31,7 @@ enum { OPT_h = (1 << 0), OPT_d = (1 << 1), + OPT_n = (1 << 2), }; static int print_attr(const char *file, const char *name, char **buf, size_t *bufsize) @@ -85,8 +86,9 @@ int getfattr_main(int argc UNUSED_PARAM, char **argv) opt = getopt32(argv, "^" "hdn:" - /* Min one arg; exactly one of -n or -d is required. */ - "\0" "-1:d:n:n--d:d--n" + /* Min one arg; -d and -n are exclusive */ + "\0" "-1:n--d:d--n" + //getfattr 2.5.1 does not enforce this: ":d:n" /* exactly one of -n or -d is required */ , &name ); argv += optind; @@ -94,8 +96,11 @@ int getfattr_main(int argc UNUSED_PARAM, char **argv) do { int r; - if (opt & OPT_d) { +//getfattr 2.5.1 with no -n/-d defaults to -d + if (!(opt & OPT_n)) { ssize_t len = list_attr(*argv, &list, &listsize); + if (len < 0) + goto err; if (len > 0) { char *key; printf("# file: %s\n", *argv); @@ -118,7 +123,7 @@ int getfattr_main(int argc UNUSED_PARAM, char **argv) err: bb_simple_perror_msg(*argv); status = EXIT_FAILURE; - // continue; maybe? + continue; } bb_putchar('\n'); } -- cgit v1.2.3-55-g6feb From c484846c4459affa769b84cbd0b586f2bbaec828 Mon Sep 17 00:00:00 2001 From: Denys Vlasenko Date: Mon, 17 Jul 2023 17:29:36 +0200 Subject: introduce and use exitcode_t function old new delta strings_main 422 420 -2 setfattr_main 175 173 -2 brctl_main 1548 1546 -2 makedevs_main 979 975 -4 rev_main 337 332 -5 getfattr_main 307 302 -5 cut_main 1201 1196 -5 cksum_main 398 393 -5 umount_main 573 565 -8 ln_main 516 508 -8 expand_main 660 652 -8 df_main 1068 1060 -8 renice_main 346 332 -14 ------------------------------------------------------------------------------ (add/remove: 0/0 grow/shrink: 0/13 up/down: 0/-76) Total: -76 bytes Signed-off-by: Denys Vlasenko --- coreutils/cksum.c | 2 +- coreutils/cut.c | 2 +- coreutils/dd.c | 2 +- coreutils/df.c | 2 +- coreutils/expand.c | 2 +- coreutils/fold.c | 2 +- coreutils/ln.c | 2 +- coreutils/touch.c | 2 +- include/libbb.h | 7 +++++++ miscutils/getfattr.c | 2 +- miscutils/makedevs.c | 2 +- miscutils/setfattr.c | 2 +- miscutils/strings.c | 3 ++- networking/brctl.c | 2 +- networking/tc.c | 5 ++--- util-linux/renice.c | 2 +- util-linux/rev.c | 2 +- util-linux/umount.c | 2 +- 18 files changed, 26 insertions(+), 19 deletions(-) (limited to 'miscutils') diff --git a/coreutils/cksum.c b/coreutils/cksum.c index badc63a6a..1fb6ef2d0 100644 --- a/coreutils/cksum.c +++ b/coreutils/cksum.c @@ -39,7 +39,7 @@ int cksum_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; int cksum_main(int argc UNUSED_PARAM, char **argv) { uint32_t *crc32_table = crc32_filltable(NULL, IS_CKSUM); - int exit_code = EXIT_SUCCESS; + exitcode_t exit_code = EXIT_SUCCESS; #if ENABLE_DESKTOP getopt32(argv, ""); /* cksum coreutils 6.9 compat */ diff --git a/coreutils/cut.c b/coreutils/cut.c index 25b16d1a8..d129f9b9d 100644 --- a/coreutils/cut.c +++ b/coreutils/cut.c @@ -311,7 +311,7 @@ int cut_main(int argc UNUSED_PARAM, char **argv) } { - int retval = EXIT_SUCCESS; + exitcode_t retval = EXIT_SUCCESS; if (!*argv) *--argv = (char *)"-"; diff --git a/coreutils/dd.c b/coreutils/dd.c index c032ebe1b..8bb782781 100644 --- a/coreutils/dd.c +++ b/coreutils/dd.c @@ -375,7 +375,7 @@ int dd_main(int argc UNUSED_PARAM, char **argv) OP_oflag_direct, #endif }; - smallint exitcode = EXIT_FAILURE; + exitcode_t exitcode = EXIT_FAILURE; int i; size_t ibs = 512; char *ibuf; diff --git a/coreutils/df.c b/coreutils/df.c index 76e9cefbf..03aa78148 100644 --- a/coreutils/df.c +++ b/coreutils/df.c @@ -113,7 +113,7 @@ int df_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; int df_main(int argc UNUSED_PARAM, char **argv) { unsigned long df_disp_hr = 1024; - int status = EXIT_SUCCESS; + exitcode_t status = EXIT_SUCCESS; unsigned opt; FILE *mount_table; struct mntent *mount_entry; diff --git a/coreutils/expand.c b/coreutils/expand.c index 47693e144..c4db26055 100644 --- a/coreutils/expand.c +++ b/coreutils/expand.c @@ -192,7 +192,7 @@ int expand_main(int argc UNUSED_PARAM, char **argv) FILE *file; unsigned tab_size; unsigned opt; - int exit_status = EXIT_SUCCESS; + exitcode_t exit_status = EXIT_SUCCESS; init_unicode(); diff --git a/coreutils/fold.c b/coreutils/fold.c index 2839c8c68..8112fe911 100644 --- a/coreutils/fold.c +++ b/coreutils/fold.c @@ -77,7 +77,7 @@ int fold_main(int argc UNUSED_PARAM, char **argv) char *line_out = NULL; const char *w_opt = "80"; unsigned width; - smallint exitcode = EXIT_SUCCESS; + exitcode_t exitcode = EXIT_SUCCESS; init_unicode(); diff --git a/coreutils/ln.c b/coreutils/ln.c index 34eec398a..080ba142e 100644 --- a/coreutils/ln.c +++ b/coreutils/ln.c @@ -52,7 +52,7 @@ int ln_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; int ln_main(int argc, char **argv) { - int status = EXIT_SUCCESS; + exitcode_t status = EXIT_SUCCESS; int opts; char *last; char *src_name; diff --git a/coreutils/touch.c b/coreutils/touch.c index 8fde70e12..ced596c89 100644 --- a/coreutils/touch.c +++ b/coreutils/touch.c @@ -77,7 +77,7 @@ int touch_main(int argc UNUSED_PARAM, char **argv) { int fd; int opts; - smalluint status = EXIT_SUCCESS; + exitcode_t status = EXIT_SUCCESS; #if ENABLE_FEATURE_TOUCH_SUSV3 char *reference_file; char *date_str; diff --git a/include/libbb.h b/include/libbb.h index 640fa3988..eb97a9880 100644 --- a/include/libbb.h +++ b/include/libbb.h @@ -1444,6 +1444,13 @@ void bb_verror_msg(const char *s, va_list p, const char *strerr) FAST_FUNC; void bb_die_memory_exhausted(void) NORETURN FAST_FUNC; void bb_logenv_override(void) FAST_FUNC; +/* x86 benefits from narrow exit code variables + * (because it has no widening MOV imm8,word32 insn, has to use MOV imm32,w + * for "exitcode = EXIT_FAILURE" and similar. The downside is that sometimes +* gcc widens the variable to int in various ugly suboptimal ways). + */ +typedef smalluint exitcode_t; + #if ENABLE_FEATURE_SYSLOG_INFO void bb_info_msg(const char *s, ...) __attribute__ ((format (printf, 1, 2))) FAST_FUNC; void bb_simple_info_msg(const char *s) FAST_FUNC; diff --git a/miscutils/getfattr.c b/miscutils/getfattr.c index 905aec65f..cb42fdac0 100644 --- a/miscutils/getfattr.c +++ b/miscutils/getfattr.c @@ -77,7 +77,7 @@ int getfattr_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; int getfattr_main(int argc UNUSED_PARAM, char **argv) { const char *name; - int status; + exitcode_t status; int opt; char *buf = NULL; size_t bufsize = 0; diff --git a/miscutils/makedevs.c b/miscutils/makedevs.c index 48be91875..999a3b976 100644 --- a/miscutils/makedevs.c +++ b/miscutils/makedevs.c @@ -181,7 +181,7 @@ int makedevs_main(int argc UNUSED_PARAM, char **argv) { parser_t *parser; char *line = (char *)"-"; - int ret = EXIT_SUCCESS; + exitcode_t ret = EXIT_SUCCESS; getopt32(argv, "^" "d:" "\0" "=1", &line); argv += optind; diff --git a/miscutils/setfattr.c b/miscutils/setfattr.c index 10d1840c9..b68bc9452 100644 --- a/miscutils/setfattr.c +++ b/miscutils/setfattr.c @@ -32,7 +32,7 @@ int setfattr_main(int argc UNUSED_PARAM, char **argv) { const char *name; const char *value = ""; - int status; + exitcode_t status; int opt; enum { OPT_h = (1 << 0), diff --git a/miscutils/strings.c b/miscutils/strings.c index 036df5c5d..bd1850cbb 100644 --- a/miscutils/strings.c +++ b/miscutils/strings.c @@ -40,7 +40,8 @@ int strings_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; int strings_main(int argc UNUSED_PARAM, char **argv) { - int n, c, status = EXIT_SUCCESS; + int n, c; + exitcode_t status = EXIT_SUCCESS; unsigned count; off_t offset; FILE *file; diff --git a/networking/brctl.c b/networking/brctl.c index 7b0270b51..0f8dc2f7a 100644 --- a/networking/brctl.c +++ b/networking/brctl.c @@ -538,7 +538,7 @@ int brctl_main(int argc UNUSED_PARAM, char **argv) DIR *net; struct dirent *ent; int need_hdr = 1; - int exitcode = EXIT_SUCCESS; + exitcode_t exitcode = EXIT_SUCCESS; if (*argv) { /* "show BR1 BR2 BR3" */ diff --git a/networking/tc.c b/networking/tc.c index 43187f7ee..3a79fd2d9 100644 --- a/networking/tc.c +++ b/networking/tc.c @@ -502,7 +502,7 @@ int tc_main(int argc UNUSED_PARAM, char **argv) }; struct rtnl_handle rth; struct tcmsg msg; - int ret, obj, cmd, arg; + int obj, cmd, arg; char *dev = NULL; INIT_G(); @@ -510,7 +510,6 @@ int tc_main(int argc UNUSED_PARAM, char **argv) if (!*++argv) bb_show_usage(); xrtnl_open(&rth); - ret = EXIT_SUCCESS; obj = index_in_substrings(objects, *argv++); if (obj < 0) @@ -625,5 +624,5 @@ int tc_main(int argc UNUSED_PARAM, char **argv) if (ENABLE_FEATURE_CLEAN_UP) { rtnl_close(&rth); } - return ret; + return EXIT_SUCCESS; } diff --git a/util-linux/renice.c b/util-linux/renice.c index 53f197cce..f2737f29b 100644 --- a/util-linux/renice.c +++ b/util-linux/renice.c @@ -45,7 +45,7 @@ int renice_main(int argc UNUSED_PARAM, char **argv) { static const char Xetpriority_msg[] ALIGN1 = "%cetpriority"; - int retval = EXIT_SUCCESS; + exitcode_t retval = EXIT_SUCCESS; int which = PRIO_PROCESS; /* Default 'which' value. */ int use_relative = 0; int adjustment, new_priority; diff --git a/util-linux/rev.c b/util-linux/rev.c index 12df2b9ff..aad53722d 100644 --- a/util-linux/rev.c +++ b/util-linux/rev.c @@ -51,7 +51,7 @@ static void strrev(CHAR_T *s, int len) int rev_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; int rev_main(int argc UNUSED_PARAM, char **argv) { - int retval; + exitcode_t retval; size_t bufsize; char *buf; diff --git a/util-linux/umount.c b/util-linux/umount.c index 23da32868..f5c97a034 100644 --- a/util-linux/umount.c +++ b/util-linux/umount.c @@ -97,7 +97,7 @@ int umount_main(int argc UNUSED_PARAM, char **argv) struct mntent me; FILE *fp; char *fstype = NULL; - int status = EXIT_SUCCESS; + exitcode_t status = EXIT_SUCCESS; unsigned opt; struct mtab_list { char *dir; -- cgit v1.2.3-55-g6feb