const char * vcc_regexp(struct vcc *tl) { char buf[BUFSIZ], *p; vre_t *t; const char *error; int erroroffset; struct inifin *ifp; Expect(tl, CSTR); if (tl->err) return (NULL); t = VRE_compile(tl->t->dec, 0, &error, &erroroffset); if (t == NULL) { VSB_printf(tl->sb, "Regexp compilation error:\n\n%s\n\n", error); vcc_ErrWhere(tl, tl->t); return (NULL); } VRE_free(&t); bprintf(buf, "VGC_re_%u", tl->unique++); p = TlAlloc(tl, strlen(buf) + 1); strcpy(p, buf); Fh(tl, 0, "static void *%s;\n", buf); ifp = New_IniFin(tl); VSB_printf(ifp->ini, "\tVRT_re_init(&%s, ",buf); EncToken(ifp->ini, tl->t); VSB_printf(ifp->ini, ");"); VSB_printf(ifp->fin, "\t\tVRT_re_fini(%s);", buf); vcc_NextToken(tl); return (p); }
static void vxp_expr_regex(struct vxp *vxp, struct vex_rhs **prhs) { const char *errptr; int erroff; /* XXX: Caseless option */ AN(prhs); AZ(*prhs); if (vxp->t->tok != VAL) { VSB_printf(vxp->sb, "Expected regular expression got '%.*s' ", PF(vxp->t)); vxp_ErrWhere(vxp, vxp->t, -1); return; } AN(vxp->t->dec); ALLOC_OBJ(*prhs, VEX_RHS_MAGIC); AN(*prhs); (*prhs)->type = VEX_REGEX; (*prhs)->val_string = strdup(vxp->t->dec); (*prhs)->val_regex = VRE_compile(vxp->t->dec, vxp->vre_options, &errptr, &erroff); if ((*prhs)->val_regex == NULL) { AN(errptr); VSB_printf(vxp->sb, "Regular expression error: %s ", errptr); vxp_ErrWhere(vxp, vxp->t, erroff); return; } vxp_NextToken(vxp); }
static void cmd_http_expect(CMD_ARGS) { struct http *hp; const char *lhs; char *cmp; const char *rhs; vre_t *vre; const char *error; int erroroffset; int i; (void)cmd; (void)vl; CAST_OBJ_NOTNULL(hp, priv, HTTP_MAGIC); assert(!strcmp(av[0], "expect")); av++; AN(av[0]); AN(av[1]); AN(av[2]); AZ(av[3]); lhs = cmd_var_resolve(hp, av[0]); cmp = av[1]; rhs = cmd_var_resolve(hp, av[2]); if (!strcmp(cmp, "==")) { if (strcmp(lhs, rhs)) vtc_log(hp->vl, 0, "EXPECT %s (%s) %s %s (%s) failed", av[0], lhs, av[1], av[2], rhs); else vtc_log(hp->vl, 4, "EXPECT %s (%s) %s %s (%s) match", av[0], lhs, av[1], av[2], rhs); } else if (!strcmp(cmp, "!=")) { if (!strcmp(lhs, rhs)) vtc_log(hp->vl, 0, "EXPECT %s (%s) %s %s (%s) failed", av[0], lhs, av[1], av[2], rhs); else vtc_log(hp->vl, 4, "EXPECT %s (%s) %s %s (%s) match", av[0], lhs, av[1], av[2], rhs); } else if (!strcmp(cmp, "~") || !strcmp(cmp, "!~")) { vre = VRE_compile(rhs, 0, &error, &erroroffset); if (vre == NULL) vtc_log(hp->vl, 0, "REGEXP error: %s (@%d) (%s)", error, erroroffset, rhs); i = VRE_exec(vre, lhs, strlen(lhs), 0, 0, NULL, 0, 0); if ((i >= 0 && *cmp == '~') || (i < 0 && *cmp == '!')) vtc_log(hp->vl, 4, "EXPECT %s (%s) %s \"%s\" match", av[0], lhs, cmp, rhs); else vtc_log(hp->vl, 0, "EXPECT %s (%s) %s \"%s\" failed", av[0], lhs, cmp, rhs); VRE_free(&vre); } else { vtc_log(hp->vl, 0, "EXPECT %s (%s) %s %s (%s) test not implemented", av[0], lhs, av[1], av[2], rhs); } }
static int vsl_IX_arg(struct VSL_data *vsl, int opt, const char *arg) { int i, l, off; const char *b, *e, *err; vre_t *vre; struct vslf *vslf; struct vbitmap *tags = NULL; CHECK_OBJ_NOTNULL(vsl, VSL_MAGIC); vsl->flags |= F_SEEN_ixIX; b = arg; e = strchr(b, ':'); if (e) { tags = vbit_init(SLT__MAX); AN(tags); l = e - b; i = VSL_List2Tags(b, l, vsl_vbm_bitset, tags); if (i < 0) vbit_destroy(tags); if (i == -1) return (vsl_diag(vsl, "-%c: \"%*.*s\" matches zero tags", (char)opt, l, l, b)); else if (i == -2) return (vsl_diag(vsl, "-%c: \"%*.*s\" is ambiguous", (char)opt, l, l, b)); else if (i <= -3) return (vsl_diag(vsl, "-%c: Syntax error in \"%*.*s\"", (char)opt, l, l, b)); b = e + 1; } vre = VRE_compile(b, vsl->C_opt ? VRE_CASELESS : 0, &err, &off); if (vre == NULL) { if (tags) vbit_destroy(tags); return (vsl_diag(vsl, "-%c: Regex error at position %d (%s)\n", (char)opt, off, err)); } ALLOC_OBJ(vslf, VSLF_MAGIC); AN(vslf); vslf->tags = tags; vslf->vre = vre; if (opt == 'I') VTAILQ_INSERT_TAIL(&vsl->vslf_select, vslf, list); else { assert(opt == 'X'); VTAILQ_INSERT_TAIL(&vsl->vslf_suppress, vslf, list); } return (1); }
void vtc_expect(struct vtclog *vl, const char *olhs, const char *lhs, const char *cmp, const char *orhs, const char *rhs) { vre_t *vre; const char *error; int erroroffset; int i, j, retval = -1; double fl, fr; j = lhs == NULL || rhs == NULL; if (lhs == NULL) lhs = "<undef>"; if (rhs == NULL) rhs = "<undef>"; if (!strcmp(cmp, "~") || !strcmp(cmp, "!~")) { vre = VRE_compile(rhs, 0, &error, &erroroffset); if (vre == NULL) vtc_fatal(vl, "REGEXP error: %s (@%d) (%s)", error, erroroffset, rhs); i = VRE_exec(vre, lhs, strlen(lhs), 0, 0, NULL, 0, 0); retval = (i >= 0 && *cmp == '~') || (i < 0 && *cmp == '!'); VRE_free(&vre); } else if (!strcmp(cmp, "==")) { retval = strcmp(lhs, rhs) == 0; } else if (!strcmp(cmp, "!=")) { retval = strcmp(lhs, rhs) != 0; } else if (j) { // fail inequality comparisons if either side is undef'ed retval = 0; } else { fl = VNUM(lhs); fr = VNUM(rhs); if (!strcmp(cmp, "<")) retval = isless(fl, fr); else if (!strcmp(cmp, ">")) retval = isgreater(fl, fr); else if (!strcmp(cmp, "<=")) retval = islessequal(fl, fr); else if (!strcmp(cmp, ">=")) retval = isgreaterequal(fl, fr); } if (retval == -1) vtc_fatal(vl, "EXPECT %s (%s) %s %s (%s) test not implemented", olhs, lhs, cmp, orhs, rhs); else if (retval == 0) vtc_fatal(vl, "EXPECT %s (%s) %s \"%s\" failed", olhs, lhs, cmp, rhs); else vtc_log(vl, 4, "EXPECT %s (%s) %s \"%s\" match", olhs, lhs, cmp, rhs); }
static void * compile_regex(const char *regex) { void *re; const char *error; int error_offset; re = VRE_compile(regex, 0, &error, &error_offset); return re; }
void VRT_re_init(void **rep, const char *re) { vre_t *t; const char *error; int erroroffset; /* This was already check-compiled by the VCL compiler */ t = VRE_compile(re, 0, &error, &erroroffset); AN(t); *rep = t; }
static int vsl_IX_arg(struct VSL_data *vd, const char *opt, int arg) { vre_t **rp; const char *error; int erroroffset; CHECK_OBJ_NOTNULL(vd, VSL_MAGIC); if (arg == 'I') rp = &vd->regincl; else rp = &vd->regexcl; if (*rp != NULL) { fprintf(stderr, "Option %c can only be given once", arg); return (-1); } *rp = VRE_compile(opt, vd->regflags, &error, &erroroffset); if (*rp == NULL) { fprintf(stderr, "Illegal regex: %s\n", error); return (-1); } return (1); }
struct vslq_query * vslq_newquery(struct VSL_data *vsl, enum VSL_grouping_e grouping, const char *querystring) { struct vslq_query *query; const char *error; int pos; vre_t *regex; (void)grouping; AN(querystring); regex = VRE_compile(querystring, 0, &error, &pos); if (regex == NULL) { vsl_diag(vsl, "failed to compile regex at pos %d: %s", pos, error); return (NULL); } ALLOC_OBJ(query, VSLQ_QUERY_MAGIC); if (query != NULL) query->regex = regex; return (query); }
static void cmd_http_expect(CMD_ARGS) { struct http *hp; const char *lhs, *clhs; char *cmp; const char *rhs, *crhs; vre_t *vre; const char *error; int erroroffset; int i, retval = -1; (void)cmd; (void)vl; CAST_OBJ_NOTNULL(hp, priv, HTTP_MAGIC); AZ(strcmp(av[0], "expect")); av++; AN(av[0]); AN(av[1]); AN(av[2]); AZ(av[3]); lhs = cmd_var_resolve(hp, av[0]); cmp = av[1]; rhs = cmd_var_resolve(hp, av[2]); clhs = lhs ? lhs : "<undef>"; crhs = rhs ? rhs : "<undef>"; if (!strcmp(cmp, "~") || !strcmp(cmp, "!~")) { vre = VRE_compile(crhs, 0, &error, &erroroffset); if (vre == NULL) vtc_log(hp->vl, 0, "REGEXP error: %s (@%d) (%s)", error, erroroffset, crhs); i = VRE_exec(vre, clhs, strlen(clhs), 0, 0, NULL, 0, 0); retval = (i >= 0 && *cmp == '~') || (i < 0 && *cmp == '!'); VRE_free(&vre); } else if (!strcmp(cmp, "==")) { retval = strcmp(clhs, crhs) == 0; } else if (!strcmp(cmp, "!=")) { retval = strcmp(clhs, crhs) != 0; } else if (lhs == NULL || rhs == NULL) { // fail inequality comparisons if either side is undef'ed retval = 0; } else if (!strcmp(cmp, "<")) { retval = isless(VNUM(lhs), VNUM(rhs)); } else if (!strcmp(cmp, ">")) { retval = isgreater(VNUM(lhs), VNUM(rhs)); } else if (!strcmp(cmp, "<=")) { retval = islessequal(VNUM(lhs), VNUM(rhs)); } else if (!strcmp(cmp, ">=")) { retval = isgreaterequal(VNUM(lhs), VNUM(rhs)); } if (retval == -1) vtc_log(hp->vl, 0, "EXPECT %s (%s) %s %s (%s) test not implemented", av[0], clhs, av[1], av[2], crhs); else vtc_log(hp->vl, retval ? 4 : 0, "EXPECT %s (%s) %s \"%s\" %s", av[0], clhs, cmp, crhs, retval ? "match" : "failed"); }