Beispiel #1
0
void trace_tree_emit_rule(struct xswitch *sw, struct trace_tree *tree)
{
	struct match *ma = match();
	struct action *ac_pi = action();
	action_add(ac_pi, AC_PACKET_IN, 0);
	emit_rule(sw, sw->table0, tree, ma, 1, ac_pi);
	action_free(ac_pi);
	match_free(ma);
}
Beispiel #2
0
void emit_ast(struct ast_s * n) {
    struct rule_list_s * r;
    if (n->list) {
	int count = 0;

	for (r = n->list; r; r = r->list)
	    count++;
	if (count > 1) {
	    nest();
	    /* semicolons are OR */
	    printf("or\n");
	}
	for (r = n->list; r; r = r->list) {
	    if (r->rule) {
		emit_rule(r->rule);
	    }
	}
	if (count > 1)
	    unnest();
    }
}
Beispiel #3
0
static int emit_rule(struct xswitch *sw, struct flow_table *ft,
		     struct trace_tree *tree, struct match *ma, int priority,
		     struct action *ac_pi)
{
	int i;
	struct trace_tree_L *tl;
	struct trace_tree_V *tv;
	struct trace_tree_T *tt;
	struct trace_tree_D *td;
	struct trace_tree_G *tg;

	struct msgbuf *msg;
	struct match *maa;
	struct action *a;
	char buf[128], buf2[128];

	struct expr *move_expr;
	switch(tree->type) {
	case TT_L:
		tl = (struct trace_tree_L *)tree;
		match_dump(ma, buf, 128);
		action_dump(tl->ac, buf2, 128);
		xdebug("tid %d: %2d, %s, %s\n",
		       flow_table_get_tid(ft), priority, buf, buf2);
		if(tl->index == -1) {
			tl->index = flow_table_get_entry_index(ft);
			msg = msg_flow_entry_add(ft, tl->index, priority, ma, tl->ac);
		} else {
			msg = msg_flow_entry_mod(ft, tl->index, priority, ma, tl->ac);
		}
		xswitch_send(sw, msg);
		return priority + 1;
	case TT_V:
		tv = (struct trace_tree_V *)tree;
		for(i = 0; i < tv->num_branches; i++) {
			maa = match_copy(ma);
			match_add(maa,
				  tv->name,
				  tv->branches[i].value,
				  value_from_64(0xffffffffffffffffull));
			priority = emit_rule(sw, ft, tv->branches[i].tree, maa, priority, ac_pi);
			match_free(maa);
		}
		return priority;
	case TT_T:
		tt = (struct trace_tree_T *)tree;
		priority = emit_rule(sw, ft, tt->f, ma, priority, ac_pi);
		maa = match_copy(ma);
		match_add(maa,
			  tt->name,
			  tt->value,
			  value_from_64(0xffffffffffffffffull));
		action_dump(ac_pi, buf, 128);
		xdebug("tid %d: %2d, BARRIER, %s\n",
		       flow_table_get_tid(ft), priority, buf);
		if(tt->barrier_index == -1) {
			tt->barrier_index = flow_table_get_entry_index(ft);
			msg = msg_flow_entry_add(ft, tt->barrier_index, priority, maa, ac_pi);
		} else {
			msg = msg_flow_entry_mod(ft, tt->barrier_index, priority, maa, ac_pi);
		}
		xswitch_send(sw, msg);
		priority = emit_rule(sw, ft, tt->t, maa, priority + 1, ac_pi);
		match_free(maa);
		return priority;
	case TT_G:
		tg = (struct trace_tree_G *)tree;
		if(tg->ft == NULL) {
			int tid = sw->next_table_id++;
			// add a new table
			tg->ft = header_make_flow_table(tg->new_spec, tid);
			msg = msg_flow_table_add(tg->ft);
			xswitch_send(sw, msg);
			init_entry(sw, tg->ft);
		}
		// insert GOTO_TABLE into orig table
		a = action();
		if(tg->old_spec)
			move_expr = header_get_length(tg->old_spec);
		else
			move_expr = expr_value(0);
		expr_generate_action(move_expr, tg->old_spec, tg->ft, tg->stack_base, a);

		match_dump(ma, buf, 128);
		action_dump(a, buf2, 128);
		xdebug("tid %d: %2d, %s, %s\n",
		       flow_table_get_tid(ft), priority, buf, buf2);

		if(tg->index == -1) {
			tg->index = flow_table_get_entry_index(ft);
			msg = msg_flow_entry_add(ft, tg->index, priority, ma, a);
		} else {
			msg = msg_flow_entry_mod(ft, tg->index, priority, ma, a);
		}
		xswitch_send(sw, msg);
		action_free(a);

		maa = match();
		emit_rule(sw, tg->ft, tg->t, maa, 1, ac_pi);
		match_free(maa);
		return priority + 1;
	case TT_D:
		td = (struct trace_tree_D *)tree;
		return emit_rule(sw, ft, td->t, ma, priority, ac_pi);
	case TT_E:
		return priority;
	}
	assert(0);
}