*: kill bb_get_last_path_component, replace with two functions
authorDenis Vlasenko <vda.linux@googlemail.com>
Mon, 24 Sep 2007 18:27:04 +0000 (18:27 -0000)
committerDenis Vlasenko <vda.linux@googlemail.com>
Mon, 24 Sep 2007 18:27:04 +0000 (18:27 -0000)
(one which strips trailing slash and one which does not)
wget: straighten out as a result of above change
   text    data     bss     dec     hex filename
   5056       1       0    5057    13c1 busybox.t4/networking/wget.o
   5022       0       0    5022    139e busybox.t5/networking/wget.o

13 files changed:
applets/applets.c
coreutils/basename.c
coreutils/cp.c
coreutils/ln.c
coreutils/mv.c
coreutils/rm.c
include/libbb.h
init/init.c
libbb/get_last_path_component.c
libbb/run_shell.c
modutils/insmod.c
networking/wget.c
shell/lash.c

index a1a399cd5db3d9d34d511a981dbdf098f637956f..5b7b88a548ae669cf28cafd3269f3f55789d15a8 100644 (file)
@@ -601,7 +601,7 @@ static int busybox_main(char **argv)
        }
        /* We support "busybox /a/path/to/applet args..." too. Allows for
         * "#!/bin/busybox"-style wrappers */
-       applet_name = bb_get_last_path_component(argv[0]);
+       applet_name = bb_get_last_path_component_nostrip(argv[0]);
        run_applet_and_exit(applet_name, argv);
        bb_error_msg_and_die("applet not found");
 }
index f59d7a8dee99b7c649cd0c0f6e49be69ee6c2f0b..ec1f85befd94324f86c7a0ac1304f94aa6a7bf7c 100644 (file)
@@ -34,7 +34,8 @@ int basename_main(int argc, char **argv)
                bb_show_usage();
        }
 
