~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/lib/argv_split.c

Version: ~ [ linux-5.16-rc3 ] ~ [ linux-5.15.5 ] ~ [ linux-5.14.21 ] ~ [ linux-5.13.19 ] ~ [ linux-5.12.19 ] ~ [ linux-5.11.22 ] ~ [ linux-5.10.82 ] ~ [ linux-5.9.16 ] ~ [ linux-5.8.18 ] ~ [ linux-5.7.19 ] ~ [ linux-5.6.19 ] ~ [ linux-5.5.19 ] ~ [ linux-5.4.162 ] ~ [ linux-5.3.18 ] ~ [ linux-5.2.21 ] ~ [ linux-5.1.21 ] ~ [ linux-5.0.21 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.218 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.256 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.291 ] ~ [ linux-4.8.17 ] ~ [ linux-4.7.10 ] ~ [ linux-4.6.7 ] ~ [ linux-4.5.7 ] ~ [ linux-4.4.293 ] ~ [ linux-4.3.6 ] ~ [ linux-4.2.8 ] ~ [ linux-4.1.52 ] ~ [ linux-4.0.9 ] ~ [ linux-3.18.140 ] ~ [ linux-3.16.85 ] ~ [ linux-3.14.79 ] ~ [ linux-3.12.74 ] ~ [ linux-3.10.108 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.5 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

Diff markup

Differences between /lib/argv_split.c (Version linux-4.6.7) and /lib/argv_split.c (Version linux-4.16.18)


                                                   >>   1 // SPDX-License-Identifier: GPL-2.0
  1 /*                                                  2 /*
  2  * Helper function for splitting a string into      3  * Helper function for splitting a string into an argv-like array.
  3  */                                                 4  */
  4                                                     5 
  5 #include <linux/kernel.h>                           6 #include <linux/kernel.h>
  6 #include <linux/ctype.h>                            7 #include <linux/ctype.h>
  7 #include <linux/string.h>                           8 #include <linux/string.h>
  8 #include <linux/slab.h>                             9 #include <linux/slab.h>
  9 #include <linux/export.h>                          10 #include <linux/export.h>
 10                                                    11 
 11 static int count_argc(const char *str)             12 static int count_argc(const char *str)
 12 {                                                  13 {
 13         int count = 0;                             14         int count = 0;
 14         bool was_space;                            15         bool was_space;
 15                                                    16 
 16         for (was_space = true; *str; str++) {      17         for (was_space = true; *str; str++) {
 17                 if (isspace(*str)) {               18                 if (isspace(*str)) {
 18                         was_space = true;          19                         was_space = true;
 19                 } else if (was_space) {            20                 } else if (was_space) {
 20                         was_space = false;         21                         was_space = false;
 21                         count++;                   22                         count++;
 22                 }                                  23                 }
 23         }                                          24         }
 24                                                    25 
 25         return count;                              26         return count;
 26 }                                                  27 }
 27                                                    28 
 28 /**                                                29 /**
 29  * argv_free - free an argv                        30  * argv_free - free an argv
 30  * @argv - the argument vector to be freed         31  * @argv - the argument vector to be freed
 31  *                                                 32  *
 32  * Frees an argv and the strings it points to.     33  * Frees an argv and the strings it points to.
 33  */                                                34  */
 34 void argv_free(char **argv)                        35 void argv_free(char **argv)
 35 {                                                  36 {
 36         argv--;                                    37         argv--;
 37         kfree(argv[0]);                            38         kfree(argv[0]);
 38         kfree(argv);                               39         kfree(argv);
 39 }                                                  40 }
 40 EXPORT_SYMBOL(argv_free);                          41 EXPORT_SYMBOL(argv_free);
 41                                                    42 
 42 /**                                                43 /**
 43  * argv_split - split a string at whitespace,      44  * argv_split - split a string at whitespace, returning an argv
 44  * @gfp: the GFP mask used to allocate memory      45  * @gfp: the GFP mask used to allocate memory
 45  * @str: the string to be split                    46  * @str: the string to be split
 46  * @argcp: returned argument count                 47  * @argcp: returned argument count
 47  *                                                 48  *
 48  * Returns an array of pointers to strings whi     49  * Returns an array of pointers to strings which are split out from
 49  * @str.  This is performed by strictly splitt     50  * @str.  This is performed by strictly splitting on white-space; no
 50  * quote processing is performed.  Multiple wh     51  * quote processing is performed.  Multiple whitespace characters are
 51  * considered to be a single argument separato     52  * considered to be a single argument separator.  The returned array
 52  * is always NULL-terminated.  Returns NULL on     53  * is always NULL-terminated.  Returns NULL on memory allocation
 53  * failure.                                        54  * failure.
 54  *                                                 55  *
 55  * The source string at `str' may be undergoin     56  * The source string at `str' may be undergoing concurrent alteration via
 56  * userspace sysctl activity (at least).  The      57  * userspace sysctl activity (at least).  The argv_split() implementation
 57  * attempts to handle this gracefully by takin     58  * attempts to handle this gracefully by taking a local copy to work on.
 58  */                                                59  */
 59 char **argv_split(gfp_t gfp, const char *str,      60 char **argv_split(gfp_t gfp, const char *str, int *argcp)
 60 {                                                  61 {
 61         char *argv_str;                            62         char *argv_str;
 62         bool was_space;                            63         bool was_space;
 63         char **argv, **argv_ret;                   64         char **argv, **argv_ret;
 64         int argc;                                  65         int argc;
 65                                                    66 
 66         argv_str = kstrndup(str, KMALLOC_MAX_S     67         argv_str = kstrndup(str, KMALLOC_MAX_SIZE - 1, gfp);
 67         if (!argv_str)                             68         if (!argv_str)
 68                 return NULL;                       69                 return NULL;
 69                                                    70 
 70         argc = count_argc(argv_str);               71         argc = count_argc(argv_str);
 71         argv = kmalloc(sizeof(*argv) * (argc +     72         argv = kmalloc(sizeof(*argv) * (argc + 2), gfp);
 72         if (!argv) {                               73         if (!argv) {
 73                 kfree(argv_str);                   74                 kfree(argv_str);
 74                 return NULL;                       75                 return NULL;
 75         }                                          76         }
 76                                                    77 
 77         *argv = argv_str;                          78         *argv = argv_str;
 78         argv_ret = ++argv;                         79         argv_ret = ++argv;
 79         for (was_space = true; *argv_str; argv     80         for (was_space = true; *argv_str; argv_str++) {
 80                 if (isspace(*argv_str)) {          81                 if (isspace(*argv_str)) {
 81                         was_space = true;          82                         was_space = true;
 82                         *argv_str = 0;             83                         *argv_str = 0;
 83                 } else if (was_space) {            84                 } else if (was_space) {
 84                         was_space = false;         85                         was_space = false;
 85                         *argv++ = argv_str;        86                         *argv++ = argv_str;
 86                 }                                  87                 }
 87         }                                          88         }
 88         *argv = NULL;                              89         *argv = NULL;
 89                                                    90 
 90         if (argcp)                                 91         if (argcp)
 91                 *argcp = argc;                     92                 *argcp = argc;
 92         return argv_ret;                           93         return argv_ret;
 93 }                                                  94 }
 94 EXPORT_SYMBOL(argv_split);                         95 EXPORT_SYMBOL(argv_split);
 95                                                    96 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | Wiki (Japanese) | Wiki (English) | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

osdn.jp