unzip: -d should create the dir
[oweals/busybox.git] / coreutils / printf.c
index 413273b261cf1fe3d57a2cab14b78e9b80275442..a20fc33013b849414c8c0c95aaa2da009001972e 100644 (file)
@@ -1,5 +1,6 @@
 /* vi: set sw=4 ts=4: */
-/* printf - format and print data
+/*
+ * printf - format and print data
  *
  * Copyright 1999 Dave Cinege
  * Portions copyright (C) 1990-1996 Free Software Foundation, Inc.
@@ -37,7 +38,7 @@
 /* 19990508 Busy Boxed! Dave Cinege */
 
 //config:config PRINTF
-//config:      bool "printf (3.3 kb)"
+//config:      bool "printf (3.8 kb)"
 //config:      default y
 //config:      help
 //config:      printf is used to format and print specified strings.
@@ -94,6 +95,12 @@ static int multiconvert(const char *arg, void *result, converter convert)
 
 static void FAST_FUNC conv_strtoull(const char *arg, void *result)
 {
+       /* Allow leading '+' - bb_strtoull() by itself does not allow it,
+        * and probably shouldn't (other callers might require purely numeric
+        * inputs to be allowed.
+        */
+       if (arg[0] == '+')
+               arg++;
        *(unsigned long long*)result = bb_strtoull(arg, NULL, 0);
        /* both coreutils 6.10 and bash 3.2:
         * $ printf '%x\n' -2
@@ -106,6 +113,8 @@ static void FAST_FUNC conv_strtoull(const char *arg, void *result)
 }
 static void FAST_FUNC conv_strtoll(const char *arg, void *result)
 {
+       if (arg[0] == '+')
+               arg++;
        *(long long*)result = bb_strtoll(arg, NULL, 0);
 }
 static void FAST_FUNC conv_strtod(const char *arg, void *result)
@@ -190,6 +199,7 @@ static void print_direc(char *format, unsigned fmt_length,
        if (have_width - 1 == have_prec)
                have_width = NULL;
 
+       /* multiconvert sets errno = 0, but %s needs it cleared */
        errno = 0;
 
        switch (format[fmt_length - 1]) {
@@ -198,7 +208,7 @@ static void print_direc(char *format, unsigned fmt_length,
                break;
        case 'd':
        case 'i':
-               llv = my_xstrtoll(argument);
+               llv = my_xstrtoll(skip_whitespace(argument));
  print_long:
                if (!have_width) {
                        if (!have_prec)
@@ -216,7 +226,7 @@ static void print_direc(char *format, unsigned fmt_length,
        case 'u':
        case 'x':
        case 'X':
-               llv = my_xstrtoull(argument);
+               llv = my_xstrtoull(skip_whitespace(argument));
                /* cheat: unsigned long and long have same width, so... */
                goto print_long;
        case 's':
@@ -420,7 +430,7 @@ int printf_main(int argc UNUSED_PARAM, char **argv)
                if (ENABLE_ASH_PRINTF
                 && applet_name[0] != 'p'
                ) {
-                       bb_error_msg("usage: printf FORMAT [ARGUMENT...]");
+                       bb_simple_error_msg("usage: printf FORMAT [ARGUMENT...]");
                        return 2; /* bash compat */
                }
                bb_show_usage();