varnish-cache/bin/varnishtest/vtc_varnish.c
1
/*-
2
 * Copyright (c) 2008-2015 Varnish Software AS
3
 * All rights reserved.
4
 *
5
 * Author: Poul-Henning Kamp <phk@phk.freebsd.dk>
6
 *
7
 * Redistribution and use in source and binary forms, with or without
8
 * modification, are permitted provided that the following conditions
9
 * are met:
10
 * 1. Redistributions of source code must retain the above copyright
11
 *    notice, this list of conditions and the following disclaimer.
12
 * 2. Redistributions in binary form must reproduce the above copyright
13
 *    notice, this list of conditions and the following disclaimer in the
14
 *    documentation and/or other materials provided with the distribution.
15
 *
16
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
17
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19
 * ARE DISCLAIMED.  IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
20
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26
 * SUCH DAMAGE.
27
 */
28
29
#ifdef VTEST_WITH_VTC_VARNISH
30
31
#include "config.h"
32
33
#include <sys/types.h>
34
#include <sys/socket.h>
35
36
#include <fcntl.h>
37
#include <fnmatch.h>
38
#include <inttypes.h>
39
#include <poll.h>
40
#include <stdio.h>
41
#include <stdlib.h>
42
#include <string.h>
43
#include <unistd.h>
44
45
#include "vtc.h"
46
47
#include "vapi/vsc.h"
48
#include "vapi/vsl.h"
49
#include "vapi/vsm.h"
50
#include "vcli.h"
51
#include "vjsn.h"
52
#include "vre.h"
53
#include "vsub.h"
54
#include "vtcp.h"
55
#include "vtim.h"
56
57
struct varnish {
58
        unsigned                magic;
59
#define VARNISH_MAGIC           0x208cd8e3
60
        char                    *name;
61
        struct vtclog           *vl;
62
        VTAILQ_ENTRY(varnish)   list;
63
64
        struct vsb              *args;
65
        int                     fds[4];
66
        pid_t                   pid;
67
68
        double                  syntax;
69
70
        pthread_t               tp;
71
        pthread_t               tp_vsl;
72
73
        int                     expect_exit;
74
75
        int                     cli_fd;
76
        int                     vcl_nbr;
77
        char                    *workdir;
78
        char                    *jail;
79
        char                    *proto;
80
81
        struct vsm              *vsm_vsl;
82
        struct vsm              *vsm_vsc;
83
        struct vsc              *vsc;
84
        int                     has_a_arg;
85
86
        unsigned                vsl_tag_count[256];
87
88
        volatile int            vsl_rec;
89
        volatile int            vsl_idle;
90
};
91
92
#define NONSENSE        "%XJEIFLH|)Xspa8P"
93
94
static VTAILQ_HEAD(, varnish)   varnishes =
95
    VTAILQ_HEAD_INITIALIZER(varnishes);
96
97
/**********************************************************************
98
 * Ask a question over CLI
99
 */
100
101
static enum VCLI_status_e
102 167793
varnish_ask_cli(const struct varnish *v, const char *cmd, char **repl)
103
{
104
        int i;
105
        unsigned retval;
106
        char *r;
107
108 167793
        if (cmd != NULL) {
109 156603
                vtc_dump(v->vl, 4, "CLI TX", cmd, -1);
110 156603
                i = write(v->cli_fd, cmd, strlen(cmd));
111 156603
                if (i != strlen(cmd) && !vtc_stop)
112 0
                        vtc_fatal(v->vl, "CLI write failed (%s) = %u %s",
113 0
                            cmd, errno, strerror(errno));
114 156603
                i = write(v->cli_fd, "\n", 1);
115 156603
                if (i != 1 && !vtc_stop)
116 0
                        vtc_fatal(v->vl, "CLI write failed (%s) = %u %s",
117 0
                            cmd, errno, strerror(errno));
118 156603
        }
119 167793
        i = VCLI_ReadResult(v->cli_fd, &retval, &r, vtc_maxdur);
120 167793
        if (i != 0 && !vtc_stop)
121 0
                vtc_fatal(v->vl, "CLI failed (%s) = %d %u %s",
122 0
                    cmd, i, retval, r);
123 167793
        vtc_log(v->vl, 3, "CLI RX  %u", retval);
124 167793
        vtc_dump(v->vl, 4, "CLI RX", r, -1);
125 167793
        if (repl != NULL)
126 107253
                *repl = r;
127
        else
128 60540
                free(r);
129 167793
        return ((enum VCLI_status_e)retval);
130
}
131
132
/**********************************************************************
133
 *
134
 */
135
136
static void
137 11760
wait_stopped(const struct varnish *v)
138
{
139 11760
        char *r = NULL;
140
        enum VCLI_status_e st;
141
142 11760
        vtc_log(v->vl, 3, "wait-stopped");
143 11778
        while (1) {
144 11778
                st = varnish_ask_cli(v, "status", &r);
145 11778
                if (st != CLIS_OK)
146 0
                        vtc_fatal(v->vl,
147 0
                            "CLI status command failed: %u %s", st, r);
148 11778
                if (!strcmp(r, "Child in state stopped")) {
149 11760
                        free(r);
150 11760
                        break;
151
                }
152 18
                free(r);
153 18
                r = NULL;
154 18
                (void)usleep(200000);
155
        }
156 11760
}
157
/**********************************************************************
158
 *
159
 */
160
161
static void
162 11055
wait_running(const struct varnish *v)
163
{
164 11055
        char *r = NULL;
165
        enum VCLI_status_e st;
166
167 11055
        while (1) {
168 11055
                vtc_log(v->vl, 3, "wait-running");
169 11055
                st = varnish_ask_cli(v, "status", &r);
170 11055
                if (st != CLIS_OK)
171 0
                        vtc_fatal(v->vl,
172 0
                            "CLI status command failed: %u %s", st, r);
173 11055
                if (!strcmp(r, "Child in state stopped"))
174 0
                        vtc_fatal(v->vl,
175 0
                            "Child stopped before running: %u %s", st, r);
176 11055
                if (!strcmp(r, "Child in state running")) {
177 11055
                        st = varnish_ask_cli(v, "debug.listen_address", &r);
178 11055
                        if (st != CLIS_OK)
179 0
                                vtc_fatal(v->vl,
180
                                          "CLI status command failed: %u %s",
181 0
                                          st, r);
182 11055
                        free(r);
183 11055
                        break;
184
                }
185 0
                free(r);
186 0
                r = NULL;
187 0
                (void)usleep(200000);
188
        }
189 11055
}
190
191
/**********************************************************************
192
 * Varnishlog gatherer thread
193
 */
