1*663afb9bSAndroid Build Coastguard Worker /*
2*663afb9bSAndroid Build Coastguard Worker * Copyright (c) 2003-2007 Niels Provos <[email protected]>
3*663afb9bSAndroid Build Coastguard Worker * Copyright (c) 2007-2012 Niels Provos and Nick Mathewson
4*663afb9bSAndroid Build Coastguard Worker *
5*663afb9bSAndroid Build Coastguard Worker * Redistribution and use in source and binary forms, with or without
6*663afb9bSAndroid Build Coastguard Worker * modification, are permitted provided that the following conditions
7*663afb9bSAndroid Build Coastguard Worker * are met:
8*663afb9bSAndroid Build Coastguard Worker * 1. Redistributions of source code must retain the above copyright
9*663afb9bSAndroid Build Coastguard Worker * notice, this list of conditions and the following disclaimer.
10*663afb9bSAndroid Build Coastguard Worker * 2. Redistributions in binary form must reproduce the above copyright
11*663afb9bSAndroid Build Coastguard Worker * notice, this list of conditions and the following disclaimer in the
12*663afb9bSAndroid Build Coastguard Worker * documentation and/or other materials provided with the distribution.
13*663afb9bSAndroid Build Coastguard Worker * 3. The name of the author may not be used to endorse or promote products
14*663afb9bSAndroid Build Coastguard Worker * derived from this software without specific prior written permission.
15*663afb9bSAndroid Build Coastguard Worker *
16*663afb9bSAndroid Build Coastguard Worker * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17*663afb9bSAndroid Build Coastguard Worker * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18*663afb9bSAndroid Build Coastguard Worker * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19*663afb9bSAndroid Build Coastguard Worker * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
20*663afb9bSAndroid Build Coastguard Worker * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
21*663afb9bSAndroid Build Coastguard Worker * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22*663afb9bSAndroid Build Coastguard Worker * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23*663afb9bSAndroid Build Coastguard Worker * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24*663afb9bSAndroid Build Coastguard Worker * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25*663afb9bSAndroid Build Coastguard Worker * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26*663afb9bSAndroid Build Coastguard Worker */
27*663afb9bSAndroid Build Coastguard Worker #include "util-internal.h"
28*663afb9bSAndroid Build Coastguard Worker
29*663afb9bSAndroid Build Coastguard Worker #ifdef _WIN32
30*663afb9bSAndroid Build Coastguard Worker #include <winsock2.h>
31*663afb9bSAndroid Build Coastguard Worker #include <windows.h>
32*663afb9bSAndroid Build Coastguard Worker #endif
33*663afb9bSAndroid Build Coastguard Worker
34*663afb9bSAndroid Build Coastguard Worker #include "event2/event-config.h"
35*663afb9bSAndroid Build Coastguard Worker
36*663afb9bSAndroid Build Coastguard Worker #include <sys/types.h>
37*663afb9bSAndroid Build Coastguard Worker #include <sys/stat.h>
38*663afb9bSAndroid Build Coastguard Worker #ifdef EVENT__HAVE_SYS_TIME_H
39*663afb9bSAndroid Build Coastguard Worker #include <sys/time.h>
40*663afb9bSAndroid Build Coastguard Worker #endif
41*663afb9bSAndroid Build Coastguard Worker #include <sys/queue.h>
42*663afb9bSAndroid Build Coastguard Worker #ifndef _WIN32
43*663afb9bSAndroid Build Coastguard Worker #include <sys/socket.h>
44*663afb9bSAndroid Build Coastguard Worker #include <sys/wait.h>
45*663afb9bSAndroid Build Coastguard Worker #include <signal.h>
46*663afb9bSAndroid Build Coastguard Worker #include <unistd.h>
47*663afb9bSAndroid Build Coastguard Worker #include <netdb.h>
48*663afb9bSAndroid Build Coastguard Worker #endif
49*663afb9bSAndroid Build Coastguard Worker #include <stdlib.h>
50*663afb9bSAndroid Build Coastguard Worker #include <stdio.h>
51*663afb9bSAndroid Build Coastguard Worker #include <string.h>
52*663afb9bSAndroid Build Coastguard Worker #include <errno.h>
53*663afb9bSAndroid Build Coastguard Worker #include <assert.h>
54*663afb9bSAndroid Build Coastguard Worker
55*663afb9bSAndroid Build Coastguard Worker #include "event2/event.h"
56*663afb9bSAndroid Build Coastguard Worker #include "event2/buffer.h"
57*663afb9bSAndroid Build Coastguard Worker #include "event2/buffer_compat.h"
58*663afb9bSAndroid Build Coastguard Worker #include "event2/util.h"
59*663afb9bSAndroid Build Coastguard Worker
60*663afb9bSAndroid Build Coastguard Worker #include "defer-internal.h"
61*663afb9bSAndroid Build Coastguard Worker #include "evbuffer-internal.h"
62*663afb9bSAndroid Build Coastguard Worker #include "log-internal.h"
63*663afb9bSAndroid Build Coastguard Worker
64*663afb9bSAndroid Build Coastguard Worker #include "regress.h"
65*663afb9bSAndroid Build Coastguard Worker
66*663afb9bSAndroid Build Coastguard Worker #define ARRAY_SIZE(a) (sizeof(a) / sizeof(a[0]))
67*663afb9bSAndroid Build Coastguard Worker
68*663afb9bSAndroid Build Coastguard Worker /* Validates that an evbuffer is good. Returns false if it isn't, true if it
69*663afb9bSAndroid Build Coastguard Worker * is*/
70*663afb9bSAndroid Build Coastguard Worker static int
evbuffer_validate_(struct evbuffer * buf)71*663afb9bSAndroid Build Coastguard Worker evbuffer_validate_(struct evbuffer *buf)
72*663afb9bSAndroid Build Coastguard Worker {
73*663afb9bSAndroid Build Coastguard Worker struct evbuffer_chain *chain;
74*663afb9bSAndroid Build Coastguard Worker size_t sum = 0;
75*663afb9bSAndroid Build Coastguard Worker int found_last_with_datap = 0;
76*663afb9bSAndroid Build Coastguard Worker
77*663afb9bSAndroid Build Coastguard Worker if (buf->first == NULL) {
78*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->last == NULL);
79*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->total_len == 0);
80*663afb9bSAndroid Build Coastguard Worker }
81*663afb9bSAndroid Build Coastguard Worker
82*663afb9bSAndroid Build Coastguard Worker chain = buf->first;
83*663afb9bSAndroid Build Coastguard Worker
84*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->last_with_datap);
85*663afb9bSAndroid Build Coastguard Worker if (buf->last_with_datap == &buf->first)
86*663afb9bSAndroid Build Coastguard Worker found_last_with_datap = 1;
87*663afb9bSAndroid Build Coastguard Worker
88*663afb9bSAndroid Build Coastguard Worker while (chain != NULL) {
89*663afb9bSAndroid Build Coastguard Worker if (&chain->next == buf->last_with_datap)
90*663afb9bSAndroid Build Coastguard Worker found_last_with_datap = 1;
91*663afb9bSAndroid Build Coastguard Worker sum += chain->off;
92*663afb9bSAndroid Build Coastguard Worker if (chain->next == NULL) {
93*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->last == chain);
94*663afb9bSAndroid Build Coastguard Worker }
95*663afb9bSAndroid Build Coastguard Worker tt_assert(chain->buffer_len >= chain->misalign + chain->off);
96*663afb9bSAndroid Build Coastguard Worker chain = chain->next;
97*663afb9bSAndroid Build Coastguard Worker }
98*663afb9bSAndroid Build Coastguard Worker
99*663afb9bSAndroid Build Coastguard Worker if (buf->first)
100*663afb9bSAndroid Build Coastguard Worker tt_assert(*buf->last_with_datap);
101*663afb9bSAndroid Build Coastguard Worker
102*663afb9bSAndroid Build Coastguard Worker if (*buf->last_with_datap) {
103*663afb9bSAndroid Build Coastguard Worker chain = *buf->last_with_datap;
104*663afb9bSAndroid Build Coastguard Worker if (chain->off == 0 || buf->total_len == 0) {
105*663afb9bSAndroid Build Coastguard Worker tt_assert(chain->off == 0)
106*663afb9bSAndroid Build Coastguard Worker tt_assert(chain == buf->first);
107*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->total_len == 0);
108*663afb9bSAndroid Build Coastguard Worker }
109*663afb9bSAndroid Build Coastguard Worker chain = chain->next;
110*663afb9bSAndroid Build Coastguard Worker while (chain != NULL) {
111*663afb9bSAndroid Build Coastguard Worker tt_assert(chain->off == 0);
112*663afb9bSAndroid Build Coastguard Worker chain = chain->next;
113*663afb9bSAndroid Build Coastguard Worker }
114*663afb9bSAndroid Build Coastguard Worker } else {
115*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->last_with_datap == &buf->first);
116*663afb9bSAndroid Build Coastguard Worker }
117*663afb9bSAndroid Build Coastguard Worker tt_assert(found_last_with_datap);
118*663afb9bSAndroid Build Coastguard Worker
119*663afb9bSAndroid Build Coastguard Worker tt_assert(sum == buf->total_len);
120*663afb9bSAndroid Build Coastguard Worker return 1;
121*663afb9bSAndroid Build Coastguard Worker end:
122*663afb9bSAndroid Build Coastguard Worker return 0;
123*663afb9bSAndroid Build Coastguard Worker }
124*663afb9bSAndroid Build Coastguard Worker
125*663afb9bSAndroid Build Coastguard Worker static void
evbuffer_get_waste(struct evbuffer * buf,size_t * allocatedp,size_t * wastedp,size_t * usedp)126*663afb9bSAndroid Build Coastguard Worker evbuffer_get_waste(struct evbuffer *buf, size_t *allocatedp, size_t *wastedp, size_t *usedp)
127*663afb9bSAndroid Build Coastguard Worker {
128*663afb9bSAndroid Build Coastguard Worker struct evbuffer_chain *chain;
129*663afb9bSAndroid Build Coastguard Worker size_t a, w, u;
130*663afb9bSAndroid Build Coastguard Worker int n = 0;
131*663afb9bSAndroid Build Coastguard Worker u = a = w = 0;
132*663afb9bSAndroid Build Coastguard Worker
133*663afb9bSAndroid Build Coastguard Worker chain = buf->first;
134*663afb9bSAndroid Build Coastguard Worker /* skip empty at start */
135*663afb9bSAndroid Build Coastguard Worker while (chain && chain->off==0) {
136*663afb9bSAndroid Build Coastguard Worker ++n;
137*663afb9bSAndroid Build Coastguard Worker a += chain->buffer_len;
138*663afb9bSAndroid Build Coastguard Worker chain = chain->next;
139*663afb9bSAndroid Build Coastguard Worker }
140*663afb9bSAndroid Build Coastguard Worker /* first nonempty chain: stuff at the end only is wasted. */
141*663afb9bSAndroid Build Coastguard Worker if (chain) {
142*663afb9bSAndroid Build Coastguard Worker ++n;
143*663afb9bSAndroid Build Coastguard Worker a += chain->buffer_len;
144*663afb9bSAndroid Build Coastguard Worker u += chain->off;
145*663afb9bSAndroid Build Coastguard Worker if (chain->next && chain->next->off)
146*663afb9bSAndroid Build Coastguard Worker w += (size_t)(chain->buffer_len - (chain->misalign + chain->off));
147*663afb9bSAndroid Build Coastguard Worker chain = chain->next;
148*663afb9bSAndroid Build Coastguard Worker }
149*663afb9bSAndroid Build Coastguard Worker /* subsequent nonempty chains */
150*663afb9bSAndroid Build Coastguard Worker while (chain && chain->off) {
151*663afb9bSAndroid Build Coastguard Worker ++n;
152*663afb9bSAndroid Build Coastguard Worker a += chain->buffer_len;
153*663afb9bSAndroid Build Coastguard Worker w += (size_t)chain->misalign;
154*663afb9bSAndroid Build Coastguard Worker u += chain->off;
155*663afb9bSAndroid Build Coastguard Worker if (chain->next && chain->next->off)
156*663afb9bSAndroid Build Coastguard Worker w += (size_t) (chain->buffer_len - (chain->misalign + chain->off));
157*663afb9bSAndroid Build Coastguard Worker chain = chain->next;
158*663afb9bSAndroid Build Coastguard Worker }
159*663afb9bSAndroid Build Coastguard Worker /* subsequent empty chains */
160*663afb9bSAndroid Build Coastguard Worker while (chain) {
161*663afb9bSAndroid Build Coastguard Worker ++n;
162*663afb9bSAndroid Build Coastguard Worker a += chain->buffer_len;
163*663afb9bSAndroid Build Coastguard Worker }
164*663afb9bSAndroid Build Coastguard Worker *allocatedp = a;
165*663afb9bSAndroid Build Coastguard Worker *wastedp = w;
166*663afb9bSAndroid Build Coastguard Worker *usedp = u;
167*663afb9bSAndroid Build Coastguard Worker }
168*663afb9bSAndroid Build Coastguard Worker
169*663afb9bSAndroid Build Coastguard Worker #define evbuffer_validate(buf) \
170*663afb9bSAndroid Build Coastguard Worker TT_STMT_BEGIN if (!evbuffer_validate_(buf)) TT_DIE(("Buffer format invalid")); TT_STMT_END
171*663afb9bSAndroid Build Coastguard Worker
172*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer(void * ptr)173*663afb9bSAndroid Build Coastguard Worker test_evbuffer(void *ptr)
174*663afb9bSAndroid Build Coastguard Worker {
175*663afb9bSAndroid Build Coastguard Worker static char buffer[512], *tmp;
176*663afb9bSAndroid Build Coastguard Worker struct evbuffer *evb = evbuffer_new();
177*663afb9bSAndroid Build Coastguard Worker struct evbuffer *evb_two = evbuffer_new();
178*663afb9bSAndroid Build Coastguard Worker size_t sz_tmp;
179*663afb9bSAndroid Build Coastguard Worker int i;
180*663afb9bSAndroid Build Coastguard Worker
181*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
182*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(evb, "%s/%d", "hello", 1);
183*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
184*663afb9bSAndroid Build Coastguard Worker
185*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) == 7);
186*663afb9bSAndroid Build Coastguard Worker tt_assert(!memcmp((char*)EVBUFFER_DATA(evb), "hello/1", 1));
187*663afb9bSAndroid Build Coastguard Worker
188*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(evb, evb_two);
189*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
190*663afb9bSAndroid Build Coastguard Worker
191*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(evb, strlen("hello/"));
192*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
193*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) == 1);
194*663afb9bSAndroid Build Coastguard Worker tt_assert(!memcmp((char*)EVBUFFER_DATA(evb), "1", 1));
195*663afb9bSAndroid Build Coastguard Worker
196*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(evb_two, "%s", "/hello");
197*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
198*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(evb, evb_two);
199*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
200*663afb9bSAndroid Build Coastguard Worker
201*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb_two) == 0);
202*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) == 7);
203*663afb9bSAndroid Build Coastguard Worker tt_assert(!memcmp((char*)EVBUFFER_DATA(evb), "1/hello", 7));
204*663afb9bSAndroid Build Coastguard Worker
205*663afb9bSAndroid Build Coastguard Worker memset(buffer, 0, sizeof(buffer));
206*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, buffer, sizeof(buffer));
207*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
208*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) == 7 + 512);
209*663afb9bSAndroid Build Coastguard Worker
210*663afb9bSAndroid Build Coastguard Worker tmp = (char *)evbuffer_pullup(evb, 7 + 512);
211*663afb9bSAndroid Build Coastguard Worker tt_assert(tmp);
212*663afb9bSAndroid Build Coastguard Worker tt_assert(!strncmp(tmp, "1/hello", 7));
213*663afb9bSAndroid Build Coastguard Worker tt_assert(!memcmp(tmp + 7, buffer, sizeof(buffer)));
214*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
215*663afb9bSAndroid Build Coastguard Worker
216*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(evb, "something", 9);
217*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
218*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(evb, "else", 4);
219*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
220*663afb9bSAndroid Build Coastguard Worker
221*663afb9bSAndroid Build Coastguard Worker tmp = (char *)evbuffer_pullup(evb, 4 + 9 + 7);
222*663afb9bSAndroid Build Coastguard Worker tt_assert(!strncmp(tmp, "elsesomething1/hello", 4 + 9 + 7));
223*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
224*663afb9bSAndroid Build Coastguard Worker
225*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(evb, -1);
226*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
227*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(evb_two, -1);
228*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
229*663afb9bSAndroid Build Coastguard Worker
230*663afb9bSAndroid Build Coastguard Worker for (i = 0; i < 3; ++i) {
231*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb_two, buffer, sizeof(buffer));
232*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb_two);
233*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(evb, evb_two);
234*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
235*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb_two);
236*663afb9bSAndroid Build Coastguard Worker }
237*663afb9bSAndroid Build Coastguard Worker
238*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb_two) == 0);
239*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) == i * sizeof(buffer));
240*663afb9bSAndroid Build Coastguard Worker
241*663afb9bSAndroid Build Coastguard Worker /* test remove buffer */
242*663afb9bSAndroid Build Coastguard Worker sz_tmp = (size_t)(sizeof(buffer)*2.5);
243*663afb9bSAndroid Build Coastguard Worker evbuffer_remove_buffer(evb, evb_two, sz_tmp);
244*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb_two) == sz_tmp);
245*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) == sizeof(buffer) / 2);
246*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
247*663afb9bSAndroid Build Coastguard Worker
248*663afb9bSAndroid Build Coastguard Worker if (memcmp(evbuffer_pullup(
249*663afb9bSAndroid Build Coastguard Worker evb, -1), buffer, sizeof(buffer) / 2) != 0 ||
250*663afb9bSAndroid Build Coastguard Worker memcmp(evbuffer_pullup(
251*663afb9bSAndroid Build Coastguard Worker evb_two, -1), buffer, sizeof(buffer)) != 0)
252*663afb9bSAndroid Build Coastguard Worker tt_abort_msg("Pullup did not preserve content");
253*663afb9bSAndroid Build Coastguard Worker
254*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
255*663afb9bSAndroid Build Coastguard Worker
256*663afb9bSAndroid Build Coastguard Worker
257*663afb9bSAndroid Build Coastguard Worker /* testing one-vector reserve and commit */
258*663afb9bSAndroid Build Coastguard Worker {
259*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec v[1];
260*663afb9bSAndroid Build Coastguard Worker char *buf;
261*663afb9bSAndroid Build Coastguard Worker int i, j, r;
262*663afb9bSAndroid Build Coastguard Worker
263*663afb9bSAndroid Build Coastguard Worker for (i = 0; i < 3; ++i) {
264*663afb9bSAndroid Build Coastguard Worker r = evbuffer_reserve_space(evb, 10000, v, 1);
265*663afb9bSAndroid Build Coastguard Worker tt_int_op(r, ==, 1);
266*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_len >= 10000);
267*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_base != NULL);
268*663afb9bSAndroid Build Coastguard Worker
269*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
270*663afb9bSAndroid Build Coastguard Worker buf = v[0].iov_base;
271*663afb9bSAndroid Build Coastguard Worker for (j = 0; j < 10000; ++j) {
272*663afb9bSAndroid Build Coastguard Worker buf[j] = j;
273*663afb9bSAndroid Build Coastguard Worker }
274*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
275*663afb9bSAndroid Build Coastguard Worker
276*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_commit_space(evb, v, 1), ==, 0);
277*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
278*663afb9bSAndroid Build Coastguard Worker
279*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) >= 10000);
280*663afb9bSAndroid Build Coastguard Worker
281*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(evb, j * 5000);
282*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
283*663afb9bSAndroid Build Coastguard Worker }
284*663afb9bSAndroid Build Coastguard Worker }
285*663afb9bSAndroid Build Coastguard Worker
286*663afb9bSAndroid Build Coastguard Worker end:
287*663afb9bSAndroid Build Coastguard Worker evbuffer_free(evb);
288*663afb9bSAndroid Build Coastguard Worker evbuffer_free(evb_two);
289*663afb9bSAndroid Build Coastguard Worker }
290*663afb9bSAndroid Build Coastguard Worker
291*663afb9bSAndroid Build Coastguard Worker static void
no_cleanup(const void * data,size_t datalen,void * extra)292*663afb9bSAndroid Build Coastguard Worker no_cleanup(const void *data, size_t datalen, void *extra)
293*663afb9bSAndroid Build Coastguard Worker {
294*663afb9bSAndroid Build Coastguard Worker }
295*663afb9bSAndroid Build Coastguard Worker
296*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_remove_buffer_with_empty(void * ptr)297*663afb9bSAndroid Build Coastguard Worker test_evbuffer_remove_buffer_with_empty(void *ptr)
298*663afb9bSAndroid Build Coastguard Worker {
299*663afb9bSAndroid Build Coastguard Worker struct evbuffer *src = evbuffer_new();
300*663afb9bSAndroid Build Coastguard Worker struct evbuffer *dst = evbuffer_new();
301*663afb9bSAndroid Build Coastguard Worker char buf[2] = { 'A', 'A' };
302*663afb9bSAndroid Build Coastguard Worker
303*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
304*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
305*663afb9bSAndroid Build Coastguard Worker
306*663afb9bSAndroid Build Coastguard Worker /* setup the buffers */
307*663afb9bSAndroid Build Coastguard Worker /* we need more data in src than we will move later */
308*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(src, buf, sizeof(buf), no_cleanup, NULL);
309*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(src, buf, sizeof(buf), no_cleanup, NULL);
310*663afb9bSAndroid Build Coastguard Worker /* we need one buffer in dst and one empty buffer at the end */
311*663afb9bSAndroid Build Coastguard Worker evbuffer_add(dst, buf, sizeof(buf));
312*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(dst, buf, 0, no_cleanup, NULL);
313*663afb9bSAndroid Build Coastguard Worker
314*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
315*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
316*663afb9bSAndroid Build Coastguard Worker
317*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(src, -1), ==, "AAAA", 4);
318*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(dst, -1), ==, "AA", 2);
319*663afb9bSAndroid Build Coastguard Worker
320*663afb9bSAndroid Build Coastguard Worker /* move three bytes over */
321*663afb9bSAndroid Build Coastguard Worker evbuffer_remove_buffer(src, dst, 3);
322*663afb9bSAndroid Build Coastguard Worker
323*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
324*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
325*663afb9bSAndroid Build Coastguard Worker
326*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(src, -1), ==, "A", 1);
327*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(dst, -1), ==, "AAAAA", 5);
328*663afb9bSAndroid Build Coastguard Worker
329*663afb9bSAndroid Build Coastguard Worker end:
330*663afb9bSAndroid Build Coastguard Worker evbuffer_free(src);
331*663afb9bSAndroid Build Coastguard Worker evbuffer_free(dst);
332*663afb9bSAndroid Build Coastguard Worker }
333*663afb9bSAndroid Build Coastguard Worker
334*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_remove_buffer_with_empty2(void * ptr)335*663afb9bSAndroid Build Coastguard Worker test_evbuffer_remove_buffer_with_empty2(void *ptr)
336*663afb9bSAndroid Build Coastguard Worker {
337*663afb9bSAndroid Build Coastguard Worker struct evbuffer *src = evbuffer_new();
338*663afb9bSAndroid Build Coastguard Worker struct evbuffer *dst = evbuffer_new();
339*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
340*663afb9bSAndroid Build Coastguard Worker
341*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "foo", 3);
342*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, "foo", 3, NULL, NULL);
343*663afb9bSAndroid Build Coastguard Worker
344*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(src, "foo", 3, NULL, NULL);
345*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(src, NULL, 0, NULL, NULL);
346*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(src, buf);
347*663afb9bSAndroid Build Coastguard Worker
348*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "foo", 3);
349*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, "foo", 3, NULL, NULL);
350*663afb9bSAndroid Build Coastguard Worker
351*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(dst, "foo", 3, NULL, NULL);
352*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(dst, NULL, 0, NULL, NULL);
353*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(dst, buf);
354*663afb9bSAndroid Build Coastguard Worker
355*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(src), ==, 9);
356*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(dst), ==, 9);
357*663afb9bSAndroid Build Coastguard Worker
358*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
359*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
360*663afb9bSAndroid Build Coastguard Worker
361*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(src, -1), ==, "foofoofoo", 9);
362*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(dst, -1), ==, "foofoofoo", 9);
363*663afb9bSAndroid Build Coastguard Worker
364*663afb9bSAndroid Build Coastguard Worker evbuffer_remove_buffer(src, dst, 8);
365*663afb9bSAndroid Build Coastguard Worker
366*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
367*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
368*663afb9bSAndroid Build Coastguard Worker
369*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(src), ==, 1);
370*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(dst), ==, 17);
371*663afb9bSAndroid Build Coastguard Worker
372*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(src, -1), ==, "o", 1);
373*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(dst, -1), ==, "foofoofoofoofoofo", 17);
374*663afb9bSAndroid Build Coastguard Worker
375*663afb9bSAndroid Build Coastguard Worker end:
376*663afb9bSAndroid Build Coastguard Worker evbuffer_free(src);
377*663afb9bSAndroid Build Coastguard Worker evbuffer_free(dst);
378*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
379*663afb9bSAndroid Build Coastguard Worker }
380*663afb9bSAndroid Build Coastguard Worker
381*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_remove_buffer_with_empty3(void * ptr)382*663afb9bSAndroid Build Coastguard Worker test_evbuffer_remove_buffer_with_empty3(void *ptr)
383*663afb9bSAndroid Build Coastguard Worker {
384*663afb9bSAndroid Build Coastguard Worker struct evbuffer *src = evbuffer_new();
385*663afb9bSAndroid Build Coastguard Worker struct evbuffer *dst = evbuffer_new();
386*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
387*663afb9bSAndroid Build Coastguard Worker
388*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "foo", 3);
389*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, NULL, 0, NULL, NULL);
390*663afb9bSAndroid Build Coastguard Worker
391*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(src, "foo", 3, NULL, NULL);
392*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(src, NULL, 0, NULL, NULL);
393*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend_buffer(src, buf);
394*663afb9bSAndroid Build Coastguard Worker
395*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "foo", 3);
396*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, NULL, 0, NULL, NULL);
397*663afb9bSAndroid Build Coastguard Worker
398*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(dst, "foo", 3, NULL, NULL);
399*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(dst, NULL, 0, NULL, NULL);
400*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend_buffer(dst, buf);
401*663afb9bSAndroid Build Coastguard Worker
402*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(src), ==, 6);
403*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(dst), ==, 6);
404*663afb9bSAndroid Build Coastguard Worker
405*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
406*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
407*663afb9bSAndroid Build Coastguard Worker
408*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(src, -1), ==, "foofoo", 6);
409*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(dst, -1), ==, "foofoo", 6);
410*663afb9bSAndroid Build Coastguard Worker
411*663afb9bSAndroid Build Coastguard Worker evbuffer_remove_buffer(src, dst, 5);
412*663afb9bSAndroid Build Coastguard Worker
413*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
414*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
415*663afb9bSAndroid Build Coastguard Worker
416*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(src), ==, 1);
417*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(dst), ==, 11);
418*663afb9bSAndroid Build Coastguard Worker
419*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(src, -1), ==, "o", 1);
420*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(dst, -1), ==, "foofoofoofo", 11);
421*663afb9bSAndroid Build Coastguard Worker
422*663afb9bSAndroid Build Coastguard Worker end:
423*663afb9bSAndroid Build Coastguard Worker evbuffer_free(src);
424*663afb9bSAndroid Build Coastguard Worker evbuffer_free(dst);
425*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
426*663afb9bSAndroid Build Coastguard Worker }
427*663afb9bSAndroid Build Coastguard Worker
428*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_pullup_with_empty(void * ptr)429*663afb9bSAndroid Build Coastguard Worker test_evbuffer_pullup_with_empty(void *ptr)
430*663afb9bSAndroid Build Coastguard Worker {
431*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = NULL;
432*663afb9bSAndroid Build Coastguard Worker
433*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
434*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "foo", 3);
435*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, NULL, 0, NULL, NULL);
436*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
437*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf), ==, 3);
438*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(buf, -1), ==, "foo", 3);
439*663afb9bSAndroid Build Coastguard Worker
440*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
441*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
442*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
443*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf), ==, 0);
444*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_pullup(buf, -1), ==, NULL);
445*663afb9bSAndroid Build Coastguard Worker
446*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
447*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
448*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "foo", 3);
449*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, NULL, 0, NULL, NULL);
450*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
451*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(buf, 3), ==, "foo", 3);
452*663afb9bSAndroid Build Coastguard Worker
453*663afb9bSAndroid Build Coastguard Worker end:
454*663afb9bSAndroid Build Coastguard Worker if (buf)
455*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
456*663afb9bSAndroid Build Coastguard Worker }
457*663afb9bSAndroid Build Coastguard Worker
458*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_remove_buffer_with_empty_front(void * ptr)459*663afb9bSAndroid Build Coastguard Worker test_evbuffer_remove_buffer_with_empty_front(void *ptr)
460*663afb9bSAndroid Build Coastguard Worker {
461*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf1 = NULL, *buf2 = NULL;
462*663afb9bSAndroid Build Coastguard Worker
463*663afb9bSAndroid Build Coastguard Worker buf1 = evbuffer_new();
464*663afb9bSAndroid Build Coastguard Worker tt_assert(buf1);
465*663afb9bSAndroid Build Coastguard Worker
466*663afb9bSAndroid Build Coastguard Worker buf2 = evbuffer_new();
467*663afb9bSAndroid Build Coastguard Worker tt_assert(buf2);
468*663afb9bSAndroid Build Coastguard Worker
469*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_add_reference(buf1, "foo", 3, NULL, NULL), ==, 0);
470*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_prepend(buf1, "", 0), ==, 0);
471*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_remove_buffer(buf1, buf2, 1), ==, 1);
472*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_add(buf1, "bar", 3), ==, 0);
473*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(buf1, -1), ==, "oobar", 5);
474*663afb9bSAndroid Build Coastguard Worker
475*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
476*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
477*663afb9bSAndroid Build Coastguard Worker
478*663afb9bSAndroid Build Coastguard Worker end:
479*663afb9bSAndroid Build Coastguard Worker if (buf1)
480*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf1);
481*663afb9bSAndroid Build Coastguard Worker if (buf2)
482*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf2);
483*663afb9bSAndroid Build Coastguard Worker }
484*663afb9bSAndroid Build Coastguard Worker
485*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_remove_buffer_adjust_last_with_datap_with_empty(void * ptr)486*663afb9bSAndroid Build Coastguard Worker test_evbuffer_remove_buffer_adjust_last_with_datap_with_empty(void *ptr)
487*663afb9bSAndroid Build Coastguard Worker {
488*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf1 = NULL, *buf2 = NULL;
489*663afb9bSAndroid Build Coastguard Worker
490*663afb9bSAndroid Build Coastguard Worker buf1 = evbuffer_new();
491*663afb9bSAndroid Build Coastguard Worker tt_assert(buf1);
492*663afb9bSAndroid Build Coastguard Worker
493*663afb9bSAndroid Build Coastguard Worker buf2 = evbuffer_new();
494*663afb9bSAndroid Build Coastguard Worker tt_assert(buf2);
495*663afb9bSAndroid Build Coastguard Worker
496*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_add(buf1, "aaaaaa", 6), ==, 0);
497*663afb9bSAndroid Build Coastguard Worker
498*663afb9bSAndroid Build Coastguard Worker // buf1: aaaaaab
499*663afb9bSAndroid Build Coastguard Worker // buf2:
500*663afb9bSAndroid Build Coastguard Worker {
501*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec iovecs[2];
502*663afb9bSAndroid Build Coastguard Worker /** we want two chains, to leave one chain empty */
503*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_reserve_space(buf1, 971, iovecs, 2), ==, 2);
504*663afb9bSAndroid Build Coastguard Worker tt_int_op(iovecs[0].iov_len, >=, 1);
505*663afb9bSAndroid Build Coastguard Worker tt_int_op(iovecs[1].iov_len, >=, 1);
506*663afb9bSAndroid Build Coastguard Worker tt_assert(*(char *)(iovecs[0].iov_base) = 'b');
507*663afb9bSAndroid Build Coastguard Worker tt_assert(iovecs[0].iov_len = 1);
508*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_commit_space(buf1, iovecs, 1), ==, 0);
509*663afb9bSAndroid Build Coastguard Worker }
510*663afb9bSAndroid Build Coastguard Worker
511*663afb9bSAndroid Build Coastguard Worker // buf1: aaaaaab
512*663afb9bSAndroid Build Coastguard Worker // buf2: dddcc
513*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_add(buf2, "cc", 2), ==, 0);
514*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_prepend(buf2, "ddd", 3), ==, 0);
515*663afb9bSAndroid Build Coastguard Worker
516*663afb9bSAndroid Build Coastguard Worker // buf1:
517*663afb9bSAndroid Build Coastguard Worker // buf2: aaaaaabdddcc
518*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_prepend_buffer(buf2, buf1), ==, 0);
519*663afb9bSAndroid Build Coastguard Worker
520*663afb9bSAndroid Build Coastguard Worker // buf1: aaaaaabdddcc
521*663afb9bSAndroid Build Coastguard Worker // buf2:
522*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_add_buffer(buf1, buf2), ==, 0);
523*663afb9bSAndroid Build Coastguard Worker
524*663afb9bSAndroid Build Coastguard Worker // buf1: c
525*663afb9bSAndroid Build Coastguard Worker // buf2: aaaaaabdddc
526*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_remove_buffer(buf1, buf2, 11), ==, 11);
527*663afb9bSAndroid Build Coastguard Worker
528*663afb9bSAndroid Build Coastguard Worker // This fails today, we observe "aaaaaabcddd" instead!
529*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(buf2, -1), ==, "aaaaaabdddc", 11);
530*663afb9bSAndroid Build Coastguard Worker
531*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
532*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
533*663afb9bSAndroid Build Coastguard Worker
534*663afb9bSAndroid Build Coastguard Worker end:
535*663afb9bSAndroid Build Coastguard Worker if (buf1)
536*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf1);
537*663afb9bSAndroid Build Coastguard Worker if (buf2)
538*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf2);
539*663afb9bSAndroid Build Coastguard Worker }
540*663afb9bSAndroid Build Coastguard Worker
541*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_add_buffer_with_empty(void * ptr)542*663afb9bSAndroid Build Coastguard Worker test_evbuffer_add_buffer_with_empty(void *ptr)
543*663afb9bSAndroid Build Coastguard Worker {
544*663afb9bSAndroid Build Coastguard Worker struct evbuffer *src = evbuffer_new();
545*663afb9bSAndroid Build Coastguard Worker struct evbuffer *dst = evbuffer_new();
546*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
547*663afb9bSAndroid Build Coastguard Worker
548*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "foo", 3);
549*663afb9bSAndroid Build Coastguard Worker
550*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(src, "foo", 3, NULL, NULL);
551*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(src, NULL, 0, NULL, NULL);
552*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(src, buf);
553*663afb9bSAndroid Build Coastguard Worker
554*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "foo", 3);
555*663afb9bSAndroid Build Coastguard Worker
556*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(dst, "foo", 3, NULL, NULL);
557*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(dst, NULL, 0, NULL, NULL);
558*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(dst, buf);
559*663afb9bSAndroid Build Coastguard Worker
560*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(src), ==, 6);
561*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(dst), ==, 6);
562*663afb9bSAndroid Build Coastguard Worker
563*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
564*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
565*663afb9bSAndroid Build Coastguard Worker
566*663afb9bSAndroid Build Coastguard Worker end:
567*663afb9bSAndroid Build Coastguard Worker evbuffer_free(src);
568*663afb9bSAndroid Build Coastguard Worker evbuffer_free(dst);
569*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
570*663afb9bSAndroid Build Coastguard Worker }
571*663afb9bSAndroid Build Coastguard Worker
572*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_add_buffer_with_empty2(void * ptr)573*663afb9bSAndroid Build Coastguard Worker test_evbuffer_add_buffer_with_empty2(void *ptr)
574*663afb9bSAndroid Build Coastguard Worker {
575*663afb9bSAndroid Build Coastguard Worker struct evbuffer *src = evbuffer_new();
576*663afb9bSAndroid Build Coastguard Worker struct evbuffer *dst = evbuffer_new();
577*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
578*663afb9bSAndroid Build Coastguard Worker
579*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "foo", 3);
580*663afb9bSAndroid Build Coastguard Worker
581*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(src, NULL, 0, NULL, NULL);
582*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(src, buf);
583*663afb9bSAndroid Build Coastguard Worker
584*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "foo", 3);
585*663afb9bSAndroid Build Coastguard Worker
586*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(dst, NULL, 0, NULL, NULL);
587*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(dst, buf);
588*663afb9bSAndroid Build Coastguard Worker
589*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(src), ==, 3);
590*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(dst), ==, 3);
591*663afb9bSAndroid Build Coastguard Worker
592*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
593*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
594*663afb9bSAndroid Build Coastguard Worker
595*663afb9bSAndroid Build Coastguard Worker end:
596*663afb9bSAndroid Build Coastguard Worker evbuffer_free(src);
597*663afb9bSAndroid Build Coastguard Worker evbuffer_free(dst);
598*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
599*663afb9bSAndroid Build Coastguard Worker }
600*663afb9bSAndroid Build Coastguard Worker
601*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_reserve2(void * ptr)602*663afb9bSAndroid Build Coastguard Worker test_evbuffer_reserve2(void *ptr)
603*663afb9bSAndroid Build Coastguard Worker {
604*663afb9bSAndroid Build Coastguard Worker /* Test the two-vector cases of reserve/commit. */
605*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
606*663afb9bSAndroid Build Coastguard Worker int n, i;
607*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec v[2];
608*663afb9bSAndroid Build Coastguard Worker size_t remaining;
609*663afb9bSAndroid Build Coastguard Worker char *cp, *cp2;
610*663afb9bSAndroid Build Coastguard Worker
611*663afb9bSAndroid Build Coastguard Worker /* First chunk will necessarily be one chunk. Use 512 bytes of it.*/
612*663afb9bSAndroid Build Coastguard Worker n = evbuffer_reserve_space(buf, 1024, v, 2);
613*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 1);
614*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf), ==, 0);
615*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_base != NULL);
616*663afb9bSAndroid Build Coastguard Worker tt_int_op(v[0].iov_len, >=, 1024);
617*663afb9bSAndroid Build Coastguard Worker memset(v[0].iov_base, 'X', 512);
618*663afb9bSAndroid Build Coastguard Worker cp = v[0].iov_base;
619*663afb9bSAndroid Build Coastguard Worker remaining = v[0].iov_len - 512;
620*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = 512;
621*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
622*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, evbuffer_commit_space(buf, v, 1));
623*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf), ==, 512);
624*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
625*663afb9bSAndroid Build Coastguard Worker
626*663afb9bSAndroid Build Coastguard Worker /* Ask for another same-chunk request, in an existing chunk. Use 8
627*663afb9bSAndroid Build Coastguard Worker * bytes of it. */
628*663afb9bSAndroid Build Coastguard Worker n = evbuffer_reserve_space(buf, 32, v, 2);
629*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 1);
630*663afb9bSAndroid Build Coastguard Worker tt_assert(cp + 512 == v[0].iov_base);
631*663afb9bSAndroid Build Coastguard Worker tt_int_op(remaining, ==, v[0].iov_len);
632*663afb9bSAndroid Build Coastguard Worker memset(v[0].iov_base, 'Y', 8);
633*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = 8;
634*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, evbuffer_commit_space(buf, v, 1));
635*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf), ==, 520);
636*663afb9bSAndroid Build Coastguard Worker remaining -= 8;
637*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
638*663afb9bSAndroid Build Coastguard Worker
639*663afb9bSAndroid Build Coastguard Worker /* Now ask for a request that will be split. Use only one byte of it,
640*663afb9bSAndroid Build Coastguard Worker though. */
641*663afb9bSAndroid Build Coastguard Worker n = evbuffer_reserve_space(buf, remaining+64, v, 2);
642*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 2);
643*663afb9bSAndroid Build Coastguard Worker tt_assert(cp + 520 == v[0].iov_base);
644*663afb9bSAndroid Build Coastguard Worker tt_int_op(remaining, ==, v[0].iov_len);
645*663afb9bSAndroid Build Coastguard Worker tt_assert(v[1].iov_base);
646*663afb9bSAndroid Build Coastguard Worker tt_assert(v[1].iov_len >= 64);
647*663afb9bSAndroid Build Coastguard Worker cp2 = v[1].iov_base;
648*663afb9bSAndroid Build Coastguard Worker memset(v[0].iov_base, 'Z', 1);
649*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = 1;
650*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, evbuffer_commit_space(buf, v, 1));
651*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf), ==, 521);
652*663afb9bSAndroid Build Coastguard Worker remaining -= 1;
653*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
654*663afb9bSAndroid Build Coastguard Worker
655*663afb9bSAndroid Build Coastguard Worker /* Now ask for a request that will be split. Use some of the first
656*663afb9bSAndroid Build Coastguard Worker * part and some of the second. */
657*663afb9bSAndroid Build Coastguard Worker n = evbuffer_reserve_space(buf, remaining+64, v, 2);
658*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
659*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 2);
660*663afb9bSAndroid Build Coastguard Worker tt_assert(cp + 521 == v[0].iov_base);
661*663afb9bSAndroid Build Coastguard Worker tt_int_op(remaining, ==, v[0].iov_len);
662*663afb9bSAndroid Build Coastguard Worker tt_assert(v[1].iov_base == cp2);
663*663afb9bSAndroid Build Coastguard Worker tt_assert(v[1].iov_len >= 64);
664*663afb9bSAndroid Build Coastguard Worker memset(v[0].iov_base, 'W', 400);
665*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = 400;
666*663afb9bSAndroid Build Coastguard Worker memset(v[1].iov_base, 'x', 60);
667*663afb9bSAndroid Build Coastguard Worker v[1].iov_len = 60;
668*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, evbuffer_commit_space(buf, v, 2));
669*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf), ==, 981);
670*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
671*663afb9bSAndroid Build Coastguard Worker
672*663afb9bSAndroid Build Coastguard Worker /* Now peek to make sure stuff got made how we like. */
673*663afb9bSAndroid Build Coastguard Worker memset(v,0,sizeof(v));
674*663afb9bSAndroid Build Coastguard Worker n = evbuffer_peek(buf, -1, NULL, v, 2);
675*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 2);
676*663afb9bSAndroid Build Coastguard Worker tt_int_op(v[0].iov_len, ==, 921);
677*663afb9bSAndroid Build Coastguard Worker tt_int_op(v[1].iov_len, ==, 60);
678*663afb9bSAndroid Build Coastguard Worker
679*663afb9bSAndroid Build Coastguard Worker cp = v[0].iov_base;
680*663afb9bSAndroid Build Coastguard Worker for (i=0; i<512; ++i)
681*663afb9bSAndroid Build Coastguard Worker tt_int_op(cp[i], ==, 'X');
682*663afb9bSAndroid Build Coastguard Worker for (i=512; i<520; ++i)
683*663afb9bSAndroid Build Coastguard Worker tt_int_op(cp[i], ==, 'Y');
684*663afb9bSAndroid Build Coastguard Worker for (i=520; i<521; ++i)
685*663afb9bSAndroid Build Coastguard Worker tt_int_op(cp[i], ==, 'Z');
686*663afb9bSAndroid Build Coastguard Worker for (i=521; i<921; ++i)
687*663afb9bSAndroid Build Coastguard Worker tt_int_op(cp[i], ==, 'W');
688*663afb9bSAndroid Build Coastguard Worker
689*663afb9bSAndroid Build Coastguard Worker cp = v[1].iov_base;
690*663afb9bSAndroid Build Coastguard Worker for (i=0; i<60; ++i)
691*663afb9bSAndroid Build Coastguard Worker tt_int_op(cp[i], ==, 'x');
692*663afb9bSAndroid Build Coastguard Worker
693*663afb9bSAndroid Build Coastguard Worker end:
694*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
695*663afb9bSAndroid Build Coastguard Worker }
696*663afb9bSAndroid Build Coastguard Worker
697*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_reserve_many(void * ptr)698*663afb9bSAndroid Build Coastguard Worker test_evbuffer_reserve_many(void *ptr)
699*663afb9bSAndroid Build Coastguard Worker {
700*663afb9bSAndroid Build Coastguard Worker /* This is a glass-box test to handle expanding a buffer with more
701*663afb9bSAndroid Build Coastguard Worker * chunks and reallocating chunks as needed */
702*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
703*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec v[8];
704*663afb9bSAndroid Build Coastguard Worker int n;
705*663afb9bSAndroid Build Coastguard Worker size_t sz;
706*663afb9bSAndroid Build Coastguard Worker int add_data = ptr && !strcmp(ptr, "add");
707*663afb9bSAndroid Build Coastguard Worker int fill_first = ptr && !strcmp(ptr, "fill");
708*663afb9bSAndroid Build Coastguard Worker char *cp1, *cp2;
709*663afb9bSAndroid Build Coastguard Worker
710*663afb9bSAndroid Build Coastguard Worker /* When reserving the the first chunk, we just allocate it */
711*663afb9bSAndroid Build Coastguard Worker n = evbuffer_reserve_space(buf, 128, v, 2);
712*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
713*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 1);
714*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_len >= 128);
715*663afb9bSAndroid Build Coastguard Worker sz = v[0].iov_len;
716*663afb9bSAndroid Build Coastguard Worker cp1 = v[0].iov_base;
717*663afb9bSAndroid Build Coastguard Worker if (add_data) {
718*663afb9bSAndroid Build Coastguard Worker *(char*)v[0].iov_base = 'X';
719*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = 1;
720*663afb9bSAndroid Build Coastguard Worker n = evbuffer_commit_space(buf, v, 1);
721*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 0);
722*663afb9bSAndroid Build Coastguard Worker } else if (fill_first) {
723*663afb9bSAndroid Build Coastguard Worker memset(v[0].iov_base, 'X', v[0].iov_len);
724*663afb9bSAndroid Build Coastguard Worker n = evbuffer_commit_space(buf, v, 1);
725*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 0);
726*663afb9bSAndroid Build Coastguard Worker n = evbuffer_reserve_space(buf, 128, v, 2);
727*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 1);
728*663afb9bSAndroid Build Coastguard Worker sz = v[0].iov_len;
729*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_base != cp1);
730*663afb9bSAndroid Build Coastguard Worker cp1 = v[0].iov_base;
731*663afb9bSAndroid Build Coastguard Worker }
732*663afb9bSAndroid Build Coastguard Worker
733*663afb9bSAndroid Build Coastguard Worker /* Make another chunk get added. */
734*663afb9bSAndroid Build Coastguard Worker n = evbuffer_reserve_space(buf, sz+128, v, 2);
735*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
736*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 2);
737*663afb9bSAndroid Build Coastguard Worker sz = v[0].iov_len + v[1].iov_len;
738*663afb9bSAndroid Build Coastguard Worker tt_int_op(sz, >=, v[0].iov_len+128);
739*663afb9bSAndroid Build Coastguard Worker if (add_data) {
740*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_base == cp1 + 1);
741*663afb9bSAndroid Build Coastguard Worker } else {
742*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_base == cp1);
743*663afb9bSAndroid Build Coastguard Worker }
744*663afb9bSAndroid Build Coastguard Worker cp1 = v[0].iov_base;
745*663afb9bSAndroid Build Coastguard Worker cp2 = v[1].iov_base;
746*663afb9bSAndroid Build Coastguard Worker
747*663afb9bSAndroid Build Coastguard Worker /* And a third chunk. */
748*663afb9bSAndroid Build Coastguard Worker n = evbuffer_reserve_space(buf, sz+128, v, 3);
749*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
750*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 3);
751*663afb9bSAndroid Build Coastguard Worker tt_assert(cp1 == v[0].iov_base);
752*663afb9bSAndroid Build Coastguard Worker tt_assert(cp2 == v[1].iov_base);
753*663afb9bSAndroid Build Coastguard Worker sz = v[0].iov_len + v[1].iov_len + v[2].iov_len;
754*663afb9bSAndroid Build Coastguard Worker
755*663afb9bSAndroid Build Coastguard Worker /* Now force a reallocation by asking for more space in only 2
756*663afb9bSAndroid Build Coastguard Worker * buffers. */
757*663afb9bSAndroid Build Coastguard Worker n = evbuffer_reserve_space(buf, sz+128, v, 2);
758*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
759*663afb9bSAndroid Build Coastguard Worker if (add_data) {
760*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 2);
761*663afb9bSAndroid Build Coastguard Worker tt_assert(cp1 == v[0].iov_base);
762*663afb9bSAndroid Build Coastguard Worker } else {
763*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, ==, 1);
764*663afb9bSAndroid Build Coastguard Worker }
765*663afb9bSAndroid Build Coastguard Worker
766*663afb9bSAndroid Build Coastguard Worker end:
767*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
768*663afb9bSAndroid Build Coastguard Worker }
769*663afb9bSAndroid Build Coastguard Worker
770*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_reserve_with_empty(void * ptr)771*663afb9bSAndroid Build Coastguard Worker test_evbuffer_reserve_with_empty(void *ptr)
772*663afb9bSAndroid Build Coastguard Worker {
773*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf;
774*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec v[2];
775*663afb9bSAndroid Build Coastguard Worker
776*663afb9bSAndroid Build Coastguard Worker tt_assert(buf = evbuffer_new());
777*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "a", 1);
778*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_reserve_space(buf, 1<<12, v, 2), ==, 2);
779*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = 1;
780*663afb9bSAndroid Build Coastguard Worker *(char *)v[0].iov_base = 'b';
781*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_commit_space(buf, v, 1), ==, 0);
782*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "c", 1);
783*663afb9bSAndroid Build Coastguard Worker tt_mem_op(evbuffer_pullup(buf, -1), ==, "abc", 2);
784*663afb9bSAndroid Build Coastguard Worker
785*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
786*663afb9bSAndroid Build Coastguard Worker
787*663afb9bSAndroid Build Coastguard Worker end:
788*663afb9bSAndroid Build Coastguard Worker if (buf)
789*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
790*663afb9bSAndroid Build Coastguard Worker }
791*663afb9bSAndroid Build Coastguard Worker
792*663afb9bSAndroid Build Coastguard Worker /* regression for evbuffer_expand_fast_() with invalid last_with_datap that has
793*663afb9bSAndroid Build Coastguard Worker * been left after evbuffer_prepend() with empty chain in it */
794*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_reserve_invalid_last_with_datap(void * ptr)795*663afb9bSAndroid Build Coastguard Worker test_evbuffer_reserve_invalid_last_with_datap(void *ptr)
796*663afb9bSAndroid Build Coastguard Worker {
797*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = NULL;
798*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec vec[2];
799*663afb9bSAndroid Build Coastguard Worker const int nvec = ARRAY_SIZE(vec);
800*663afb9bSAndroid Build Coastguard Worker int i, avec;
801*663afb9bSAndroid Build Coastguard Worker
802*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
803*663afb9bSAndroid Build Coastguard Worker tt_assert(buf);
804*663afb9bSAndroid Build Coastguard Worker
805*663afb9bSAndroid Build Coastguard Worker /* prepend with an empty chain */
806*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, "", 0, NULL, NULL);
807*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(buf, "foo", 3);
808*663afb9bSAndroid Build Coastguard Worker /* after invalid last_with_datap will create new chain */
809*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "", 0);
810*663afb9bSAndroid Build Coastguard Worker /* we need to create at least 2 "used" (in evbuffer_expand_fast_()) chains */
811*663afb9bSAndroid Build Coastguard Worker tt_int_op(avec = evbuffer_reserve_space(buf, 1<<12, vec, nvec), >=, 1);
812*663afb9bSAndroid Build Coastguard Worker for (i = 0; i < avec; ++i)
813*663afb9bSAndroid Build Coastguard Worker vec[i].iov_len = 0;
814*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_commit_space(buf, vec, avec), ==, 0);
815*663afb9bSAndroid Build Coastguard Worker
816*663afb9bSAndroid Build Coastguard Worker /* and an actual problem, that triggers an assert(chain == buf->first) in
817*663afb9bSAndroid Build Coastguard Worker * evbuffer_expand_fast_() */
818*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_reserve_space(buf, 1<<13, vec, nvec), >=, 1);
819*663afb9bSAndroid Build Coastguard Worker
820*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
821*663afb9bSAndroid Build Coastguard Worker
822*663afb9bSAndroid Build Coastguard Worker end:
823*663afb9bSAndroid Build Coastguard Worker if (buf)
824*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
825*663afb9bSAndroid Build Coastguard Worker }
826*663afb9bSAndroid Build Coastguard Worker
827*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_expand(void * ptr)828*663afb9bSAndroid Build Coastguard Worker test_evbuffer_expand(void *ptr)
829*663afb9bSAndroid Build Coastguard Worker {
830*663afb9bSAndroid Build Coastguard Worker char data[4096];
831*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf;
832*663afb9bSAndroid Build Coastguard Worker size_t a,w,u;
833*663afb9bSAndroid Build Coastguard Worker void *buffer;
834*663afb9bSAndroid Build Coastguard Worker
835*663afb9bSAndroid Build Coastguard Worker memset(data, 'X', sizeof(data));
836*663afb9bSAndroid Build Coastguard Worker
837*663afb9bSAndroid Build Coastguard Worker /* Make sure that expand() works on an empty buffer */
838*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
839*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_expand(buf, 20000), ==, 0);
840*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
841*663afb9bSAndroid Build Coastguard Worker a=w=u=0;
842*663afb9bSAndroid Build Coastguard Worker evbuffer_get_waste(buf, &a,&w,&u);
843*663afb9bSAndroid Build Coastguard Worker tt_assert(w == 0);
844*663afb9bSAndroid Build Coastguard Worker tt_assert(u == 0);
845*663afb9bSAndroid Build Coastguard Worker tt_assert(a >= 20000);
846*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first);
847*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first == buf->last);
848*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first->off == 0);
849*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first->buffer_len >= 20000);
850*663afb9bSAndroid Build Coastguard Worker
851*663afb9bSAndroid Build Coastguard Worker /* Make sure that expand() works as a no-op when there's enough
852*663afb9bSAndroid Build Coastguard Worker * contiguous space already. */
853*663afb9bSAndroid Build Coastguard Worker buffer = buf->first->buffer;
854*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, data, 1024);
855*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_expand(buf, 1024), ==, 0);
856*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first->buffer == buffer);
857*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
858*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
859*663afb9bSAndroid Build Coastguard Worker
860*663afb9bSAndroid Build Coastguard Worker /* Make sure that expand() can work by moving misaligned data
861*663afb9bSAndroid Build Coastguard Worker * when it makes sense to do so. */
862*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
863*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, data, 400);
864*663afb9bSAndroid Build Coastguard Worker {
865*663afb9bSAndroid Build Coastguard Worker int n = (int)(buf->first->buffer_len - buf->first->off - 1);
866*663afb9bSAndroid Build Coastguard Worker tt_assert(n < (int)sizeof(data));
867*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, data, n);
868*663afb9bSAndroid Build Coastguard Worker }
869*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first == buf->last);
870*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first->off == buf->first->buffer_len - 1);
871*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf, buf->first->off - 1);
872*663afb9bSAndroid Build Coastguard Worker tt_assert(1 == evbuffer_get_length(buf));
873*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first->misalign > 0);
874*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first->off == 1);
875*663afb9bSAndroid Build Coastguard Worker buffer = buf->first->buffer;
876*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_expand(buf, 40) == 0);
877*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first == buf->last);
878*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first->off == 1);
879*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first->buffer == buffer);
880*663afb9bSAndroid Build Coastguard Worker tt_assert(buf->first->misalign == 0);
881*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
882*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
883*663afb9bSAndroid Build Coastguard Worker
884*663afb9bSAndroid Build Coastguard Worker /* add, expand, pull-up: This used to crash libevent. */
885*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
886*663afb9bSAndroid Build Coastguard Worker
887*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, data, sizeof(data));
888*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, data, sizeof(data));
889*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, data, sizeof(data));
890*663afb9bSAndroid Build Coastguard Worker
891*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
892*663afb9bSAndroid Build Coastguard Worker evbuffer_expand(buf, 1024);
893*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
894*663afb9bSAndroid Build Coastguard Worker evbuffer_pullup(buf, -1);
895*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
896*663afb9bSAndroid Build Coastguard Worker
897*663afb9bSAndroid Build Coastguard Worker end:
898*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
899*663afb9bSAndroid Build Coastguard Worker }
900*663afb9bSAndroid Build Coastguard Worker
901*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_expand_overflow(void * ptr)902*663afb9bSAndroid Build Coastguard Worker test_evbuffer_expand_overflow(void *ptr)
903*663afb9bSAndroid Build Coastguard Worker {
904*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf;
905*663afb9bSAndroid Build Coastguard Worker
906*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
907*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "1", 1);
908*663afb9bSAndroid Build Coastguard Worker evbuffer_expand(buf, EVBUFFER_CHAIN_MAX);
909*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
910*663afb9bSAndroid Build Coastguard Worker
911*663afb9bSAndroid Build Coastguard Worker evbuffer_expand(buf, EV_SIZE_MAX);
912*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
913*663afb9bSAndroid Build Coastguard Worker
914*663afb9bSAndroid Build Coastguard Worker end:
915*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
916*663afb9bSAndroid Build Coastguard Worker }
917*663afb9bSAndroid Build Coastguard Worker
918*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_add1(void * ptr)919*663afb9bSAndroid Build Coastguard Worker test_evbuffer_add1(void *ptr)
920*663afb9bSAndroid Build Coastguard Worker {
921*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf;
922*663afb9bSAndroid Build Coastguard Worker char *str;
923*663afb9bSAndroid Build Coastguard Worker
924*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
925*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "1", 1);
926*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
927*663afb9bSAndroid Build Coastguard Worker evbuffer_expand(buf, 2048);
928*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
929*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "2", 1);
930*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
931*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(buf, "3");
932*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
933*663afb9bSAndroid Build Coastguard Worker
934*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(buf) == 3);
935*663afb9bSAndroid Build Coastguard Worker str = (char *)evbuffer_pullup(buf, -1);
936*663afb9bSAndroid Build Coastguard Worker tt_assert(str[0] == '1');
937*663afb9bSAndroid Build Coastguard Worker tt_assert(str[1] == '2');
938*663afb9bSAndroid Build Coastguard Worker tt_assert(str[2] == '3');
939*663afb9bSAndroid Build Coastguard Worker end:
940*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
941*663afb9bSAndroid Build Coastguard Worker }
942*663afb9bSAndroid Build Coastguard Worker
943*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_add2(void * ptr)944*663afb9bSAndroid Build Coastguard Worker test_evbuffer_add2(void *ptr)
945*663afb9bSAndroid Build Coastguard Worker {
946*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf;
947*663afb9bSAndroid Build Coastguard Worker static char data[4096];
948*663afb9bSAndroid Build Coastguard Worker int data_len = MIN_BUFFER_SIZE-EVBUFFER_CHAIN_SIZE-10;
949*663afb9bSAndroid Build Coastguard Worker char *str;
950*663afb9bSAndroid Build Coastguard Worker int len;
951*663afb9bSAndroid Build Coastguard Worker
952*663afb9bSAndroid Build Coastguard Worker memset(data, 'P', sizeof(data));
953*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
954*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, data, data_len);
955*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
956*663afb9bSAndroid Build Coastguard Worker evbuffer_expand(buf, 100);
957*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
958*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "2", 1);
959*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
960*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(buf, "3");
961*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
962*663afb9bSAndroid Build Coastguard Worker
963*663afb9bSAndroid Build Coastguard Worker len = evbuffer_get_length(buf);
964*663afb9bSAndroid Build Coastguard Worker tt_assert(len == data_len+2);
965*663afb9bSAndroid Build Coastguard Worker str = (char *)evbuffer_pullup(buf, -1);
966*663afb9bSAndroid Build Coastguard Worker tt_assert(str[len-3] == 'P');
967*663afb9bSAndroid Build Coastguard Worker tt_assert(str[len-2] == '2');
968*663afb9bSAndroid Build Coastguard Worker tt_assert(str[len-1] == '3');
969*663afb9bSAndroid Build Coastguard Worker end:
970*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
971*663afb9bSAndroid Build Coastguard Worker }
972*663afb9bSAndroid Build Coastguard Worker
973*663afb9bSAndroid Build Coastguard Worker static int reference_cb_called;
974*663afb9bSAndroid Build Coastguard Worker static void
reference_cb(const void * data,size_t len,void * extra)975*663afb9bSAndroid Build Coastguard Worker reference_cb(const void *data, size_t len, void *extra)
976*663afb9bSAndroid Build Coastguard Worker {
977*663afb9bSAndroid Build Coastguard Worker tt_str_op(data, ==, "this is what we add as read-only memory.");
978*663afb9bSAndroid Build Coastguard Worker tt_int_op(len, ==, strlen(data));
979*663afb9bSAndroid Build Coastguard Worker tt_want(extra == (void *)0xdeadaffe);
980*663afb9bSAndroid Build Coastguard Worker ++reference_cb_called;
981*663afb9bSAndroid Build Coastguard Worker end:
982*663afb9bSAndroid Build Coastguard Worker ;
983*663afb9bSAndroid Build Coastguard Worker }
984*663afb9bSAndroid Build Coastguard Worker
985*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_reference(void * ptr)986*663afb9bSAndroid Build Coastguard Worker test_evbuffer_reference(void *ptr)
987*663afb9bSAndroid Build Coastguard Worker {
988*663afb9bSAndroid Build Coastguard Worker struct evbuffer *src = evbuffer_new();
989*663afb9bSAndroid Build Coastguard Worker struct evbuffer *dst = evbuffer_new();
990*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec v[1];
991*663afb9bSAndroid Build Coastguard Worker const char *data = "this is what we add as read-only memory.";
992*663afb9bSAndroid Build Coastguard Worker reference_cb_called = 0;
993*663afb9bSAndroid Build Coastguard Worker
994*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_add_reference(src, data, strlen(data),
995*663afb9bSAndroid Build Coastguard Worker reference_cb, (void *)0xdeadaffe) != -1);
996*663afb9bSAndroid Build Coastguard Worker
997*663afb9bSAndroid Build Coastguard Worker evbuffer_reserve_space(dst, strlen(data), v, 1);
998*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_remove(src, v[0].iov_base, 10) != -1);
999*663afb9bSAndroid Build Coastguard Worker
1000*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
1001*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
1002*663afb9bSAndroid Build Coastguard Worker
1003*663afb9bSAndroid Build Coastguard Worker /* make sure that we don't write data at the beginning */
1004*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(src, "aaaaa", 5);
1005*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
1006*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(src, 5);
1007*663afb9bSAndroid Build Coastguard Worker
1008*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_remove(src, ((char*)(v[0].iov_base)) + 10,
1009*663afb9bSAndroid Build Coastguard Worker strlen(data) - 10) != -1);
1010*663afb9bSAndroid Build Coastguard Worker
1011*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = strlen(data);
1012*663afb9bSAndroid Build Coastguard Worker
1013*663afb9bSAndroid Build Coastguard Worker evbuffer_commit_space(dst, v, 1);
1014*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
1015*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
1016*663afb9bSAndroid Build Coastguard Worker
1017*663afb9bSAndroid Build Coastguard Worker tt_int_op(reference_cb_called, ==, 1);
1018*663afb9bSAndroid Build Coastguard Worker
1019*663afb9bSAndroid Build Coastguard Worker tt_assert(!memcmp(evbuffer_pullup(dst, strlen(data)),
1020*663afb9bSAndroid Build Coastguard Worker data, strlen(data)));
1021*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dst);
1022*663afb9bSAndroid Build Coastguard Worker
1023*663afb9bSAndroid Build Coastguard Worker end:
1024*663afb9bSAndroid Build Coastguard Worker evbuffer_free(dst);
1025*663afb9bSAndroid Build Coastguard Worker evbuffer_free(src);
1026*663afb9bSAndroid Build Coastguard Worker }
1027*663afb9bSAndroid Build Coastguard Worker
1028*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_reference2(void * ptr)1029*663afb9bSAndroid Build Coastguard Worker test_evbuffer_reference2(void *ptr)
1030*663afb9bSAndroid Build Coastguard Worker {
1031*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf;
1032*663afb9bSAndroid Build Coastguard Worker static char data[4096];
1033*663afb9bSAndroid Build Coastguard Worker int data_len = MIN_BUFFER_SIZE-EVBUFFER_CHAIN_SIZE-10;
1034*663afb9bSAndroid Build Coastguard Worker char *str;
1035*663afb9bSAndroid Build Coastguard Worker int len;
1036*663afb9bSAndroid Build Coastguard Worker
1037*663afb9bSAndroid Build Coastguard Worker memset(data, 'P', sizeof(data));
1038*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
1039*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, data, data_len);
1040*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1041*663afb9bSAndroid Build Coastguard Worker evbuffer_expand(buf, 100);
1042*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1043*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, "2", 1, no_cleanup, NULL);
1044*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1045*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(buf, "3");
1046*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1047*663afb9bSAndroid Build Coastguard Worker
1048*663afb9bSAndroid Build Coastguard Worker len = evbuffer_get_length(buf);
1049*663afb9bSAndroid Build Coastguard Worker tt_assert(len == data_len+2);
1050*663afb9bSAndroid Build Coastguard Worker str = (char *)evbuffer_pullup(buf, -1);
1051*663afb9bSAndroid Build Coastguard Worker tt_assert(str[len-3] == 'P');
1052*663afb9bSAndroid Build Coastguard Worker tt_assert(str[len-2] == '2');
1053*663afb9bSAndroid Build Coastguard Worker tt_assert(str[len-1] == '3');
1054*663afb9bSAndroid Build Coastguard Worker end:
1055*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
1056*663afb9bSAndroid Build Coastguard Worker }
1057*663afb9bSAndroid Build Coastguard Worker
1058*663afb9bSAndroid Build Coastguard Worker static struct event_base *addfile_test_event_base;
1059*663afb9bSAndroid Build Coastguard Worker static int addfile_test_done_writing;
1060*663afb9bSAndroid Build Coastguard Worker static int addfile_test_total_written;
1061*663afb9bSAndroid Build Coastguard Worker static int addfile_test_total_read;
1062*663afb9bSAndroid Build Coastguard Worker
1063*663afb9bSAndroid Build Coastguard Worker static void
addfile_test_writecb(evutil_socket_t fd,short what,void * arg)1064*663afb9bSAndroid Build Coastguard Worker addfile_test_writecb(evutil_socket_t fd, short what, void *arg)
1065*663afb9bSAndroid Build Coastguard Worker {
1066*663afb9bSAndroid Build Coastguard Worker struct evbuffer *b = arg;
1067*663afb9bSAndroid Build Coastguard Worker int r;
1068*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(b);
1069*663afb9bSAndroid Build Coastguard Worker while (evbuffer_get_length(b)) {
1070*663afb9bSAndroid Build Coastguard Worker r = evbuffer_write(b, fd);
1071*663afb9bSAndroid Build Coastguard Worker if (r > 0) {
1072*663afb9bSAndroid Build Coastguard Worker addfile_test_total_written += r;
1073*663afb9bSAndroid Build Coastguard Worker TT_BLATHER(("Wrote %d/%d bytes", r, addfile_test_total_written));
1074*663afb9bSAndroid Build Coastguard Worker } else {
1075*663afb9bSAndroid Build Coastguard Worker int e = evutil_socket_geterror(fd);
1076*663afb9bSAndroid Build Coastguard Worker if (EVUTIL_ERR_RW_RETRIABLE(e))
1077*663afb9bSAndroid Build Coastguard Worker return;
1078*663afb9bSAndroid Build Coastguard Worker tt_fail_perror("write");
1079*663afb9bSAndroid Build Coastguard Worker event_base_loopexit(addfile_test_event_base,NULL);
1080*663afb9bSAndroid Build Coastguard Worker }
1081*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(b);
1082*663afb9bSAndroid Build Coastguard Worker }
1083*663afb9bSAndroid Build Coastguard Worker addfile_test_done_writing = 1;
1084*663afb9bSAndroid Build Coastguard Worker return;
1085*663afb9bSAndroid Build Coastguard Worker end:
1086*663afb9bSAndroid Build Coastguard Worker event_base_loopexit(addfile_test_event_base,NULL);
1087*663afb9bSAndroid Build Coastguard Worker }
1088*663afb9bSAndroid Build Coastguard Worker
1089*663afb9bSAndroid Build Coastguard Worker static void
addfile_test_readcb(evutil_socket_t fd,short what,void * arg)1090*663afb9bSAndroid Build Coastguard Worker addfile_test_readcb(evutil_socket_t fd, short what, void *arg)
1091*663afb9bSAndroid Build Coastguard Worker {
1092*663afb9bSAndroid Build Coastguard Worker struct evbuffer *b = arg;
1093*663afb9bSAndroid Build Coastguard Worker int e, r = 0;
1094*663afb9bSAndroid Build Coastguard Worker do {
1095*663afb9bSAndroid Build Coastguard Worker r = evbuffer_read(b, fd, 1024);
1096*663afb9bSAndroid Build Coastguard Worker if (r > 0) {
1097*663afb9bSAndroid Build Coastguard Worker addfile_test_total_read += r;
1098*663afb9bSAndroid Build Coastguard Worker TT_BLATHER(("Read %d/%d bytes", r, addfile_test_total_read));
1099*663afb9bSAndroid Build Coastguard Worker }
1100*663afb9bSAndroid Build Coastguard Worker } while (r > 0);
1101*663afb9bSAndroid Build Coastguard Worker if (r < 0) {
1102*663afb9bSAndroid Build Coastguard Worker e = evutil_socket_geterror(fd);
1103*663afb9bSAndroid Build Coastguard Worker if (! EVUTIL_ERR_RW_RETRIABLE(e)) {
1104*663afb9bSAndroid Build Coastguard Worker tt_fail_perror("read");
1105*663afb9bSAndroid Build Coastguard Worker event_base_loopexit(addfile_test_event_base,NULL);
1106*663afb9bSAndroid Build Coastguard Worker }
1107*663afb9bSAndroid Build Coastguard Worker }
1108*663afb9bSAndroid Build Coastguard Worker if (addfile_test_done_writing &&
1109*663afb9bSAndroid Build Coastguard Worker addfile_test_total_read >= addfile_test_total_written) {
1110*663afb9bSAndroid Build Coastguard Worker event_base_loopexit(addfile_test_event_base,NULL);
1111*663afb9bSAndroid Build Coastguard Worker }
1112*663afb9bSAndroid Build Coastguard Worker }
1113*663afb9bSAndroid Build Coastguard Worker
1114*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_add_file(void * ptr)1115*663afb9bSAndroid Build Coastguard Worker test_evbuffer_add_file(void *ptr)
1116*663afb9bSAndroid Build Coastguard Worker {
1117*663afb9bSAndroid Build Coastguard Worker struct basic_test_data *testdata = ptr;
1118*663afb9bSAndroid Build Coastguard Worker const char *impl = testdata->setup_data;
1119*663afb9bSAndroid Build Coastguard Worker struct evbuffer *src = evbuffer_new(), *dest = evbuffer_new();
1120*663afb9bSAndroid Build Coastguard Worker char *tmpfilename = NULL;
1121*663afb9bSAndroid Build Coastguard Worker char *data = NULL;
1122*663afb9bSAndroid Build Coastguard Worker const char *expect_data;
1123*663afb9bSAndroid Build Coastguard Worker size_t datalen, expect_len;
1124*663afb9bSAndroid Build Coastguard Worker const char *compare;
1125*663afb9bSAndroid Build Coastguard Worker int fd = -1;
1126*663afb9bSAndroid Build Coastguard Worker int want_ismapping = -1, want_cansendfile = -1;
1127*663afb9bSAndroid Build Coastguard Worker unsigned flags = 0;
1128*663afb9bSAndroid Build Coastguard Worker int use_segment = 1, use_bigfile = 0, map_from_offset = 0,
1129*663afb9bSAndroid Build Coastguard Worker view_from_offset = 0;
1130*663afb9bSAndroid Build Coastguard Worker struct evbuffer_file_segment *seg = NULL;
1131*663afb9bSAndroid Build Coastguard Worker ev_off_t starting_offset = 0, mapping_len = -1;
1132*663afb9bSAndroid Build Coastguard Worker ev_off_t segment_offset = 0, segment_len = -1;
1133*663afb9bSAndroid Build Coastguard Worker struct event *rev=NULL, *wev=NULL;
1134*663afb9bSAndroid Build Coastguard Worker struct event_base *base = testdata->base;
1135*663afb9bSAndroid Build Coastguard Worker evutil_socket_t pair[2] = {-1, -1};
1136*663afb9bSAndroid Build Coastguard Worker struct evutil_weakrand_state seed = { 123456789U };
1137*663afb9bSAndroid Build Coastguard Worker
1138*663afb9bSAndroid Build Coastguard Worker /* This test is highly parameterized based on substrings of its
1139*663afb9bSAndroid Build Coastguard Worker * argument. The strings are: */
1140*663afb9bSAndroid Build Coastguard Worker tt_assert(impl);
1141*663afb9bSAndroid Build Coastguard Worker if (strstr(impl, "nosegment")) {
1142*663afb9bSAndroid Build Coastguard Worker /* If nosegment is set, use the older evbuffer_add_file
1143*663afb9bSAndroid Build Coastguard Worker * interface */
1144*663afb9bSAndroid Build Coastguard Worker use_segment = 0;
1145*663afb9bSAndroid Build Coastguard Worker }
1146*663afb9bSAndroid Build Coastguard Worker if (strstr(impl, "bigfile")) {
1147*663afb9bSAndroid Build Coastguard Worker /* If bigfile is set, use a 512K file. Else use a smaller
1148*663afb9bSAndroid Build Coastguard Worker * one. */
1149*663afb9bSAndroid Build Coastguard Worker use_bigfile = 1;
1150*663afb9bSAndroid Build Coastguard Worker }
1151*663afb9bSAndroid Build Coastguard Worker if (strstr(impl, "map_offset")) {
1152*663afb9bSAndroid Build Coastguard Worker /* If map_offset is set, we build the file segment starting
1153*663afb9bSAndroid Build Coastguard Worker * from a point other than byte 0 and ending somewhere other
1154*663afb9bSAndroid Build Coastguard Worker * than the last byte. Otherwise we map the whole thing */
1155*663afb9bSAndroid Build Coastguard Worker map_from_offset = 1;
1156*663afb9bSAndroid Build Coastguard Worker }
1157*663afb9bSAndroid Build Coastguard Worker if (strstr(impl, "offset_in_segment")) {
1158*663afb9bSAndroid Build Coastguard Worker /* If offset_in_segment is set, we add a subsection of the
1159*663afb9bSAndroid Build Coastguard Worker * file semgment starting from a point other than byte 0 of
1160*663afb9bSAndroid Build Coastguard Worker * the segment. */
1161*663afb9bSAndroid Build Coastguard Worker view_from_offset = 1;
1162*663afb9bSAndroid Build Coastguard Worker }
1163*663afb9bSAndroid Build Coastguard Worker if (strstr(impl, "sendfile")) {
1164*663afb9bSAndroid Build Coastguard Worker /* If sendfile is set, we try to use a sendfile/splice style
1165*663afb9bSAndroid Build Coastguard Worker * backend. */
1166*663afb9bSAndroid Build Coastguard Worker flags = EVBUF_FS_DISABLE_MMAP;
1167*663afb9bSAndroid Build Coastguard Worker want_cansendfile = 1;
1168*663afb9bSAndroid Build Coastguard Worker want_ismapping = 0;
1169*663afb9bSAndroid Build Coastguard Worker } else if (strstr(impl, "mmap")) {
1170*663afb9bSAndroid Build Coastguard Worker /* If sendfile is set, we try to use a mmap/CreateFileMapping
1171*663afb9bSAndroid Build Coastguard Worker * style backend. */
1172*663afb9bSAndroid Build Coastguard Worker flags = EVBUF_FS_DISABLE_SENDFILE;
1173*663afb9bSAndroid Build Coastguard Worker want_ismapping = 1;
1174*663afb9bSAndroid Build Coastguard Worker want_cansendfile = 0;
1175*663afb9bSAndroid Build Coastguard Worker } else if (strstr(impl, "linear")) {
1176*663afb9bSAndroid Build Coastguard Worker /* If linear is set, we try to use a read-the-whole-thing
1177*663afb9bSAndroid Build Coastguard Worker * backend. */
1178*663afb9bSAndroid Build Coastguard Worker flags = EVBUF_FS_DISABLE_SENDFILE|EVBUF_FS_DISABLE_MMAP;
1179*663afb9bSAndroid Build Coastguard Worker want_ismapping = 0;
1180*663afb9bSAndroid Build Coastguard Worker want_cansendfile = 0;
1181*663afb9bSAndroid Build Coastguard Worker } else if (strstr(impl, "default")) {
1182*663afb9bSAndroid Build Coastguard Worker /* The caller doesn't care which backend we use. */
1183*663afb9bSAndroid Build Coastguard Worker ;
1184*663afb9bSAndroid Build Coastguard Worker } else {
1185*663afb9bSAndroid Build Coastguard Worker /* The caller must choose a backend. */
1186*663afb9bSAndroid Build Coastguard Worker TT_DIE(("Didn't recognize the implementation"));
1187*663afb9bSAndroid Build Coastguard Worker }
1188*663afb9bSAndroid Build Coastguard Worker
1189*663afb9bSAndroid Build Coastguard Worker if (use_bigfile) {
1190*663afb9bSAndroid Build Coastguard Worker unsigned int i;
1191*663afb9bSAndroid Build Coastguard Worker datalen = 1024*512;
1192*663afb9bSAndroid Build Coastguard Worker data = malloc(1024*512);
1193*663afb9bSAndroid Build Coastguard Worker tt_assert(data);
1194*663afb9bSAndroid Build Coastguard Worker for (i = 0; i < datalen; ++i)
1195*663afb9bSAndroid Build Coastguard Worker data[i] = (char)evutil_weakrand_(&seed);
1196*663afb9bSAndroid Build Coastguard Worker } else {
1197*663afb9bSAndroid Build Coastguard Worker data = strdup("here is a relatively small string.");
1198*663afb9bSAndroid Build Coastguard Worker tt_assert(data);
1199*663afb9bSAndroid Build Coastguard Worker datalen = strlen(data);
1200*663afb9bSAndroid Build Coastguard Worker }
1201*663afb9bSAndroid Build Coastguard Worker
1202*663afb9bSAndroid Build Coastguard Worker fd = regress_make_tmpfile(data, datalen, &tmpfilename);
1203*663afb9bSAndroid Build Coastguard Worker
1204*663afb9bSAndroid Build Coastguard Worker if (map_from_offset) {
1205*663afb9bSAndroid Build Coastguard Worker starting_offset = datalen/4 + 1;
1206*663afb9bSAndroid Build Coastguard Worker mapping_len = datalen / 2 - 1;
1207*663afb9bSAndroid Build Coastguard Worker expect_data = data + starting_offset;
1208*663afb9bSAndroid Build Coastguard Worker expect_len = mapping_len;
1209*663afb9bSAndroid Build Coastguard Worker } else {
1210*663afb9bSAndroid Build Coastguard Worker expect_data = data;
1211*663afb9bSAndroid Build Coastguard Worker expect_len = datalen;
1212*663afb9bSAndroid Build Coastguard Worker }
1213*663afb9bSAndroid Build Coastguard Worker if (view_from_offset) {
1214*663afb9bSAndroid Build Coastguard Worker tt_assert(use_segment); /* Can't do this with add_file*/
1215*663afb9bSAndroid Build Coastguard Worker segment_offset = expect_len / 3;
1216*663afb9bSAndroid Build Coastguard Worker segment_len = expect_len / 2;
1217*663afb9bSAndroid Build Coastguard Worker expect_data = expect_data + segment_offset;
1218*663afb9bSAndroid Build Coastguard Worker expect_len = segment_len;
1219*663afb9bSAndroid Build Coastguard Worker }
1220*663afb9bSAndroid Build Coastguard Worker
1221*663afb9bSAndroid Build Coastguard Worker if (use_segment) {
1222*663afb9bSAndroid Build Coastguard Worker seg = evbuffer_file_segment_new(fd, starting_offset,
1223*663afb9bSAndroid Build Coastguard Worker mapping_len, flags);
1224*663afb9bSAndroid Build Coastguard Worker tt_assert(seg);
1225*663afb9bSAndroid Build Coastguard Worker if (want_ismapping >= 0) {
1226*663afb9bSAndroid Build Coastguard Worker if (seg->is_mapping != (unsigned)want_ismapping)
1227*663afb9bSAndroid Build Coastguard Worker tt_skip();
1228*663afb9bSAndroid Build Coastguard Worker }
1229*663afb9bSAndroid Build Coastguard Worker if (want_cansendfile >= 0) {
1230*663afb9bSAndroid Build Coastguard Worker if (seg->can_sendfile != (unsigned)want_cansendfile)
1231*663afb9bSAndroid Build Coastguard Worker tt_skip();
1232*663afb9bSAndroid Build Coastguard Worker }
1233*663afb9bSAndroid Build Coastguard Worker }
1234*663afb9bSAndroid Build Coastguard Worker
1235*663afb9bSAndroid Build Coastguard Worker /* Say that it drains to a fd so that we can use sendfile. */
1236*663afb9bSAndroid Build Coastguard Worker evbuffer_set_flags(src, EVBUFFER_FLAG_DRAINS_TO_FD);
1237*663afb9bSAndroid Build Coastguard Worker
1238*663afb9bSAndroid Build Coastguard Worker #if defined(EVENT__HAVE_SENDFILE) && defined(__sun__) && defined(__svr4__)
1239*663afb9bSAndroid Build Coastguard Worker /* We need to use a pair of AF_INET sockets, since Solaris
1240*663afb9bSAndroid Build Coastguard Worker doesn't support sendfile() over AF_UNIX. */
1241*663afb9bSAndroid Build Coastguard Worker if (evutil_ersatz_socketpair_(AF_INET, SOCK_STREAM, 0, pair) == -1)
1242*663afb9bSAndroid Build Coastguard Worker tt_abort_msg("ersatz_socketpair failed");
1243*663afb9bSAndroid Build Coastguard Worker #else
1244*663afb9bSAndroid Build Coastguard Worker if (evutil_socketpair(AF_UNIX, SOCK_STREAM, 0, pair) == -1)
1245*663afb9bSAndroid Build Coastguard Worker tt_abort_msg("socketpair failed");
1246*663afb9bSAndroid Build Coastguard Worker #endif
1247*663afb9bSAndroid Build Coastguard Worker evutil_make_socket_nonblocking(pair[0]);
1248*663afb9bSAndroid Build Coastguard Worker evutil_make_socket_nonblocking(pair[1]);
1249*663afb9bSAndroid Build Coastguard Worker
1250*663afb9bSAndroid Build Coastguard Worker tt_assert(fd != -1);
1251*663afb9bSAndroid Build Coastguard Worker
1252*663afb9bSAndroid Build Coastguard Worker if (use_segment) {
1253*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_add_file_segment(src, seg,
1254*663afb9bSAndroid Build Coastguard Worker segment_offset, segment_len)!=-1);
1255*663afb9bSAndroid Build Coastguard Worker } else {
1256*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_add_file(src, fd, starting_offset,
1257*663afb9bSAndroid Build Coastguard Worker mapping_len) != -1);
1258*663afb9bSAndroid Build Coastguard Worker }
1259*663afb9bSAndroid Build Coastguard Worker
1260*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
1261*663afb9bSAndroid Build Coastguard Worker
1262*663afb9bSAndroid Build Coastguard Worker addfile_test_event_base = base;
1263*663afb9bSAndroid Build Coastguard Worker addfile_test_done_writing = 0;
1264*663afb9bSAndroid Build Coastguard Worker addfile_test_total_written = 0;
1265*663afb9bSAndroid Build Coastguard Worker addfile_test_total_read = 0;
1266*663afb9bSAndroid Build Coastguard Worker
1267*663afb9bSAndroid Build Coastguard Worker wev = event_new(base, pair[0], EV_WRITE|EV_PERSIST,
1268*663afb9bSAndroid Build Coastguard Worker addfile_test_writecb, src);
1269*663afb9bSAndroid Build Coastguard Worker rev = event_new(base, pair[1], EV_READ|EV_PERSIST,
1270*663afb9bSAndroid Build Coastguard Worker addfile_test_readcb, dest);
1271*663afb9bSAndroid Build Coastguard Worker
1272*663afb9bSAndroid Build Coastguard Worker event_add(wev, NULL);
1273*663afb9bSAndroid Build Coastguard Worker event_add(rev, NULL);
1274*663afb9bSAndroid Build Coastguard Worker event_base_dispatch(base);
1275*663afb9bSAndroid Build Coastguard Worker
1276*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(src);
1277*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dest);
1278*663afb9bSAndroid Build Coastguard Worker
1279*663afb9bSAndroid Build Coastguard Worker tt_assert(addfile_test_done_writing);
1280*663afb9bSAndroid Build Coastguard Worker tt_int_op(addfile_test_total_written, ==, expect_len);
1281*663afb9bSAndroid Build Coastguard Worker tt_int_op(addfile_test_total_read, ==, expect_len);
1282*663afb9bSAndroid Build Coastguard Worker
1283*663afb9bSAndroid Build Coastguard Worker compare = (char *)evbuffer_pullup(dest, expect_len);
1284*663afb9bSAndroid Build Coastguard Worker tt_assert(compare != NULL);
1285*663afb9bSAndroid Build Coastguard Worker if (memcmp(compare, expect_data, expect_len)) {
1286*663afb9bSAndroid Build Coastguard Worker tt_abort_msg("Data from add_file differs.");
1287*663afb9bSAndroid Build Coastguard Worker }
1288*663afb9bSAndroid Build Coastguard Worker
1289*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(dest);
1290*663afb9bSAndroid Build Coastguard Worker end:
1291*663afb9bSAndroid Build Coastguard Worker if (data)
1292*663afb9bSAndroid Build Coastguard Worker free(data);
1293*663afb9bSAndroid Build Coastguard Worker if (seg)
1294*663afb9bSAndroid Build Coastguard Worker evbuffer_file_segment_free(seg);
1295*663afb9bSAndroid Build Coastguard Worker if (src)
1296*663afb9bSAndroid Build Coastguard Worker evbuffer_free(src);
1297*663afb9bSAndroid Build Coastguard Worker if (dest)
1298*663afb9bSAndroid Build Coastguard Worker evbuffer_free(dest);
1299*663afb9bSAndroid Build Coastguard Worker if (pair[0] >= 0)
1300*663afb9bSAndroid Build Coastguard Worker evutil_closesocket(pair[0]);
1301*663afb9bSAndroid Build Coastguard Worker if (pair[1] >= 0)
1302*663afb9bSAndroid Build Coastguard Worker evutil_closesocket(pair[1]);
1303*663afb9bSAndroid Build Coastguard Worker if (wev)
1304*663afb9bSAndroid Build Coastguard Worker event_free(wev);
1305*663afb9bSAndroid Build Coastguard Worker if (rev)
1306*663afb9bSAndroid Build Coastguard Worker event_free(rev);
1307*663afb9bSAndroid Build Coastguard Worker if (tmpfilename) {
1308*663afb9bSAndroid Build Coastguard Worker unlink(tmpfilename);
1309*663afb9bSAndroid Build Coastguard Worker free(tmpfilename);
1310*663afb9bSAndroid Build Coastguard Worker }
1311*663afb9bSAndroid Build Coastguard Worker }
1312*663afb9bSAndroid Build Coastguard Worker
1313*663afb9bSAndroid Build Coastguard Worker static int file_segment_cleanup_cb_called_count = 0;
1314*663afb9bSAndroid Build Coastguard Worker static struct evbuffer_file_segment const* file_segment_cleanup_cb_called_with = NULL;
1315*663afb9bSAndroid Build Coastguard Worker static int file_segment_cleanup_cb_called_with_flags = 0;
1316*663afb9bSAndroid Build Coastguard Worker static void* file_segment_cleanup_cb_called_with_arg = NULL;
1317*663afb9bSAndroid Build Coastguard Worker static void
file_segment_cleanup_cp(struct evbuffer_file_segment const * seg,int flags,void * arg)1318*663afb9bSAndroid Build Coastguard Worker file_segment_cleanup_cp(struct evbuffer_file_segment const* seg, int flags, void* arg)
1319*663afb9bSAndroid Build Coastguard Worker {
1320*663afb9bSAndroid Build Coastguard Worker ++file_segment_cleanup_cb_called_count;
1321*663afb9bSAndroid Build Coastguard Worker file_segment_cleanup_cb_called_with = seg;
1322*663afb9bSAndroid Build Coastguard Worker file_segment_cleanup_cb_called_with_flags = flags;
1323*663afb9bSAndroid Build Coastguard Worker file_segment_cleanup_cb_called_with_arg = arg;
1324*663afb9bSAndroid Build Coastguard Worker }
1325*663afb9bSAndroid Build Coastguard Worker
1326*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_file_segment_add_cleanup_cb(void * ptr)1327*663afb9bSAndroid Build Coastguard Worker test_evbuffer_file_segment_add_cleanup_cb(void* ptr)
1328*663afb9bSAndroid Build Coastguard Worker {
1329*663afb9bSAndroid Build Coastguard Worker char *tmpfilename = NULL;
1330*663afb9bSAndroid Build Coastguard Worker int fd = -1;
1331*663afb9bSAndroid Build Coastguard Worker struct evbuffer *evb = NULL;
1332*663afb9bSAndroid Build Coastguard Worker struct evbuffer_file_segment *seg = NULL, *segptr;
1333*663afb9bSAndroid Build Coastguard Worker char const* arg = "token";
1334*663afb9bSAndroid Build Coastguard Worker
1335*663afb9bSAndroid Build Coastguard Worker fd = regress_make_tmpfile("file_segment_test_file", 22, &tmpfilename);
1336*663afb9bSAndroid Build Coastguard Worker tt_int_op(fd, >=, 0);
1337*663afb9bSAndroid Build Coastguard Worker
1338*663afb9bSAndroid Build Coastguard Worker evb = evbuffer_new();
1339*663afb9bSAndroid Build Coastguard Worker tt_assert(evb);
1340*663afb9bSAndroid Build Coastguard Worker
1341*663afb9bSAndroid Build Coastguard Worker segptr = seg = evbuffer_file_segment_new(fd, 0, -1, 0);
1342*663afb9bSAndroid Build Coastguard Worker tt_assert(seg);
1343*663afb9bSAndroid Build Coastguard Worker
1344*663afb9bSAndroid Build Coastguard Worker evbuffer_file_segment_add_cleanup_cb(
1345*663afb9bSAndroid Build Coastguard Worker seg, &file_segment_cleanup_cp, (void*)arg);
1346*663afb9bSAndroid Build Coastguard Worker
1347*663afb9bSAndroid Build Coastguard Worker tt_assert(fd != -1);
1348*663afb9bSAndroid Build Coastguard Worker
1349*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_add_file_segment(evb, seg, 0, -1)!=-1);
1350*663afb9bSAndroid Build Coastguard Worker
1351*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1352*663afb9bSAndroid Build Coastguard Worker
1353*663afb9bSAndroid Build Coastguard Worker tt_int_op(file_segment_cleanup_cb_called_count, ==, 0);
1354*663afb9bSAndroid Build Coastguard Worker evbuffer_file_segment_free(seg);
1355*663afb9bSAndroid Build Coastguard Worker seg = NULL; /* Prevent double-free. */
1356*663afb9bSAndroid Build Coastguard Worker
1357*663afb9bSAndroid Build Coastguard Worker tt_int_op(file_segment_cleanup_cb_called_count, ==, 0);
1358*663afb9bSAndroid Build Coastguard Worker evbuffer_free(evb);
1359*663afb9bSAndroid Build Coastguard Worker evb = NULL; /* pevent double-free */
1360*663afb9bSAndroid Build Coastguard Worker
1361*663afb9bSAndroid Build Coastguard Worker tt_int_op(file_segment_cleanup_cb_called_count, ==, 1);
1362*663afb9bSAndroid Build Coastguard Worker tt_assert(file_segment_cleanup_cb_called_with == segptr);
1363*663afb9bSAndroid Build Coastguard Worker tt_assert(file_segment_cleanup_cb_called_with_flags == 0);
1364*663afb9bSAndroid Build Coastguard Worker tt_assert(file_segment_cleanup_cb_called_with_arg == (void*)arg);
1365*663afb9bSAndroid Build Coastguard Worker
1366*663afb9bSAndroid Build Coastguard Worker end:
1367*663afb9bSAndroid Build Coastguard Worker if (evb)
1368*663afb9bSAndroid Build Coastguard Worker evbuffer_free(evb);
1369*663afb9bSAndroid Build Coastguard Worker if (seg)
1370*663afb9bSAndroid Build Coastguard Worker evbuffer_file_segment_free(seg);
1371*663afb9bSAndroid Build Coastguard Worker if (tmpfilename) {
1372*663afb9bSAndroid Build Coastguard Worker unlink(tmpfilename);
1373*663afb9bSAndroid Build Coastguard Worker free(tmpfilename);
1374*663afb9bSAndroid Build Coastguard Worker }
1375*663afb9bSAndroid Build Coastguard Worker }
1376*663afb9bSAndroid Build Coastguard Worker
1377*663afb9bSAndroid Build Coastguard Worker #ifndef EVENT__DISABLE_MM_REPLACEMENT
1378*663afb9bSAndroid Build Coastguard Worker static void *
failing_malloc(size_t how_much)1379*663afb9bSAndroid Build Coastguard Worker failing_malloc(size_t how_much)
1380*663afb9bSAndroid Build Coastguard Worker {
1381*663afb9bSAndroid Build Coastguard Worker errno = ENOMEM;
1382*663afb9bSAndroid Build Coastguard Worker return NULL;
1383*663afb9bSAndroid Build Coastguard Worker }
1384*663afb9bSAndroid Build Coastguard Worker #endif
1385*663afb9bSAndroid Build Coastguard Worker
1386*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_readln(void * ptr)1387*663afb9bSAndroid Build Coastguard Worker test_evbuffer_readln(void *ptr)
1388*663afb9bSAndroid Build Coastguard Worker {
1389*663afb9bSAndroid Build Coastguard Worker struct evbuffer *evb = evbuffer_new();
1390*663afb9bSAndroid Build Coastguard Worker struct evbuffer *evb_tmp = evbuffer_new();
1391*663afb9bSAndroid Build Coastguard Worker const char *s;
1392*663afb9bSAndroid Build Coastguard Worker char *cp = NULL;
1393*663afb9bSAndroid Build Coastguard Worker size_t sz;
1394*663afb9bSAndroid Build Coastguard Worker
1395*663afb9bSAndroid Build Coastguard Worker #define tt_line_eq(content) \
1396*663afb9bSAndroid Build Coastguard Worker TT_STMT_BEGIN \
1397*663afb9bSAndroid Build Coastguard Worker if (!cp || sz != strlen(content) || strcmp(cp, content)) { \
1398*663afb9bSAndroid Build Coastguard Worker TT_DIE(("Wanted %s; got %s [%d]", content, cp, (int)sz)); \
1399*663afb9bSAndroid Build Coastguard Worker } \
1400*663afb9bSAndroid Build Coastguard Worker TT_STMT_END
1401*663afb9bSAndroid Build Coastguard Worker
1402*663afb9bSAndroid Build Coastguard Worker /* Test EOL_ANY. */
1403*663afb9bSAndroid Build Coastguard Worker s = "complex silly newline\r\n\n\r\n\n\rmore\0\n";
1404*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, s, strlen(s)+2);
1405*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1406*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_ANY);
1407*663afb9bSAndroid Build Coastguard Worker tt_line_eq("complex silly newline");
1408*663afb9bSAndroid Build Coastguard Worker free(cp);
1409*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1410*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_ANY);
1411*663afb9bSAndroid Build Coastguard Worker if (!cp || sz != 5 || memcmp(cp, "more\0\0", 6))
1412*663afb9bSAndroid Build Coastguard Worker tt_abort_msg("Not as expected");
1413*663afb9bSAndroid Build Coastguard Worker tt_uint_op(evbuffer_get_length(evb), ==, 0);
1414*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1415*663afb9bSAndroid Build Coastguard Worker s = "\nno newline";
1416*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, s, strlen(s));
1417*663afb9bSAndroid Build Coastguard Worker free(cp);
1418*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1419*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_ANY);
1420*663afb9bSAndroid Build Coastguard Worker tt_line_eq("");
1421*663afb9bSAndroid Build Coastguard Worker free(cp);
1422*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1423*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_ANY);
1424*663afb9bSAndroid Build Coastguard Worker tt_assert(!cp);
1425*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1426*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(evb, evbuffer_get_length(evb));
1427*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) == 0);
1428*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1429*663afb9bSAndroid Build Coastguard Worker
1430*663afb9bSAndroid Build Coastguard Worker /* Test EOL_CRLF */
1431*663afb9bSAndroid Build Coastguard Worker s = "Line with\rin the middle\nLine with good crlf\r\n\nfinal\n";
1432*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, s, strlen(s));
1433*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1434*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF);
1435*663afb9bSAndroid Build Coastguard Worker tt_line_eq("Line with\rin the middle");
1436*663afb9bSAndroid Build Coastguard Worker free(cp);
1437*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1438*663afb9bSAndroid Build Coastguard Worker
1439*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF);
1440*663afb9bSAndroid Build Coastguard Worker tt_line_eq("Line with good crlf");
1441*663afb9bSAndroid Build Coastguard Worker free(cp);
1442*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1443*663afb9bSAndroid Build Coastguard Worker
1444*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF);
1445*663afb9bSAndroid Build Coastguard Worker tt_line_eq("");
1446*663afb9bSAndroid Build Coastguard Worker free(cp);
1447*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1448*663afb9bSAndroid Build Coastguard Worker
1449*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF);
1450*663afb9bSAndroid Build Coastguard Worker tt_line_eq("final");
1451*663afb9bSAndroid Build Coastguard Worker s = "x";
1452*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1453*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, s, 1);
1454*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1455*663afb9bSAndroid Build Coastguard Worker free(cp);
1456*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF);
1457*663afb9bSAndroid Build Coastguard Worker tt_assert(!cp);
1458*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1459*663afb9bSAndroid Build Coastguard Worker
1460*663afb9bSAndroid Build Coastguard Worker /* Test CRLF_STRICT */
1461*663afb9bSAndroid Build Coastguard Worker s = " and a bad crlf\nand a good one\r\n\r\nMore\r";
1462*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, s, strlen(s));
1463*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1464*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1465*663afb9bSAndroid Build Coastguard Worker tt_line_eq("x and a bad crlf\nand a good one");
1466*663afb9bSAndroid Build Coastguard Worker free(cp);
1467*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1468*663afb9bSAndroid Build Coastguard Worker
1469*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1470*663afb9bSAndroid Build Coastguard Worker tt_line_eq("");
1471*663afb9bSAndroid Build Coastguard Worker free(cp);
1472*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1473*663afb9bSAndroid Build Coastguard Worker
1474*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1475*663afb9bSAndroid Build Coastguard Worker tt_assert(!cp);
1476*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1477*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, "\n", 1);
1478*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1479*663afb9bSAndroid Build Coastguard Worker
1480*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1481*663afb9bSAndroid Build Coastguard Worker tt_line_eq("More");
1482*663afb9bSAndroid Build Coastguard Worker free(cp);
1483*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) == 0);
1484*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1485*663afb9bSAndroid Build Coastguard Worker
1486*663afb9bSAndroid Build Coastguard Worker s = "An internal CR\r is not an eol\r\nNor is a lack of one";
1487*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, s, strlen(s));
1488*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1489*663afb9bSAndroid Build Coastguard Worker tt_line_eq("An internal CR\r is not an eol");
1490*663afb9bSAndroid Build Coastguard Worker free(cp);
1491*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1492*663afb9bSAndroid Build Coastguard Worker
1493*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1494*663afb9bSAndroid Build Coastguard Worker tt_assert(!cp);
1495*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1496*663afb9bSAndroid Build Coastguard Worker
1497*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, "\r\n", 2);
1498*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1499*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1500*663afb9bSAndroid Build Coastguard Worker tt_line_eq("Nor is a lack of one");
1501*663afb9bSAndroid Build Coastguard Worker free(cp);
1502*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) == 0);
1503*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1504*663afb9bSAndroid Build Coastguard Worker
1505*663afb9bSAndroid Build Coastguard Worker /* Test LF */
1506*663afb9bSAndroid Build Coastguard Worker s = "An\rand a nl\n\nText";
1507*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, s, strlen(s));
1508*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1509*663afb9bSAndroid Build Coastguard Worker
1510*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_LF);
1511*663afb9bSAndroid Build Coastguard Worker tt_line_eq("An\rand a nl");
1512*663afb9bSAndroid Build Coastguard Worker free(cp);
1513*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1514*663afb9bSAndroid Build Coastguard Worker
1515*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_LF);
1516*663afb9bSAndroid Build Coastguard Worker tt_line_eq("");
1517*663afb9bSAndroid Build Coastguard Worker free(cp);
1518*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1519*663afb9bSAndroid Build Coastguard Worker
1520*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_LF);
1521*663afb9bSAndroid Build Coastguard Worker tt_assert(!cp);
1522*663afb9bSAndroid Build Coastguard Worker free(cp);
1523*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, "\n", 1);
1524*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1525*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_LF);
1526*663afb9bSAndroid Build Coastguard Worker tt_line_eq("Text");
1527*663afb9bSAndroid Build Coastguard Worker free(cp);
1528*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1529*663afb9bSAndroid Build Coastguard Worker
1530*663afb9bSAndroid Build Coastguard Worker /* Test NUL */
1531*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(evb), ==, 0);
1532*663afb9bSAndroid Build Coastguard Worker {
1533*663afb9bSAndroid Build Coastguard Worker char x[] =
1534*663afb9bSAndroid Build Coastguard Worker "NUL\n\0\0"
1535*663afb9bSAndroid Build Coastguard Worker "The all-zeros character which may serve\0"
1536*663afb9bSAndroid Build Coastguard Worker "to accomplish time fill\0and media fill";
1537*663afb9bSAndroid Build Coastguard Worker /* Add all but the final NUL of x. */
1538*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, x, sizeof(x)-1);
1539*663afb9bSAndroid Build Coastguard Worker }
1540*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_NUL);
1541*663afb9bSAndroid Build Coastguard Worker tt_line_eq("NUL\n");
1542*663afb9bSAndroid Build Coastguard Worker free(cp);
1543*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_NUL);
1544*663afb9bSAndroid Build Coastguard Worker tt_line_eq("");
1545*663afb9bSAndroid Build Coastguard Worker free(cp);
1546*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_NUL);
1547*663afb9bSAndroid Build Coastguard Worker tt_line_eq("The all-zeros character which may serve");
1548*663afb9bSAndroid Build Coastguard Worker free(cp);
1549*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_NUL);
1550*663afb9bSAndroid Build Coastguard Worker tt_line_eq("to accomplish time fill");
1551*663afb9bSAndroid Build Coastguard Worker free(cp);
1552*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_NUL);
1553*663afb9bSAndroid Build Coastguard Worker tt_ptr_op(cp, ==, NULL);
1554*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(evb, -1);
1555*663afb9bSAndroid Build Coastguard Worker
1556*663afb9bSAndroid Build Coastguard Worker /* Test CRLF_STRICT - across boundaries*/
1557*663afb9bSAndroid Build Coastguard Worker s = " and a bad crlf\nand a good one\r";
1558*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb_tmp, s, strlen(s));
1559*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1560*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(evb, evb_tmp);
1561*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1562*663afb9bSAndroid Build Coastguard Worker s = "\n\r";
1563*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb_tmp, s, strlen(s));
1564*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1565*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(evb, evb_tmp);
1566*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1567*663afb9bSAndroid Build Coastguard Worker s = "\nMore\r";
1568*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb_tmp, s, strlen(s));
1569*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1570*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(evb, evb_tmp);
1571*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1572*663afb9bSAndroid Build Coastguard Worker
1573*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1574*663afb9bSAndroid Build Coastguard Worker tt_line_eq(" and a bad crlf\nand a good one");
1575*663afb9bSAndroid Build Coastguard Worker free(cp);
1576*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1577*663afb9bSAndroid Build Coastguard Worker
1578*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1579*663afb9bSAndroid Build Coastguard Worker tt_line_eq("");
1580*663afb9bSAndroid Build Coastguard Worker free(cp);
1581*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1582*663afb9bSAndroid Build Coastguard Worker
1583*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1584*663afb9bSAndroid Build Coastguard Worker tt_assert(!cp);
1585*663afb9bSAndroid Build Coastguard Worker free(cp);
1586*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1587*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb, "\n", 1);
1588*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1589*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_CRLF_STRICT);
1590*663afb9bSAndroid Build Coastguard Worker tt_line_eq("More");
1591*663afb9bSAndroid Build Coastguard Worker free(cp); cp = NULL;
1592*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1593*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(evb) == 0);
1594*663afb9bSAndroid Build Coastguard Worker
1595*663afb9bSAndroid Build Coastguard Worker /* Test memory problem*/
1596*663afb9bSAndroid Build Coastguard Worker s = "one line\ntwo line\nblue line";
1597*663afb9bSAndroid Build Coastguard Worker evbuffer_add(evb_tmp, s, strlen(s));
1598*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1599*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(evb, evb_tmp);
1600*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1601*663afb9bSAndroid Build Coastguard Worker
1602*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_LF);
1603*663afb9bSAndroid Build Coastguard Worker tt_line_eq("one line");
1604*663afb9bSAndroid Build Coastguard Worker free(cp); cp = NULL;
1605*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1606*663afb9bSAndroid Build Coastguard Worker
1607*663afb9bSAndroid Build Coastguard Worker /* the next call to readline should fail */
1608*663afb9bSAndroid Build Coastguard Worker #ifndef EVENT__DISABLE_MM_REPLACEMENT
1609*663afb9bSAndroid Build Coastguard Worker event_set_mem_functions(failing_malloc, realloc, free);
1610*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_LF);
1611*663afb9bSAndroid Build Coastguard Worker tt_assert(cp == NULL);
1612*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1613*663afb9bSAndroid Build Coastguard Worker
1614*663afb9bSAndroid Build Coastguard Worker /* now we should get the next line back */
1615*663afb9bSAndroid Build Coastguard Worker event_set_mem_functions(malloc, realloc, free);
1616*663afb9bSAndroid Build Coastguard Worker #endif
1617*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(evb, &sz, EVBUFFER_EOL_LF);
1618*663afb9bSAndroid Build Coastguard Worker tt_line_eq("two line");
1619*663afb9bSAndroid Build Coastguard Worker free(cp); cp = NULL;
1620*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(evb);
1621*663afb9bSAndroid Build Coastguard Worker
1622*663afb9bSAndroid Build Coastguard Worker end:
1623*663afb9bSAndroid Build Coastguard Worker evbuffer_free(evb);
1624*663afb9bSAndroid Build Coastguard Worker evbuffer_free(evb_tmp);
1625*663afb9bSAndroid Build Coastguard Worker if (cp) free(cp);
1626*663afb9bSAndroid Build Coastguard Worker }
1627*663afb9bSAndroid Build Coastguard Worker
1628*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_search_eol(void * ptr)1629*663afb9bSAndroid Build Coastguard Worker test_evbuffer_search_eol(void *ptr)
1630*663afb9bSAndroid Build Coastguard Worker {
1631*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
1632*663afb9bSAndroid Build Coastguard Worker struct evbuffer_ptr ptr1, ptr2;
1633*663afb9bSAndroid Build Coastguard Worker const char *s;
1634*663afb9bSAndroid Build Coastguard Worker size_t eol_len;
1635*663afb9bSAndroid Build Coastguard Worker
1636*663afb9bSAndroid Build Coastguard Worker s = "string! \r\n\r\nx\n";
1637*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, s, strlen(s));
1638*663afb9bSAndroid Build Coastguard Worker eol_len = -1;
1639*663afb9bSAndroid Build Coastguard Worker ptr1 = evbuffer_search_eol(buf, NULL, &eol_len, EVBUFFER_EOL_CRLF);
1640*663afb9bSAndroid Build Coastguard Worker tt_int_op(ptr1.pos, ==, 8);
1641*663afb9bSAndroid Build Coastguard Worker tt_int_op(eol_len, ==, 2);
1642*663afb9bSAndroid Build Coastguard Worker
1643*663afb9bSAndroid Build Coastguard Worker eol_len = -1;
1644*663afb9bSAndroid Build Coastguard Worker ptr2 = evbuffer_search_eol(buf, &ptr1, &eol_len, EVBUFFER_EOL_CRLF);
1645*663afb9bSAndroid Build Coastguard Worker tt_int_op(ptr2.pos, ==, 8);
1646*663afb9bSAndroid Build Coastguard Worker tt_int_op(eol_len, ==, 2);
1647*663afb9bSAndroid Build Coastguard Worker
1648*663afb9bSAndroid Build Coastguard Worker evbuffer_ptr_set(buf, &ptr1, 1, EVBUFFER_PTR_ADD);
1649*663afb9bSAndroid Build Coastguard Worker eol_len = -1;
1650*663afb9bSAndroid Build Coastguard Worker ptr2 = evbuffer_search_eol(buf, &ptr1, &eol_len, EVBUFFER_EOL_CRLF);
1651*663afb9bSAndroid Build Coastguard Worker tt_int_op(ptr2.pos, ==, 9);
1652*663afb9bSAndroid Build Coastguard Worker tt_int_op(eol_len, ==, 1);
1653*663afb9bSAndroid Build Coastguard Worker
1654*663afb9bSAndroid Build Coastguard Worker eol_len = -1;
1655*663afb9bSAndroid Build Coastguard Worker ptr2 = evbuffer_search_eol(buf, &ptr1, &eol_len, EVBUFFER_EOL_CRLF_STRICT);
1656*663afb9bSAndroid Build Coastguard Worker tt_int_op(ptr2.pos, ==, 10);
1657*663afb9bSAndroid Build Coastguard Worker tt_int_op(eol_len, ==, 2);
1658*663afb9bSAndroid Build Coastguard Worker
1659*663afb9bSAndroid Build Coastguard Worker eol_len = -1;
1660*663afb9bSAndroid Build Coastguard Worker ptr1 = evbuffer_search_eol(buf, NULL, &eol_len, EVBUFFER_EOL_LF);
1661*663afb9bSAndroid Build Coastguard Worker tt_int_op(ptr1.pos, ==, 9);
1662*663afb9bSAndroid Build Coastguard Worker tt_int_op(eol_len, ==, 1);
1663*663afb9bSAndroid Build Coastguard Worker
1664*663afb9bSAndroid Build Coastguard Worker eol_len = -1;
1665*663afb9bSAndroid Build Coastguard Worker ptr2 = evbuffer_search_eol(buf, &ptr1, &eol_len, EVBUFFER_EOL_LF);
1666*663afb9bSAndroid Build Coastguard Worker tt_int_op(ptr2.pos, ==, 9);
1667*663afb9bSAndroid Build Coastguard Worker tt_int_op(eol_len, ==, 1);
1668*663afb9bSAndroid Build Coastguard Worker
1669*663afb9bSAndroid Build Coastguard Worker evbuffer_ptr_set(buf, &ptr1, 1, EVBUFFER_PTR_ADD);
1670*663afb9bSAndroid Build Coastguard Worker eol_len = -1;
1671*663afb9bSAndroid Build Coastguard Worker ptr2 = evbuffer_search_eol(buf, &ptr1, &eol_len, EVBUFFER_EOL_LF);
1672*663afb9bSAndroid Build Coastguard Worker tt_int_op(ptr2.pos, ==, 11);
1673*663afb9bSAndroid Build Coastguard Worker tt_int_op(eol_len, ==, 1);
1674*663afb9bSAndroid Build Coastguard Worker
1675*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &ptr1, evbuffer_get_length(buf), EVBUFFER_PTR_SET) == 0);
1676*663afb9bSAndroid Build Coastguard Worker eol_len = -1;
1677*663afb9bSAndroid Build Coastguard Worker ptr2 = evbuffer_search_eol(buf, &ptr1, &eol_len, EVBUFFER_EOL_LF);
1678*663afb9bSAndroid Build Coastguard Worker tt_int_op(ptr2.pos, ==, -1);
1679*663afb9bSAndroid Build Coastguard Worker tt_int_op(eol_len, ==, 0);
1680*663afb9bSAndroid Build Coastguard Worker
1681*663afb9bSAndroid Build Coastguard Worker end:
1682*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
1683*663afb9bSAndroid Build Coastguard Worker }
1684*663afb9bSAndroid Build Coastguard Worker
1685*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_iterative(void * ptr)1686*663afb9bSAndroid Build Coastguard Worker test_evbuffer_iterative(void *ptr)
1687*663afb9bSAndroid Build Coastguard Worker {
1688*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
1689*663afb9bSAndroid Build Coastguard Worker const char *abc = "abcdefghijklmnopqrstvuwxyzabcdefghijklmnopqrstvuwxyzabcdefghijklmnopqrstvuwxyzabcdefghijklmnopqrstvuwxyz";
1690*663afb9bSAndroid Build Coastguard Worker unsigned i, j, sum, n;
1691*663afb9bSAndroid Build Coastguard Worker
1692*663afb9bSAndroid Build Coastguard Worker sum = 0;
1693*663afb9bSAndroid Build Coastguard Worker n = 0;
1694*663afb9bSAndroid Build Coastguard Worker for (i = 0; i < 1000; ++i) {
1695*663afb9bSAndroid Build Coastguard Worker for (j = 1; j < strlen(abc); ++j) {
1696*663afb9bSAndroid Build Coastguard Worker char format[32];
1697*663afb9bSAndroid Build Coastguard Worker evutil_snprintf(format, sizeof(format), "%%%u.%us", j, j);
1698*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(buf, format, abc);
1699*663afb9bSAndroid Build Coastguard Worker
1700*663afb9bSAndroid Build Coastguard Worker /* Only check for rep violations every so often.
1701*663afb9bSAndroid Build Coastguard Worker Walking over the whole list of chains can get
1702*663afb9bSAndroid Build Coastguard Worker pretty expensive as it gets long.
1703*663afb9bSAndroid Build Coastguard Worker */
1704*663afb9bSAndroid Build Coastguard Worker if ((n % 337) == 0)
1705*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1706*663afb9bSAndroid Build Coastguard Worker
1707*663afb9bSAndroid Build Coastguard Worker sum += j;
1708*663afb9bSAndroid Build Coastguard Worker n++;
1709*663afb9bSAndroid Build Coastguard Worker }
1710*663afb9bSAndroid Build Coastguard Worker }
1711*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1712*663afb9bSAndroid Build Coastguard Worker
1713*663afb9bSAndroid Build Coastguard Worker tt_uint_op(sum, ==, evbuffer_get_length(buf));
1714*663afb9bSAndroid Build Coastguard Worker
1715*663afb9bSAndroid Build Coastguard Worker {
1716*663afb9bSAndroid Build Coastguard Worker size_t a,w,u;
1717*663afb9bSAndroid Build Coastguard Worker a=w=u=0;
1718*663afb9bSAndroid Build Coastguard Worker evbuffer_get_waste(buf, &a, &w, &u);
1719*663afb9bSAndroid Build Coastguard Worker if (0)
1720*663afb9bSAndroid Build Coastguard Worker printf("Allocated: %u.\nWasted: %u.\nUsed: %u.",
1721*663afb9bSAndroid Build Coastguard Worker (unsigned)a, (unsigned)w, (unsigned)u);
1722*663afb9bSAndroid Build Coastguard Worker tt_assert( ((double)w)/a < .125);
1723*663afb9bSAndroid Build Coastguard Worker }
1724*663afb9bSAndroid Build Coastguard Worker end:
1725*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
1726*663afb9bSAndroid Build Coastguard Worker
1727*663afb9bSAndroid Build Coastguard Worker }
1728*663afb9bSAndroid Build Coastguard Worker
1729*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_find(void * ptr)1730*663afb9bSAndroid Build Coastguard Worker test_evbuffer_find(void *ptr)
1731*663afb9bSAndroid Build Coastguard Worker {
1732*663afb9bSAndroid Build Coastguard Worker unsigned char* p;
1733*663afb9bSAndroid Build Coastguard Worker const char* test1 = "1234567890\r\n";
1734*663afb9bSAndroid Build Coastguard Worker const char* test2 = "1234567890\r";
1735*663afb9bSAndroid Build Coastguard Worker #define EVBUFFER_INITIAL_LENGTH 256
1736*663afb9bSAndroid Build Coastguard Worker char test3[EVBUFFER_INITIAL_LENGTH];
1737*663afb9bSAndroid Build Coastguard Worker unsigned int i;
1738*663afb9bSAndroid Build Coastguard Worker struct evbuffer * buf = evbuffer_new();
1739*663afb9bSAndroid Build Coastguard Worker
1740*663afb9bSAndroid Build Coastguard Worker tt_assert(buf);
1741*663afb9bSAndroid Build Coastguard Worker
1742*663afb9bSAndroid Build Coastguard Worker /* make sure evbuffer_find doesn't match past the end of the buffer */
1743*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, (unsigned char*)test1, strlen(test1));
1744*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1745*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf, strlen(test1));
1746*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1747*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, (unsigned char*)test2, strlen(test2));
1748*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1749*663afb9bSAndroid Build Coastguard Worker p = evbuffer_find(buf, (unsigned char*)"\r\n", 2);
1750*663afb9bSAndroid Build Coastguard Worker tt_want(p == NULL);
1751*663afb9bSAndroid Build Coastguard Worker
1752*663afb9bSAndroid Build Coastguard Worker /*
1753*663afb9bSAndroid Build Coastguard Worker * drain the buffer and do another find; in r309 this would
1754*663afb9bSAndroid Build Coastguard Worker * read past the allocated buffer causing a valgrind error.
1755*663afb9bSAndroid Build Coastguard Worker */
1756*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf, strlen(test2));
1757*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1758*663afb9bSAndroid Build Coastguard Worker for (i = 0; i < EVBUFFER_INITIAL_LENGTH; ++i)
1759*663afb9bSAndroid Build Coastguard Worker test3[i] = 'a';
1760*663afb9bSAndroid Build Coastguard Worker test3[EVBUFFER_INITIAL_LENGTH - 1] = 'x';
1761*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, (unsigned char *)test3, EVBUFFER_INITIAL_LENGTH);
1762*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1763*663afb9bSAndroid Build Coastguard Worker p = evbuffer_find(buf, (unsigned char *)"xy", 2);
1764*663afb9bSAndroid Build Coastguard Worker tt_want(p == NULL);
1765*663afb9bSAndroid Build Coastguard Worker
1766*663afb9bSAndroid Build Coastguard Worker /* simple test for match at end of allocated buffer */
1767*663afb9bSAndroid Build Coastguard Worker p = evbuffer_find(buf, (unsigned char *)"ax", 2);
1768*663afb9bSAndroid Build Coastguard Worker tt_assert(p != NULL);
1769*663afb9bSAndroid Build Coastguard Worker tt_want(strncmp((char*)p, "ax", 2) == 0);
1770*663afb9bSAndroid Build Coastguard Worker
1771*663afb9bSAndroid Build Coastguard Worker end:
1772*663afb9bSAndroid Build Coastguard Worker if (buf)
1773*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
1774*663afb9bSAndroid Build Coastguard Worker }
1775*663afb9bSAndroid Build Coastguard Worker
1776*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_ptr_set(void * ptr)1777*663afb9bSAndroid Build Coastguard Worker test_evbuffer_ptr_set(void *ptr)
1778*663afb9bSAndroid Build Coastguard Worker {
1779*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
1780*663afb9bSAndroid Build Coastguard Worker struct evbuffer_ptr pos;
1781*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec v[1];
1782*663afb9bSAndroid Build Coastguard Worker
1783*663afb9bSAndroid Build Coastguard Worker tt_assert(buf);
1784*663afb9bSAndroid Build Coastguard Worker
1785*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf), ==, 0);
1786*663afb9bSAndroid Build Coastguard Worker
1787*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 0, EVBUFFER_PTR_SET) == 0);
1788*663afb9bSAndroid Build Coastguard Worker tt_assert(pos.pos == 0);
1789*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 1, EVBUFFER_PTR_ADD) == -1);
1790*663afb9bSAndroid Build Coastguard Worker tt_assert(pos.pos == -1);
1791*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 1, EVBUFFER_PTR_SET) == -1);
1792*663afb9bSAndroid Build Coastguard Worker tt_assert(pos.pos == -1);
1793*663afb9bSAndroid Build Coastguard Worker
1794*663afb9bSAndroid Build Coastguard Worker /* create some chains */
1795*663afb9bSAndroid Build Coastguard Worker evbuffer_reserve_space(buf, 5000, v, 1);
1796*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = 5000;
1797*663afb9bSAndroid Build Coastguard Worker memset(v[0].iov_base, 1, v[0].iov_len);
1798*663afb9bSAndroid Build Coastguard Worker evbuffer_commit_space(buf, v, 1);
1799*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1800*663afb9bSAndroid Build Coastguard Worker
1801*663afb9bSAndroid Build Coastguard Worker evbuffer_reserve_space(buf, 4000, v, 1);
1802*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = 4000;
1803*663afb9bSAndroid Build Coastguard Worker memset(v[0].iov_base, 2, v[0].iov_len);
1804*663afb9bSAndroid Build Coastguard Worker evbuffer_commit_space(buf, v, 1);
1805*663afb9bSAndroid Build Coastguard Worker
1806*663afb9bSAndroid Build Coastguard Worker evbuffer_reserve_space(buf, 3000, v, 1);
1807*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = 3000;
1808*663afb9bSAndroid Build Coastguard Worker memset(v[0].iov_base, 3, v[0].iov_len);
1809*663afb9bSAndroid Build Coastguard Worker evbuffer_commit_space(buf, v, 1);
1810*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1811*663afb9bSAndroid Build Coastguard Worker
1812*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf), ==, 12000);
1813*663afb9bSAndroid Build Coastguard Worker
1814*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 13000, EVBUFFER_PTR_SET) == -1);
1815*663afb9bSAndroid Build Coastguard Worker tt_assert(pos.pos == -1);
1816*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 0, EVBUFFER_PTR_SET) == 0);
1817*663afb9bSAndroid Build Coastguard Worker tt_assert(pos.pos == 0);
1818*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 13000, EVBUFFER_PTR_ADD) == -1);
1819*663afb9bSAndroid Build Coastguard Worker
1820*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 0, EVBUFFER_PTR_SET) == 0);
1821*663afb9bSAndroid Build Coastguard Worker tt_assert(pos.pos == 0);
1822*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 10000, EVBUFFER_PTR_ADD) == 0);
1823*663afb9bSAndroid Build Coastguard Worker tt_assert(pos.pos == 10000);
1824*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 1000, EVBUFFER_PTR_ADD) == 0);
1825*663afb9bSAndroid Build Coastguard Worker tt_assert(pos.pos == 11000);
1826*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 1000, EVBUFFER_PTR_ADD) == 0);
1827*663afb9bSAndroid Build Coastguard Worker tt_assert(pos.pos == 12000);
1828*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 1000, EVBUFFER_PTR_ADD) == -1);
1829*663afb9bSAndroid Build Coastguard Worker tt_assert(pos.pos == -1);
1830*663afb9bSAndroid Build Coastguard Worker
1831*663afb9bSAndroid Build Coastguard Worker end:
1832*663afb9bSAndroid Build Coastguard Worker if (buf)
1833*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
1834*663afb9bSAndroid Build Coastguard Worker }
1835*663afb9bSAndroid Build Coastguard Worker
1836*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_search(void * ptr)1837*663afb9bSAndroid Build Coastguard Worker test_evbuffer_search(void *ptr)
1838*663afb9bSAndroid Build Coastguard Worker {
1839*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
1840*663afb9bSAndroid Build Coastguard Worker struct evbuffer *tmp = evbuffer_new();
1841*663afb9bSAndroid Build Coastguard Worker struct evbuffer_ptr pos, end;
1842*663afb9bSAndroid Build Coastguard Worker
1843*663afb9bSAndroid Build Coastguard Worker tt_assert(buf);
1844*663afb9bSAndroid Build Coastguard Worker tt_assert(tmp);
1845*663afb9bSAndroid Build Coastguard Worker
1846*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search(buf, "x", 1, NULL);
1847*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, -1);
1848*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 0, EVBUFFER_PTR_SET) == 0);
1849*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search(buf, "x", 1, &pos);
1850*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, -1);
1851*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 0, EVBUFFER_PTR_SET) == 0);
1852*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search_range(buf, "x", 1, &pos, &pos);
1853*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, -1);
1854*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 0, EVBUFFER_PTR_SET) == 0);
1855*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search_range(buf, "x", 1, &pos, NULL);
1856*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, -1);
1857*663afb9bSAndroid Build Coastguard Worker
1858*663afb9bSAndroid Build Coastguard Worker /* set up our chains */
1859*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(tmp, "hello"); /* 5 chars */
1860*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(buf, tmp);
1861*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(tmp, "foo"); /* 3 chars */
1862*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(buf, tmp);
1863*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(tmp, "cat"); /* 3 chars */
1864*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(buf, tmp);
1865*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(tmp, "attack");
1866*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(buf, tmp);
1867*663afb9bSAndroid Build Coastguard Worker
1868*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search(buf, "attack", 6, NULL);
1869*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, 11);
1870*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search(buf, "attacker", 8, NULL);
1871*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, -1);
1872*663afb9bSAndroid Build Coastguard Worker
1873*663afb9bSAndroid Build Coastguard Worker /* test continuing search */
1874*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search(buf, "oc", 2, NULL);
1875*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, 7);
1876*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search(buf, "cat", 3, &pos);
1877*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, 8);
1878*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search(buf, "tacking", 7, &pos);
1879*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, -1);
1880*663afb9bSAndroid Build Coastguard Worker
1881*663afb9bSAndroid Build Coastguard Worker evbuffer_ptr_set(buf, &pos, 5, EVBUFFER_PTR_SET);
1882*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search(buf, "foo", 3, &pos);
1883*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, 5);
1884*663afb9bSAndroid Build Coastguard Worker
1885*663afb9bSAndroid Build Coastguard Worker evbuffer_ptr_set(buf, &pos, 2, EVBUFFER_PTR_ADD);
1886*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search(buf, "tat", 3, &pos);
1887*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, 10);
1888*663afb9bSAndroid Build Coastguard Worker
1889*663afb9bSAndroid Build Coastguard Worker /* test bounded search. */
1890*663afb9bSAndroid Build Coastguard Worker /* Set "end" to the first t in "attack". */
1891*663afb9bSAndroid Build Coastguard Worker evbuffer_ptr_set(buf, &end, 12, EVBUFFER_PTR_SET);
1892*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search_range(buf, "foo", 3, NULL, &end);
1893*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, 5);
1894*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search_range(buf, "foocata", 7, NULL, &end);
1895*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, 5);
1896*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search_range(buf, "foocatat", 8, NULL, &end);
1897*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, -1);
1898*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search_range(buf, "ack", 3, NULL, &end);
1899*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, -1);
1900*663afb9bSAndroid Build Coastguard Worker
1901*663afb9bSAndroid Build Coastguard Worker /* Set "end" after the last byte in the buffer. */
1902*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &end, 17, EVBUFFER_PTR_SET) == 0);
1903*663afb9bSAndroid Build Coastguard Worker
1904*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search_range(buf, "attack", 6, NULL, &end);
1905*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, 11);
1906*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 11, EVBUFFER_PTR_SET) == 0);
1907*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search_range(buf, "attack", 6, &pos, &end);
1908*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, 11);
1909*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 17, EVBUFFER_PTR_SET) == 0);
1910*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search_range(buf, "attack", 6, &pos, &end);
1911*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, -1);
1912*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &pos, 17, EVBUFFER_PTR_SET) == 0);
1913*663afb9bSAndroid Build Coastguard Worker pos = evbuffer_search_range(buf, "attack", 6, &pos, NULL);
1914*663afb9bSAndroid Build Coastguard Worker tt_int_op(pos.pos, ==, -1);
1915*663afb9bSAndroid Build Coastguard Worker
1916*663afb9bSAndroid Build Coastguard Worker end:
1917*663afb9bSAndroid Build Coastguard Worker if (buf)
1918*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
1919*663afb9bSAndroid Build Coastguard Worker if (tmp)
1920*663afb9bSAndroid Build Coastguard Worker evbuffer_free(tmp);
1921*663afb9bSAndroid Build Coastguard Worker }
1922*663afb9bSAndroid Build Coastguard Worker
1923*663afb9bSAndroid Build Coastguard Worker static void
log_change_callback(struct evbuffer * buffer,const struct evbuffer_cb_info * cbinfo,void * arg)1924*663afb9bSAndroid Build Coastguard Worker log_change_callback(struct evbuffer *buffer,
1925*663afb9bSAndroid Build Coastguard Worker const struct evbuffer_cb_info *cbinfo,
1926*663afb9bSAndroid Build Coastguard Worker void *arg)
1927*663afb9bSAndroid Build Coastguard Worker {
1928*663afb9bSAndroid Build Coastguard Worker
1929*663afb9bSAndroid Build Coastguard Worker size_t old_len = cbinfo->orig_size;
1930*663afb9bSAndroid Build Coastguard Worker size_t new_len = old_len + cbinfo->n_added - cbinfo->n_deleted;
1931*663afb9bSAndroid Build Coastguard Worker struct evbuffer *out = arg;
1932*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(out, "%lu->%lu; ", (unsigned long)old_len,
1933*663afb9bSAndroid Build Coastguard Worker (unsigned long)new_len);
1934*663afb9bSAndroid Build Coastguard Worker }
1935*663afb9bSAndroid Build Coastguard Worker static void
self_draining_callback(struct evbuffer * evbuffer,size_t old_len,size_t new_len,void * arg)1936*663afb9bSAndroid Build Coastguard Worker self_draining_callback(struct evbuffer *evbuffer, size_t old_len,
1937*663afb9bSAndroid Build Coastguard Worker size_t new_len, void *arg)
1938*663afb9bSAndroid Build Coastguard Worker {
1939*663afb9bSAndroid Build Coastguard Worker if (new_len > old_len)
1940*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(evbuffer, new_len);
1941*663afb9bSAndroid Build Coastguard Worker }
1942*663afb9bSAndroid Build Coastguard Worker
1943*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_callbacks(void * ptr)1944*663afb9bSAndroid Build Coastguard Worker test_evbuffer_callbacks(void *ptr)
1945*663afb9bSAndroid Build Coastguard Worker {
1946*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = evbuffer_new();
1947*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf_out1 = evbuffer_new();
1948*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf_out2 = evbuffer_new();
1949*663afb9bSAndroid Build Coastguard Worker struct evbuffer_cb_entry *cb1, *cb2;
1950*663afb9bSAndroid Build Coastguard Worker
1951*663afb9bSAndroid Build Coastguard Worker tt_assert(buf);
1952*663afb9bSAndroid Build Coastguard Worker tt_assert(buf_out1);
1953*663afb9bSAndroid Build Coastguard Worker tt_assert(buf_out2);
1954*663afb9bSAndroid Build Coastguard Worker
1955*663afb9bSAndroid Build Coastguard Worker cb1 = evbuffer_add_cb(buf, log_change_callback, buf_out1);
1956*663afb9bSAndroid Build Coastguard Worker cb2 = evbuffer_add_cb(buf, log_change_callback, buf_out2);
1957*663afb9bSAndroid Build Coastguard Worker
1958*663afb9bSAndroid Build Coastguard Worker /* Let's run through adding and deleting some stuff from the buffer
1959*663afb9bSAndroid Build Coastguard Worker * and turning the callbacks on and off and removing them. The callback
1960*663afb9bSAndroid Build Coastguard Worker * adds a summary of length changes to buf_out1/buf_out2 when called. */
1961*663afb9bSAndroid Build Coastguard Worker /* size: 0-> 36. */
1962*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(buf, "The %d magic words are spotty pudding", 2);
1963*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1964*663afb9bSAndroid Build Coastguard Worker evbuffer_cb_clear_flags(buf, cb2, EVBUFFER_CB_ENABLED);
1965*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf, 10); /*36->26*/
1966*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1967*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(buf, "Hello", 5);/*26->31*/
1968*663afb9bSAndroid Build Coastguard Worker evbuffer_cb_set_flags(buf, cb2, EVBUFFER_CB_ENABLED);
1969*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, "Goodbye", 7, NULL, NULL); /*31->38*/
1970*663afb9bSAndroid Build Coastguard Worker evbuffer_remove_cb_entry(buf, cb1);
1971*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1972*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf, evbuffer_get_length(buf)); /*38->0*/;
1973*663afb9bSAndroid Build Coastguard Worker tt_assert(-1 == evbuffer_remove_cb(buf, log_change_callback, NULL));
1974*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, "X", 1); /* 0->1 */
1975*663afb9bSAndroid Build Coastguard Worker tt_assert(!evbuffer_remove_cb(buf, log_change_callback, buf_out2));
1976*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1977*663afb9bSAndroid Build Coastguard Worker
1978*663afb9bSAndroid Build Coastguard Worker tt_str_op((const char *) evbuffer_pullup(buf_out1, -1), ==,
1979*663afb9bSAndroid Build Coastguard Worker "0->36; 36->26; 26->31; 31->38; ");
1980*663afb9bSAndroid Build Coastguard Worker tt_str_op((const char *) evbuffer_pullup(buf_out2, -1), ==,
1981*663afb9bSAndroid Build Coastguard Worker "0->36; 31->38; 38->0; 0->1; ");
1982*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf_out1, evbuffer_get_length(buf_out1));
1983*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf_out2, evbuffer_get_length(buf_out2));
1984*663afb9bSAndroid Build Coastguard Worker /* Let's test the obsolete buffer_setcb function too. */
1985*663afb9bSAndroid Build Coastguard Worker cb1 = evbuffer_add_cb(buf, log_change_callback, buf_out1);
1986*663afb9bSAndroid Build Coastguard Worker tt_assert(cb1 != NULL);
1987*663afb9bSAndroid Build Coastguard Worker cb2 = evbuffer_add_cb(buf, log_change_callback, buf_out2);
1988*663afb9bSAndroid Build Coastguard Worker tt_assert(cb2 != NULL);
1989*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_setcb(buf, self_draining_callback, NULL), ==, 0);
1990*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(buf, "This should get drained right away.");
1991*663afb9bSAndroid Build Coastguard Worker tt_uint_op(evbuffer_get_length(buf), ==, 0);
1992*663afb9bSAndroid Build Coastguard Worker tt_uint_op(evbuffer_get_length(buf_out1), ==, 0);
1993*663afb9bSAndroid Build Coastguard Worker tt_uint_op(evbuffer_get_length(buf_out2), ==, 0);
1994*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_setcb(buf, NULL, NULL), ==, 0);
1995*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(buf, "This will not.");
1996*663afb9bSAndroid Build Coastguard Worker tt_str_op((const char *) evbuffer_pullup(buf, -1), ==, "This will not.");
1997*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
1998*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf, evbuffer_get_length(buf));
1999*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
2000*663afb9bSAndroid Build Coastguard Worker #if 0
2001*663afb9bSAndroid Build Coastguard Worker /* Now let's try a suspended callback. */
2002*663afb9bSAndroid Build Coastguard Worker cb1 = evbuffer_add_cb(buf, log_change_callback, buf_out1);
2003*663afb9bSAndroid Build Coastguard Worker cb2 = evbuffer_add_cb(buf, log_change_callback, buf_out2);
2004*663afb9bSAndroid Build Coastguard Worker evbuffer_cb_suspend(buf,cb2);
2005*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(buf,"Hello world",11); /*0->11*/
2006*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
2007*663afb9bSAndroid Build Coastguard Worker evbuffer_cb_suspend(buf,cb1);
2008*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf,"more",4); /* 11->15 */
2009*663afb9bSAndroid Build Coastguard Worker evbuffer_cb_unsuspend(buf,cb2);
2010*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf, 4); /* 15->11 */
2011*663afb9bSAndroid Build Coastguard Worker evbuffer_cb_unsuspend(buf,cb1);
2012*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf, evbuffer_get_length(buf)); /* 11->0 */
2013*663afb9bSAndroid Build Coastguard Worker
2014*663afb9bSAndroid Build Coastguard Worker tt_str_op(evbuffer_pullup(buf_out1, -1), ==,
2015*663afb9bSAndroid Build Coastguard Worker "0->11; 11->11; 11->0; ");
2016*663afb9bSAndroid Build Coastguard Worker tt_str_op(evbuffer_pullup(buf_out2, -1), ==,
2017*663afb9bSAndroid Build Coastguard Worker "0->15; 15->11; 11->0; ");
2018*663afb9bSAndroid Build Coastguard Worker #endif
2019*663afb9bSAndroid Build Coastguard Worker
2020*663afb9bSAndroid Build Coastguard Worker /* the next call to readline should fail */
2021*663afb9bSAndroid Build Coastguard Worker #ifndef EVENT__DISABLE_MM_REPLACEMENT
2022*663afb9bSAndroid Build Coastguard Worker event_set_mem_functions(failing_malloc, realloc, free);
2023*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_setcb(buf, self_draining_callback, NULL), ==, -1);
2024*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
2025*663afb9bSAndroid Build Coastguard Worker event_set_mem_functions(malloc, realloc, free);
2026*663afb9bSAndroid Build Coastguard Worker #endif
2027*663afb9bSAndroid Build Coastguard Worker
2028*663afb9bSAndroid Build Coastguard Worker end:
2029*663afb9bSAndroid Build Coastguard Worker if (buf)
2030*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
2031*663afb9bSAndroid Build Coastguard Worker if (buf_out1)
2032*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf_out1);
2033*663afb9bSAndroid Build Coastguard Worker if (buf_out2)
2034*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf_out2);
2035*663afb9bSAndroid Build Coastguard Worker }
2036*663afb9bSAndroid Build Coastguard Worker
2037*663afb9bSAndroid Build Coastguard Worker static int ref_done_cb_called_count = 0;
2038*663afb9bSAndroid Build Coastguard Worker static void *ref_done_cb_called_with = NULL;
2039*663afb9bSAndroid Build Coastguard Worker static const void *ref_done_cb_called_with_data = NULL;
2040*663afb9bSAndroid Build Coastguard Worker static size_t ref_done_cb_called_with_len = 0;
ref_done_cb(const void * data,size_t len,void * info)2041*663afb9bSAndroid Build Coastguard Worker static void ref_done_cb(const void *data, size_t len, void *info)
2042*663afb9bSAndroid Build Coastguard Worker {
2043*663afb9bSAndroid Build Coastguard Worker ++ref_done_cb_called_count;
2044*663afb9bSAndroid Build Coastguard Worker ref_done_cb_called_with = info;
2045*663afb9bSAndroid Build Coastguard Worker ref_done_cb_called_with_data = data;
2046*663afb9bSAndroid Build Coastguard Worker ref_done_cb_called_with_len = len;
2047*663afb9bSAndroid Build Coastguard Worker }
2048*663afb9bSAndroid Build Coastguard Worker
2049*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_add_reference(void * ptr)2050*663afb9bSAndroid Build Coastguard Worker test_evbuffer_add_reference(void *ptr)
2051*663afb9bSAndroid Build Coastguard Worker {
2052*663afb9bSAndroid Build Coastguard Worker const char chunk1[] = "If you have found the answer to such a problem";
2053*663afb9bSAndroid Build Coastguard Worker const char chunk2[] = "you ought to write it up for publication";
2054*663afb9bSAndroid Build Coastguard Worker /* -- Knuth's "Notes on the Exercises" from TAOCP */
2055*663afb9bSAndroid Build Coastguard Worker char tmp[16];
2056*663afb9bSAndroid Build Coastguard Worker size_t len1 = strlen(chunk1), len2=strlen(chunk2);
2057*663afb9bSAndroid Build Coastguard Worker
2058*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf1 = NULL, *buf2 = NULL;
2059*663afb9bSAndroid Build Coastguard Worker
2060*663afb9bSAndroid Build Coastguard Worker buf1 = evbuffer_new();
2061*663afb9bSAndroid Build Coastguard Worker tt_assert(buf1);
2062*663afb9bSAndroid Build Coastguard Worker
2063*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf1, chunk1, len1, ref_done_cb, (void*)111);
2064*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf1, ", ", 2);
2065*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf1, chunk2, len2, ref_done_cb, (void*)222);
2066*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf1), ==, len1+len2+2);
2067*663afb9bSAndroid Build Coastguard Worker
2068*663afb9bSAndroid Build Coastguard Worker /* Make sure we can drain a little from a reference. */
2069*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_remove(buf1, tmp, 6), ==, 6);
2070*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(tmp, "If you", 6), ==, 0);
2071*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_remove(buf1, tmp, 5), ==, 5);
2072*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(tmp, " have", 5), ==, 0);
2073*663afb9bSAndroid Build Coastguard Worker
2074*663afb9bSAndroid Build Coastguard Worker /* Make sure that prepending does not meddle with immutable data */
2075*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_prepend(buf1, "I have ", 7), ==, 0);
2076*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(chunk1, "If you", 6), ==, 0);
2077*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
2078*663afb9bSAndroid Build Coastguard Worker
2079*663afb9bSAndroid Build Coastguard Worker /* Make sure that when the chunk is over, the callback is invoked. */
2080*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf1, 7); /* Remove prepended stuff. */
2081*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf1, len1-11-1); /* remove all but one byte of chunk1 */
2082*663afb9bSAndroid Build Coastguard Worker tt_int_op(ref_done_cb_called_count, ==, 0);
2083*663afb9bSAndroid Build Coastguard Worker evbuffer_remove(buf1, tmp, 1);
2084*663afb9bSAndroid Build Coastguard Worker tt_int_op(tmp[0], ==, 'm');
2085*663afb9bSAndroid Build Coastguard Worker tt_assert(ref_done_cb_called_with == (void*)111);
2086*663afb9bSAndroid Build Coastguard Worker tt_assert(ref_done_cb_called_with_data == chunk1);
2087*663afb9bSAndroid Build Coastguard Worker tt_assert(ref_done_cb_called_with_len == len1);
2088*663afb9bSAndroid Build Coastguard Worker tt_int_op(ref_done_cb_called_count, ==, 1);
2089*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
2090*663afb9bSAndroid Build Coastguard Worker
2091*663afb9bSAndroid Build Coastguard Worker /* Drain some of the remaining chunk, then add it to another buffer */
2092*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf1, 6); /* Remove the ", you ". */
2093*663afb9bSAndroid Build Coastguard Worker buf2 = evbuffer_new();
2094*663afb9bSAndroid Build Coastguard Worker tt_assert(buf2);
2095*663afb9bSAndroid Build Coastguard Worker tt_int_op(ref_done_cb_called_count, ==, 1);
2096*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf2, "I ", 2);
2097*663afb9bSAndroid Build Coastguard Worker
2098*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(buf2, buf1);
2099*663afb9bSAndroid Build Coastguard Worker tt_int_op(ref_done_cb_called_count, ==, 1);
2100*663afb9bSAndroid Build Coastguard Worker evbuffer_remove(buf2, tmp, 16);
2101*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp("I ought to write", tmp, 16), ==, 0);
2102*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf2, evbuffer_get_length(buf2));
2103*663afb9bSAndroid Build Coastguard Worker tt_int_op(ref_done_cb_called_count, ==, 2);
2104*663afb9bSAndroid Build Coastguard Worker tt_assert(ref_done_cb_called_with == (void*)222);
2105*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
2106*663afb9bSAndroid Build Coastguard Worker
2107*663afb9bSAndroid Build Coastguard Worker /* Now add more stuff to buf1 and make sure that it gets removed on
2108*663afb9bSAndroid Build Coastguard Worker * free. */
2109*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf1, "You shake and shake the ", 24);
2110*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf1, "ketchup bottle", 14, ref_done_cb,
2111*663afb9bSAndroid Build Coastguard Worker (void*)3333);
2112*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf1, ". Nothing comes and then a lot'll.", 35);
2113*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf1);
2114*663afb9bSAndroid Build Coastguard Worker buf1 = NULL;
2115*663afb9bSAndroid Build Coastguard Worker tt_int_op(ref_done_cb_called_count, ==, 3);
2116*663afb9bSAndroid Build Coastguard Worker tt_assert(ref_done_cb_called_with == (void*)3333);
2117*663afb9bSAndroid Build Coastguard Worker
2118*663afb9bSAndroid Build Coastguard Worker end:
2119*663afb9bSAndroid Build Coastguard Worker if (buf1)
2120*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf1);
2121*663afb9bSAndroid Build Coastguard Worker if (buf2)
2122*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf2);
2123*663afb9bSAndroid Build Coastguard Worker }
2124*663afb9bSAndroid Build Coastguard Worker
2125*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_multicast(void * ptr)2126*663afb9bSAndroid Build Coastguard Worker test_evbuffer_multicast(void *ptr)
2127*663afb9bSAndroid Build Coastguard Worker {
2128*663afb9bSAndroid Build Coastguard Worker const char chunk1[] = "If you have found the answer to such a problem";
2129*663afb9bSAndroid Build Coastguard Worker const char chunk2[] = "you ought to write it up for publication";
2130*663afb9bSAndroid Build Coastguard Worker /* -- Knuth's "Notes on the Exercises" from TAOCP */
2131*663afb9bSAndroid Build Coastguard Worker char tmp[16];
2132*663afb9bSAndroid Build Coastguard Worker size_t len1 = strlen(chunk1), len2=strlen(chunk2);
2133*663afb9bSAndroid Build Coastguard Worker
2134*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf1 = NULL, *buf2 = NULL;
2135*663afb9bSAndroid Build Coastguard Worker
2136*663afb9bSAndroid Build Coastguard Worker buf1 = evbuffer_new();
2137*663afb9bSAndroid Build Coastguard Worker tt_assert(buf1);
2138*663afb9bSAndroid Build Coastguard Worker
2139*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf1, chunk1, len1);
2140*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf1, ", ", 2);
2141*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf1, chunk2, len2);
2142*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf1), ==, len1+len2+2);
2143*663afb9bSAndroid Build Coastguard Worker
2144*663afb9bSAndroid Build Coastguard Worker buf2 = evbuffer_new();
2145*663afb9bSAndroid Build Coastguard Worker tt_assert(buf2);
2146*663afb9bSAndroid Build Coastguard Worker
2147*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_add_buffer_reference(buf2, buf1), ==, 0);
2148*663afb9bSAndroid Build Coastguard Worker /* nested references are not allowed */
2149*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_add_buffer_reference(buf2, buf2), ==, -1);
2150*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_add_buffer_reference(buf1, buf2), ==, -1);
2151*663afb9bSAndroid Build Coastguard Worker
2152*663afb9bSAndroid Build Coastguard Worker /* both buffers contain the same amount of data */
2153*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf1), ==, evbuffer_get_length(buf1));
2154*663afb9bSAndroid Build Coastguard Worker
2155*663afb9bSAndroid Build Coastguard Worker /* Make sure we can drain a little from the first buffer. */
2156*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_remove(buf1, tmp, 6), ==, 6);
2157*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(tmp, "If you", 6), ==, 0);
2158*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_remove(buf1, tmp, 5), ==, 5);
2159*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(tmp, " have", 5), ==, 0);
2160*663afb9bSAndroid Build Coastguard Worker
2161*663afb9bSAndroid Build Coastguard Worker /* Make sure that prepending does not meddle with immutable data */
2162*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_prepend(buf1, "I have ", 7), ==, 0);
2163*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(chunk1, "If you", 6), ==, 0);
2164*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
2165*663afb9bSAndroid Build Coastguard Worker
2166*663afb9bSAndroid Build Coastguard Worker /* Make sure we can drain a little from the second buffer. */
2167*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_remove(buf2, tmp, 6), ==, 6);
2168*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(tmp, "If you", 6), ==, 0);
2169*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_remove(buf2, tmp, 5), ==, 5);
2170*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(tmp, " have", 5), ==, 0);
2171*663afb9bSAndroid Build Coastguard Worker
2172*663afb9bSAndroid Build Coastguard Worker /* Make sure that prepending does not meddle with immutable data */
2173*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_prepend(buf2, "I have ", 7), ==, 0);
2174*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(chunk1, "If you", 6), ==, 0);
2175*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
2176*663afb9bSAndroid Build Coastguard Worker
2177*663afb9bSAndroid Build Coastguard Worker /* Make sure the data can be read from the second buffer when the first is freed */
2178*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf1);
2179*663afb9bSAndroid Build Coastguard Worker buf1 = NULL;
2180*663afb9bSAndroid Build Coastguard Worker
2181*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_remove(buf2, tmp, 6), ==, 6);
2182*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(tmp, "I have", 6), ==, 0);
2183*663afb9bSAndroid Build Coastguard Worker
2184*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_remove(buf2, tmp, 6), ==, 6);
2185*663afb9bSAndroid Build Coastguard Worker tt_int_op(memcmp(tmp, " foun", 6), ==, 0);
2186*663afb9bSAndroid Build Coastguard Worker
2187*663afb9bSAndroid Build Coastguard Worker end:
2188*663afb9bSAndroid Build Coastguard Worker if (buf1)
2189*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf1);
2190*663afb9bSAndroid Build Coastguard Worker if (buf2)
2191*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf2);
2192*663afb9bSAndroid Build Coastguard Worker }
2193*663afb9bSAndroid Build Coastguard Worker
2194*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_multicast_drain(void * ptr)2195*663afb9bSAndroid Build Coastguard Worker test_evbuffer_multicast_drain(void *ptr)
2196*663afb9bSAndroid Build Coastguard Worker {
2197*663afb9bSAndroid Build Coastguard Worker const char chunk1[] = "If you have found the answer to such a problem";
2198*663afb9bSAndroid Build Coastguard Worker const char chunk2[] = "you ought to write it up for publication";
2199*663afb9bSAndroid Build Coastguard Worker /* -- Knuth's "Notes on the Exercises" from TAOCP */
2200*663afb9bSAndroid Build Coastguard Worker size_t len1 = strlen(chunk1), len2=strlen(chunk2);
2201*663afb9bSAndroid Build Coastguard Worker
2202*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf1 = NULL, *buf2 = NULL;
2203*663afb9bSAndroid Build Coastguard Worker
2204*663afb9bSAndroid Build Coastguard Worker buf1 = evbuffer_new();
2205*663afb9bSAndroid Build Coastguard Worker tt_assert(buf1);
2206*663afb9bSAndroid Build Coastguard Worker
2207*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf1, chunk1, len1);
2208*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf1, ", ", 2);
2209*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf1, chunk2, len2);
2210*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf1), ==, len1+len2+2);
2211*663afb9bSAndroid Build Coastguard Worker
2212*663afb9bSAndroid Build Coastguard Worker buf2 = evbuffer_new();
2213*663afb9bSAndroid Build Coastguard Worker tt_assert(buf2);
2214*663afb9bSAndroid Build Coastguard Worker
2215*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_add_buffer_reference(buf2, buf1), ==, 0);
2216*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf2), ==, len1+len2+2);
2217*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_drain(buf1, evbuffer_get_length(buf1)), ==, 0);
2218*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf2), ==, len1+len2+2);
2219*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_drain(buf2, evbuffer_get_length(buf2)), ==, 0);
2220*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
2221*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
2222*663afb9bSAndroid Build Coastguard Worker
2223*663afb9bSAndroid Build Coastguard Worker end:
2224*663afb9bSAndroid Build Coastguard Worker if (buf1)
2225*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf1);
2226*663afb9bSAndroid Build Coastguard Worker if (buf2)
2227*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf2);
2228*663afb9bSAndroid Build Coastguard Worker }
2229*663afb9bSAndroid Build Coastguard Worker
2230*663afb9bSAndroid Build Coastguard Worker static void
check_prepend(struct evbuffer * buffer,const struct evbuffer_cb_info * cbinfo,void * arg)2231*663afb9bSAndroid Build Coastguard Worker check_prepend(struct evbuffer *buffer,
2232*663afb9bSAndroid Build Coastguard Worker const struct evbuffer_cb_info *cbinfo,
2233*663afb9bSAndroid Build Coastguard Worker void *arg)
2234*663afb9bSAndroid Build Coastguard Worker {
2235*663afb9bSAndroid Build Coastguard Worker tt_int_op(cbinfo->orig_size, ==, 3);
2236*663afb9bSAndroid Build Coastguard Worker tt_int_op(cbinfo->n_added, ==, 8096);
2237*663afb9bSAndroid Build Coastguard Worker tt_int_op(cbinfo->n_deleted, ==, 0);
2238*663afb9bSAndroid Build Coastguard Worker end:
2239*663afb9bSAndroid Build Coastguard Worker ;
2240*663afb9bSAndroid Build Coastguard Worker }
2241*663afb9bSAndroid Build Coastguard Worker /* Some cases that we didn't get in test_evbuffer() above, for more coverage. */
2242*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_prepend(void * ptr)2243*663afb9bSAndroid Build Coastguard Worker test_evbuffer_prepend(void *ptr)
2244*663afb9bSAndroid Build Coastguard Worker {
2245*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf1 = NULL, *buf2 = NULL;
2246*663afb9bSAndroid Build Coastguard Worker char tmp[128], *buffer = malloc(8096);
2247*663afb9bSAndroid Build Coastguard Worker int n;
2248*663afb9bSAndroid Build Coastguard Worker
2249*663afb9bSAndroid Build Coastguard Worker buf1 = evbuffer_new();
2250*663afb9bSAndroid Build Coastguard Worker tt_assert(buf1);
2251*663afb9bSAndroid Build Coastguard Worker
2252*663afb9bSAndroid Build Coastguard Worker /* Case 0: The evbuffer is entirely empty. */
2253*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(buf1, "This string has 29 characters", 29);
2254*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
2255*663afb9bSAndroid Build Coastguard Worker
2256*663afb9bSAndroid Build Coastguard Worker /* Case 1: Prepend goes entirely in new chunk. */
2257*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(buf1, "Short.", 6);
2258*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
2259*663afb9bSAndroid Build Coastguard Worker
2260*663afb9bSAndroid Build Coastguard Worker /* Case 2: prepend goes entirely in first chunk. */
2261*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf1, 6+11);
2262*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(buf1, "it", 2);
2263*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
2264*663afb9bSAndroid Build Coastguard Worker tt_assert(!memcmp(buf1->first->buffer+buf1->first->misalign,
2265*663afb9bSAndroid Build Coastguard Worker "it has", 6));
2266*663afb9bSAndroid Build Coastguard Worker
2267*663afb9bSAndroid Build Coastguard Worker /* Case 3: prepend is split over multiple chunks. */
2268*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(buf1, "It is no longer true to say ", 28);
2269*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
2270*663afb9bSAndroid Build Coastguard Worker n = evbuffer_remove(buf1, tmp, sizeof(tmp)-1);
2271*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, >=, 0);
2272*663afb9bSAndroid Build Coastguard Worker tmp[n]='\0';
2273*663afb9bSAndroid Build Coastguard Worker tt_str_op(tmp,==,"It is no longer true to say it has 29 characters");
2274*663afb9bSAndroid Build Coastguard Worker
2275*663afb9bSAndroid Build Coastguard Worker buf2 = evbuffer_new();
2276*663afb9bSAndroid Build Coastguard Worker tt_assert(buf2);
2277*663afb9bSAndroid Build Coastguard Worker
2278*663afb9bSAndroid Build Coastguard Worker /* Case 4: prepend a buffer to an empty buffer. */
2279*663afb9bSAndroid Build Coastguard Worker n = 999;
2280*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(buf1, "Here is string %d. ", n++);
2281*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend_buffer(buf2, buf1);
2282*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
2283*663afb9bSAndroid Build Coastguard Worker
2284*663afb9bSAndroid Build Coastguard Worker /* Case 5: prepend a buffer to a nonempty buffer. */
2285*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(buf1, "Here is string %d. ", n++);
2286*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend_buffer(buf2, buf1);
2287*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
2288*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
2289*663afb9bSAndroid Build Coastguard Worker n = evbuffer_remove(buf2, tmp, sizeof(tmp)-1);
2290*663afb9bSAndroid Build Coastguard Worker tt_int_op(n, >=, 0);
2291*663afb9bSAndroid Build Coastguard Worker tmp[n]='\0';
2292*663afb9bSAndroid Build Coastguard Worker tt_str_op(tmp,==,"Here is string 1000. Here is string 999. ");
2293*663afb9bSAndroid Build Coastguard Worker
2294*663afb9bSAndroid Build Coastguard Worker /* Case 5: evbuffer_prepend() will need a new buffer, with callbacks */
2295*663afb9bSAndroid Build Coastguard Worker memset(buffer, 'A', 8096);
2296*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf2);
2297*663afb9bSAndroid Build Coastguard Worker buf2 = evbuffer_new();
2298*663afb9bSAndroid Build Coastguard Worker tt_assert(buf2);
2299*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(buf2, "foo", 3);
2300*663afb9bSAndroid Build Coastguard Worker evbuffer_add_cb(buf2, check_prepend, NULL);
2301*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(buf2, buffer, 8096);
2302*663afb9bSAndroid Build Coastguard Worker evbuffer_remove_cb(buf2, check_prepend, NULL);
2303*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
2304*663afb9bSAndroid Build Coastguard Worker tt_nstr_op(8096,(char *)evbuffer_pullup(buf2, 8096),==,buffer);
2305*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf2, 8096);
2306*663afb9bSAndroid Build Coastguard Worker tt_nstr_op(3,(char *)evbuffer_pullup(buf2, 3),==,"foo");
2307*663afb9bSAndroid Build Coastguard Worker evbuffer_drain(buf2, 3);
2308*663afb9bSAndroid Build Coastguard Worker
2309*663afb9bSAndroid Build Coastguard Worker end:
2310*663afb9bSAndroid Build Coastguard Worker free(buffer);
2311*663afb9bSAndroid Build Coastguard Worker if (buf1)
2312*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf1);
2313*663afb9bSAndroid Build Coastguard Worker if (buf2)
2314*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf2);
2315*663afb9bSAndroid Build Coastguard Worker
2316*663afb9bSAndroid Build Coastguard Worker }
2317*663afb9bSAndroid Build Coastguard Worker
2318*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_empty_reference_prepend(void * ptr)2319*663afb9bSAndroid Build Coastguard Worker test_evbuffer_empty_reference_prepend(void *ptr)
2320*663afb9bSAndroid Build Coastguard Worker {
2321*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = NULL;
2322*663afb9bSAndroid Build Coastguard Worker
2323*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
2324*663afb9bSAndroid Build Coastguard Worker tt_assert(buf);
2325*663afb9bSAndroid Build Coastguard Worker
2326*663afb9bSAndroid Build Coastguard Worker /** empty chain could leave invalid last_with_datap */
2327*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, "", 0, NULL, NULL);
2328*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
2329*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend(buf, "foo", 3);
2330*663afb9bSAndroid Build Coastguard Worker
2331*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
2332*663afb9bSAndroid Build Coastguard Worker tt_assert(!strncmp((char *)evbuffer_pullup(buf, -1), "foo", 3));
2333*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf);
2334*663afb9bSAndroid Build Coastguard Worker
2335*663afb9bSAndroid Build Coastguard Worker end:
2336*663afb9bSAndroid Build Coastguard Worker if (buf)
2337*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
2338*663afb9bSAndroid Build Coastguard Worker }
2339*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_empty_reference_prepend_buffer(void * ptr)2340*663afb9bSAndroid Build Coastguard Worker test_evbuffer_empty_reference_prepend_buffer(void *ptr)
2341*663afb9bSAndroid Build Coastguard Worker {
2342*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf1 = NULL, *buf2 = NULL;
2343*663afb9bSAndroid Build Coastguard Worker
2344*663afb9bSAndroid Build Coastguard Worker buf1 = evbuffer_new();
2345*663afb9bSAndroid Build Coastguard Worker tt_assert(buf1);
2346*663afb9bSAndroid Build Coastguard Worker buf2 = evbuffer_new();
2347*663afb9bSAndroid Build Coastguard Worker tt_assert(buf2);
2348*663afb9bSAndroid Build Coastguard Worker
2349*663afb9bSAndroid Build Coastguard Worker /** empty chain could leave invalid last_with_datap */
2350*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf1, "", 0, NULL, NULL);
2351*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf1);
2352*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf2, "foo", 3);
2353*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
2354*663afb9bSAndroid Build Coastguard Worker evbuffer_prepend_buffer(buf2, buf1);
2355*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
2356*663afb9bSAndroid Build Coastguard Worker
2357*663afb9bSAndroid Build Coastguard Worker tt_assert(!strncmp((char *)evbuffer_pullup(buf2, -1), "foo", 3));
2358*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
2359*663afb9bSAndroid Build Coastguard Worker
2360*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_pullup(buf1, -1) == NULL);
2361*663afb9bSAndroid Build Coastguard Worker evbuffer_validate(buf2);
2362*663afb9bSAndroid Build Coastguard Worker
2363*663afb9bSAndroid Build Coastguard Worker end:
2364*663afb9bSAndroid Build Coastguard Worker if (buf1)
2365*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf1);
2366*663afb9bSAndroid Build Coastguard Worker if (buf2)
2367*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf2);
2368*663afb9bSAndroid Build Coastguard Worker }
2369*663afb9bSAndroid Build Coastguard Worker
2370*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_peek_first_gt(void * info)2371*663afb9bSAndroid Build Coastguard Worker test_evbuffer_peek_first_gt(void *info)
2372*663afb9bSAndroid Build Coastguard Worker {
2373*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = NULL, *tmp_buf = NULL;
2374*663afb9bSAndroid Build Coastguard Worker struct evbuffer_ptr ptr;
2375*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec v[2];
2376*663afb9bSAndroid Build Coastguard Worker
2377*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
2378*663afb9bSAndroid Build Coastguard Worker tmp_buf = evbuffer_new();
2379*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(tmp_buf, "Contents of chunk 100\n");
2380*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(buf, tmp_buf);
2381*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(tmp_buf, "Contents of chunk 1\n");
2382*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(buf, tmp_buf);
2383*663afb9bSAndroid Build Coastguard Worker
2384*663afb9bSAndroid Build Coastguard Worker evbuffer_ptr_set(buf, &ptr, 0, EVBUFFER_PTR_SET);
2385*663afb9bSAndroid Build Coastguard Worker
2386*663afb9bSAndroid Build Coastguard Worker /** The only case that matters*/
2387*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_peek(buf, -1, &ptr, NULL, 0), ==, 2);
2388*663afb9bSAndroid Build Coastguard Worker /** Just in case */
2389*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_peek(buf, -1, &ptr, v, 2), ==, 2);
2390*663afb9bSAndroid Build Coastguard Worker
2391*663afb9bSAndroid Build Coastguard Worker evbuffer_ptr_set(buf, &ptr, 20, EVBUFFER_PTR_ADD);
2392*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_peek(buf, -1, &ptr, NULL, 0), ==, 2);
2393*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_peek(buf, -1, &ptr, v, 2), ==, 2);
2394*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_peek(buf, 2, &ptr, NULL, 0), ==, 1);
2395*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_peek(buf, 2, &ptr, v, 2), ==, 1);
2396*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_peek(buf, 3, &ptr, NULL, 0), ==, 2);
2397*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_peek(buf, 3, &ptr, v, 2), ==, 2);
2398*663afb9bSAndroid Build Coastguard Worker
2399*663afb9bSAndroid Build Coastguard Worker end:
2400*663afb9bSAndroid Build Coastguard Worker if (buf)
2401*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
2402*663afb9bSAndroid Build Coastguard Worker if (tmp_buf)
2403*663afb9bSAndroid Build Coastguard Worker evbuffer_free(tmp_buf);
2404*663afb9bSAndroid Build Coastguard Worker }
2405*663afb9bSAndroid Build Coastguard Worker
2406*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_peek(void * info)2407*663afb9bSAndroid Build Coastguard Worker test_evbuffer_peek(void *info)
2408*663afb9bSAndroid Build Coastguard Worker {
2409*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = NULL, *tmp_buf = NULL;
2410*663afb9bSAndroid Build Coastguard Worker int i;
2411*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec v[20];
2412*663afb9bSAndroid Build Coastguard Worker struct evbuffer_ptr ptr;
2413*663afb9bSAndroid Build Coastguard Worker
2414*663afb9bSAndroid Build Coastguard Worker #define tt_iov_eq(v, s) \
2415*663afb9bSAndroid Build Coastguard Worker tt_int_op((v)->iov_len, ==, strlen(s)); \
2416*663afb9bSAndroid Build Coastguard Worker tt_assert(!memcmp((v)->iov_base, (s), strlen(s)))
2417*663afb9bSAndroid Build Coastguard Worker
2418*663afb9bSAndroid Build Coastguard Worker /* Let's make a very fragmented buffer. */
2419*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
2420*663afb9bSAndroid Build Coastguard Worker tmp_buf = evbuffer_new();
2421*663afb9bSAndroid Build Coastguard Worker for (i = 0; i < 16; ++i) {
2422*663afb9bSAndroid Build Coastguard Worker evbuffer_add_printf(tmp_buf, "Contents of chunk [%d]\n", i);
2423*663afb9bSAndroid Build Coastguard Worker evbuffer_add_buffer(buf, tmp_buf);
2424*663afb9bSAndroid Build Coastguard Worker }
2425*663afb9bSAndroid Build Coastguard Worker
2426*663afb9bSAndroid Build Coastguard Worker /* How many chunks do we need for everything? */
2427*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(buf, -1, NULL, NULL, 0);
2428*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 16);
2429*663afb9bSAndroid Build Coastguard Worker
2430*663afb9bSAndroid Build Coastguard Worker /* Simple peek: get everything. */
2431*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(buf, -1, NULL, v, 20);
2432*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 16); /* we used only 16 chunks. */
2433*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[0], "Contents of chunk [0]\n");
2434*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[3], "Contents of chunk [3]\n");
2435*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[12], "Contents of chunk [12]\n");
2436*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[15], "Contents of chunk [15]\n");
2437*663afb9bSAndroid Build Coastguard Worker
2438*663afb9bSAndroid Build Coastguard Worker /* Just get one chunk worth. */
2439*663afb9bSAndroid Build Coastguard Worker memset(v, 0, sizeof(v));
2440*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(buf, -1, NULL, v, 1);
2441*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 1);
2442*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[0], "Contents of chunk [0]\n");
2443*663afb9bSAndroid Build Coastguard Worker tt_assert(v[1].iov_base == NULL);
2444*663afb9bSAndroid Build Coastguard Worker
2445*663afb9bSAndroid Build Coastguard Worker /* Suppose we want at least the first 40 bytes. */
2446*663afb9bSAndroid Build Coastguard Worker memset(v, 0, sizeof(v));
2447*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(buf, 40, NULL, v, 16);
2448*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 2);
2449*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[0], "Contents of chunk [0]\n");
2450*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[1], "Contents of chunk [1]\n");
2451*663afb9bSAndroid Build Coastguard Worker tt_assert(v[2].iov_base == NULL);
2452*663afb9bSAndroid Build Coastguard Worker
2453*663afb9bSAndroid Build Coastguard Worker /* How many chunks do we need for 100 bytes? */
2454*663afb9bSAndroid Build Coastguard Worker memset(v, 0, sizeof(v));
2455*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(buf, 100, NULL, NULL, 0);
2456*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 5);
2457*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_base == NULL);
2458*663afb9bSAndroid Build Coastguard Worker
2459*663afb9bSAndroid Build Coastguard Worker /* Now we ask for more bytes than we provide chunks for */
2460*663afb9bSAndroid Build Coastguard Worker memset(v, 0, sizeof(v));
2461*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(buf, 60, NULL, v, 1);
2462*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 3);
2463*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[0], "Contents of chunk [0]\n");
2464*663afb9bSAndroid Build Coastguard Worker tt_assert(v[1].iov_base == NULL);
2465*663afb9bSAndroid Build Coastguard Worker
2466*663afb9bSAndroid Build Coastguard Worker /* Now we ask for more bytes than the buffer has. */
2467*663afb9bSAndroid Build Coastguard Worker memset(v, 0, sizeof(v));
2468*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(buf, 65536, NULL, v, 20);
2469*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 16); /* we used only 16 chunks. */
2470*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[0], "Contents of chunk [0]\n");
2471*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[3], "Contents of chunk [3]\n");
2472*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[12], "Contents of chunk [12]\n");
2473*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[15], "Contents of chunk [15]\n");
2474*663afb9bSAndroid Build Coastguard Worker tt_assert(v[16].iov_base == NULL);
2475*663afb9bSAndroid Build Coastguard Worker
2476*663afb9bSAndroid Build Coastguard Worker /* What happens if we try an empty buffer? */
2477*663afb9bSAndroid Build Coastguard Worker memset(v, 0, sizeof(v));
2478*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(tmp_buf, -1, NULL, v, 20);
2479*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 0);
2480*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_base == NULL);
2481*663afb9bSAndroid Build Coastguard Worker memset(v, 0, sizeof(v));
2482*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(tmp_buf, 50, NULL, v, 20);
2483*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 0);
2484*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_base == NULL);
2485*663afb9bSAndroid Build Coastguard Worker
2486*663afb9bSAndroid Build Coastguard Worker /* Okay, now time to have fun with pointers. */
2487*663afb9bSAndroid Build Coastguard Worker memset(v, 0, sizeof(v));
2488*663afb9bSAndroid Build Coastguard Worker evbuffer_ptr_set(buf, &ptr, 30, EVBUFFER_PTR_SET);
2489*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(buf, 50, &ptr, v, 20);
2490*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 3);
2491*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[0], " of chunk [1]\n");
2492*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[1], "Contents of chunk [2]\n");
2493*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[2], "Contents of chunk [3]\n"); /*more than we asked for*/
2494*663afb9bSAndroid Build Coastguard Worker
2495*663afb9bSAndroid Build Coastguard Worker /* advance to the start of another chain. */
2496*663afb9bSAndroid Build Coastguard Worker memset(v, 0, sizeof(v));
2497*663afb9bSAndroid Build Coastguard Worker evbuffer_ptr_set(buf, &ptr, 14, EVBUFFER_PTR_ADD);
2498*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(buf, 44, &ptr, v, 20);
2499*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 2);
2500*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[0], "Contents of chunk [2]\n");
2501*663afb9bSAndroid Build Coastguard Worker tt_iov_eq(&v[1], "Contents of chunk [3]\n"); /*more than we asked for*/
2502*663afb9bSAndroid Build Coastguard Worker
2503*663afb9bSAndroid Build Coastguard Worker /* peek at the end of the buffer */
2504*663afb9bSAndroid Build Coastguard Worker memset(v, 0, sizeof(v));
2505*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_ptr_set(buf, &ptr, evbuffer_get_length(buf), EVBUFFER_PTR_SET) == 0);
2506*663afb9bSAndroid Build Coastguard Worker i = evbuffer_peek(buf, 44, &ptr, v, 20);
2507*663afb9bSAndroid Build Coastguard Worker tt_int_op(i, ==, 0);
2508*663afb9bSAndroid Build Coastguard Worker tt_assert(v[0].iov_base == NULL);
2509*663afb9bSAndroid Build Coastguard Worker
2510*663afb9bSAndroid Build Coastguard Worker end:
2511*663afb9bSAndroid Build Coastguard Worker if (buf)
2512*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
2513*663afb9bSAndroid Build Coastguard Worker if (tmp_buf)
2514*663afb9bSAndroid Build Coastguard Worker evbuffer_free(tmp_buf);
2515*663afb9bSAndroid Build Coastguard Worker }
2516*663afb9bSAndroid Build Coastguard Worker
2517*663afb9bSAndroid Build Coastguard Worker /* Check whether evbuffer freezing works right. This is called twice,
2518*663afb9bSAndroid Build Coastguard Worker once with the argument "start" and once with the argument "end".
2519*663afb9bSAndroid Build Coastguard Worker When we test "start", we freeze the start of an evbuffer and make sure
2520*663afb9bSAndroid Build Coastguard Worker that modifying the start of the buffer doesn't work. When we test
2521*663afb9bSAndroid Build Coastguard Worker "end", we freeze the end of an evbuffer and make sure that modifying
2522*663afb9bSAndroid Build Coastguard Worker the end of the buffer doesn't work.
2523*663afb9bSAndroid Build Coastguard Worker */
2524*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_freeze(void * ptr)2525*663afb9bSAndroid Build Coastguard Worker test_evbuffer_freeze(void *ptr)
2526*663afb9bSAndroid Build Coastguard Worker {
2527*663afb9bSAndroid Build Coastguard Worker struct basic_test_data *testdata = ptr;
2528*663afb9bSAndroid Build Coastguard Worker evutil_socket_t *pair = testdata->pair;
2529*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf = NULL, *buf_two = NULL, *tmp_buf = NULL;
2530*663afb9bSAndroid Build Coastguard Worker const char string[] = /* Year's End, Richard Wilbur */
2531*663afb9bSAndroid Build Coastguard Worker "I've known the wind by water banks to shake\n"
2532*663afb9bSAndroid Build Coastguard Worker "The late leaves down, which frozen where they fell\n"
2533*663afb9bSAndroid Build Coastguard Worker "And held in ice as dancers in a spell\n"
2534*663afb9bSAndroid Build Coastguard Worker "Fluttered all winter long into a lake...";
2535*663afb9bSAndroid Build Coastguard Worker const int start = !strcmp(testdata->setup_data, "start");
2536*663afb9bSAndroid Build Coastguard Worker const char tmpfilecontent[] = "file_freeze_test_file";
2537*663afb9bSAndroid Build Coastguard Worker char *cp;
2538*663afb9bSAndroid Build Coastguard Worker char charbuf[128];
2539*663afb9bSAndroid Build Coastguard Worker char *tmpfilename = NULL;
2540*663afb9bSAndroid Build Coastguard Worker int fd = -1;
2541*663afb9bSAndroid Build Coastguard Worker int r;
2542*663afb9bSAndroid Build Coastguard Worker size_t orig_length, len;
2543*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec v[1];
2544*663afb9bSAndroid Build Coastguard Worker
2545*663afb9bSAndroid Build Coastguard Worker if (!start)
2546*663afb9bSAndroid Build Coastguard Worker tt_str_op(testdata->setup_data, ==, "end");
2547*663afb9bSAndroid Build Coastguard Worker
2548*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
2549*663afb9bSAndroid Build Coastguard Worker buf_two = evbuffer_new();
2550*663afb9bSAndroid Build Coastguard Worker tmp_buf = evbuffer_new();
2551*663afb9bSAndroid Build Coastguard Worker tt_assert(tmp_buf);
2552*663afb9bSAndroid Build Coastguard Worker
2553*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, string, strlen(string));
2554*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf_two, "abc", 3);
2555*663afb9bSAndroid Build Coastguard Worker evbuffer_add(tmp_buf, "xyz", 3);
2556*663afb9bSAndroid Build Coastguard Worker evbuffer_freeze(buf, start); /* Freeze the start or the end.*/
2557*663afb9bSAndroid Build Coastguard Worker evbuffer_freeze(buf_two, start);
2558*663afb9bSAndroid Build Coastguard Worker
2559*663afb9bSAndroid Build Coastguard Worker #define FREEZE_EQ(a, startcase, endcase) \
2560*663afb9bSAndroid Build Coastguard Worker do { \
2561*663afb9bSAndroid Build Coastguard Worker if (start) { \
2562*663afb9bSAndroid Build Coastguard Worker tt_int_op((a), ==, (startcase)); \
2563*663afb9bSAndroid Build Coastguard Worker } else { \
2564*663afb9bSAndroid Build Coastguard Worker tt_int_op((a), ==, (endcase)); \
2565*663afb9bSAndroid Build Coastguard Worker } \
2566*663afb9bSAndroid Build Coastguard Worker } while (0)
2567*663afb9bSAndroid Build Coastguard Worker
2568*663afb9bSAndroid Build Coastguard Worker
2569*663afb9bSAndroid Build Coastguard Worker orig_length = evbuffer_get_length(buf);
2570*663afb9bSAndroid Build Coastguard Worker
2571*663afb9bSAndroid Build Coastguard Worker /* These functions all manipulate the end of buf. */
2572*663afb9bSAndroid Build Coastguard Worker r = evbuffer_add(buf, "abc", 0);
2573*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, 0, -1);
2574*663afb9bSAndroid Build Coastguard Worker r = evbuffer_reserve_space(buf, 10, v, 1);
2575*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, 1, -1);
2576*663afb9bSAndroid Build Coastguard Worker if (r == 1) {
2577*663afb9bSAndroid Build Coastguard Worker memset(v[0].iov_base, 'X', 10);
2578*663afb9bSAndroid Build Coastguard Worker v[0].iov_len = 10;
2579*663afb9bSAndroid Build Coastguard Worker }
2580*663afb9bSAndroid Build Coastguard Worker r = evbuffer_commit_space(buf, v, 1);
2581*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, 0, -1);
2582*663afb9bSAndroid Build Coastguard Worker r = evbuffer_add_reference(buf, string, 5, NULL, NULL);
2583*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, 0, -1);
2584*663afb9bSAndroid Build Coastguard Worker r = evbuffer_add_printf(buf, "Hello %s", "world");
2585*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, 11, -1);
2586*663afb9bSAndroid Build Coastguard Worker
2587*663afb9bSAndroid Build Coastguard Worker r = evbuffer_add_buffer(buf, tmp_buf);
2588*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, 0, -1);
2589*663afb9bSAndroid Build Coastguard Worker len = strlen(tmpfilecontent);
2590*663afb9bSAndroid Build Coastguard Worker fd = regress_make_tmpfile(tmpfilecontent, len, &tmpfilename);
2591*663afb9bSAndroid Build Coastguard Worker r = evbuffer_add_file(buf, fd, 0, len);
2592*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, 0, -1);
2593*663afb9bSAndroid Build Coastguard Worker
2594*663afb9bSAndroid Build Coastguard Worker if (start)
2595*663afb9bSAndroid Build Coastguard Worker evbuffer_add(tmp_buf, "xyz", 3);
2596*663afb9bSAndroid Build Coastguard Worker
2597*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(tmp_buf));
2598*663afb9bSAndroid Build Coastguard Worker len = evbuffer_get_length(tmp_buf);
2599*663afb9bSAndroid Build Coastguard Worker evbuffer_write(tmp_buf, pair[0]);
2600*663afb9bSAndroid Build Coastguard Worker r = evbuffer_read(buf, pair[1], -1);
2601*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, len, -1);
2602*663afb9bSAndroid Build Coastguard Worker
2603*663afb9bSAndroid Build Coastguard Worker if (!start)
2604*663afb9bSAndroid Build Coastguard Worker tt_int_op(orig_length, ==, evbuffer_get_length(buf));
2605*663afb9bSAndroid Build Coastguard Worker
2606*663afb9bSAndroid Build Coastguard Worker orig_length = evbuffer_get_length(buf);
2607*663afb9bSAndroid Build Coastguard Worker
2608*663afb9bSAndroid Build Coastguard Worker /* These functions all manipulate the start of buf. */
2609*663afb9bSAndroid Build Coastguard Worker r = evbuffer_remove(buf, charbuf, 1);
2610*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, -1, 1);
2611*663afb9bSAndroid Build Coastguard Worker r = evbuffer_drain(buf, 3);
2612*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, -1, 0);
2613*663afb9bSAndroid Build Coastguard Worker r = evbuffer_prepend(buf, "dummy", 5);
2614*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, -1, 0);
2615*663afb9bSAndroid Build Coastguard Worker cp = evbuffer_readln(buf, NULL, EVBUFFER_EOL_LF);
2616*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(cp==NULL, 1, 0);
2617*663afb9bSAndroid Build Coastguard Worker if (cp)
2618*663afb9bSAndroid Build Coastguard Worker free(cp);
2619*663afb9bSAndroid Build Coastguard Worker
2620*663afb9bSAndroid Build Coastguard Worker evbuffer_add(tmp_buf, "xyz", 3);
2621*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(tmp_buf));
2622*663afb9bSAndroid Build Coastguard Worker r = evbuffer_remove_buffer(buf, tmp_buf, 3);
2623*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, -1, 3);
2624*663afb9bSAndroid Build Coastguard Worker r = evbuffer_drain(buf, 3);
2625*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, -1, 0);
2626*663afb9bSAndroid Build Coastguard Worker r = evbuffer_prepend_buffer(buf, tmp_buf);
2627*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, -1, 0);
2628*663afb9bSAndroid Build Coastguard Worker
2629*663afb9bSAndroid Build Coastguard Worker len = evbuffer_get_length(buf);
2630*663afb9bSAndroid Build Coastguard Worker r = evbuffer_write(buf, pair[0]);
2631*663afb9bSAndroid Build Coastguard Worker evbuffer_read(tmp_buf, pair[1], -1);
2632*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, -1, len);
2633*663afb9bSAndroid Build Coastguard Worker len = evbuffer_get_length(buf_two);
2634*663afb9bSAndroid Build Coastguard Worker r = evbuffer_write_atmost(buf_two, pair[0], -1);
2635*663afb9bSAndroid Build Coastguard Worker evbuffer_read(tmp_buf, pair[1], -1);
2636*663afb9bSAndroid Build Coastguard Worker FREEZE_EQ(r, -1, len);
2637*663afb9bSAndroid Build Coastguard Worker
2638*663afb9bSAndroid Build Coastguard Worker if (start)
2639*663afb9bSAndroid Build Coastguard Worker tt_int_op(orig_length, ==, evbuffer_get_length(buf));
2640*663afb9bSAndroid Build Coastguard Worker
2641*663afb9bSAndroid Build Coastguard Worker end:
2642*663afb9bSAndroid Build Coastguard Worker if (buf)
2643*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
2644*663afb9bSAndroid Build Coastguard Worker
2645*663afb9bSAndroid Build Coastguard Worker if (buf_two)
2646*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf_two);
2647*663afb9bSAndroid Build Coastguard Worker
2648*663afb9bSAndroid Build Coastguard Worker if (tmp_buf)
2649*663afb9bSAndroid Build Coastguard Worker evbuffer_free(tmp_buf);
2650*663afb9bSAndroid Build Coastguard Worker
2651*663afb9bSAndroid Build Coastguard Worker if (tmpfilename) {
2652*663afb9bSAndroid Build Coastguard Worker unlink(tmpfilename);
2653*663afb9bSAndroid Build Coastguard Worker free(tmpfilename);
2654*663afb9bSAndroid Build Coastguard Worker }
2655*663afb9bSAndroid Build Coastguard Worker }
2656*663afb9bSAndroid Build Coastguard Worker
2657*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_add_iovec(void * ptr)2658*663afb9bSAndroid Build Coastguard Worker test_evbuffer_add_iovec(void * ptr)
2659*663afb9bSAndroid Build Coastguard Worker {
2660*663afb9bSAndroid Build Coastguard Worker struct evbuffer * buf = NULL;
2661*663afb9bSAndroid Build Coastguard Worker struct evbuffer_iovec vec[4];
2662*663afb9bSAndroid Build Coastguard Worker const char * data[] = {
2663*663afb9bSAndroid Build Coastguard Worker "Guilt resembles a sword with two edges.",
2664*663afb9bSAndroid Build Coastguard Worker "On the one hand, it cuts for Justice, imposing practical morality upon those who fear it.",
2665*663afb9bSAndroid Build Coastguard Worker "Conscience does not always adhere to rational judgment.",
2666*663afb9bSAndroid Build Coastguard Worker "Guilt is always a self-imposed burden, but it is not always rightly imposed."
2667*663afb9bSAndroid Build Coastguard Worker /* -- R.A. Salvatore, _Sojurn_ */
2668*663afb9bSAndroid Build Coastguard Worker };
2669*663afb9bSAndroid Build Coastguard Worker size_t expected_length = 0;
2670*663afb9bSAndroid Build Coastguard Worker size_t returned_length = 0;
2671*663afb9bSAndroid Build Coastguard Worker int i;
2672*663afb9bSAndroid Build Coastguard Worker
2673*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
2674*663afb9bSAndroid Build Coastguard Worker
2675*663afb9bSAndroid Build Coastguard Worker tt_assert(buf);
2676*663afb9bSAndroid Build Coastguard Worker
2677*663afb9bSAndroid Build Coastguard Worker for (i = 0; i < 4; i++) {
2678*663afb9bSAndroid Build Coastguard Worker vec[i].iov_len = strlen(data[i]);
2679*663afb9bSAndroid Build Coastguard Worker vec[i].iov_base = (char*) data[i];
2680*663afb9bSAndroid Build Coastguard Worker expected_length += vec[i].iov_len;
2681*663afb9bSAndroid Build Coastguard Worker }
2682*663afb9bSAndroid Build Coastguard Worker
2683*663afb9bSAndroid Build Coastguard Worker returned_length = evbuffer_add_iovec(buf, vec, 4);
2684*663afb9bSAndroid Build Coastguard Worker
2685*663afb9bSAndroid Build Coastguard Worker tt_int_op(returned_length, ==, evbuffer_get_length(buf));
2686*663afb9bSAndroid Build Coastguard Worker tt_int_op(evbuffer_get_length(buf), ==, expected_length);
2687*663afb9bSAndroid Build Coastguard Worker
2688*663afb9bSAndroid Build Coastguard Worker for (i = 0; i < 4; i++) {
2689*663afb9bSAndroid Build Coastguard Worker char charbuf[1024];
2690*663afb9bSAndroid Build Coastguard Worker
2691*663afb9bSAndroid Build Coastguard Worker memset(charbuf, 0, 1024);
2692*663afb9bSAndroid Build Coastguard Worker evbuffer_remove(buf, charbuf, strlen(data[i]));
2693*663afb9bSAndroid Build Coastguard Worker tt_assert(strcmp(charbuf, data[i]) == 0);
2694*663afb9bSAndroid Build Coastguard Worker }
2695*663afb9bSAndroid Build Coastguard Worker
2696*663afb9bSAndroid Build Coastguard Worker tt_assert(evbuffer_get_length(buf) == 0);
2697*663afb9bSAndroid Build Coastguard Worker end:
2698*663afb9bSAndroid Build Coastguard Worker if (buf) {
2699*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
2700*663afb9bSAndroid Build Coastguard Worker }
2701*663afb9bSAndroid Build Coastguard Worker }
2702*663afb9bSAndroid Build Coastguard Worker
2703*663afb9bSAndroid Build Coastguard Worker static void
test_evbuffer_copyout(void * dummy)2704*663afb9bSAndroid Build Coastguard Worker test_evbuffer_copyout(void *dummy)
2705*663afb9bSAndroid Build Coastguard Worker {
2706*663afb9bSAndroid Build Coastguard Worker const char string[] =
2707*663afb9bSAndroid Build Coastguard Worker "Still they skirmish to and fro, men my messmates on the snow "
2708*663afb9bSAndroid Build Coastguard Worker "When we headed off the aurochs turn for turn; "
2709*663afb9bSAndroid Build Coastguard Worker "When the rich Allobrogenses never kept amanuenses, "
2710*663afb9bSAndroid Build Coastguard Worker "And our only plots were piled in lakes at Berne.";
2711*663afb9bSAndroid Build Coastguard Worker /* -- Kipling, "In The Neolithic Age" */
2712*663afb9bSAndroid Build Coastguard Worker char tmp[1024];
2713*663afb9bSAndroid Build Coastguard Worker struct evbuffer_ptr ptr;
2714*663afb9bSAndroid Build Coastguard Worker struct evbuffer *buf;
2715*663afb9bSAndroid Build Coastguard Worker
2716*663afb9bSAndroid Build Coastguard Worker (void)dummy;
2717*663afb9bSAndroid Build Coastguard Worker
2718*663afb9bSAndroid Build Coastguard Worker buf = evbuffer_new();
2719*663afb9bSAndroid Build Coastguard Worker tt_assert(buf);
2720*663afb9bSAndroid Build Coastguard Worker
2721*663afb9bSAndroid Build Coastguard Worker tt_int_op(strlen(string), ==, 206);
2722*663afb9bSAndroid Build Coastguard Worker
2723*663afb9bSAndroid Build Coastguard Worker /* Ensure separate chains */
2724*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, string, 80, no_cleanup, NULL);
2725*663afb9bSAndroid Build Coastguard Worker evbuffer_add_reference(buf, string+80, 80, no_cleanup, NULL);
2726*663afb9bSAndroid Build Coastguard Worker evbuffer_add(buf, string+160, strlen(string)-160);
2727*663afb9bSAndroid Build Coastguard Worker
2728*663afb9bSAndroid Build Coastguard Worker tt_int_op(206, ==, evbuffer_get_length(buf));
2729*663afb9bSAndroid Build Coastguard Worker
2730*663afb9bSAndroid Build Coastguard Worker /* First, let's test plain old copyout. */
2731*663afb9bSAndroid Build Coastguard Worker
2732*663afb9bSAndroid Build Coastguard Worker /* Copy a little from the beginning. */
2733*663afb9bSAndroid Build Coastguard Worker tt_int_op(10, ==, evbuffer_copyout(buf, tmp, 10));
2734*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, memcmp(tmp, "Still they", 10));
2735*663afb9bSAndroid Build Coastguard Worker
2736*663afb9bSAndroid Build Coastguard Worker /* Now copy more than a little from the beginning */
2737*663afb9bSAndroid Build Coastguard Worker memset(tmp, 0, sizeof(tmp));
2738*663afb9bSAndroid Build Coastguard Worker tt_int_op(100, ==, evbuffer_copyout(buf, tmp, 100));
2739*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, memcmp(tmp, string, 100));
2740*663afb9bSAndroid Build Coastguard Worker
2741*663afb9bSAndroid Build Coastguard Worker /* Copy too much; ensure truncation. */
2742*663afb9bSAndroid Build Coastguard Worker memset(tmp, 0, sizeof(tmp));
2743*663afb9bSAndroid Build Coastguard Worker tt_int_op(206, ==, evbuffer_copyout(buf, tmp, 230));
2744*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, memcmp(tmp, string, 206));
2745*663afb9bSAndroid Build Coastguard Worker
2746*663afb9bSAndroid Build Coastguard Worker /* That was supposed to be nondestructive, btw */
2747*663afb9bSAndroid Build Coastguard Worker tt_int_op(206, ==, evbuffer_get_length(buf));
2748*663afb9bSAndroid Build Coastguard Worker
2749*663afb9bSAndroid Build Coastguard Worker /* Now it's time to test copyout_from! First, let's start in the
2750*663afb9bSAndroid Build Coastguard Worker * first chain. */
2751*663afb9bSAndroid Build Coastguard Worker evbuffer_ptr_set(buf, &ptr, 15, EVBUFFER_PTR_SET);
2752*663afb9bSAndroid Build Coastguard Worker memset(tmp, 0, sizeof(tmp));
2753*663afb9bSAndroid Build Coastguard Worker tt_int_op(10, ==, evbuffer_copyout_from(buf, &ptr, tmp, 10));
2754*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, memcmp(tmp, "mish to an", 10));
2755*663afb9bSAndroid Build Coastguard Worker
2756*663afb9bSAndroid Build Coastguard Worker /* Right up to the end of the first chain */
2757*663afb9bSAndroid Build Coastguard Worker memset(tmp, 0, sizeof(tmp));
2758*663afb9bSAndroid Build Coastguard Worker tt_int_op(65, ==, evbuffer_copyout_from(buf, &ptr, tmp, 65));
2759*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, memcmp(tmp, string+15, 65));
2760*663afb9bSAndroid Build Coastguard Worker
2761*663afb9bSAndroid Build Coastguard Worker /* Span into the second chain */
2762*663afb9bSAndroid Build Coastguard Worker memset(tmp, 0, sizeof(tmp));
2763*663afb9bSAndroid Build Coastguard Worker tt_int_op(90, ==, evbuffer_copyout_from(buf, &ptr, tmp, 90));
2764*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, memcmp(tmp, string+15, 90));
2765*663afb9bSAndroid Build Coastguard Worker
2766*663afb9bSAndroid Build Coastguard Worker /* Span into the third chain */
2767*663afb9bSAndroid Build Coastguard Worker memset(tmp, 0, sizeof(tmp));
2768*663afb9bSAndroid Build Coastguard Worker tt_int_op(160, ==, evbuffer_copyout_from(buf, &ptr, tmp, 160));
2769*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, memcmp(tmp, string+15, 160));
2770*663afb9bSAndroid Build Coastguard Worker
2771*663afb9bSAndroid Build Coastguard Worker /* Overrun */
2772*663afb9bSAndroid Build Coastguard Worker memset(tmp, 0, sizeof(tmp));
2773*663afb9bSAndroid Build Coastguard Worker tt_int_op(206-15, ==, evbuffer_copyout_from(buf, &ptr, tmp, 999));
2774*663afb9bSAndroid Build Coastguard Worker tt_int_op(0, ==, memcmp(tmp, string+15, 206-15));
2775*663afb9bSAndroid Build Coastguard Worker
2776*663afb9bSAndroid Build Coastguard Worker /* That was supposed to be nondestructive, too */
2777*663afb9bSAndroid Build Coastguard Worker tt_int_op(206, ==, evbuffer_get_length(buf));
2778*663afb9bSAndroid Build Coastguard Worker
2779*663afb9bSAndroid Build Coastguard Worker end:
2780*663afb9bSAndroid Build Coastguard Worker if (buf)
2781*663afb9bSAndroid Build Coastguard Worker evbuffer_free(buf);
2782*663afb9bSAndroid Build Coastguard Worker }
2783*663afb9bSAndroid Build Coastguard Worker
2784*663afb9bSAndroid Build Coastguard Worker static void *
setup_passthrough(const struct testcase_t * testcase)2785*663afb9bSAndroid Build Coastguard Worker setup_passthrough(const struct testcase_t *testcase)
2786*663afb9bSAndroid Build Coastguard Worker {
2787*663afb9bSAndroid Build Coastguard Worker return testcase->setup_data;
2788*663afb9bSAndroid Build Coastguard Worker }
2789*663afb9bSAndroid Build Coastguard Worker static int
cleanup_passthrough(const struct testcase_t * testcase,void * ptr)2790*663afb9bSAndroid Build Coastguard Worker cleanup_passthrough(const struct testcase_t *testcase, void *ptr)
2791*663afb9bSAndroid Build Coastguard Worker {
2792*663afb9bSAndroid Build Coastguard Worker (void) ptr;
2793*663afb9bSAndroid Build Coastguard Worker return 1;
2794*663afb9bSAndroid Build Coastguard Worker }
2795*663afb9bSAndroid Build Coastguard Worker
2796*663afb9bSAndroid Build Coastguard Worker static const struct testcase_setup_t nil_setup = {
2797*663afb9bSAndroid Build Coastguard Worker setup_passthrough,
2798*663afb9bSAndroid Build Coastguard Worker cleanup_passthrough
2799*663afb9bSAndroid Build Coastguard Worker };
2800*663afb9bSAndroid Build Coastguard Worker
2801*663afb9bSAndroid Build Coastguard Worker struct testcase_t evbuffer_testcases[] = {
2802*663afb9bSAndroid Build Coastguard Worker { "evbuffer", test_evbuffer, 0, NULL, NULL },
2803*663afb9bSAndroid Build Coastguard Worker { "remove_buffer_with_empty", test_evbuffer_remove_buffer_with_empty, 0, NULL, NULL },
2804*663afb9bSAndroid Build Coastguard Worker { "remove_buffer_with_empty2", test_evbuffer_remove_buffer_with_empty2, 0, NULL, NULL },
2805*663afb9bSAndroid Build Coastguard Worker { "remove_buffer_with_empty3", test_evbuffer_remove_buffer_with_empty3, 0, NULL, NULL },
2806*663afb9bSAndroid Build Coastguard Worker { "remove_buffer_with_empty_front", test_evbuffer_remove_buffer_with_empty_front, 0, NULL, NULL },
2807*663afb9bSAndroid Build Coastguard Worker { "remove_buffer_adjust_last_with_datap_with_empty",
2808*663afb9bSAndroid Build Coastguard Worker test_evbuffer_remove_buffer_adjust_last_with_datap_with_empty, 0, NULL, NULL },
2809*663afb9bSAndroid Build Coastguard Worker { "add_buffer_with_empty", test_evbuffer_add_buffer_with_empty, 0, NULL, NULL },
2810*663afb9bSAndroid Build Coastguard Worker { "add_buffer_with_empty2", test_evbuffer_add_buffer_with_empty2, 0, NULL, NULL },
2811*663afb9bSAndroid Build Coastguard Worker { "reserve2", test_evbuffer_reserve2, 0, NULL, NULL },
2812*663afb9bSAndroid Build Coastguard Worker { "reserve_many", test_evbuffer_reserve_many, 0, NULL, NULL },
2813*663afb9bSAndroid Build Coastguard Worker { "reserve_many2", test_evbuffer_reserve_many, 0, &nil_setup, (void*)"add" },
2814*663afb9bSAndroid Build Coastguard Worker { "reserve_many3", test_evbuffer_reserve_many, 0, &nil_setup, (void*)"fill" },
2815*663afb9bSAndroid Build Coastguard Worker { "reserve_with_empty", test_evbuffer_reserve_with_empty, 0, NULL, NULL },
2816*663afb9bSAndroid Build Coastguard Worker { "reserve_invalid_last_with_datap", test_evbuffer_reserve_invalid_last_with_datap, TT_FORK, NULL, NULL },
2817*663afb9bSAndroid Build Coastguard Worker { "expand", test_evbuffer_expand, 0, NULL, NULL },
2818*663afb9bSAndroid Build Coastguard Worker { "expand_overflow", test_evbuffer_expand_overflow, 0, NULL, NULL },
2819*663afb9bSAndroid Build Coastguard Worker { "add1", test_evbuffer_add1, 0, NULL, NULL },
2820*663afb9bSAndroid Build Coastguard Worker { "add2", test_evbuffer_add2, 0, NULL, NULL },
2821*663afb9bSAndroid Build Coastguard Worker { "reference", test_evbuffer_reference, 0, NULL, NULL },
2822*663afb9bSAndroid Build Coastguard Worker { "reference2", test_evbuffer_reference2, 0, NULL, NULL },
2823*663afb9bSAndroid Build Coastguard Worker { "iterative", test_evbuffer_iterative, 0, NULL, NULL },
2824*663afb9bSAndroid Build Coastguard Worker { "readln", test_evbuffer_readln, TT_NO_LOGS, &basic_setup, NULL },
2825*663afb9bSAndroid Build Coastguard Worker { "search_eol", test_evbuffer_search_eol, 0, NULL, NULL },
2826*663afb9bSAndroid Build Coastguard Worker { "find", test_evbuffer_find, 0, NULL, NULL },
2827*663afb9bSAndroid Build Coastguard Worker { "ptr_set", test_evbuffer_ptr_set, 0, NULL, NULL },
2828*663afb9bSAndroid Build Coastguard Worker { "search", test_evbuffer_search, 0, NULL, NULL },
2829*663afb9bSAndroid Build Coastguard Worker { "callbacks", test_evbuffer_callbacks, 0, NULL, NULL },
2830*663afb9bSAndroid Build Coastguard Worker { "add_reference", test_evbuffer_add_reference, 0, NULL, NULL },
2831*663afb9bSAndroid Build Coastguard Worker { "multicast", test_evbuffer_multicast, 0, NULL, NULL },
2832*663afb9bSAndroid Build Coastguard Worker { "multicast_drain", test_evbuffer_multicast_drain, 0, NULL, NULL },
2833*663afb9bSAndroid Build Coastguard Worker { "prepend", test_evbuffer_prepend, TT_FORK, NULL, NULL },
2834*663afb9bSAndroid Build Coastguard Worker { "empty_reference_prepend", test_evbuffer_empty_reference_prepend, TT_FORK, NULL, NULL },
2835*663afb9bSAndroid Build Coastguard Worker { "empty_reference_prepend_buffer", test_evbuffer_empty_reference_prepend_buffer, TT_FORK, NULL, NULL },
2836*663afb9bSAndroid Build Coastguard Worker { "peek", test_evbuffer_peek, 0, NULL, NULL },
2837*663afb9bSAndroid Build Coastguard Worker { "peek_first_gt", test_evbuffer_peek_first_gt, 0, NULL, NULL },
2838*663afb9bSAndroid Build Coastguard Worker { "freeze_start", test_evbuffer_freeze, TT_NEED_SOCKETPAIR, &basic_setup, (void*)"start" },
2839*663afb9bSAndroid Build Coastguard Worker { "freeze_end", test_evbuffer_freeze, TT_NEED_SOCKETPAIR, &basic_setup, (void*)"end" },
2840*663afb9bSAndroid Build Coastguard Worker { "add_iovec", test_evbuffer_add_iovec, 0, NULL, NULL},
2841*663afb9bSAndroid Build Coastguard Worker { "copyout", test_evbuffer_copyout, 0, NULL, NULL},
2842*663afb9bSAndroid Build Coastguard Worker { "file_segment_add_cleanup_cb", test_evbuffer_file_segment_add_cleanup_cb, 0, NULL, NULL },
2843*663afb9bSAndroid Build Coastguard Worker { "pullup_with_empty", test_evbuffer_pullup_with_empty, 0, NULL, NULL },
2844*663afb9bSAndroid Build Coastguard Worker
2845*663afb9bSAndroid Build Coastguard Worker #define ADDFILE_TEST(name, parameters) \
2846*663afb9bSAndroid Build Coastguard Worker { name, test_evbuffer_add_file, TT_FORK|TT_NEED_BASE, \
2847*663afb9bSAndroid Build Coastguard Worker &basic_setup, (void*)(parameters) }
2848*663afb9bSAndroid Build Coastguard Worker
2849*663afb9bSAndroid Build Coastguard Worker #define ADDFILE_TEST_GROUP(name, parameters) \
2850*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST(name "_sendfile", "sendfile " parameters), \
2851*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST(name "_mmap", "mmap " parameters), \
2852*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST(name "_linear", "linear " parameters)
2853*663afb9bSAndroid Build Coastguard Worker
2854*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST_GROUP("add_file", ""),
2855*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST("add_file_nosegment", "default nosegment"),
2856*663afb9bSAndroid Build Coastguard Worker
2857*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST_GROUP("add_big_file", "bigfile"),
2858*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST("add_big_file_nosegment", "default nosegment bigfile"),
2859*663afb9bSAndroid Build Coastguard Worker
2860*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST_GROUP("add_file_offset", "bigfile map_offset"),
2861*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST("add_file_offset_nosegment",
2862*663afb9bSAndroid Build Coastguard Worker "default nosegment bigfile map_offset"),
2863*663afb9bSAndroid Build Coastguard Worker
2864*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST_GROUP("add_file_offset2", "bigfile offset_in_segment"),
2865*663afb9bSAndroid Build Coastguard Worker
2866*663afb9bSAndroid Build Coastguard Worker ADDFILE_TEST_GROUP("add_file_offset3",
2867*663afb9bSAndroid Build Coastguard Worker "bigfile offset_in_segment map_offset"),
2868*663afb9bSAndroid Build Coastguard Worker
2869*663afb9bSAndroid Build Coastguard Worker END_OF_TESTCASES
2870*663afb9bSAndroid Build Coastguard Worker };
2871