-       s = bb_get_last_path_component(*++argv);
+       /* It should strip slash: /abc/def/ -> def */
+       s = bb_get_last_path_component_strip(*++argv);
 
        if (*++argv) {
                n = strlen(*argv);
index 76dc566b3832b6e007d8fc2463b1b827b5ff39ca..889e4604dddfbae6a5acde8dfa7d97d62045f45d 100644 (file)
@@ -87,7 +87,7 @@ int cp_main(int argc, char **argv)
        }
 
        while (1) {
-               dest = concat_path_file(last, bb_get_last_path_component(*argv));
+               dest = concat_path_file(last, bb_get_last_path_component_strip(*argv));
  DO_COPY:
                if (copy_file(*argv, dest, flags) < 0) {
                        status = 1;
index a6499039e4d77b0237c2a8d61d0d87b292ec1e83..f3c67aa36e947eec00a4f3fcd93fe5e48b93ddb7 100644 (file)
@@ -45,7 +45,7 @@ int ln_main(int argc, char **argv)
 
        if (argc == optind + 1) {
                *--argv = last;
-               last = bb_get_last_path_component(xstrdup(last));
+               last = bb_get_last_path_component_strip(xstrdup(last));
        }
 
        do {
@@ -57,7 +57,7 @@ int ln_main(int argc, char **argv)
                                NULL)
                ) {
                        src_name = xstrdup(*argv);
-                       src = concat_path_file(src, bb_get_last_path_component(src_name));
+                       src = concat_path_file(src, bb_get_last_path_component_strip(src_name));
                        free(src_name);
                        src_name = src;
                }
index 1d29770602b68ad4cab362eed707d182cc1524da..d13f4d54faa4b7f0274e9ba0d3c85d72dbc7c2a4 100644 (file)
@@ -68,7 +68,7 @@ int mv_main(int argc, char **argv)
        }
 
        do {
-               dest = concat_path_file(last, bb_get_last_path_component(*argv));
+               dest = concat_path_file(last, bb_get_last_path_component_strip(*argv));
                dest_exists = cp_mv_stat(dest, &dest_stat);
                if (dest_exists < 0) {
                        goto RET_1;
index ba37762a83a2dff0523ad9bb82c23872ba7986c4..a686fc40c9bbbc56fbf59f3425ffab915f180886 100644 (file)
@@ -38,7 +38,7 @@ int rm_main(int argc, char **argv)
 
        if (*argv != NULL) {
                do {
-                       const char *base = bb_get_last_path_component(*argv);
+                       const char *base = bb_get_last_path_component_strip(*argv);
 
                        if (DOT_OR_DOTDOT(base)) {
                                bb_error_msg("cannot remove '.' or '..'");
index e5f03517f88e5c690d7202a07dbe8445c3910fe3..25b2e448953b1d3559450b4fa81bb9caa762bc51 100644 (file)
@@ -236,9 +236,15 @@ extern void bb_copyfd_exact_size(int fd1, int fd2, off_t size);
 /* this helper yells "short read!" if param is not -1 */
 extern void complain_copyfd_and_die(off_t sz) ATTRIBUTE_NORETURN;
 extern char bb_process_escape_sequence(const char **ptr);
-/* TODO: sometimes modifies its parameter, which
- * makes it rather inconvenient at times: */
-extern char *bb_get_last_path_component(char *path);
+/* xxxx_strip version can modify its parameter:
+ * "/"        -> "/"
+ * "abc"      -> "abc"
+ * "abc/def"  -> "def"
+ * "abc/def/" -> "def" !!
+ */
+extern char *bb_get_last_path_component_strip(char *path);
+/* "abc/def/" -> "" and it never modifies 'path' */
+extern char *bb_get_last_path_component_nostrip(const char *path);
 
 int ndelay_on(int fd);
 int ndelay_off(int fd);
index a196ab3ed16e8d0dd9295dc4421c3c9bfdb045eb..543ec2ea84adfb68ea51304fc57735b1c4943065 100644 (file)
@@ -436,10 +436,11 @@ static pid_t run(const struct init_action *a)
                ++cmdpath;
 
                /* find the last component in the command pathname */
-               s = bb_get_last_path_component(cmdpath);
+               s = bb_get_last_path_component_nostrip(cmdpath);
 
                /* make a new argv[0] */
-               if ((cmd[0] = malloc(strlen(s) + 2)) == NULL) {
+               cmd[0] = malloc(strlen(s) + 2);
+               if (cmd[0] == NULL) {
                        message(L_LOG | L_CONSOLE, bb_msg_memory_exhausted);
                        cmd[0] = cmdpath;
                } else {
index b7bc0e626ae1b6a8175ad83a9bd842b68d2ecdaf..0f602157d970ea177d32f8843b995027da4c1532 100644 (file)
@@ -8,25 +8,35 @@
  */
 
 #include "libbb.h"
-
-char *bb_get_last_path_component(char *path)
+/*
+ * "/"        -> "/"
+ * "abc"      -> "abc"
+ * "abc/def"  -> "def"
+ * "abc/def/" -> ""
+ */
+char *bb_get_last_path_component_nostrip(const char *path)
 {
-       char *first = path;
-       char *last;
+       char *slash = strrchr(path, '/');
+
+       if (!slash || (slash == path && !slash[1]))
+               return (char*)path;
 
-       last = path - 1;
+       return slash + 1;
+}
 
-       while (*path) {
-               if ((*path != '/') && (path > ++last)) {
-                       last = first = path;
-               }
-               ++path;
-       }
+/*
+ * "/"        -> "/"
+ * "abc"      -> "abc"
+ * "abc/def"  -> "def"
+ * "abc/def/" -> "def" !!
+ */
+char *bb_get_last_path_component_strip(char *path)
+{
+       char *slash = last_char_is(path, '/');
 
-       if (*first == '/') {
-               last = first;
-       }
-       last[1] = '\0';
+       if (slash)
+               while (*slash == '/' && slash != path)
+                       *slash-- = '\0';
 
-       return first;
+       return bb_get_last_path_component_nostrip(path);
 }
index b2b4216f4bd5845045ebf9fd4dd275789e5ea9bf..239887d85c6469f16d9008c4574c5a470b7e8aa3 100644 (file)
@@ -67,7 +67,7 @@ void run_shell(const char *shell, int loginshell, const char *command, const cha
 
        args = xmalloc(sizeof(char*) * (4 + additional_args_cnt));
 
-       args[0] = bb_get_last_path_component(xstrdup(shell));
+       args[0] = bb_get_last_path_component_nostrip(xstrdup(shell));
 
        if (loginshell)
                args[0] = xasprintf("-%s", args[0]);
index 503367298eeb33291630e1742a65a55b292672ee..0baf5d7f265568ef1c96013115a5c090f06926a0 100644 (file)
@@ -806,7 +806,7 @@ static int check_module_name_match(const char *filename, struct stat *statbuf,
                return FALSE;
        else {
                char *tmp, *tmp1 = xstrdup(filename);
-               tmp = bb_get_last_path_component(tmp1);
+               tmp = bb_get_last_path_component_nostrip(tmp1);
                if (strcmp(tmp, fullname) == 0) {
                        free(tmp1);
                        /* Stop searching if we find a match */
index 5feb539d5174fc053abb222307c9c2dd16dc1e3f..86d6f00ecf1a4f2a2db6fc504690962baca32a07 100644 (file)
 struct host_info {
        // May be used if we ever will want to free() all xstrdup()s...
        /* char *allocated; */
-       char    *path;
-       char    *user;
-       char    *host;
-       int      port;
-       smallint is_ftp;
+       const char *path;
+       const char *user;
+       char       *host;
+       int         port;
+       smallint    is_ftp;
 };
 
 
@@ -318,9 +318,7 @@ static void parse_url(char *src_url, struct host_info *h)
        p = strchr(h->host, '?'); if (!sp || (p && sp > p)) sp = p;
        p = strchr(h->host, '#'); if (!sp || (p && sp > p)) sp = p;
        if (!sp) {
-               /* must be writable because of bb_get_last_path_component() */
-               static char nullstr[] ALIGN1 = "";
-               h->path = nullstr;
+               h->path = "";
        } else if (*sp == '/') {
                *sp = '\0';
                h->path = sp + 1;
@@ -328,7 +326,7 @@ static void parse_url(char *src_url, struct host_info *h)
                // http://busybox.net?login=john@doe is a valid URL
                // memmove converts to:
                // http:/busybox.nett?login=john@doe...
-               memmove(h->host-1, h->host, sp - h->host);
+               memmove(h->host - 1, h->host, sp - h->host);
                h->host--;
                sp[-1] = '\0';
                h->path = sp;
@@ -497,31 +495,20 @@ int wget_main(int argc, char **argv)
                }
        }
 
-       /* Guess an output filename */
+       /* Guess an output filename, if there was no -O FILE */
        if (!fname_out) {
-               // Dirty hack. Needed because bb_get_last_path_component
-               // will destroy trailing / by storing '\0' in last byte!
-               if (!last_char_is(target.path, '/')) {
-                       fname_out = bb_get_last_path_component(target.path);
-#if ENABLE_FEATURE_WGET_STATUSBAR
-                       curfile = fname_out;
-#endif
-               }
-               if (!fname_out || !fname_out[0]) {
-                       /* bb_get_last_path_component writes
-                        * to last '/' only. We don't have one here... */
+               fname_out = bb_get_last_path_component_nostrip(target.path);
+               /* handle "wget http://kernel.org//" */
+               if (fname_out[0] == '/' || !fname_out[0])
                        fname_out = (char*)"index.html";
-#if ENABLE_FEATURE_WGET_STATUSBAR
-                       curfile = fname_out;
-#endif
-               }
-               if (dir_prefix != NULL)
+               /* -P DIR is considered only if there was no -O FILE */
+               if (dir_prefix)
                        fname_out = concat_path_file(dir_prefix, fname_out);
+       }
 #if ENABLE_FEATURE_WGET_STATUSBAR
-       } else {
-               curfile = bb_get_last_path_component(fname_out);
+       curfile = bb_get_last_path_component_nostrip(fname_out);
 #endif
-       }
+
        /* Impossible?
        if ((opt & WGET_OPT_CONTINUE) && !fname_out)
                bb_error_msg_and_die("cannot specify continue (-c) without a filename (-O)"); */
index d4dba8e63e6d5164b6e042a196e98610dc863a3c..889fe49d8db84ce1e74a8f9667f9a6e5d7fc9ce8 100644 (file)
@@ -1141,12 +1141,11 @@ static int pseudo_exec(struct child_prog *child)
                }
        }
 
-
        /* Check if the command matches any busybox internal
         * commands ("applets") here.  Following discussions from
         * November 2000 on busybox@busybox.net, don't use
-        * bb_get_last_path_component().  This way explicit (with
-        * slashes) filenames will never be interpreted as an
+        * bb_get_last_path_component_nostrip().  This way explicit
+        * (with slashes) filenames will never be interpreted as an
         * applet, just like with builtins.  This way the user can
         * override an applet with an explicit filename reference.
         * The only downside to this change is that an explicit