194
195
static void
196 1425
vsl_catchup(const struct varnish *v)
197
{
198
        int vsl_idle;
199
200 1425
        vsl_idle = v->vsl_idle;
201 2962
        while (!vtc_error && vsl_idle == v->vsl_idle)
202 1537
                VTIM_sleep(0.1);
203 1425
}
204
205
static void *
206 11190
varnishlog_thread(void *priv)
207
{
208
        struct varnish *v;
209
        struct VSL_data *vsl;
210
        struct vsm *vsm;
211
        struct VSL_cursor *c;
212
        enum VSL_tag_e tag;
213
        uint32_t vxid;
214
        unsigned len;
215
        const char *tagname, *data;
216
        int type, i, opt;
217 11190
        struct vsb *vsb = NULL;
218
219 11190
        CAST_OBJ_NOTNULL(v, priv, VARNISH_MAGIC);
220
221 11190
        vsl = VSL_New();
222 11190
        AN(vsl);
223 11190
        vsm = v->vsm_vsl;
224
225 11190
        c = NULL;
226 11190
        opt = 0;
227 457310
        while (v->fds[1] > 0 || c != NULL) {    //lint !e845 bug in flint
228 446122
                if (c == NULL) {
229 114286
                        if (vtc_error)
230 0
                                break;
231 114286
                        VTIM_sleep(0.1);
232 114286
                        (void)VSM_Status(vsm);
233 114286
                        c = VSL_CursorVSM(vsl, vsm, opt);
234 114286
                        if (c == NULL) {
235 103156
                                vtc_log(v->vl, 3, "vsl|%s", VSL_Error(vsl));
236 103156
                                VSL_ResetError(vsl);
237 103156
                                continue;
238
                        }
239 11130
                }
240 342967
                AN(c);
241
242 342967
                opt = VSL_COPT_TAIL;
243
244 3288023
                while (1) {
245 3288022
                        i = VSL_Next(c);
246 3288022
                        if (i != 1)
247 342960
                                break;
248
249 2945058
                        v->vsl_rec = 1;
250
251 2945058
                        tag = VSL_TAG(c->rec.ptr);
252 2945058
                        vxid = VSL_ID(c->rec.ptr);
253 2945058
                        if (tag == SLT__Batch)
254 0
                                continue;
255 2945058
                        tagname = VSL_tags[tag];
256 2945058
                        len = VSL_LEN(c->rec.ptr);
257 2945058
                        type = VSL_CLIENT(c->rec.ptr) ?
258 1217763
                            'c' : VSL_BACKEND(c->rec.ptr) ?
259
                            'b' : '-';
260 2945059
                        data = VSL_CDATA(c->rec.ptr);
261 2945059
                        v->vsl_tag_count[tag]++;
262 2945059
                        if (VSL_tagflags[tag] & SLT_F_BINARY) {
263 630
                                if (vsb == NULL)
264 30
                                        vsb = VSB_new_auto();
265 630
                                VSB_clear(vsb);
266 630
                                VSB_quote(vsb, data, len, VSB_QUOTE_HEX);
267 630
                                AZ(VSB_finish(vsb));
268
                                /* +2 to skip "0x" */
269 1260
                                vtc_log(v->vl, 4, "vsl| %10u %-15s %c [%s]",
270 630
                                    vxid, tagname, type, VSB_data(vsb) + 2);
271 630
                        } else {
272 5888858
                                vtc_log(v->vl, 4, "vsl| %10u %-15s %c %.*s",
273 2944429
                                    vxid, tagname, type, (int)len, data);
274
                        }
275
                }
276 342962
                if (i == 0) {
277
                        /* Nothing to do but wait */
278 342853
                        v->vsl_idle++;
279 342853
                        if (!(VSM_Status(vsm) & VSM_WRK_RUNNING)) {
280
                                /* Abandoned - try reconnect */
281 11018
                                VSL_DeleteCursor(c);
282 11018
                                c = NULL;
283 11018
                        } else {
284 331836
                                VTIM_sleep(0.1);
285
                        }
286 342965
                } else if (i == -2) {
287
                        /* Abandoned - try reconnect */
288 112
                        VSL_DeleteCursor(c);
289 112
                        c = NULL;
290 112
                } else
291 0
                        break;
292
        }
293
294 11190
        if (c)
295 0
                VSL_DeleteCursor(c);
296 11190
        VSL_Delete(vsl);
297 11190
        if (vsb != NULL)
298 30
                VSB_destroy(&vsb);
299
300 11190
        return (NULL);
301
}
302
303
/**********************************************************************
304
 * Allocate and initialize a varnish
305
 */
306
307
static struct varnish *
308 11190
varnish_new(const char *name)
309
{
310
        struct varnish *v;
311
        struct vsb *vsb;
312
        char buf[1024];
313
314 11190
        ALLOC_OBJ(v, VARNISH_MAGIC);
315 11190
        AN(v);
316 11190
        REPLACE(v->name, name);
317
318 11190
        REPLACE(v->jail, "");
319
320 11190
        v->vl = vtc_logopen(name);
321 11190
        AN(v->vl);
322
323 11190
        vsb = macro_expandf(v->vl, "${tmpdir}/%s", name);
324 11190
        AN(vsb);
325 11190
        v->workdir = strdup(VSB_data(vsb));
326 11190
        AN(v->workdir);
327 11190
        VSB_destroy(&vsb);
328
329 11190
        bprintf(buf, "rm -rf %s ; mkdir -p %s", v->workdir, v->workdir);
330 11190
        AZ(system(buf));
331
332 11190
        v->args = VSB_new_auto();
333
334 11190
        v->cli_fd = -1;
335 11190
        VTAILQ_INSERT_TAIL(&varnishes, v, list);
336
337
338 11190
        return (v);
339
}
340
341
/**********************************************************************
342
 * Delete a varnish instance
343
 */
