Mercurial > code
annotate buf.c @ 161:81d64d4a5473
Complete rewrite of pack.c:
o more concise,
o for buffer, available in autoallocation and static,
author | David Demelier <markand@malikania.fr> |
---|---|
date | Mon, 03 Sep 2012 21:21:33 +0200 |
parents | 44e7b975618a |
children | 7f214f26a4c0 |
rev | line source |
---|---|
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
1 /* |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
2 * buf.c -- easy way to manipulate strings |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
3 * |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
4 * Copyright (c) 2011, 2012, David Demelier <markand@malikania.fr> |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
5 * |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
6 * Permission to use, copy, modify, and/or distribute this software for any |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
7 * purpose with or without fee is hereby granted, provided that the above |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
8 * copyright notice and this permission notice appear in all copies. |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
9 * |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
17 */ |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
18 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
19 #include <stdio.h> |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
20 #include <stdlib.h> |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
21 #include <string.h> |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
22 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
23 #include "buf.h" |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
24 |
128
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
25 #define BUF_AVAIL(buf) ((buf)->alsize - (buf)->length) |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
26 #define BUF_SAFE(buf) (!((buf)->flags & BUF_UNSAFE)) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
27 #define BUF_FIXED(buf) ((buf)->flags & BUF_FIXED) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
28 #define BUF_AUTO(buf) (buf->flags == 0) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
29 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
30 static void copy(struct buf *, const void *, size_t); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
31 static int grow(struct buf *, size_t); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
32 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
33 int |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
34 buf_init(struct buf *buf) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
35 { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
36 /* Set defaults if needed */ |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
37 buf->bsize = (buf->bsize <= 0) ? BUF_DEFAULT_BSIZE : buf->bsize; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
38 buf->alsize = buf->bsize + 1; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
39 buf->malloc = (buf->malloc == NULL) ? &malloc : buf->malloc; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
40 buf->realloc = (buf->realloc == NULL) ? &realloc : buf->realloc; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
41 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
42 if ((buf->text = buf->malloc(buf->alsize)) == NULL) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
43 return -1; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
44 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
45 memset(buf->text, 0, buf->alsize); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
46 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
47 return 0; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
48 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
49 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
50 /* |
133 | 51 * Valid options that can be set for a buffer : |
52 * l -> optional buf block size of type int | |
53 * m -> malloc function that must matches void * (*malloc)(size_t) | |
54 * r -> realloc function that must matches void * (*realloc)(void *, size_t) | |
55 * f -> buffer flags that are OR'ed | |
56 */ | |
57 | |
58 void | |
59 buf_set(struct buf *buf, const char *fmt, ...) | |
60 { | |
61 va_list ap; | |
62 const char *p; | |
63 | |
64 va_start(ap, fmt); | |
65 for (p = fmt; *p != '\0'; ++p) | |
66 switch (*p) { | |
67 case 'l': | |
68 buf->bsize = va_arg(ap, int); | |
69 break; | |
70 case 'm': | |
71 buf->malloc = va_arg(ap, void *(*)(size_t)); | |
72 break; | |
73 case 'r': | |
74 buf->realloc = va_arg(ap, void *(*)(void *, size_t)); | |
75 break; | |
76 case 'f': | |
77 case 't': | |
78 buf->flags = va_arg(ap, int); | |
79 break; | |
80 default: | |
81 break; | |
82 } | |
83 } | |
84 | |
85 /* | |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
86 * This function appends not more than max characters from str. |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
87 */ |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
88 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
89 int |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
90 buf_ncat(struct buf *buf, const char *str, size_t max) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
91 { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
92 size_t tocopy = max; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
93 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
94 for (tocopy = 0; str[tocopy] != '\0' && tocopy < max; ++tocopy) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
95 continue; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
96 |
128
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
97 if (BUF_AVAIL(buf) <= tocopy) { |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
98 /* Can't add more */ |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
99 if (BUF_SAFE(buf) && BUF_FIXED(buf)) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
100 return -1; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
101 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
102 if (BUF_AUTO(buf)) { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
103 if (grow(buf, tocopy) < 0) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
104 return -1; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
105 } else { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
106 /* String is unsafe, truncate to the available size */ |
128
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
107 tocopy = BUF_AVAIL(buf) - 1; |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
108 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
109 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
110 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
111 copy(buf, str, tocopy); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
112 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
113 return 0; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
114 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
115 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
116 /* |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
117 * Append the string str to the end of the string buffer. |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
118 */ |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
119 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
120 int |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
121 buf_cat(struct buf *buf, const char *str) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
122 { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
123 return buf_ncat(buf, str, strlen(str)); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
124 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
125 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
126 /* |
133 | 127 * Append the caracter c to the end of buffer |
128 */ | |
129 | |
130 int | |
131 buf_putc(struct buf *buf, int c) | |
132 { | |
141
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
133 char str[2] = { c, '\0' }; |
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
134 |
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
135 return buf_ncat(buf, str, 1); |
133 | 136 } |
137 | |
138 /* | |
127 | 139 * Concatenate the printf(3) like call to the string buffer, this function |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
140 * returns -1 on fixed safe buffer, otherwise 0 is returned if there |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
141 * is no allocation failure. |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
142 */ |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
143 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
144 int |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
145 buf_vprintf(struct buf *buf, const char *fmt, va_list ap) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
146 { |
128
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
147 int copied, rv = 0, done = 0; |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
148 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
149 if (BUF_FIXED(buf) && BUF_SAFE(buf)) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
150 return -1; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
151 |
127 | 152 do { |
153 copied = vsnprintf(&buf->text[buf->length], | |
154 BUF_AVAIL(buf), fmt, ap); | |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
155 |
127 | 156 if (copied >= (signed int)BUF_AVAIL(buf) || copied == -1) { |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
157 if (BUF_FIXED(buf)) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
158 done = 1; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
159 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
160 /* |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
161 * vsnprintf returns -1 on windows, we need to grow |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
162 * the buffer by block size. |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
163 */ |
128
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
164 if (grow(buf, buf->alsize + buf->bsize) < 0) { |
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
165 done = 1; |
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
166 rv = -1; |
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
167 } |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
168 } else { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
169 done = 1; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
170 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
171 } while (!done); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
172 |
128
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
173 buf->length = strlen(buf->text); |
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
174 |
7e72d4008f6d
Little changes in buffer
David Demelier <markand@malikania.fr>
parents:
127
diff
changeset
|
175 return rv; |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
176 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
177 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
178 int |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
179 buf_printf(struct buf *buf, const char *fmt, ...) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
180 { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
181 va_list ap; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
182 int rv; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
183 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
184 va_start(ap, fmt); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
185 rv = buf_vprintf(buf, fmt, ap); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
186 va_end(ap); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
187 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
188 return rv; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
189 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
190 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
191 /* |
133 | 192 * Realloc the string to it's size and remove useless bytes. |
129
2f71e113be63
Remove copy and ncopy and putc/puts
David Demelier <markand@malikania.fr>
parents:
128
diff
changeset
|
193 */ |
2f71e113be63
Remove copy and ncopy and putc/puts
David Demelier <markand@malikania.fr>
parents:
128
diff
changeset
|
194 |
2f71e113be63
Remove copy and ncopy and putc/puts
David Demelier <markand@malikania.fr>
parents:
128
diff
changeset
|
195 int |
133 | 196 buf_trim(struct buf *buf) |
129
2f71e113be63
Remove copy and ncopy and putc/puts
David Demelier <markand@malikania.fr>
parents:
128
diff
changeset
|
197 { |
133 | 198 if ((buf->text = realloc(buf->text, buf->length + 1)) == NULL) { |
199 buf->alsize = 0; | |
200 return -1; | |
201 } | |
129
2f71e113be63
Remove copy and ncopy and putc/puts
David Demelier <markand@malikania.fr>
parents:
128
diff
changeset
|
202 |
133 | 203 buf->alsize = buf->length + 1; |
129
2f71e113be63
Remove copy and ncopy and putc/puts
David Demelier <markand@malikania.fr>
parents:
128
diff
changeset
|
204 |
133 | 205 return 0; |
129
2f71e113be63
Remove copy and ncopy and putc/puts
David Demelier <markand@malikania.fr>
parents:
128
diff
changeset
|
206 } |
2f71e113be63
Remove copy and ncopy and putc/puts
David Demelier <markand@malikania.fr>
parents:
128
diff
changeset
|
207 |
2f71e113be63
Remove copy and ncopy and putc/puts
David Demelier <markand@malikania.fr>
parents:
128
diff
changeset
|
208 /* |
141
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
209 * Remove `n' characters from the buffer, a positive value will cut the string |
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
210 * from beginning, negative value will cut from end. |
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
211 */ |
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
212 |
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
213 void |
156 | 214 buf_cut(struct buf *buf, int start) |
141
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
215 { |
156 | 216 if ((start > 0 && start >= buf->length) || |
217 (start < 0 && (int)buf->length + start < 0)) | |
141
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
218 return; |
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
219 |
158 | 220 if (start < 0 && (int)buf->length + start >= 0) |
156 | 221 start = buf->length + start; |
141
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
222 |
156 | 223 buf->text[start] = '\0'; |
224 buf->length -= buf->length - start; | |
141
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
225 } |
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
226 |
5ed54050ae31
Added buf_cut, cut the buffer
David Demelier <markand@malikania.fr>
parents:
138
diff
changeset
|
227 /* |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
228 * Clear the string buffer. |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
229 */ |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
230 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
231 void |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
232 buf_clear(struct buf *buf) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
233 { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
234 memset(buf->text, 0, buf->alsize); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
235 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
236 buf->length = 0; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
237 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
238 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
239 void |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
240 buf_free(struct buf *buf) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
241 { |
133 | 242 if (buf != NULL) { |
243 buf_clear(buf); | |
244 free(buf->text); | |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
245 |
133 | 246 buf->text = NULL; |
247 buf->alsize = 0; | |
248 } | |
125
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
249 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
250 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
251 /* |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
252 * Append to the end of buffer the void ptr of count size. |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
253 */ |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
254 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
255 static void |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
256 copy(struct buf *buf, const void *ptr, size_t count) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
257 { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
258 memcpy(buf->text + buf->length, ptr, count); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
259 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
260 buf->text[buf->length + count] = '\0'; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
261 buf->length += count; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
262 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
263 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
264 /* |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
265 * Grow the text buffer until the available size fit the needed |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
266 * size. This function may return -1 on allocation failure. |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
267 */ |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
268 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
269 static int |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
270 grow(struct buf *buf, size_t needed) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
271 { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
272 while (BUF_AVAIL(buf) <= needed) { |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
273 buf->text = buf->realloc(buf->text, buf->alsize + buf->bsize); |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
274 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
275 if (buf->text == NULL) |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
276 return -1; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
277 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
278 buf->alsize += buf->bsize; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
279 } |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
280 |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
281 return 0; |
b9723c197038
Add brand new string buffer
David Demelier <markand@malikania.fr>
parents:
diff
changeset
|
282 } |