TCPCHK_EXPECT_CUSTOM, /* Execute a custom function. */
};
+/* tcp-check expect flags */
+#define TCPCHK_EXPT_FL_INV 0x0001 /* Matching is inversed */
+#define TCPCHK_EXPT_FL_CAP 0x0002 /* Regex matching with capture */
+
struct tcpcheck_expect {
- enum tcpcheck_expect_type type; /* Type of pattern used for matching. */
+ enum tcpcheck_expect_type type; /* Type of pattern used for matching. */
+ unsigned int flags; /* TCPCHK_EXPT_FL_* */
union {
- struct ist data; /* Matching a literal string / binary anywhere in the response. */
- struct my_regex *regex; /* Matching a regex pattern. */
+ struct ist data; /* Matching a literal string / binary anywhere in the response. */
+ struct my_regex *regex; /* Matching a regex pattern. */
/* custom function to eval epxect rule */
enum tcpcheck_eval_ret (*custom)(struct check *, struct tcpcheck_rule *, int);
};
struct tcpcheck_rule *head; /* first expect of a chain. */
- int inverse; /* Match is inversed. */
- int with_capture; /* Match will store captured groups for back-reference in comment. */
int min_recv; /* Minimum amount of data before an expect can be applied. (default: -1, ignored) */
struct list onerror_fmt; /* log-format string to use as comment on error */
struct list onsuccess_fmt; /* log-format string to use as comment on success (if last rule) */
/* If references to the matched text were made, divide the
* offsets by 2 to match offset of the original response buffer.
*/
- if (rule->expect.with_capture) {
+ if (rule->expect.flags & TCPCHK_EXPT_FL_CAP) {
int i;
for (i = 1; i < MAX_MATCH && pmatch[i].rm_so != -1; i++) {
comment:
if (rule->comment) {
chunk_strcat(msg, " comment: ");
- if (rule->expect.with_capture) {
+ if (rule->expect.flags & TCPCHK_EXPT_FL_CAP) {
int ret = exp_replace(b_tail(msg), b_room(msg), b_head(&check->bi), rule->comment, pmatch);
if (ret != -1) /* ignore comment if too large */
msg->data += ret;
enum tcpcheck_eval_ret ret = TCPCHK_EVAL_CONTINUE;
struct tcpcheck_expect *expect = &rule->expect;
struct buffer *msg = NULL;
- int match;
+ int match, inverse;
/* The current expect might need more data than the previous one, check again
* that the minimum amount data required to match is respected.
}
}
+ inverse = !!(expect->flags & TCPCHK_EXPT_FL_INV);
/* Make GCC happy ; initialize match to a failure state. */
- match = expect->inverse;
+ match = inverse;
switch (expect->type) {
case TCPCHK_EXPECT_STRING:
match = my_memmem(b_head(&check->bi), b_data(&check->bi), expect->data.ptr, istlen(expect->data)) != NULL;
break;
case TCPCHK_EXPECT_REGEX:
- if (expect->with_capture)
+ if (expect->flags & TCPCHK_EXPT_FL_CAP)
match = regex_exec_match2(expect->regex, b_head(&check->bi), MIN(b_data(&check->bi), b_size(&check->bi)-1),
MAX_MATCH, pmatch, 0);
else
case TCPCHK_EXPECT_REGEX_BINARY:
chunk_reset(&trash);
dump_binary(&trash, b_head(&check->bi), b_data(&check->bi));
- if (expect->with_capture)
+ if (expect->flags & TCPCHK_EXPT_FL_CAP)
match = regex_exec_match2(expect->regex, b_head(&trash), MIN(b_data(&trash), b_size(&trash)-1),
MAX_MATCH, pmatch, 0);
else
}
/* Result as expected, next rule. */
- if (match ^ expect->inverse)
+ if (match ^ inverse)
goto out;
tcpcheck->expect.head = tcpcheck;
list_for_each_entry_rev(prev_check, rules->list, list) {
if (prev_check->action == TCPCHK_ACT_EXPECT) {
- if (prev_check->expect.inverse)
+ if (prev_check->expect.flags & TCPCHK_EXPT_FL_INV)
tcpcheck->expect.head = prev_check;
continue;
}
chk->comment = comment; comment = NULL;
chk->expect.type = type;
chk->expect.min_recv = min_recv;
- chk->expect.inverse = inverse;
- chk->expect.with_capture = with_capture;
+ chk->expect.flags |= (inverse ? TCPCHK_EXPT_FL_INV : 0);
+ chk->expect.flags |= (with_capture ? TCPCHK_EXPT_FL_CAP : 0);
chk->expect.ok_status = ok_st;
chk->expect.err_status = err_st;
chk->expect.tout_status = tout_st;
chk->expect.head = chk;
list_for_each_entry_rev(prev_check, rules, list) {
if (prev_check->action == TCPCHK_ACT_EXPECT) {
- if (prev_check->expect.inverse)
+ if (prev_check->expect.flags & TCPCHK_EXPT_FL_INV)
chk->expect.head = prev_check;
continue;
}