344
345
static void
346 11190
varnish_delete(struct varnish *v)
347
{
348
349 11190
        CHECK_OBJ_NOTNULL(v, VARNISH_MAGIC);
350 11190
        vtc_logclose(v->vl);
351 11190
        free(v->name);
352 11190
        free(v->workdir);
353 11190
        if (v->vsc != NULL)
354 11190
                VSC_Destroy(&v->vsc, v->vsm_vsc);
355 11190
        if (v->vsm_vsc != NULL)
356 11190
                VSM_Destroy(&v->vsm_vsc);
357 11190
        if (v->vsm_vsl != NULL)
358 11190
                VSM_Destroy(&v->vsm_vsl);
359
360
        /*
361
         * We do not delete the workdir, it may contain stuff people
362
         * want (coredumps, shmlog/stats etc), and trying to divine
363
         * "may want" is just too much trouble.  Leave it around and
364
         * nuke it at the start of the next test-run.
365
         */
366
367
        /* XXX: MEMLEAK (?) */
368 11190
        FREE_OBJ(v);
369 11190
}
370
371
/**********************************************************************
372
 * Varnish listener
373
 */
374
375
static void *
376 11190
varnish_thread(void *priv)
377
{
378
        struct varnish *v;
379
380 11190
        CAST_OBJ_NOTNULL(v, priv, VARNISH_MAGIC);
381 11190
        return (vtc_record(v->vl, v->fds[0], NULL));
382
}
383
384
/**********************************************************************
385
 * Launch a Varnish
386
 */
387
388
static void
389 11190
varnish_launch(struct varnish *v)
390
{
391
        struct vsb *vsb, *vsb1;
392
        int i, nfd;
393
        char abuf[128], pbuf[128];
394
        struct pollfd fd[2];
395
        enum VCLI_status_e u;
396
        const char *err;
397 11190
        char *r = NULL;
398
399
        /* Create listener socket */
400 11190
        v->cli_fd = VTCP_listen_on("127.0.0.1:0", NULL, 1, &err);
401 11190
        if (err != NULL)
402 0
                vtc_fatal(v->vl, "Create CLI listen socket failed: %s", err);
403 11190
        assert(v->cli_fd > 0);
404 11190
        VTCP_myname(v->cli_fd, abuf, sizeof abuf, pbuf, sizeof pbuf);
405
406 11190
        AZ(VSB_finish(v->args));
407 11190
        vtc_log(v->vl, 2, "Launch");
408 11190
        vsb = VSB_new_auto();
409 11190
        AN(vsb);
410 11190
        VSB_printf(vsb, "cd ${pwd} &&");
411 22380
        VSB_printf(vsb, " exec varnishd %s -d -n %s",
412 11190
            v->jail, v->workdir);
413 11190
        VSB_cat(vsb, VSB_data(params_vsb));
414 11190
        if (vtc_witness)
415 0
                VSB_cat(vsb, " -p debug=+witness");
416 11190
        if (leave_temp) {
417 0
                VSB_cat(vsb, " -p debug=+vcl_keep");
418 0
                VSB_cat(vsb, " -p debug=+vmod_so_keep");
419 0
                VSB_cat(vsb, " -p debug=+vsm_keep");
420 0
        }
421 11190
        VSB_printf(vsb, " -l 2m");
422 11190
        VSB_printf(vsb, " -p auto_restart=off");
423 11190
        VSB_printf(vsb, " -p syslog_cli_traffic=off");
424 11190
        VSB_printf(vsb, " -p sigsegv_handler=on");
425 11190
        VSB_printf(vsb, " -p thread_pool_min=10");
426 11190
        VSB_printf(vsb, " -p debug=+vtc_mode");
427 11190
        VSB_printf(vsb, " -p vsl_mask=+Debug");
428 11190
        if (!v->has_a_arg) {
429 10815
                VSB_printf(vsb, " -a '%s'", "127.0.0.1:0");
430 10815
                if (v->proto != NULL)
431 120
                        VSB_printf(vsb, ",%s", v->proto);
432 10815
        }
433 11190
        VSB_printf(vsb, " -M '%s %s'", abuf, pbuf);
434 11190
        VSB_printf(vsb, " -P %s/varnishd.pid", v->workdir);
435 11190
        if (vmod_path != NULL)
436 11175
                VSB_printf(vsb, " -p vmod_path=%s", vmod_path);
437 11190
        VSB_printf(vsb, " %s", VSB_data(v->args));
438 11190
        AZ(VSB_finish(vsb));
439 11190
        vtc_log(v->vl, 3, "CMD: %s", VSB_data(vsb));
440 11190
        vsb1 = macro_expand(v->vl, VSB_data(vsb));
441 11190
        AN(vsb1);
442 11190
        VSB_destroy(&vsb);
443 11190
        vsb = vsb1;
444 11190
        vtc_log(v->vl, 3, "CMD: %s", VSB_data(vsb));
445 11190
        AZ(pipe(&v->fds[0]));
446 11190
        AZ(pipe(&v->fds[2]));
447 11190
        v->pid = fork();
448 22380
        assert(v->pid >= 0);
449 22380
        if (v->pid == 0) {
450 11190
                AZ(dup2(v->fds[0], 0));
451 11190
                assert(dup2(v->fds[3], 1) == 1);
452 11190
                assert(dup2(1, 2) == 2);
453 11190
                closefd(&v->fds[0]);
454 11190
                closefd(&v->fds[1]);
455 11190
                closefd(&v->fds[2]);
456 11190
                closefd(&v->fds[3]);
457 11190
                VSUB_closefrom(STDERR_FILENO + 1);
458 11190
                AZ(execl("/bin/sh", "/bin/sh", "-c", VSB_data(vsb), (char*)0));
459 0
                exit(1);
460
        } else {
461 11190
                vtc_log(v->vl, 3, "PID: %ld", (long)v->pid);
462 11190
                macro_def(v->vl, v->name, "pid", "%ld", (long)v->pid);
463 11190
                macro_def(v->vl, v->name, "name", "%s", v->workdir);
464
        }
465 11190
        closefd(&v->fds[0]);
466 11190
        closefd(&v->fds[3]);
467 11190
        v->fds[0] = v->fds[2];
468 11190
        v->fds[2] = v->fds[3] = -1;
469 11190
        VSB_destroy(&vsb);
470 11190
        AZ(pthread_create(&v->tp, NULL, varnish_thread, v));
471
472
        /* Wait for the varnish to call home */
473 11190
        memset(fd, 0, sizeof fd);
474 11190
        fd[0].fd = v->cli_fd;
475 11190
        fd[0].events = POLLIN;
476 11190
        fd[1].fd = v->fds[1];
477 11190
        fd[1].events = POLLIN;
478 11190
        i = poll(fd, 2, vtc_maxdur * 1000 / 3);
479 22380
        vtc_log(v->vl, 4, "CLIPOLL %d 0x%x 0x%x",
480 11190
            i, fd[0].revents, fd[1].revents);
481 11190
        if (i == 0)
482 0
                vtc_fatal(v->vl, "FAIL timeout waiting for CLI connection");
483 11190
        if (fd[1].revents & POLLHUP)
484 0
                vtc_fatal(v->vl, "FAIL debug pipe closed");
485 11190
        if (!(fd[0].revents & POLLIN))
486 0
                vtc_fatal(v->vl, "FAIL CLI connection wait failure");
487 11190
        nfd = accept(v->cli_fd, NULL, NULL);
488 11190
        if (nfd < 0) {
489 0
                closefd(&v->cli_fd);
490 0
                vtc_fatal(v->vl, "FAIL no CLI connection accepted");
491
        }
492
493 11190
        closefd(&v->cli_fd);
494 11190
        v->cli_fd = nfd;
495
496 11190
        vtc_log(v->vl, 3, "CLI connection fd = %d", v->cli_fd);
497 11190
        assert(v->cli_fd >= 0);
498
499
        /* Receive the banner or auth response */
500 11190
        u = varnish_ask_cli(v, NULL, &r);
501 11190
        if (vtc_error)
502 0
                return;
503 11190
        if (u != CLIS_AUTH)
504 0
                vtc_fatal(v->vl, "CLI auth demand expected: %u %s", u, r);
505
506 11190
        bprintf(abuf, "%s/_.secret", v->workdir);
507 11190
        nfd = open(abuf, O_RDONLY);
508 11190
        assert(nfd >= 0);
509
510 11190
        assert(sizeof abuf >= CLI_AUTH_RESPONSE_LEN + 7);
511 11190
        strcpy(abuf, "auth ");
512 11190
        VCLI_AuthResponse(nfd, r, abuf + 5);
513 11190
        closefd(&nfd);
514 11190
        free(r);
515 11190
        r = NULL;
516 11190
        strcat(abuf, "\n");
517
518 11190
        u = varnish_ask_cli(v, abuf, &r);
519 11190
        if (vtc_error)
520 0
                return;
521 11190
        if (u != CLIS_OK)
522 0
                vtc_fatal(v->vl, "CLI auth command failed: %u %s", u, r);
523 11190
        free(r);
524
525 11190
        v->vsm_vsc = VSM_New();
526 11190
        AN(v->vsm_vsc);
527 11190
        v->vsc = VSC_New();
528 11190
        AN(v->vsc);
529 11190
        assert(VSM_Arg(v->vsm_vsc, 'n', v->workdir) > 0);
530 11190
        AZ(VSM_Attach(v->vsm_vsc, -1));
531
532 11190
        v->vsm_vsl = VSM_New();
533 11190
        assert(VSM_Arg(v->vsm_vsl, 'n', v->workdir) > 0);
534 11190
        AZ(VSM_Attach(v->vsm_vsl, -1));
535
536 11190
        AZ(pthread_create(&v->tp_vsl, NULL, varnishlog_thread, v));
537 11190
}
538
539
/**********************************************************************
540
 * Start a Varnish
541
 */
