1 /* Copyright (C) 2018 by John Schember <john@nachtimwald.com>
3 * Permission to use, copy, modify, and distribute this
4 * software and its documentation for any purpose and without
5 * fee is hereby granted, provided that the above copyright
6 * notice appear in all copies and that both that copyright
7 * notice and this permission notice appear in supporting
8 * documentation, and that the name of M.I.T. not be used in
9 * advertising or publicity pertaining to distribution of the
10 * software without specific, written prior permission.
11 * M.I.T. makes no representations about the suitability of
12 * this software for any purpose. It is provided "as is"
13 * without express or implied warranty.
20 #include "ares_setup.h"
21 #include "ares_strsplit.h"
23 #include "ares_private.h"
25 static int list_contains(char * const *list, size_t num_elem, const char *str, int insensitive)
31 for (i=0; i<num_elem; i++)
36 if (strnicmp(list[i], str, len) == 0)
38 if (strncasecmp(list[i], str, len) == 0)
44 if (strncmp(list[i], str, len) == 0)
52 static int is_delim(char c, const char *delims, size_t num_delims)
56 for (i=0; i<num_delims; i++)
65 void ares_strsplit_free(char **elms, size_t num_elm)
72 for (i=0; i<num_elm; i++)
78 char **ares_strsplit(const char *in, const char *delms, int make_set, size_t *num_elm)
89 if (in == NULL || delms == NULL || num_elm == NULL)
95 num_delims = strlen(delms);
97 /* Figure out how many elements. */
99 for (i=0; i<in_len; i++)
101 if (is_delim(in[i], delms, num_delims))
107 /* Copy of input so we can cut it up. */
108 parsestr = ares_strdup(in);
109 if (parsestr == NULL)
112 /* Temporary array to store locations of start of each element
113 * within parsestr. */
114 temp = ares_malloc(nelms * sizeof(*temp));
122 for (i=0; i<in_len && cnt<nelms; i++)
124 if (!is_delim(parsestr[i], delms, num_delims))
127 /* Replace sep with NULL. */
129 /* Add the pointer to the array of elements */
130 temp[cnt] = parsestr+i+1;
134 /* Copy each element to our output array. */
135 out = ares_malloc(nelms * sizeof(*out));
144 for (i=0; i<cnt; i++)
146 if (temp[i][0] == '\0')
149 if (make_set && list_contains(out, nelms, temp[i], 1))
152 out[nelms] = ares_strdup(temp[i]);
153 if (out[nelms] == NULL)
155 ares_strsplit_free(out, nelms);
164 /* If there are no elements don't return an empty allocated
168 ares_strsplit_free(out, nelms);
172 /* Get the true number of elements (recalculated because of make_set) */