==> tests/req.c <==1/* Control lines parsed as the Rust parses them: every answer (request or error text) matches. */
2#include "mesh/jobs/req.h"
3#include "mesh/check.h"
4#include "mesh/strbuf.h"
5#include "gold_req.h"
6
7#include <stdlib.h>
8#include <string.h>
9
10static char *canon(const mj_req *r) {
11 msb b = {0};
12 switch (r->kind) {
13 case MJ_REQ_SUBMIT: {
14 const mj_submit *s = &r->submit;
15 msb_printf(&b, "submit members %u program %s op %u items ", s->members, s->program, s->op);
16 mj_ranges_word(&s->items, &b);
17 msb_printf(&b, " priority %d attempts %u deadline %llu mode %s setup ", s->priority, s->attempts, (unsigned long long)s->deadline_s,
18 mj_mode_word(s->mode));
19 for (size_t i = 0; i < s->nsetup; i++) msb_printf(&b, "%s%u:%u", i ? "," : "", s->setup[i].op, s->setup[i].arg);
20 break;
21 }
22 case MJ_REQ_CANCEL: msb_printf(&b, "cancel %llu", (unsigned long long)r->job); break;
23 case MJ_REQ_FORGET: msb_printf(&b, "forget %llu", (unsigned long long)r->job); break;
24 case MJ_REQ_TONE: msb_printf(&b, "tone %llu %u", (unsigned long long)r->job, r->tone); break;
25 }
26 return msb_take(&b);
27}
28
29int main(void) {
30 for (size_t i = 0; i < sizeof GOLD / sizeof *GOLD; i++) {
31 char *line = mstrdup(GOLD[i][0]);
32 const char *w[64];
33 size_t n = 0;
34 for (char *t = strtok(line, " "); t && n < 64; t = strtok(NULL, " ")) w[n++] = t;
35 mj_req r;
36 char *err = NULL;
37 char *got;
38 if (mj_req_parse(w, n, &r, &err)) {
39 got = canon(&r);
40 mj_req c = mj_req_clone(&r);
41 mj_req_free(&c);
42 mj_req_free(&r);
43 } else {
44 got = mfmt("error %s", err);
45 free(err);
46 }
47 if (!CHECK_S(got, GOLD[i][1])) fprintf(stderr, " for: %s\n", GOLD[i][0]);
48 free(got);
49 free(line);
50 }
51 return mesh_check_done();
52}