542
543
static void
544 11010
varnish_start(struct varnish *v)
545
{
546
        enum VCLI_status_e u;
547 11010
        char *resp = NULL, *h, *p;
548
549 11010
        if (v->cli_fd < 0)
550 120
                varnish_launch(v);
551 11010
        if (vtc_error)
552 0
                return;
553 11010
        vtc_log(v->vl, 2, "Start");
554 11010
        u = varnish_ask_cli(v, "start", &resp);
555 11010
        if (vtc_error)
556 0
                return;
557 11010
        if (u != CLIS_OK)
558 0
                vtc_fatal(v->vl, "CLI start command failed: %u %s", u, resp);
559 11010
        wait_running(v);
560 11010
        free(resp);
561 11010
        resp = NULL;
562 11010
        u = varnish_ask_cli(v, "debug.xid 999", &resp);
563 11010
        if (vtc_error)
564 0
                return;
565 11010
        if (u != CLIS_OK)
566 0
                vtc_fatal(v->vl, "CLI debug.xid command failed: %u %s",
567 0
                    u, resp);
568 11010
        free(resp);
569 11010
        resp = NULL;
570 11010
        u = varnish_ask_cli(v, "debug.listen_address", &resp);
571 11010
        if (vtc_error)
572 0
                return;
573 11010
        if (u != CLIS_OK)
574 0
                vtc_fatal(v->vl,
575 0
                    "CLI debug.listen_address command failed: %u %s", u, resp);
576 11010
        h = resp;
577 11010
        p = strchr(h, '\n');
578 11010
        if (p != NULL)
579 11010
                *p = '\0';
580 11010
        p = strchr(h, ' ');
581 11010
        AN(p);
582 11010
        *p++ = '\0';
583 11010
        vtc_log(v->vl, 2, "Listen on %s %s", h, p);
584 11010
        macro_def(v->vl, v->name, "addr", "%s", h);
585 11010
        macro_def(v->vl, v->name, "port", "%s", p);
586 11010
        macro_def(v->vl, v->name, "sock", "%s %s", h, p);
587 11010
        free(resp);
588
        /* Wait for vsl logging to get underway */
589 11010
        while (v->vsl_rec == 0)
590 0
                VTIM_sleep(.1);
591 11010
}
592
593
/**********************************************************************
594
 * Stop a Varnish
595
 */
596
597
static void
598 11730
varnish_stop(struct varnish *v)
599
{
600 11730
        if (v->cli_fd < 0)
601 0
                varnish_launch(v);
602 11730
        if (vtc_error)
603 0
                return;
604 11730
        vtc_log(v->vl, 2, "Stop");
605 11730
        (void)varnish_ask_cli(v, "stop", NULL);
606 11730
        wait_stopped(v);
607 11730
}
608
609
/**********************************************************************
610
 * Cleanup
611
 */
