Blob


1 /*
2 * Copyright (c) 2021, 2022 Omar Polo <op@omarpolo.com>
3 *
4 * Permission to use, copy, modify, and distribute this software for any
5 * purpose with or without fee is hereby granted, provided that the above
6 * copyright notice and this permission notice appear in all copies.
7 *
8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15 */
17 #include "compat.h"
19 #include <sys/socket.h>
20 #include <sys/stat.h>
21 #include <sys/wait.h>
23 #include <assert.h>
24 #include <endian.h>
25 #include <errno.h>
26 #include <fcntl.h>
27 #include <inttypes.h>
28 #include <poll.h>
29 #include <pwd.h>
30 #include <regex.h>
31 #include <signal.h>
32 #include <stdio.h>
33 #include <stdlib.h>
34 #include <string.h>
35 #include <syslog.h>
36 #include <unistd.h>
38 #include "client.h"
39 #include "kami.h"
40 #include "kamid.h"
41 #include "log.h"
42 #include "script.h"
43 #include "utils.h"
45 #define DEBUG 0
47 #ifndef INFTIM
48 #define INFTIM -1
49 #endif
51 int verbose;
53 static const char *argv0;
54 static const char *dir;
55 static uid_t uid;
57 static uint8_t *lastmsg;
59 static struct imsgbuf ibuf;
60 static int ibuf_inuse;
61 static int child_out = -1;
63 static struct procs procs = TAILQ_HEAD_INITIALIZER(procs);
64 static struct tests tests = TAILQ_HEAD_INITIALIZER(tests);
66 static int ntests;
68 static struct opstacks blocks = TAILQ_HEAD_INITIALIZER(blocks);
69 static struct opstacks args = TAILQ_HEAD_INITIALIZER(args);
71 #define STACK_HEIGHT 64
72 static struct value vstack[STACK_HEIGHT];
73 static int stackh;
75 static struct envs envs = TAILQ_HEAD_INITIALIZER(envs);
77 static struct value v_false = {.type = V_NUM, .v = {.num = 0}};
78 static struct value v_true = {.type = V_NUM, .v = {.num = 1}};
80 static uint8_t lasttag;
82 static int debug;
83 static int syntaxcheck;
85 static const char *filler;
87 static inline void
88 before_printing(void)
89 {
90 if (filler != NULL) {
91 printf("%s", filler);
92 filler = NULL;
93 }
94 }
96 static inline void
97 check_for_output(void)
98 {
99 static char buf[BUFSIZ];
100 struct pollfd pfd;
101 ssize_t r;
103 pfd.fd = child_out;
104 pfd.events = POLLIN;
105 if (poll(&pfd, 1, 0) == -1)
106 fatal("poll");
108 if (!(pfd.revents & POLLIN))
109 return;
111 for (;;) {
112 if ((r = read(child_out, buf, sizeof(buf))) == -1) {
113 if (errno == EAGAIN)
114 break;
115 fatal("read");
117 if (r == 0)
118 break;
119 before_printing();
120 fwrite(buf, 1, r, stdout);
124 static inline void
125 peekn(int depth, struct value *v)
127 if (depth > stackh)
128 errx(1, "can't peek the stack at %d: underflow",
129 depth);
130 memcpy(v, &vstack[stackh - depth], sizeof(*v));
132 #if DEBUG
133 printf("peeking(%d) ", depth); pp_val(v); printf("\n");
134 #endif
137 static inline void
138 popv(struct value *v)
140 if (stackh == 0)
141 errx(1, "can't pop the stack: underflow");
142 memcpy(v, &vstack[--stackh], sizeof(*v));
144 #if DEBUG
145 printf("popping "); pp_val(v); printf("\n");
146 #endif
149 static inline void
150 popvn(int n)
152 struct value v;
154 while (n-- > 0)
155 popv(&v);
158 static inline void
159 pushv(struct value *v)
161 if (stackh == STACK_HEIGHT)
162 errx(1, "can't push the stack: overflow");
164 #if DEBUG
165 printf("pushing "); pp_val(v); printf("\n");
166 #endif
168 memcpy(&vstack[stackh++], v, sizeof(*v));
171 static inline void
172 pushbool(int n)
174 pushv(n ? &v_true : &v_false);
177 static inline void
178 pushnum(int64_t n)
180 struct value v;
182 v.type = V_NUM;
183 v.v.num = n;
184 pushv(&v);
187 static inline struct opstack *
188 pushstack(struct opstacks *stack)
190 struct opstack *ops;
192 ops = xcalloc(1, sizeof(*ops));
193 TAILQ_INSERT_HEAD(stack, ops, entry);
194 return ops;
197 static inline struct opstack *
198 peek(struct opstacks *stack)
200 if (TAILQ_EMPTY(stack))
201 errx(1, "%s: args underflow", __func__);
203 return TAILQ_FIRST(stack);
206 static inline struct op *
207 finalize(struct opstacks *stack, int *argc)
209 struct opstack *ops;
210 struct op *op;
212 if (TAILQ_EMPTY(stack))
213 errx(1, "%s: args underflow", __func__);
215 ops = peek(stack);
216 TAILQ_REMOVE(&args, ops, entry);
217 op = ops->base.next;
219 if (argc != NULL)
220 *argc = ops->counter;
222 free(ops);
223 return op;
226 static inline void
227 push(struct opstacks *stack, struct op *op)
229 struct opstack *ops;
231 ops = peek(stack);
232 if (ops->last == NULL) {
233 ops->base.next = op;
234 ops->last = op;
235 } else {
236 ops->last->next = op;
237 ops->last = op;
240 ops->counter++;
243 static inline void
244 pushenv(void)
246 struct env *e;
248 e = xcalloc(1, sizeof(*e));
249 TAILQ_INSERT_HEAD(&envs, e, entry);
252 static inline struct env *
253 currentenv(void)
255 assert(!TAILQ_EMPTY(&envs));
256 return TAILQ_FIRST(&envs);
259 static void
260 popenv(void)
262 struct env *e;
263 struct binding *b, *tb;
265 e = currentenv();
266 TAILQ_REMOVE(&envs, e, entry);
268 TAILQ_FOREACH_SAFE(b, &e->bindings, entry, tb)
269 free(b);
271 free(e);
274 static inline int
275 setvar(char *sym, struct op *op)
277 struct binding *b;
278 struct env *e;
279 int ret, height;
281 height = stackh;
282 if ((ret = eval(op)) != EVAL_OK)
283 return ret;
285 if (stackh != height + 1) {
286 before_printing();
287 printf("trying to assign to `%s' a void value: ", sym);
288 pp_op(op);
289 printf("\n");
290 return EVAL_ERR;
293 b = xcalloc(1, sizeof(*b));
294 b->name = sym;
295 popv(&b->val);
297 e = TAILQ_FIRST(&envs);
298 TAILQ_INSERT_HEAD(&e->bindings, b, entry);
300 return EVAL_OK;
303 static inline void
304 setvar_raw(char *sym, struct op *op)
306 struct binding *b;
307 struct env *e;
309 b = xcalloc(1, sizeof(*b));
310 b->name = sym;
311 b->raw = op;
313 e = TAILQ_FIRST(&envs);
314 TAILQ_INSERT_HEAD(&e->bindings, b, entry);
317 static inline int
318 getvar(const char *sym, struct value *v)
320 struct env *e;
321 struct binding *b;
323 TAILQ_FOREACH(e, &envs, entry) {
324 TAILQ_FOREACH(b, &e->bindings, entry) {
325 if (!strcmp(sym, b->name)) {
326 memcpy(v, &b->val, sizeof(*v));
327 return EVAL_OK;
332 before_printing();
333 fprintf(stderr, "unbound variable %s\n", sym);
334 return EVAL_ERR;
337 static inline int
338 getvar_raw(const char *sym, struct op **raw)
340 struct env *e;
341 struct binding *b;
343 TAILQ_FOREACH(e, &envs, entry) {
344 TAILQ_FOREACH(b, &e->bindings, entry) {
345 if (!strcmp(sym, b->name)) {
346 *raw = b->raw;
347 return EVAL_OK;
352 return EVAL_ERR;
355 int
356 global_set(char *sym, struct op *op)
358 struct binding *b;
359 struct env *e;
361 /* TODO: check for duplicates */
363 if (op->type != OP_LITERAL &&
364 (op->type == OP_CAST && op->v.cast.expr->type != OP_LITERAL))
365 return 0;
367 b = xcalloc(1, sizeof(*b));
368 b->name = sym;
370 /* it's only a cast on a literal! */
371 if (op->type == OP_CAST) {
372 if (eval(op) != EVAL_OK) {
373 free(b);
374 return 0;
376 popv(&b->val);
377 } else
378 memcpy(&b->val, &op->v.literal, sizeof(b->val));
380 e = TAILQ_LAST(&envs, envs);
381 TAILQ_INSERT_HEAD(&e->bindings, b, entry);
383 return 1;
386 struct op *
387 newop(int type)
389 struct op *op;
391 op = xcalloc(1, sizeof(*op));
392 op->type = type;
394 return op;
397 void
398 free_op_rec(struct op *op)
400 struct op *n;
402 while (op != NULL) {
403 n = op->next;
404 free_op(op);
405 op = n;
409 void
410 free_op(struct op *op)
412 if (op == NULL)
413 return;
415 switch (op->type) {
416 case OP_REST:
417 case OP_LITERAL:
418 case OP_VARGS:
419 break;
420 case OP_ASSIGN:
421 free(op->v.assign.name);
422 free_op_rec(op->v.assign.expr);
423 break;
424 case OP_ASSERT:
425 free_op_rec(op->v.assert);
426 break;
427 case OP_FUNCALL:
428 free_op_rec(op->v.funcall.argv);
429 break;
430 case OP_VAR:
431 free(op->v.var);
432 break;
433 case OP_CAST:
434 free_op_rec(op->v.cast.expr);
435 break;
436 case OP_CMP_EQ:
437 case OP_CMP_LEQ:
438 free_op_rec(op->v.bin_cmp.a);
439 free_op_rec(op->v.bin_cmp.b);
440 break;
441 case OP_FACCESS:
442 free_op_rec(op->v.faccess.expr);
443 free(op->v.faccess.field);
444 break;
445 case OP_SFAIL:
446 free(op->v.sfail.msg);
447 free_op_rec(op->v.sfail.expr);
448 break;
449 default:
450 /* unreachable */
451 abort();
454 free(op);
457 struct op *
458 op_rest(void)
460 return newop(OP_REST);
463 struct op *
464 op_assign(char *sym, struct op *expr)
466 struct op *op;
468 op = newop(OP_ASSIGN);
469 op->v.assign.name = sym;
470 op->v.assign.expr = expr;
472 return op;
475 struct op *
476 op_assert(struct op *expr)
478 struct op *op;
480 op = newop(OP_ASSERT);
481 op->v.assert = expr;
483 return op;
486 struct op *
487 op_var(char *sym)
489 struct op *op;
491 op = newop(OP_VAR);
492 op->v.var = sym;
494 return op;
497 struct op *
498 op_lit_str(char *str)
500 struct op *op;
502 op = newop(OP_LITERAL);
503 op->v.literal.type = V_STR;
504 op->v.literal.v.str = str;
506 return op;
509 struct op *
510 op_lit_num(uint64_t n)
512 struct op *op;
514 op = newop(OP_LITERAL);
515 op->v.literal.type = V_NUM;
516 op->v.literal.v.num = n;
518 return op;
521 struct op *
522 op_cmp_eq(struct op *a, struct op *b)
524 struct op *op;
526 op = newop(OP_CMP_EQ);
527 op->v.bin_cmp.a = a;
528 op->v.bin_cmp.b = b;
530 return op;
533 struct op *
534 op_cmp_leq(struct op *a, struct op *b)
536 struct op *op;
538 op = newop(OP_CMP_LEQ);
539 op->v.bin_cmp.a = a;
540 op->v.bin_cmp.b = b;
542 return op;
545 struct op *
546 op_cast(struct op *expr, int totype)
548 struct op *op;
550 op = newop(OP_CAST);
551 op->v.cast.expr = expr;
552 op->v.cast.totype = totype;
554 return op;
557 struct op *
558 op_faccess(struct op *expr, char *field)
560 struct op *op;
562 op = newop(OP_FACCESS);
563 op->v.faccess.expr = expr;
564 op->v.faccess.field = field;
566 return op;
569 struct op *
570 op_sfail(struct op *expr, char *msg)
572 struct op *op;
574 op = newop(OP_SFAIL);
575 op->v.sfail.expr = expr;
576 op->v.sfail.msg = msg;
578 return op;
581 struct op *
582 op_vargs(void)
584 struct op *op;
586 op = newop(OP_VARGS);
588 return op;
591 void
592 ppf_val(FILE *f, struct value *val)
594 size_t i;
596 switch (val->type) {
597 case V_SYM:
598 fprintf(f, "%s", val->v.str);
599 break;
600 case V_STR:
601 fprintf(f, "\"%s\"", val->v.str);
602 break;
603 case V_NUM:
604 fprintf(f, "%"PRIi64, val->v.num);
605 break;
606 case V_U8:
607 fprintf(f, "%"PRIu8, val->v.u8);
608 break;
609 case V_U16:
610 fprintf(f, "%"PRIu16, val->v.u16);
611 break;
612 case V_U32:
613 fprintf(f, "%"PRIu32, val->v.u32);
614 break;
615 case V_MSG:
616 fprintf(f, "(");
617 for (i = 0; i < val->v.msg.len; ++i)
618 fprintf(f, "%x%s", val->v.msg.msg[i],
619 i == val->v.msg.len-1 ? "" : " ");
620 fprintf(f, ")");
621 break;
622 case V_QIDVEC:
623 fprintf(f, "qids[n=%zu]", val->v.qidvec.len);
624 break;
625 default:
626 fprintf(f, "<unknown value>");
627 break;
631 void
632 pp_val(struct value *val)
634 ppf_val(stdout, val);
637 const char *
638 val_type(struct value *v)
640 switch (v->type) {
641 case V_SYM: return "symbol";
642 case V_STR: return "string";
643 case V_NUM: return "number";
644 case V_MSG: return "message";
645 case V_QID: return "qid";
646 case V_U8: return "u8";
647 case V_U16: return "u16";
648 case V_U32: return "u32";
649 default: return "unknown";
653 int
654 val_trueish(struct value *a)
656 if (val_isnum(a))
657 return val_tonum(a);
658 return 1;
661 int
662 val_isnum(struct value *a)
664 return a->type == V_NUM
665 || a->type == V_U8
666 || a->type == V_U16
667 || a->type == V_U32;
670 int64_t
671 val_tonum(struct value *a)
673 switch (a->type) {
674 case V_NUM: return a->v.num;
675 case V_U8: return a->v.u8;
676 case V_U16: return a->v.u16;
677 case V_U32: return a->v.u32;
678 default:
679 before_printing();
680 fprintf(stderr, "%s: given value is not a number\n", __func__);
681 abort();
685 int
686 val_eq(struct value *a, struct value *b)
688 if (val_isnum(a) && val_isnum(b))
689 return val_tonum(a) == val_tonum(b);
691 if (a->type != b->type)
692 return 0;
694 switch (a->type) {
695 case V_STR:
696 case V_SYM:
697 return !strcmp(a->v.str, b->v.str);
700 return 0;
703 int
704 val_leq(struct value *a, struct value *b)
706 if (val_isnum(a) && val_isnum(b))
707 return val_tonum(a) <= val_tonum(b);
708 return 0;
711 static inline const char *
712 pp_totype(int totype)
714 /*
715 * Not all of these are valid cast type thought, including
716 * every possibility only to aid debugging.
717 */
718 switch (totype) {
719 case V_STR: return "str";
720 case V_SYM: return "sym";
721 case V_NUM: return "num";
722 case V_QID: return "qid";
723 case V_U8: return "u8";
724 case V_U16: return "u16";
725 case V_U32: return "u32";
726 default: return "unknown";
730 int
731 val_cast(struct value *a, int totype)
733 int64_t v;
735 #define NUMCAST(val, t, c, totype, max) do { \
736 if (val > max) { \
737 before_printing(); \
738 fprintf(stderr, "can't cast %"PRIu64 \
739 " to %s\n", val, pp_totype(totype)); \
740 return EVAL_ERR; \
741 } \
742 a->type = totype; \
743 a->v.t = (c)val; \
744 return EVAL_OK; \
745 } while (0)
747 if (a->type == totype)
748 return EVAL_OK;
750 if (!val_isnum(a)) {
751 before_printing();
752 fprintf(stderr, "can't cast ");
753 ppf_val(stderr, a);
754 fprintf(stderr, " to type %s\n", pp_totype(totype));
755 return EVAL_ERR;
758 v = a->v.num;
759 switch (totype) {
760 case V_U8: NUMCAST(v, u8, uint8_t, totype, UINT8_MAX);
761 case V_U16: NUMCAST(v, u16, uint16_t, totype, UINT16_MAX);
762 case V_U32: NUMCAST(v, u32, uint32_t, totype, UINT32_MAX);
763 default:
764 before_printing();
765 fprintf(stderr, "can't cast %"PRIu64" to %s\n",
766 v, pp_totype(totype));
767 return EVAL_ERR;
770 #undef NUMCAST
773 int
774 val_faccess(struct value *a, const char *field, struct value *ret)
776 uint8_t mtype;
777 uint16_t len;
778 const char *errstr;
780 #define MSGTYPE(m) *(m.msg + 4) /* skip the length */
782 switch (a->type) {
783 case V_QID:
784 /* TODO: add path. needs uint64_t values thought! */
785 if (!strcmp(field, "vers")) {
786 ret->type = V_U32;
787 memcpy(&ret->v.u32, a->v.qid+1, 4);
788 return EVAL_OK;
789 } else if (!strcmp(field, "type")) {
790 ret->type = V_U8;
791 ret->v.u8 = *a->v.qid;
792 return EVAL_OK;
794 break;
796 case V_MSG:
797 mtype = MSGTYPE(a->v.msg);
798 if (!strcmp(field, "type")) {
799 ret->type = V_U8;
800 ret->v.u8 = MSGTYPE(a->v.msg);
801 return EVAL_OK;
802 } else if (!strcmp(field, "tag")) {
803 ret->type = V_U16;
804 memcpy(&ret->v.u16, &a->v.msg.msg[5], 2);
805 ret->v.u16 = le16toh(ret->v.u16);
806 return EVAL_OK;
807 } else if (!strcmp(field, "msize") && mtype == Rversion) {
808 ret->type = V_U32;
809 memcpy(&ret->v.u32, &a->v.msg.msg[7], 4);
810 ret->v.u32 = le32toh(ret->v.u32);
811 return EVAL_OK;
812 } else if (!strcmp(field, "qid") && mtype == Rattach) {
813 ret->type = V_QID;
814 memcpy(&ret->v.qid, &a->v.msg.msg[7], QIDSIZE);
815 return EVAL_OK;
816 } else if (!strcmp(field, "nwqid") && mtype == Rwalk) {
817 ret->type = V_U16;
818 memcpy(&ret->v.u16, &a->v.msg.msg[7], 2);
819 ret->v.u16 = le16toh(ret->v.u16);
820 return EVAL_OK;
821 } else if (!strcmp(field, "wqid") && mtype == Rwalk) {
822 ret->type = V_QIDVEC;
823 ret->v.qidvec.start = &a->v.msg.msg[9];
824 memcpy(&len, &a->v.msg.msg[7], 2);
825 len = le16toh(len);
826 ret->v.qidvec.len = len;
827 return EVAL_OK;
829 break;
831 case V_QIDVEC:
832 len = strtonum(field, 0, MAXWELEM, &errstr);
833 if (errstr != NULL) {
834 before_printing();
835 printf("can't access qid #%s: %s\n", field, errstr);
836 return EVAL_ERR;
839 if (len >= a->v.qidvec.len) {
840 before_printing();
841 printf("can't access qid #%d: out-of-bound "
842 "(max %zu)\n", len, a->v.qidvec.len);
843 return EVAL_ERR;
846 ret->type = V_QID;
847 memcpy(&ret->v.qid, a->v.qidvec.start + len * QIDSIZE,
848 QIDSIZE);
850 return EVAL_OK;
852 default:
853 break;
856 before_printing();
857 printf("can't access field `%s' on type %s (", field, val_type(a));
858 pp_val(a);
859 printf(")\n");
860 return EVAL_ERR;
862 #undef MSGTYPE
865 void
866 pp_op(struct op *op)
868 struct op *aux;
870 switch (op->type) {
871 case OP_REST:
872 printf("...");
873 break;
874 case OP_ASSIGN:
875 printf("%s = ", op->v.assign.name);
876 pp_op(op->v.assign.expr);
877 break;
878 case OP_ASSERT:
879 printf("assert ");
880 pp_op(op->v.assert);
881 break;
882 case OP_FUNCALL:
883 printf("funcall %s(", op->v.funcall.proc->name);
884 for (aux = op->v.funcall.argv; aux != NULL; aux = aux->next) {
885 pp_op(aux);
886 if (aux->next != NULL)
887 printf(", ");
889 printf(")");
890 break;
891 case OP_LITERAL:
892 pp_val(&op->v.literal);
893 break;
894 case OP_VAR:
895 printf("%s", op->v.var);
896 break;
897 case OP_CAST:
898 pp_op(op->v.cast.expr);
899 printf(":");
900 switch (op->v.cast.totype) {
901 case V_U8: printf("u8"); break;
902 case V_U16: printf("u16"); break;
903 case V_U32: printf("u32"); break;
904 case V_STR: printf("str"); break;
905 default: printf("???"); break;
907 break;
908 case OP_CMP_EQ:
909 pp_op(op->v.bin_cmp.a);
910 printf(" == ");
911 pp_op(op->v.bin_cmp.b);
912 break;
913 case OP_CMP_LEQ:
914 pp_op(op->v.bin_cmp.a);
915 printf(" <= ");
916 pp_op(op->v.bin_cmp.b);
917 break;
918 case OP_FACCESS:
919 pp_op(op->v.faccess.expr);
920 printf(".%s", op->v.faccess.field);
921 break;
922 case OP_SFAIL:
923 printf("should-fail ");
924 pp_op(op->v.sfail.expr);
925 if (op->v.sfail.msg != NULL)
926 printf(": \"%s\"", op->v.sfail.msg);
927 break;
928 case OP_VARGS:
929 printf("vargs");
930 break;
931 default:
932 printf(" ???[%d] ", op->type);
936 void
937 pp_block(struct op *op)
939 while (op != NULL) {
940 printf("> ");
941 pp_op(op);
942 printf("\n");
944 op = op->next;
948 int
949 eval(struct op *op)
951 struct value a, b;
952 struct proc *proc;
953 struct op *t, *tnext;
954 int i, ret;
956 #if DEBUG
957 pp_op(op);
958 printf("\n");
959 #endif
961 switch (op->type) {
962 case OP_REST:
963 /*
964 * Try to load the rest argument. Note that it can be
965 * empty!
966 */
967 if ((ret = getvar_raw("...", &t)) == EVAL_OK)
968 if ((ret = eval(t)) != EVAL_OK)
969 return ret;
970 break;
972 case OP_ASSIGN:
973 ret = setvar(op->v.assign.name, op->v.assign.expr);
974 if (ret != EVAL_OK)
975 return ret;
976 break;
978 case OP_ASSERT:
979 if ((ret = eval(op->v.assert)) != EVAL_OK)
980 return ret;
981 popv(&a);
982 if (!val_trueish(&a)) {
983 before_printing();
984 printf("assertion failed: ");
985 pp_op(op->v.assert);
986 printf("\n");
987 return EVAL_ERR;
989 break;
991 case OP_FUNCALL:
992 /* assume airity matches */
994 proc = op->v.funcall.proc;
995 if (proc->nativefn != NULL) {
996 /*
997 * Push arguments on the stack for builtin
998 * functions. Counting the height of the
999 * stack is done to compute the correct number
1000 * in the vararg case. argc only counts the
1001 * "syntactical" arguments, i.e. foo(x, ...)
1002 * has argc == 2, but at runtime argc may be
1003 * 1, 2 or a greater number!
1006 i = stackh;
1007 t = op->v.funcall.argv;
1008 if (t != NULL && (ret = eval(t)) != EVAL_OK)
1009 return ret;
1010 i = stackh - i;
1012 assert(i >= 0);
1014 if ((ret = proc->nativefn(i))
1015 != EVAL_OK)
1016 return ret;
1017 } else {
1018 if (proc->body == NULL) {
1019 before_printing();
1020 printf("warn: calling the empty proc `%s'\n",
1021 proc->name);
1022 break;
1025 pushenv();
1027 for (t = op->v.funcall.argv, i = 0;
1028 t != NULL;
1029 t = t->next, i++) {
1031 * Push a pseudo variable `...' (and
1032 * don't evaluate it) in the vararg
1033 * case. A special case is when the
1034 * variable is itself `...'.
1036 if (proc->vararg && i == proc->minargs) {
1037 if (t->type != OP_REST)
1038 setvar_raw(xstrdup("..."), t);
1039 break;
1043 * The arguments are a linked list of
1044 * ops. Setvar will call eval that
1045 * will evaluate *all* the arguments.
1046 * The dance here that sets next to
1047 * NULL and then restores it is to
1048 * avoid this behaviour.
1050 tnext = t->next;
1051 t->next = NULL;
1052 ret = setvar(proc->args[i], t);
1053 t->next = tnext;
1055 if (ret != EVAL_OK)
1056 return ret;
1059 if ((ret = eval(proc->body)) != EVAL_OK)
1060 return ret;
1062 popenv();
1065 break;
1067 case OP_LITERAL:
1068 pushv(&op->v.literal);
1069 break;
1071 case OP_VAR:
1072 if ((ret = getvar(op->v.var, &a)) != EVAL_OK)
1073 return ret;
1074 pushv(&a);
1075 break;
1077 case OP_CAST:
1078 if ((ret = eval(op->v.cast.expr)) != EVAL_OK)
1079 return ret;
1080 popv(&a);
1081 if ((ret = val_cast(&a, op->v.cast.totype)) != EVAL_OK)
1082 return ret;
1083 pushv(&a);
1084 break;
1086 case OP_CMP_EQ:
1087 if ((ret = eval(op->v.bin_cmp.a)) != EVAL_OK)
1088 return ret;
1089 if ((ret = eval(op->v.bin_cmp.b)) != EVAL_OK)
1090 return ret;
1092 popv(&b);
1093 popv(&a);
1094 pushbool(val_eq(&a, &b));
1095 break;
1097 case OP_CMP_LEQ:
1098 if ((ret = eval(op->v.bin_cmp.a)) != EVAL_OK)
1099 return ret;
1100 if ((ret = eval(op->v.bin_cmp.b)) != EVAL_OK)
1101 return ret;
1103 popv(&b);
1104 popv(&a);
1105 pushbool(val_leq(&a, &b));
1106 break;
1108 case OP_FACCESS:
1109 if ((ret = eval(op->v.faccess.expr)) != EVAL_OK)
1110 return ret;
1111 popv(&a);
1112 if ((ret = val_faccess(&a, op->v.faccess.field, &b))
1113 != EVAL_OK)
1114 return ret;
1115 pushv(&b);
1116 break;
1118 case OP_SFAIL:
1119 if ((ret = eval(op->v.sfail.expr)) == EVAL_OK) {
1120 before_printing();
1121 printf("expecting failure");
1122 if (op->v.sfail.msg != NULL)
1123 printf(" \"%s\"", op->v.sfail.msg);
1124 printf("\n");
1125 printf("expression: ");
1126 pp_op(op->v.sfail.expr);
1127 printf("\n");
1128 return EVAL_ERR;
1130 if (ret == EVAL_SKIP)
1131 return ret;
1132 break;
1134 case OP_VARGS:
1135 if ((ret = getvar_raw("...", &t)) == EVAL_OK) {
1136 for (i = 0; t != NULL; t = t->next)
1137 i++;
1138 pushnum(i);
1139 } else
1140 pushnum(0);
1141 break;
1143 default:
1144 before_printing();
1145 fprintf(stderr, "invalid op, aborting.\n");
1146 abort();
1149 if (op->next)
1150 return eval(op->next);
1151 return EVAL_OK;
1154 void
1155 prepare_funcall(void)
1157 pushstack(&args);
1160 void
1161 push_arg(struct op *op)
1163 push(&args, op);
1166 struct op *
1167 op_funcall(struct proc *proc)
1169 struct op *op, *argv;
1170 int argc;
1172 argv = finalize(&args, &argc);
1174 op = newop(OP_FUNCALL);
1175 op->v.funcall.proc = proc;
1176 op->v.funcall.argv = argv;
1177 op->v.funcall.argc = argc;
1179 return op;
1182 void
1183 add_builtin_proc(const char *name, int (*fn)(int), int argc, int vararg)
1185 struct proc *proc;
1187 proc = xcalloc(1, sizeof(*proc));
1188 proc->name = xstrdup(name);
1189 proc->nativefn = fn;
1190 proc->minargs = argc;
1191 proc->vararg = vararg;
1193 TAILQ_INSERT_HEAD(&procs, proc, entry);
1196 void
1197 prepare_proc(void)
1199 pushstack(&args);
1202 int
1203 proc_setup_body(void)
1205 struct opstack *argv;
1206 struct op *op;
1207 int i;
1209 argv = peek(&args);
1210 for (i = 0, op = argv->base.next; op != NULL; i++) {
1212 * TODO: should free the whole list on error but..,
1213 * we're gonna exit real soon(tm)!
1215 if (op->type != OP_VAR && op->type != OP_REST)
1216 return 0;
1218 op = op->next;
1221 assert(i == argv->counter);
1222 pushstack(&blocks);
1223 return 1;
1226 void
1227 proc_done(char *name)
1229 struct proc *proc;
1230 struct op *op, *next, *argv, *body;
1231 int i, argc;
1233 argv = finalize(&args, &argc);
1234 body = finalize(&blocks, NULL);
1236 proc = xcalloc(1, sizeof(*proc));
1237 proc->name = name;
1238 proc->minargs = argc;
1240 for (i = 0, op = argv; op != NULL; ++i) {
1241 if (op->type == OP_REST) {
1242 proc->vararg = 1;
1243 proc->minargs = i;
1244 break;
1247 proc->args[i] = xstrdup(op->v.var);
1249 next = op->next;
1250 free_op(op);
1251 op = next;
1253 assert(i == argc || (proc->vararg && i == proc->minargs));
1255 proc->body = body;
1257 TAILQ_INSERT_HEAD(&procs, proc, entry);
1260 void
1261 block_push(struct op *op)
1263 push(&blocks, op);
1266 struct proc *
1267 proc_by_name(const char *name)
1269 struct proc *p;
1271 TAILQ_FOREACH(p, &procs, entry) {
1272 if (!strcmp(p->name, name))
1273 return p;
1276 return NULL;
1279 void
1280 prepare_test(void)
1282 pushstack(&blocks);
1285 void
1286 test_done(int shouldfail, char *name)
1288 struct test *test;
1290 test = xcalloc(1, sizeof(*test));
1291 test->shouldfail = shouldfail;
1292 test->name = name;
1293 test->body = finalize(&blocks, NULL);
1295 TAILQ_INSERT_TAIL(&tests, test, entry);
1297 ntests++;
1300 static int
1301 builtin_print(int argc)
1303 struct value v;
1304 int i;
1306 before_printing();
1308 for (i = argc; i > 0; --i) {
1309 peekn(i, &v);
1310 if (v.type == V_STR)
1311 printf("%s", v.v.str);
1312 else
1313 pp_val(&v);
1314 printf(" ");
1317 printf("\n");
1319 popvn(argc);
1321 return EVAL_OK;
1324 static int
1325 builtin_debug(int argc)
1327 if (debug)
1328 return builtin_print(argc);
1330 popvn(argc);
1331 return EVAL_OK;
1334 static int
1335 builtin_skip(int argc)
1337 return EVAL_SKIP;
1340 static int
1341 builtin_iota(int argc)
1343 struct value v;
1345 v.type = V_U16;
1346 if ((v.v.u16 = ++lasttag) == 255)
1347 v.v.u16 = ++lasttag;
1349 pushv(&v);
1350 return EVAL_OK;
1353 static int
1354 builtin_send(int argc)
1356 struct ibuf *buf;
1357 struct value v;
1358 uint32_t len;
1359 uint16_t slen;
1360 int i;
1362 check_for_output();
1365 * Compute the length of the packet. 4 is for the initial
1366 * length field
1368 len = 4;
1370 for (i = argc; i > 0; --i) {
1371 peekn(i, &v);
1372 switch (v.type) {
1373 case V_STR:
1374 len += 2; /* count */
1375 len += strlen(v.v.str);
1376 break;
1378 case V_U8:
1379 len += 1;
1380 break;
1382 case V_U16:
1383 len += 2;
1384 break;
1386 case V_U32:
1387 len += 4;
1388 break;
1390 default:
1391 before_printing();
1392 printf("%s: can't serialize ", __func__);
1393 pp_val(&v);
1394 printf("\n");
1395 return EVAL_ERR;
1399 if (len > UINT16_MAX) {
1400 before_printing();
1401 printf("%s: message size too long: got %d when max is %d\n",
1402 __func__, len, UINT16_MAX);
1403 return EVAL_ERR;
1406 if ((buf = imsg_create(&ibuf, IMSG_BUF, 0, 0, len)) == NULL)
1407 fatal("imsg_create(%d)", len);
1409 len = htole32(len);
1410 imsg_add(buf, &len, sizeof(len));
1412 for (i = argc; i > 0; --i) {
1413 peekn(i, &v);
1414 switch (v.type) {
1415 case V_STR:
1416 slen = strlen(v.v.str);
1417 slen = htole16(slen);
1418 imsg_add(buf, &slen, sizeof(slen));
1419 imsg_add(buf, v.v.str, strlen(v.v.str));
1420 break;
1422 case V_U8:
1423 imsg_add(buf, &v.v.u8, 1);
1424 break;
1426 case V_U16:
1427 v.v.u16 = htole16(v.v.u16);
1428 imsg_add(buf, &v.v.u16, 2);
1429 break;
1431 case V_U32:
1432 v.v.u32 = htole32(v.v.u32);
1433 imsg_add(buf, &v.v.u32, 4);
1434 break;
1438 imsg_close(&ibuf, buf);
1440 if (imsg_flush(&ibuf) == -1) {
1441 i = errno;
1442 before_printing();
1443 printf("%s: imsg_flush failed: %s\n", __func__, strerror(i));
1444 return EVAL_ERR;
1447 check_for_output();
1448 return EVAL_OK;
1451 static int
1452 builtin_recv(int argc)
1454 struct pollfd pfd;
1455 struct value v;
1456 struct imsg imsg;
1457 ssize_t n, datalen;
1458 int serrno;
1460 if (lastmsg != NULL) {
1461 free(lastmsg);
1462 lastmsg = NULL;
1465 pfd.fd = ibuf.fd;
1466 pfd.events = POLLIN;
1467 if (poll(&pfd, 1, INFTIM) == -1) {
1468 serrno = errno;
1469 before_printing();
1470 printf("%s: poll failed: %s\n", __func__, strerror(serrno));
1471 return EVAL_ERR;
1474 again:
1475 if ((n = imsg_read(&ibuf)) == -1) {
1476 if (errno == EAGAIN)
1477 goto again;
1478 fatal("imsg_read");
1480 if (n == 0) {
1481 disconnect:
1482 before_printing();
1483 printf("child disconnected\n");
1484 return EVAL_ERR;
1487 nextmessage:
1488 check_for_output();
1490 /* read only one message */
1491 if ((n = imsg_get(&ibuf, &imsg)) == -1)
1492 fatal("imsg_get");
1493 if (n == 0)
1494 goto disconnect;
1496 datalen = imsg.hdr.len - IMSG_HEADER_SIZE;
1497 switch (imsg.hdr.type) {
1498 case IMSG_BUF:
1499 v.type = V_MSG;
1500 if ((v.v.msg.msg = malloc(datalen)) == NULL)
1501 fatal("malloc");
1502 memcpy(v.v.msg.msg, imsg.data, datalen);
1503 v.v.msg.len = datalen;
1504 pushv(&v);
1505 imsg_free(&imsg);
1506 return EVAL_OK;
1508 case IMSG_CLOSE:
1509 before_printing();
1510 printf("subprocess closed the connection\n");
1511 imsg_free(&imsg);
1512 return EVAL_ERR;
1514 case IMSG_MSIZE:
1515 imsg_free(&imsg);
1516 goto nextmessage;
1518 default:
1519 before_printing();
1520 printf("got unknown message from subprocess: %d\n",
1521 imsg.hdr.type);
1522 imsg_free(&imsg);
1523 return EVAL_ERR;
1527 static pid_t
1528 spawn_client_proc(void)
1530 const char *argv[4];
1531 int p[2], out[2], argc = 0;
1532 pid_t pid;
1534 if (child_out != -1)
1535 close(child_out);
1537 if (socketpair(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC | SOCK_NONBLOCK,
1538 PF_UNSPEC, p) == -1)
1539 fatal("socketpair");
1541 if (socketpair(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC | SOCK_NONBLOCK,
1542 PF_UNSPEC, out) == -1)
1543 fatal("socketpair");
1545 switch (pid = fork()) {
1546 case -1:
1547 fatal("cannot fork");
1548 case 0:
1549 break;
1550 default:
1551 close(p[1]);
1552 close(out[1]);
1553 child_out = out[0];
1554 if (ibuf_inuse) {
1555 msgbuf_clear(&ibuf.w);
1556 close(ibuf.fd);
1558 imsg_init(&ibuf, p[0]);
1559 ibuf_inuse = 1;
1560 return pid;
1563 close(p[0]);
1564 close(out[0]);
1566 if (dup2(out[1], 1) == -1 ||
1567 dup2(out[1], 2) == -1)
1568 fatal("dup2");
1570 if (p[1] != 3) {
1571 if (dup2(p[1], 3) == -1)
1572 fatal("cannot setup imsg fd");
1573 } else if (fcntl(F_SETFD, 0) == -1)
1574 fatal("cannot setup imsg fd");
1576 argv[argc++] = argv0;
1577 argv[argc++] = "-Tc";
1579 #if DEBUG
1580 argv[argc++] = "-v";
1581 #endif
1583 argv[argc++] = NULL;
1585 execvp(argv0, (char *const *)argv);
1586 fatal("execvp");
1589 static void
1590 prepare_child_for_test(struct test *t)
1592 struct passwd *pw;
1593 struct kd_auth_proc rauth;
1595 if ((pw = getpwuid(uid)) == NULL)
1596 fatal("getpwuid(%d)", uid);
1598 memset(&rauth, 0, sizeof(rauth));
1599 strlcpy(rauth.uname, pw->pw_name, sizeof(rauth.uname));
1600 strlcpy(rauth.dir, dir, sizeof(rauth.dir));
1602 imsg_compose(&ibuf, IMSG_AUTH, 0, 0, -1,
1603 &rauth, sizeof(rauth));
1605 if (imsg_flush(&ibuf) == -1)
1606 fatal("imsg_flush");
1609 static int
1610 run_test(struct test *t)
1612 pid_t pid;
1613 int ret;
1615 #if DEBUG
1616 before_printing();
1617 puts("=====================");
1618 pp_block(t->body);
1619 puts("=====================");
1620 #endif
1622 if (stackh != 0)
1623 popvn(stackh);
1625 if (t->body == NULL) {
1626 before_printing();
1627 printf("no instructions, skipping...\n");
1628 return EVAL_SKIP;
1631 pid = spawn_client_proc();
1632 prepare_child_for_test(t);
1633 ret = eval(t->body);
1635 imsg_compose(&ibuf, IMSG_CONN_GONE, 0, 0, -1, NULL, 0);
1636 imsg_flush(&ibuf);
1638 while (waitpid(pid, NULL, 0) != pid)
1639 ; /* nop */
1641 check_for_output();
1643 if (t->shouldfail) {
1644 if (ret == EVAL_OK) {
1645 before_printing();
1646 printf("test was expected to fail\n");
1647 return EVAL_ERR;
1648 } else if (ret == EVAL_ERR)
1649 return EVAL_OK;
1652 return ret;
1655 int
1656 main(int argc, char **argv)
1658 struct stat sb;
1659 struct test *t;
1660 int ch, i, r, passed = 0, failed = 0, skipped = 0;
1661 int runclient = 0;
1662 const char *pat = NULL;
1663 regex_t reg;
1665 assert(argv0 = argv[0]);
1667 signal(SIGPIPE, SIG_IGN);
1669 log_init(1, LOG_DAEMON);
1670 log_setverbose(1);
1672 /* prepare the global env */
1673 pushenv();
1675 add_builtin_proc("print", builtin_print, 1, 1);
1676 add_builtin_proc("debug", builtin_debug, 1, 1);
1677 add_builtin_proc("skip", builtin_skip, 0, 0);
1678 add_builtin_proc("iota", builtin_iota, 0, 0);
1679 add_builtin_proc("send", builtin_send, 2, 1);
1680 add_builtin_proc("recv", builtin_recv, 0, 0);
1682 while ((ch = getopt(argc, argv, "nT:r:vx:")) != -1) {
1683 switch (ch) {
1684 case 'n':
1685 syntaxcheck = 1;
1686 break;
1687 case 'T':
1688 assert(*optarg == 'c');
1689 runclient = 1;
1690 break;
1691 case 'r':
1692 dir = optarg;
1693 break;
1694 case 'v':
1695 debug = 1;
1696 break;
1697 case 'x':
1698 pat = optarg;
1699 break;
1700 default:
1701 fprintf(stderr, "Usage: %s [-nv] [files...]\n",
1702 *argv);
1703 exit(1);
1706 argc -= optind;
1707 argv += optind;
1709 if (runclient)
1710 client(1, debug);
1712 if (dir == NULL)
1713 fatal("missing root test dir");
1715 if (stat(dir, &sb) == -1)
1716 fatal("stat(\"%s\")", dir);
1717 uid = sb.st_uid;
1719 if (pat == NULL)
1720 pat = ".*";
1722 if (regcomp(&reg, pat, REG_ICASE | REG_NOSUB) != 0)
1723 fatalx("invalid regexp: %s", pat);
1725 for (i = 0; i < argc; ++i)
1726 loadfile(argv[i]);
1728 if (syntaxcheck) {
1729 fprintf(stderr, "files OK\n");
1730 return 0;
1733 /* Check for root privileges. */
1734 if (geteuid())
1735 fatalx("need root privileges");
1737 i = 0;
1738 TAILQ_FOREACH(t, &tests, entry) {
1739 if (regexec(&reg, t->name, 0, NULL, 0) != 0)
1740 continue;
1742 printf("===> [%d/%d] running test \"%s\"... ", i+1, ntests,
1743 t->name);
1744 fflush(stdout);
1746 filler = "\n";
1747 r = run_test(t);
1748 if (filler == NULL)
1749 printf("=> test ");
1751 switch (r) {
1752 case EVAL_OK:
1753 printf("passed\n");
1754 passed++;
1755 break;
1756 case EVAL_ERR:
1757 failed++;
1758 printf("failed\n");
1759 break;
1760 case EVAL_SKIP:
1761 printf("skipped\n");
1762 skipped++;
1763 break;
1766 if (filler == NULL)
1767 printf("\n");
1768 i++;
1771 printf("\n");
1772 printf("%d/%d passed (%d skipped and %d failed)\n",
1773 passed, i, skipped, failed);
1775 popenv();
1776 free(lastmsg);
1777 regfree(&reg);
1779 return failed != 0;