Mercurial > libjeffpc
annotate str.c @ 257:068955620d10
str: str_free(NULL) should assert
str_free is essentially an internal function. Therefore, it doesn't have to
be nice to use, and instead it should have extra sanity checking instead.
Signed-off-by: Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
author | Josef 'Jeff' Sipek <jeffpc@josefsipek.net> |
---|---|
date | Wed, 12 Jul 2017 09:17:17 +0300 |
parents | 7b1c311a77e4 |
children | 88f777a374ad |
rev | line source |
---|---|
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
1 /* |
155
a68a3c91f9b6
str: use the generic getref/putref generator macros
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
120
diff
changeset
|
2 * Copyright (c) 2014-2017 Josef 'Jeff' Sipek <jeffpc@josefsipek.net> |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
3 * |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
4 * Permission is hereby granted, free of charge, to any person obtaining a copy |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
5 * of this software and associated documentation files (the "Software"), to deal |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
6 * in the Software without restriction, including without limitation the rights |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
8 * copies of the Software, and to permit persons to whom the Software is |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
9 * furnished to do so, subject to the following conditions: |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
10 * |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
11 * The above copyright notice and this permission notice shall be included in |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
12 * all copies or substantial portions of the Software. |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
13 * |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
19 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
20 * SOFTWARE. |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
21 */ |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
22 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
23 #include <stdlib.h> |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
24 #include <stdbool.h> |
41
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
25 #include <alloca.h> |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
26 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
27 #include <jeffpc/str.h> |
159
59d3f2a362a9
str: use the libjeffpc slab allocator API instead of libumem
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
155
diff
changeset
|
28 #include <jeffpc/mem.h> |
19
017a4abcfe3d
init: add a single initialize-the-library function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
12
diff
changeset
|
29 #include <jeffpc/jeffpc.h> |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
30 |
190
471436f681f3
str: preallocate the empty string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
174
diff
changeset
|
31 static struct str empty_string = STR_STATIC_INITIALIZER(""); |
192
94c9db63f1c3
str: preallocate " " string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
191
diff
changeset
|
32 static struct str one_char[128] = { |
230
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
33 ['\''] = STR_STATIC_INITIALIZER("'"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
34 ['\\'] = STR_STATIC_INITIALIZER("\\"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
35 ['\n'] = STR_STATIC_INITIALIZER("\n"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
36 ['\r'] = STR_STATIC_INITIALIZER("\r"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
37 ['\t'] = STR_STATIC_INITIALIZER("\t"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
38 |
192
94c9db63f1c3
str: preallocate " " string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
191
diff
changeset
|
39 [' '] = STR_STATIC_INITIALIZER(" "), |
230
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
40 ['!'] = STR_STATIC_INITIALIZER("!"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
41 ['"'] = STR_STATIC_INITIALIZER("\""), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
42 ['#'] = STR_STATIC_INITIALIZER("#"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
43 ['$'] = STR_STATIC_INITIALIZER("$"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
44 ['%'] = STR_STATIC_INITIALIZER("%"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
45 ['&'] = STR_STATIC_INITIALIZER("&"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
46 ['('] = STR_STATIC_INITIALIZER("("), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
47 [')'] = STR_STATIC_INITIALIZER(")"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
48 ['*'] = STR_STATIC_INITIALIZER("*"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
49 ['+'] = STR_STATIC_INITIALIZER("+"), |
197
f35a81a465db
str: preallocate "," string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
196
diff
changeset
|
50 [','] = STR_STATIC_INITIALIZER(","), |
194
4b12a5cec16b
str: preallocate "-" string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
193
diff
changeset
|
51 ['-'] = STR_STATIC_INITIALIZER("-"), |
230
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
52 ['-'] = STR_STATIC_INITIALIZER("-"), |
193
f377dd66ddb4
str: preallocate "." string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
192
diff
changeset
|
53 ['.'] = STR_STATIC_INITIALIZER("."), |
195
f02f6cd40052
str: preallocate "/" string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
194
diff
changeset
|
54 ['/'] = STR_STATIC_INITIALIZER("/"), |
230
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
55 [':'] = STR_STATIC_INITIALIZER(":"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
56 [';'] = STR_STATIC_INITIALIZER(";"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
57 ['<'] = STR_STATIC_INITIALIZER("<"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
58 ['='] = STR_STATIC_INITIALIZER("="), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
59 ['>'] = STR_STATIC_INITIALIZER(">"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
60 ['?'] = STR_STATIC_INITIALIZER("?"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
61 ['@'] = STR_STATIC_INITIALIZER("@"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
62 ['['] = STR_STATIC_INITIALIZER("["), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
63 [']'] = STR_STATIC_INITIALIZER("]"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
64 ['^'] = STR_STATIC_INITIALIZER("^"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
65 ['_'] = STR_STATIC_INITIALIZER("_"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
66 ['`'] = STR_STATIC_INITIALIZER("`"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
67 ['{'] = STR_STATIC_INITIALIZER("{"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
68 ['|'] = STR_STATIC_INITIALIZER("|"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
69 ['}'] = STR_STATIC_INITIALIZER("}"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
70 ['~'] = STR_STATIC_INITIALIZER("~"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
71 |
198
dc5dc389d0d2
str: preallocate "0" .. "9" strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
197
diff
changeset
|
72 ['0'] = STR_STATIC_INITIALIZER("0"), |
dc5dc389d0d2
str: preallocate "0" .. "9" strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
197
diff
changeset
|
73 ['1'] = STR_STATIC_INITIALIZER("1"), |
dc5dc389d0d2
str: preallocate "0" .. "9" strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
197
diff
changeset
|
74 ['2'] = STR_STATIC_INITIALIZER("2"), |
dc5dc389d0d2
str: preallocate "0" .. "9" strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
197
diff
changeset
|
75 ['3'] = STR_STATIC_INITIALIZER("3"), |
dc5dc389d0d2
str: preallocate "0" .. "9" strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
197
diff
changeset
|
76 ['4'] = STR_STATIC_INITIALIZER("4"), |
dc5dc389d0d2
str: preallocate "0" .. "9" strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
197
diff
changeset
|
77 ['5'] = STR_STATIC_INITIALIZER("5"), |
dc5dc389d0d2
str: preallocate "0" .. "9" strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
197
diff
changeset
|
78 ['6'] = STR_STATIC_INITIALIZER("6"), |
dc5dc389d0d2
str: preallocate "0" .. "9" strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
197
diff
changeset
|
79 ['7'] = STR_STATIC_INITIALIZER("7"), |
dc5dc389d0d2
str: preallocate "0" .. "9" strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
197
diff
changeset
|
80 ['8'] = STR_STATIC_INITIALIZER("8"), |
dc5dc389d0d2
str: preallocate "0" .. "9" strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
197
diff
changeset
|
81 ['9'] = STR_STATIC_INITIALIZER("9"), |
230
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
82 |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
83 ['A'] = STR_STATIC_INITIALIZER("A"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
84 ['B'] = STR_STATIC_INITIALIZER("B"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
85 ['C'] = STR_STATIC_INITIALIZER("C"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
86 ['D'] = STR_STATIC_INITIALIZER("D"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
87 ['E'] = STR_STATIC_INITIALIZER("E"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
88 ['F'] = STR_STATIC_INITIALIZER("F"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
89 ['G'] = STR_STATIC_INITIALIZER("G"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
90 ['H'] = STR_STATIC_INITIALIZER("H"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
91 ['I'] = STR_STATIC_INITIALIZER("I"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
92 ['J'] = STR_STATIC_INITIALIZER("J"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
93 ['K'] = STR_STATIC_INITIALIZER("K"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
94 ['L'] = STR_STATIC_INITIALIZER("L"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
95 ['M'] = STR_STATIC_INITIALIZER("M"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
96 ['N'] = STR_STATIC_INITIALIZER("N"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
97 ['O'] = STR_STATIC_INITIALIZER("O"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
98 ['P'] = STR_STATIC_INITIALIZER("P"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
99 ['Q'] = STR_STATIC_INITIALIZER("Q"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
100 ['R'] = STR_STATIC_INITIALIZER("R"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
101 ['S'] = STR_STATIC_INITIALIZER("S"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
102 ['T'] = STR_STATIC_INITIALIZER("T"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
103 ['U'] = STR_STATIC_INITIALIZER("U"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
104 ['V'] = STR_STATIC_INITIALIZER("V"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
105 ['W'] = STR_STATIC_INITIALIZER("W"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
106 ['X'] = STR_STATIC_INITIALIZER("X"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
107 ['Y'] = STR_STATIC_INITIALIZER("Y"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
108 ['Z'] = STR_STATIC_INITIALIZER("Z"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
109 |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
110 ['a'] = STR_STATIC_INITIALIZER("a"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
111 ['b'] = STR_STATIC_INITIALIZER("b"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
112 ['c'] = STR_STATIC_INITIALIZER("c"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
113 ['d'] = STR_STATIC_INITIALIZER("d"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
114 ['e'] = STR_STATIC_INITIALIZER("e"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
115 ['f'] = STR_STATIC_INITIALIZER("f"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
116 ['g'] = STR_STATIC_INITIALIZER("g"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
117 ['h'] = STR_STATIC_INITIALIZER("h"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
118 ['i'] = STR_STATIC_INITIALIZER("i"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
119 ['j'] = STR_STATIC_INITIALIZER("j"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
120 ['k'] = STR_STATIC_INITIALIZER("k"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
121 ['l'] = STR_STATIC_INITIALIZER("l"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
122 ['m'] = STR_STATIC_INITIALIZER("m"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
123 ['n'] = STR_STATIC_INITIALIZER("n"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
124 ['o'] = STR_STATIC_INITIALIZER("o"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
125 ['p'] = STR_STATIC_INITIALIZER("p"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
126 ['q'] = STR_STATIC_INITIALIZER("q"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
127 ['r'] = STR_STATIC_INITIALIZER("r"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
128 ['s'] = STR_STATIC_INITIALIZER("s"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
129 ['t'] = STR_STATIC_INITIALIZER("t"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
130 ['u'] = STR_STATIC_INITIALIZER("u"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
131 ['v'] = STR_STATIC_INITIALIZER("v"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
132 ['w'] = STR_STATIC_INITIALIZER("w"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
133 ['x'] = STR_STATIC_INITIALIZER("x"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
134 ['y'] = STR_STATIC_INITIALIZER("y"), |
6c9d77cf8c1e
str: preallocate more single-char strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
228
diff
changeset
|
135 ['z'] = STR_STATIC_INITIALIZER("z"), |
192
94c9db63f1c3
str: preallocate " " string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
191
diff
changeset
|
136 }; |
191
626a2d545bbe
str: allow simple static preallocation of one-char long strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
190
diff
changeset
|
137 |
159
59d3f2a362a9
str: use the libjeffpc slab allocator API instead of libumem
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
155
diff
changeset
|
138 static struct mem_cache *str_cache; |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
139 |
174
532cbad2de95
init: mark val and str subsystem init functions as constructors
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
165
diff
changeset
|
140 static void __attribute__((constructor)) init_str_subsys(void) |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
141 { |
159
59d3f2a362a9
str: use the libjeffpc slab allocator API instead of libumem
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
155
diff
changeset
|
142 str_cache = mem_cache_create("str-cache", sizeof(struct str), 0); |
59d3f2a362a9
str: use the libjeffpc slab allocator API instead of libumem
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
155
diff
changeset
|
143 ASSERT(!IS_ERR(str_cache)); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
144 } |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
145 |
224
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
146 static struct str *__get_preallocated(const char *s) |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
147 { |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
148 unsigned char first_char; |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
149 |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
150 /* NULL or empty string */ |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
151 if (!s || (s[0] == '\0')) |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
152 return &empty_string; |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
153 |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
154 first_char = s[0]; |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
155 |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
156 /* preallocated one-char long strings of 7-bit ASCII */ |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
157 if ((first_char > '\0') && (first_char < '\x7f') && |
227
32fc570177ef
str: rename static_alloc to static_struct
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
226
diff
changeset
|
158 (s[1] == '\0') && one_char[first_char].static_struct) |
224
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
159 return &one_char[first_char]; |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
160 |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
161 /* nothing pre-allocated */ |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
162 return NULL; |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
163 } |
eabb98107cba
str: move preallocation lookups into a helper function
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
198
diff
changeset
|
164 |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
165 static struct str *__alloc(char *s, bool heapalloc, bool mustdup) |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
166 { |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
167 struct str *str; |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
168 bool copy; |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
169 |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
170 /* sanity check */ |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
171 if (mustdup) |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
172 ASSERT(!heapalloc); |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
173 |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
174 /* check preallocated strings */ |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
175 str = __get_preallocated(s); |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
176 if (str) |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
177 goto out; |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
178 |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
179 /* can we inline it? */ |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
180 copy = (strlen(s) <= STR_INLINE_LEN); |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
181 |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
182 /* we'll be storing a pointer - strdup as necessary */ |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
183 if (!copy && mustdup) { |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
184 s = strdup(s); |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
185 if (!s) |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
186 goto out; |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
187 |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
188 /* we're now using the heap */ |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
189 heapalloc = true; |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
190 } |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
191 |
159
59d3f2a362a9
str: use the libjeffpc slab allocator API instead of libumem
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
155
diff
changeset
|
192 str = mem_cache_alloc(str_cache); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
193 if (!str) |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
194 goto out; |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
195 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
196 refcnt_init(&str->refcnt, 1); |
227
32fc570177ef
str: rename static_alloc to static_struct
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
226
diff
changeset
|
197 str->static_struct = false; |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
198 str->static_alloc = copy || !heapalloc; |
165
cae007c76340
str: use a union and a flag to save str space
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
162
diff
changeset
|
199 str->inline_alloc = copy; |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
200 |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
201 if (copy) { |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
202 strcpy(str->inline_str, s); |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
203 if (heapalloc) |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
204 free(s); |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
205 } else { |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
206 str->str = s; |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
207 } |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
208 |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
209 return str; |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
210 |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
211 out: |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
212 if (heapalloc) |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
213 free(s); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
214 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
215 return str; |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
216 } |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
217 |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
218 /* |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
219 * Passed in str cannot be freed, and it must be dup'd. (E.g., it could be |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
220 * a string on the stack.) |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
221 */ |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
222 struct str *str_dup(const char *s) |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
223 { |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
224 return __alloc((char *) s, false, true); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
225 } |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
226 |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
227 /* Passed in str must be freed. */ |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
228 struct str *str_alloc(char *s) |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
229 { |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
230 return __alloc(s, true, false); |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
231 } |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
232 |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
233 /* |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
234 * Passed in str cannot be freed, and it doesn't have to be dup'd. (E.g., |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
235 * it could be a string in .rodata.) |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
236 */ |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
237 struct str *str_alloc_static(const char *s) |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
238 { |
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
239 return __alloc((char *) s, false, false); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
240 } |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
241 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
242 size_t str_len(const struct str *s) |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
243 { |
165
cae007c76340
str: use a union and a flag to save str space
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
162
diff
changeset
|
244 return strlen(str_cstr(s)); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
245 } |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
246 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
247 int str_cmp(const struct str *a, const struct str *b) |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
248 { |
165
cae007c76340
str: use a union and a flag to save str space
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
162
diff
changeset
|
249 return strcmp(str_cstr(a), str_cstr(b)); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
250 } |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
251 |
232
7b1c311a77e4
str: the number of strings passed to str_cat() should be a size_t
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
230
diff
changeset
|
252 struct str *str_cat(size_t n, ...) |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
253 { |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
254 size_t totallen; |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
255 struct str *ret; |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
256 char *buf, *out; |
41
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
257 size_t *len; |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
258 va_list ap; |
232
7b1c311a77e4
str: the number of strings passed to str_cat() should be a size_t
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
230
diff
changeset
|
259 size_t i; |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
260 |
41
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
261 if (!n) |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
262 return NULL; |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
263 |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
264 if (n == 1) { |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
265 va_start(ap, n); |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
266 ret = va_arg(ap, struct str *); |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
267 va_end(ap); |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
268 return ret; |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
269 } |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
270 |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
271 totallen = 0; |
41
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
272 len = alloca(sizeof(size_t) * n); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
273 |
41
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
274 va_start(ap, n); |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
275 for (i = 0; i < n; i++) { |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
276 struct str *str = va_arg(ap, struct str *); |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
277 |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
278 if (!str) |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
279 continue; |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
280 |
165
cae007c76340
str: use a union and a flag to save str space
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
162
diff
changeset
|
281 len[i] = strlen(str_cstr(str)); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
282 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
283 totallen += len[i]; |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
284 } |
41
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
285 va_end(ap); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
286 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
287 buf = malloc(totallen + 1); |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
288 ASSERT(buf); |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
289 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
290 out = buf; |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
291 |
41
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
292 va_start(ap, n); |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
293 for (i = 0; i < n; i++) { |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
294 struct str *str = va_arg(ap, struct str *); |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
295 |
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
296 if (!str) |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
297 continue; |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
298 |
165
cae007c76340
str: use a union and a flag to save str space
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
162
diff
changeset
|
299 strcpy(out, str_cstr(str)); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
300 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
301 out += len[i]; |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
302 |
41
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
303 str_putref(str); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
304 } |
41
ce17740b7bf2
str: str_cat should handle unlimited number of arguments
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
19
diff
changeset
|
305 va_end(ap); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
306 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
307 ret = str_alloc(buf); |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
308 ASSERT(ret); |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
309 |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
310 return ret; |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
311 } |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
312 |
120
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
313 struct str *str_vprintf(const char *fmt, va_list args) |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
314 { |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
315 char *tmp; |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
316 int ret; |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
317 |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
318 ret = vasprintf(&tmp, fmt, args); |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
319 if (ret < 0) |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
320 return ERR_PTR(-errno); |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
321 if (ret == 0) |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
322 return NULL; |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
323 |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
324 return STR_ALLOC(tmp); |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
325 } |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
326 |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
327 struct str *str_printf(const char *fmt, ...) |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
328 { |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
329 struct str *ret; |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
330 va_list args; |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
331 |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
332 va_start(args, fmt); |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
333 ret = str_vprintf(fmt, args); |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
334 va_end(args); |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
335 |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
336 return ret; |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
337 } |
b43b8fc87c0b
str: introduce str_printf and str_vprintf
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
67
diff
changeset
|
338 |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
339 void str_free(struct str *str) |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
340 { |
257
068955620d10
str: str_free(NULL) should assert
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
232
diff
changeset
|
341 ASSERT(str); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
342 ASSERT3U(refcnt_read(&str->refcnt), ==, 0); |
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
343 |
228
2ffb2b971149
str: add support for static strings
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
227
diff
changeset
|
344 if (!str->inline_alloc && !str->static_alloc) |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
345 free(str->str); |
159
59d3f2a362a9
str: use the libjeffpc slab allocator API instead of libumem
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
155
diff
changeset
|
346 mem_cache_free(str_cache, str); |
6
4317d47b267f
str: a reference counted string
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff
changeset
|
347 } |