612
613
static void
614 11190
varnish_cleanup(struct varnish *v)
615
{
616
        void *p;
617
618
        /* Close the CLI connection */
619 11190
        closefd(&v->cli_fd);
620
621
        /* Close the STDIN connection. */
622 11190
        closefd(&v->fds[1]);
623
624
        /* Wait until STDOUT+STDERR closes */
625 11190
        AZ(pthread_join(v->tp, &p));
626 11190
        closefd(&v->fds[0]);
627
628
        /* Pick up the VSL thread */
629 11190
        AZ(pthread_join(v->tp_vsl, &p));
630
631 11190
        vtc_wait4(v->vl, v->pid, v->expect_exit, 0, 0);
632 11190
        v->pid = 0;
633 11190
}
634
635
/**********************************************************************
636
 * Wait for a Varnish
637
 */
638
639
static void
640 11145
varnish_wait(struct varnish *v)
641
{
642 11145
        if (v->cli_fd < 0)
643 0
                return;
644
645 11145
        vtc_log(v->vl, 2, "Wait");
646
647 11145
        if (!vtc_error) {
648
                /* Do a backend.list to log if child is still running */
649 11145
                (void)varnish_ask_cli(v, "backend.list", NULL);
650 11145
        }
651
652
        /* Then stop it */
653 11145
        varnish_stop(v);
654
655 11145
        if (varnish_ask_cli(v, "panic.clear", NULL) != CLIS_CANT)
656 0
                vtc_fatal(v->vl, "Unexpected panic");
657
658 11145
        varnish_cleanup(v);
659 11145
}
660
661
662
/**********************************************************************
663
 * Ask a CLI JSON question
664
 */
665
666
static void
667 540
varnish_cli_json(struct varnish *v, const char *cli)
668
{
669
        enum VCLI_status_e u;
670 540
        char *resp = NULL;
671
        const char *errptr;
672
        struct vjsn *vj;
673
674 540
        if (v->cli_fd < 0)
675 0
                varnish_launch(v);
676 540
        if (vtc_error)
677 0
                return;
678 540
        u = varnish_ask_cli(v, cli, &resp);
679 540
        vtc_log(v->vl, 2, "CLI %03u <%s>", u, cli);
680 540
        if (u != CLIS_OK)
681 0
                vtc_fatal(v->vl,
682 0
                    "FAIL CLI response %u expected %u", u, CLIS_OK);
683 540
        vj = vjsn_parse(resp, &errptr);
684 540
        if (vj == NULL)
685 0
                vtc_fatal(v->vl, "FAIL CLI, not good JSON: %s", errptr);
686 540
        vjsn_delete(&vj);
687 540
        free(resp);
688 540
}
689
690
/**********************************************************************
691
 * Ask a CLI question
692
 */
693
694
static void
695 13980
varnish_cli(struct varnish *v, const char *cli, unsigned exp, const char *re)
696
{
697
        enum VCLI_status_e u;
698 13980
        vre_t *vre = NULL;
699 13980
        char *resp = NULL;
700
        const char *errptr;
701
        int err;
702
703 13980
        if (re != NULL) {
704 975
                vre = VRE_compile(re, 0, &errptr, &err);
705 975
                if (vre == NULL)
706 0
                        vtc_fatal(v->vl, "Illegal regexp");
707 975
        }
708 13980
        if (v->cli_fd < 0)
709 510
                varnish_launch(v);
710 13980
        if (vtc_error) {
711 0
                if (vre != NULL)
712 0
                        VRE_free(&vre);
713 0
                return;
714
        }
715 13980
        u = varnish_ask_cli(v, cli, &resp);
716 13980
        vtc_log(v->vl, 2, "CLI %03u <%s>", u, cli);
717 13980
        if (exp != 0 && exp != (unsigned)u)
718 0
                vtc_fatal(v->vl, "FAIL CLI response %u expected %u", u, exp);
719 13980
        if (vre != NULL) {
720 975
                err = VRE_exec(vre, resp, strlen(resp), 0, 0, NULL, 0, NULL);
721 975
                if (err < 1)
722 0
                        vtc_fatal(v->vl, "Expect failed (%d)", err);
723 975
                VRE_free(&vre);
724 975
        }
725 13980
        free(resp);
726 13980
}
727
728
/**********************************************************************
729
 * Load a VCL program
730
 */
731
732
static void
733 5880
varnish_vcl(struct varnish *v, const char *vcl, int fail, char **resp)
734
{
735
        struct vsb *vsb;
736
        enum VCLI_status_e u;
737
738 5880
        if (v->cli_fd < 0)
739 1800
                varnish_launch(v);
740 5880
        if (vtc_error)
741 0
                return;
742 5880
        vsb = VSB_new_auto();
743 5880
        AN(vsb);
744
745 11760
        VSB_printf(vsb, "vcl.inline vcl%d << %s\nvcl %.1f;\n%s\n%s\n",
746 5880
            ++v->vcl_nbr, NONSENSE, v->syntax, vcl, NONSENSE);
747 5880
        AZ(VSB_finish(vsb));
748
749 5880
        u = varnish_ask_cli(v, VSB_data(vsb), resp);
750 5880
        if (u == CLIS_OK) {
751 2445
                VSB_clear(vsb);
752 2445
                VSB_printf(vsb, "vcl.use vcl%d", v->vcl_nbr);
753 2445
                AZ(VSB_finish(vsb));
754 2445
                u = varnish_ask_cli(v, VSB_data(vsb), NULL);
755 2445
        }
756 5880
        if (u == CLIS_OK && fail) {
757 0
                VSB_destroy(&vsb);
758 0
                vtc_fatal(v->vl, "VCL compilation succeeded expected failure");
759 5880
        } else if (u != CLIS_OK && !fail) {
760 0
                VSB_destroy(&vsb);
761 0
                vtc_fatal(v->vl, "VCL compilation failed expected success");
762 5880
        } else if (fail)
763 3435
                vtc_log(v->vl, 2, "VCL compilation failed (as expected)");
764 5880
        VSB_destroy(&vsb);
765 5880
}
766
767
/**********************************************************************
768
 * Load a VCL program prefixed by backend decls for our servers
769
 */
