Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
torvalds
GitHub Repository: torvalds/linux
Path: blob/master/tools/lib/argv_split.c
26278 views
1
// SPDX-License-Identifier: GPL-2.0
2
/*
3
* Helper function for splitting a string into an argv-like array.
4
*/
5
6
#include <stdlib.h>
7
#include <linux/kernel.h>
8
#include <linux/ctype.h>
9
#include <linux/string.h>
10
11
static const char *skip_arg(const char *cp)
12
{
13
while (*cp && !isspace(*cp))
14
cp++;
15
16
return cp;
17
}
18
19
static int count_argc(const char *str)
20
{
21
int count = 0;
22
23
while (*str) {
24
str = skip_spaces(str);
25
if (*str) {
26
count++;
27
str = skip_arg(str);
28
}
29
}
30
31
return count;
32
}
33
34
/**
35
* argv_free - free an argv
36
* @argv - the argument vector to be freed
37
*
38
* Frees an argv and the strings it points to.
39
*/
40
void argv_free(char **argv)
41
{
42
char **p;
43
for (p = argv; *p; p++) {
44
free(*p);
45
*p = NULL;
46
}
47
48
free(argv);
49
}
50
51
/**
52
* argv_split - split a string at whitespace, returning an argv
53
* @str: the string to be split
54
* @argcp: returned argument count
55
*
56
* Returns an array of pointers to strings which are split out from
57
* @str. This is performed by strictly splitting on white-space; no
58
* quote processing is performed. Multiple whitespace characters are
59
* considered to be a single argument separator. The returned array
60
* is always NULL-terminated. Returns NULL on memory allocation
61
* failure.
62
*/
63
char **argv_split(const char *str, int *argcp)
64
{
65
int argc = count_argc(str);
66
char **argv = calloc(argc + 1, sizeof(*argv));
67
char **argvp;
68
69
if (argv == NULL)
70
goto out;
71
72
if (argcp)
73
*argcp = argc;
74
75
argvp = argv;
76
77
while (*str) {
78
str = skip_spaces(str);
79
80
if (*str) {
81
const char *p = str;
82
char *t;
83
84
str = skip_arg(str);
85
86
t = strndup(p, str-p);
87
if (t == NULL)
88
goto fail;
89
*argvp++ = t;
90
}
91
}
92
*argvp = NULL;
93
94
out:
95
return argv;
96
97
fail:
98
argv_free(argv);
99
return NULL;
100
}
101
102