770
771
static void
772 10815
varnish_vclbackend(struct varnish *v, const char *vcl)
773
{
774
        struct vsb *vsb, *vsb2;
775
        enum VCLI_status_e u;
776
777 10815
        if (v->cli_fd < 0)
778 8760
                varnish_launch(v);
779 10815
        if (vtc_error)
780 0
                return;
781 10815
        vsb = VSB_new_auto();
782 10815
        AN(vsb);
783
784 10815
        vsb2 = VSB_new_auto();
785 10815
        AN(vsb2);
786
787 10815
        VSB_printf(vsb2, "vcl %.1f;\n", v->syntax);
788
789 10815
        cmd_server_gen_vcl(vsb2);
790
791 10815
        AZ(VSB_finish(vsb2));
792
793 21630
        VSB_printf(vsb, "vcl.inline vcl%d << %s\n%s\n%s\n%s\n",
794 10815
            ++v->vcl_nbr, NONSENSE, VSB_data(vsb2), vcl, NONSENSE);
795 10815
        AZ(VSB_finish(vsb));
796
797 10815
        u = varnish_ask_cli(v, VSB_data(vsb), NULL);
798 10815
        if (u != CLIS_OK) {
799 0
                VSB_destroy(&vsb);
800 0
                VSB_destroy(&vsb2);
801 0
                vtc_fatal(v->vl, "FAIL VCL does not compile");
802
        }
803 10815
        VSB_clear(vsb);
804 10815
        VSB_printf(vsb, "vcl.use vcl%d", v->vcl_nbr);
805 10815
        AZ(VSB_finish(vsb));
806 10815
        u = varnish_ask_cli(v, VSB_data(vsb), NULL);
807 10815
        assert(u == CLIS_OK);
808 10815
        VSB_destroy(&vsb);
809 10815
        VSB_destroy(&vsb2);
810 10815
}
811
812
/**********************************************************************
813
 */
814
815
struct dump_priv {
816
        const char *arg;
817
        const struct varnish *v;
818
};
819
820
static int
821 35126
do_stat_dump_cb(void *priv, const struct VSC_point * const pt)
822
{
823
        const struct varnish *v;
824
        struct dump_priv *dp;
825
        uint64_t u;
826
827 35126
        if (pt == NULL)
828 0
                return (0);
829 35126
        dp = priv;
830 35126
        v = dp->v;
831
832 35126
        if (strcmp(pt->ctype, "uint64_t"))
833 0
                return (0);
834 35126
        u = *pt->ptr;
835
836 35126
        if (strcmp(dp->arg, "*")) {
837 25046
                if (fnmatch(dp->arg, pt->name, 0))
838 24033
                        return (0);
839 1013
        }
840
841 11093
        vtc_log(v->vl, 4, "VSC %s %ju",  pt->name, (uintmax_t)u);
842 11093
        return (0);
843 35126
}
844
845
static void
846 105
varnish_vsc(const struct varnish *v, const char *arg)
847
{
848
        struct dump_priv dp;
849
850 105
        memset(&dp, 0, sizeof dp);
851 105
        dp.v = v;
852 105
        dp.arg = arg;
853 105
        (void)VSM_Status(v->vsm_vsc);
854 105
        (void)VSC_Iter(v->vsc, v->vsm_vsc, do_stat_dump_cb, &dp);
855 105
}
856
857
/**********************************************************************
858
 * Check statistics
859
 */
860
861
struct stat_priv {
862
        char target_pattern[256];
863
        uintmax_t val;
864
        const struct varnish *v;
865
};
866
867
static int
868 2785986
do_expect_cb(void *priv, const struct VSC_point * const pt)
869
{
870 2785986
        struct stat_priv *sp = priv;
871
872 2785986
        if (pt == NULL)
873 0
                return (0);
874
875 2785986
        if (fnmatch(sp->target_pattern, pt->name, 0))
876 2776089
                return (0);
877
878 9897
        AZ(strcmp(pt->ctype, "uint64_t"));
879 9897
        AN(pt->ptr);
880 9897
        sp->val = *pt->ptr;
881 9897
        return (1);
882 2785986
}
883
884
/**********************************************************************
885
 */
886
887
static void
888 9675
varnish_expect(const struct varnish *v, char * const *av)
889
{
890
        uint64_t ref;
891
        int good;
892
        char *r;
893
        char *p;
894 9675
        int i, not = 0;
895
        struct stat_priv sp;
896
897 9675
        r = av[0];
898 9675
        if (r[0] == '!') {
899 75
                not = 1;
900 75
                r++;
901 75
                AZ(av[1]);
902 75
        } else {
903 9600
                AN(av[1]);
904 9600
                AN(av[2]);
905
        }
906 9675
        p = strrchr(r, '.');
907 9675
        if (p == NULL) {
908 5820
                bprintf(sp.target_pattern, "MAIN.%s", r);
909 5820
        } else {
910 3855
                bprintf(sp.target_pattern, "%s", r);
911
        }
912
913 9675
        sp.val = 0;
914 9675
        sp.v = v;
915 9675
        ref = 0;
916 9675
        good = 0;
917 13722
        for (i = 0; i < 50; i++, (void)usleep(100000)) {
918 13647
                (void)VSM_Status(v->vsm_vsc);
919 13647
                good = VSC_Iter(v->vsc, v->vsm_vsc, do_expect_cb, &sp);
920 13647
                if (!good) {
921 3750
                        good = -2;
922 3750
                        continue;
923
                }
924
925 9897
                if (not)
926 0
                        vtc_fatal(v->vl, "Found (not expected): %s", av[0]+1);
927
928 9897
                good = 0;
929 9897
                ref = strtoumax(av[2], &p, 0);
930 9897
                if (ref == UINTMAX_MAX || *p)
931 0
                        vtc_fatal(v->vl, "Syntax error in number (%s)", av[2]);
932 9897
                if      (!strcmp(av[1], "==")) { if (sp.val == ref) good = 1; }
933 1408
                else if (!strcmp(av[1], "!=")) { if (sp.val != ref) good = 1; }
934 1378
                else if (!strcmp(av[1], ">"))  { if (sp.val > ref)  good = 1; }
935 778
                else if (!strcmp(av[1], "<"))  { if (sp.val < ref)  good = 1; }
936 285
                else if (!strcmp(av[1], ">=")) { if (sp.val >= ref) good = 1; }
937 0
                else if (!strcmp(av[1], "<=")) { if (sp.val <= ref) good = 1; }
938
                else
939 0
                        vtc_fatal(v->vl, "comparison %s unknown", av[1]);
940 9897
                if (good)
941 9600
                        break;
942 297
        }
943 9675
        if (good == -1) {
944 0
                vtc_fatal(v->vl, "VSM error: %s", VSM_Error(v->vsm_vsc));
945
        }
946 9675
        if (good == -2) {
947 75
                if (not) {
948 150
                        vtc_log(v->vl, 2, "not found (as expected): %s",
949 75
                            av[0] + 1);
950 75
                        return;
951
                }
952 0
                vtc_fatal(v->vl, "stats field %s unknown", av[0]);
953
        }
954
955 9600
        if (good == 1) {
956 19200
                vtc_log(v->vl, 2, "as expected: %s (%ju) %s %s",
957 9600
                    av[0], sp.val, av[1], av[2]);
958 9600
        } else {
959 0
                vtc_fatal(v->vl, "Not true: %s (%ju) %s %s (%ju)",
960 0
                    av[0], (uintmax_t)sp.val, av[1], av[2], (uintmax_t)ref);
961
        }
962 9675
}
963
964
/* SECTION: varnish varnish
965
 *
966
 * Define and interact with varnish instances.
967
 *
968
 * To define a Varnish server, you'll use this syntax::
969
 *
970
 *      varnish vNAME [-arg STRING] [-vcl STRING] [-vcl+backend STRING]
971
 *              [-errvcl STRING STRING] [-jail STRING] [-proto PROXY]
972
 *
973
 * The first ``varnish vNAME`` invocation will start the varnishd master
974
 * process in the background, waiting for the ``-start`` switch to actually
975
 * start the child.
976
 *
977
 * Types used in the description below:
978
 *
979
 * PATTERN
980
 *         is a 'glob' style pattern (ie: fnmatch(3)) as used in shell filename
981
 *         expansion.
982
 *
983
 * Arguments:
984
 *
985
 * vNAME
986
 *         Identify the Varnish server with a string, it must starts with 'v'.
987
 *
988
 * \-arg STRING
989
 *         Pass an argument to varnishd, for example "-h simple_list".
990
 *
991
 * \-vcl STRING
992
 *         Specify the VCL to load on this Varnish instance. You'll probably
993
 *         want to use multi-lines strings for this ({...}).
994
 *
995
 * \-vcl+backend STRING
996
 *         Do the exact same thing as -vcl, but adds the definition block of
997
 *         known backends (ie. already defined).
998
 *
999
 * \-errvcl STRING1 STRING2
1000
 *         Load STRING2 as VCL, expecting it to fail, and Varnish to send an
1001
 *         error string matching STRING2
1002
 *
1003
 * \-jail STRING
1004
 *         Look at ``man varnishd`` (-j) for more information.
1005
 *
1006
 * \-proto PROXY
1007
 *         Have Varnish use the proxy protocol. Note that PROXY here is the
1008
 *         actual string.
1009
 *
1010
 * You can decide to start the Varnish instance and/or wait for several events::
1011
 *
1012
 *         varnish vNAME [-start] [-wait] [-wait-running] [-wait-stopped]
1013
 *
1014
 * \-start
1015
 *         Start the child process.
1016
 *
1017
 * \-stop
1018
 *         Stop the child process.
1019
 *
1020
 * \-syntax
1021
 *         Set the VCL syntax level for this command (default: 4.1)
1022
 *
1023
 * \-wait
1024
 *         Wait for that instance to terminate.
1025
 *
1026
 * \-wait-running
1027
 *         Wait for the Varnish child process to be started.
1028
 *
1029
 * \-wait-stopped
1030
 *         Wait for the Varnish child process to stop.
1031
 *
1032
 * \-cleanup
1033
 *         Once Varnish is stopped, clean everything after it. This is only used
1034
 *         in very few tests and you should never need it.
1035
 *
1036
 * Once Varnish is started, you can talk to it (as you would through
1037
 * ``varnishadm``) with these additional switches::
1038
 *
1039
 *         varnish vNAME [-cli STRING] [-cliok STRING] [-clierr STRING]
1040
 *                       [-clijson STRING] [-expect STRING OP NUMBER]
1041
 *
1042
 * \-cli STRING|-cliok STRING|-clierr STATUS STRING|-cliexpect REGEXP STRING
1043
 *         All four of these will send STRING to the CLI, the only difference
1044
 *         is what they expect the result to be. -cli doesn't expect
1045
 *         anything, -cliok expects 200, -clierr expects STATUS, and
1046
 *         -cliexpect expects the REGEXP to match the returned response.
1047
 *
1048
 * \-clijson STRING
1049
 *         Send STRING to the CLI, expect success (CLIS_OK/200) and check
1050
 *         that the response is parsable JSON.
1051
 *
1052
 * \-expect PATTERN OP NUMBER
1053
 *         Look into the VSM and make sure the first VSC counter identified by
1054
 *         PATTERN has a correct value. OP can be ==, >, >=, <, <=. For
1055
 *         example::
1056
 *
1057
 *                 varnish v1 -expect SM?.s1.g_space > 1000000
1058
 * \-expectexit NUMBER
1059
 *         Expect varnishd to exit(3) with this value
1060
 *
1061
 * \-vsc PATTERN
1062
 *         Dump VSC counters matching PATTERN.
1063
 *
1064
 * \-vsl_catchup
1065
 *         Wait until the logging thread has idled to make sure that all
1066
 *         the generated log is flushed
1067
 */
1068
1069
void
1070 55455
cmd_varnish(CMD_ARGS)
1071
{
1072
        struct varnish *v, *v2;
1073
1074 55455
        (void)priv;
1075 55455
        (void)cmd;
1076
1077 55455
        if (av == NULL) {
1078
                /* Reset and free */
1079 23190
                VTAILQ_FOREACH_SAFE(v, &varnishes, list, v2) {
1080 11190
                        if (v->cli_fd >= 0)
1081 11070
                                varnish_wait(v);
1082 11190
                        VTAILQ_REMOVE(&varnishes, v, list);
1083 11190
                        varnish_delete(v);
1084 11190
                }
1085 12000
                return;
1086
        }
1087
1088 43455
        AZ(strcmp(av[0], "varnish"));
1089 43455
        av++;
1090
1091 43455
        VTC_CHECK_NAME(vl, av[0], "Varnish", 'v');
1092 44325
        VTAILQ_FOREACH(v, &varnishes, list)
1093 33135
                if (!strcmp(v->name, av[0]))
1094 32265
                        break;
1095 43455
        if (v == NULL)
1096 11190
                v = varnish_new(av[0]);
1097 43455
        av++;
1098 43455
        v->syntax = 4.1;
1099
1100 102435
        for (; *av != NULL; av++) {
1101 58980
                if (vtc_error)
1102 0
                        break;
1103 58980
                if (!strcmp(*av, "-arg")) {
1104 3765
                        AN(av[1]);
1105 3765
                        AZ(v->pid);
1106 3765
                        VSB_cat(v->args, " ");
1107 3765
                        VSB_cat(v->args, av[1]);
1108 3765
                        if (av[1][0] == '-' && av[1][1] == 'a')
1109 405
                                v->has_a_arg = 1;
1110 3765
                        av++;
1111 3765
                        continue;
1112
                }
1113 55215
                if (!strcmp(*av, "-cleanup")) {
1114 45
                        AZ(av[1]);
1115 45
                        varnish_cleanup(v);
1116 45
                        continue;
1117
                }
1118 55170
                if (!strcmp(*av, "-cli")) {
1119 720
                        AN(av[1]);
1120 720
                        varnish_cli(v, av[1], 0, NULL);
1121 720
                        av++;
1122 720
                        continue;
1123
                }
1124 54450
                if (!strcmp(*av, "-clierr")) {
1125 1770
                        AN(av[1]);
1126 1770
                        AN(av[2]);
1127 1770
                        varnish_cli(v, av[2], atoi(av[1]), NULL);
1128 1770
                        av += 2;
1129 1770
                        continue;
1130
                }
1131 52680
                if (!strcmp(*av, "-cliexpect")) {
1132 975
                        AN(av[1]);
1133 975
                        AN(av[2]);
1134 975
                        varnish_cli(v, av[2], 0, av[1]);
1135 975
                        av += 2;
1136 975
                        continue;
1137
                }
1138 51705
                if (!strcmp(*av, "-clijson")) {
1139 540
                        AN(av[1]);
1140 540
                        varnish_cli_json(v, av[1]);
1141 540
                        av++;
1142 540
                        continue;
1143
                }
1144 51165
                if (!strcmp(*av, "-cliok")) {
1145 10515
                        AN(av[1]);
1146 10515
                        varnish_cli(v, av[1], (unsigned)CLIS_OK, NULL);
1147 10515
                        av++;
1148 10515
                        continue;
1149
                }
1150 40650
                if (!strcmp(*av, "-errvcl")) {
1151 3435
                        char *r = NULL;
1152 3435
                        AN(av[1]);
1153 3435
                        AN(av[2]);
1154 3435
                        varnish_vcl(v, av[2], 1, &r);
1155 3435
                        if (strstr(r, av[1]) == NULL)
1156 0
                                vtc_fatal(v->vl,
1157
                                    "Did not find expected string: (\"%s\")",
1158 0
                                    av[1]);
1159
                        else
1160 6870
                                vtc_log(v->vl, 3,
1161
                                    "Found expected string: (\"%s\")",
1162 3435
                                    av[1]);
1163 3435
                        free(r);
1164 3435
                        av += 2;
1165 3435
                        continue;
1166
                }
1167 37215
                if (!strcmp(*av, "-expect")) {
1168 9675
                        av++;
1169 9675
                        varnish_expect(v, av);
1170 9675
                        av += 2;
1171 9675
                        continue;
1172
                }
1173 27540
                if (!strcmp(*av, "-expectexit")) {
1174 90
                        v->expect_exit = strtoul(av[1], NULL, 0);
1175 90
                        av++;
1176 90
                        continue;
1177
                }
1178 27450
                if (!strcmp(*av, "-jail")) {
1179 60
                        AN(av[1]);
1180 60
                        AZ(v->pid);
1181 60
                        REPLACE(v->jail, av[1]);
1182 60
                        av++;
1183 60
                        continue;
1184
                }
1185 27390
                if (!strcmp(*av, "-proto")) {
1186 120
                        AN(av[1]);
1187 120
                        AZ(v->pid);
1188 120
                        REPLACE(v->proto, av[1]);
1189 120
                        av++;
1190 120
                        continue;
1191
                }
1192 27270
                if (!strcmp(*av, "-start")) {
1193 11010
                        varnish_start(v);
1194 11010
                        continue;
1195
                }
1196 16260
                if (!strcmp(*av, "-stop")) {
1197 585
                        varnish_stop(v);
1198 585
                        continue;
1199
                }
1200 15675
                if (!strcmp(*av, "-syntax")) {
1201 735
                        AN(av[1]);
1202 735
                        v->syntax = strtod(av[1], NULL);
1203 735
                        av++;
1204 735
                        continue;
1205
                }
1206 14940
                if (!strcmp(*av, "-vcl")) {
1207 2445
                        AN(av[1]);
1208 2445
                        varnish_vcl(v, av[1], 0, NULL);
1209 2445
                        av++;
1210 2445
                        continue;
1211
                }
1212 12495
                if (!strcmp(*av, "-vcl+backend")) {
1213 10815
                        AN(av[1]);
1214 10815
                        varnish_vclbackend(v, av[1]);
1215 10815
                        av++;
1216 10815
                        continue;
1217
                }
1218 1680
                if (!strcmp(*av, "-vsc")) {
1219 105
                        AN(av[1]);
1220 105
                        varnish_vsc(v, av[1]);
1221 105
                        av++;
1222 105
                        continue;
1223
                }
1224 1575
                if (!strcmp(*av, "-wait-stopped")) {
1225 30
                        wait_stopped(v);
1226 30
                        continue;
1227
                }
1228 1545
                if (!strcmp(*av, "-wait-running")) {
1229 45
                        wait_running(v);
1230 45
                        continue;
1231
                }
1232 1500
                if (!strcmp(*av, "-wait")) {
1233 75
                        varnish_wait(v);
1234 75
                        continue;
1235
                }
1236 1425
                if (!strcmp(*av, "-vsl_catchup")) {
1237 1425
                        vsl_catchup(v);
1238 1425
                        continue;
1239
                }
1240 0
                vtc_fatal(v->vl, "Unknown varnish argument: %s", *av);
1241
        }
1242 55455
}
1243
1244
#endif /* VTEST_WITH_VTC_VARNISH */