示例#1
0
static void test_bool_ops()
{
    Expr *e_not_t = expr_not(expr_true());
    Expr *e_not_f = expr_not(expr_false());
    Expr *e_and_tt = expr_and(expr_true(), expr_true());
    Expr *e_and_tf = expr_and(expr_true(), expr_false());
    Expr *e_or_tf = expr_or(expr_true(), expr_false());
    Expr *e_or_ff = expr_or(expr_false(), expr_false());

    if (expr_bool_val(e_not_t, NULL, NULL) != 0)
        fail();
    if (expr_bool_val(e_not_f, NULL, NULL) == 0)
        fail();
    if (expr_bool_val(e_and_tt, NULL, NULL) == 0)
        fail();
    if (expr_bool_val(e_and_tf, NULL, NULL) != 0)
        fail();
    if (expr_bool_val(e_or_tf, NULL, NULL) == 0)
        fail();
    if (expr_bool_val(e_or_ff, NULL, NULL) != 0)
        fail();

    expr_free(e_not_t);
    expr_free(e_not_f);
    expr_free(e_and_tt);
    expr_free(e_and_tf);
    expr_free(e_or_tf);
    expr_free(e_or_ff);
}
示例#2
0
/* L -> 'a' .. 'z' | 'A' .. 'Z' | '(' S ')' | '[' S ']' */
static inline node* expr_sym(expr *e) {
	node *a;
	uint8_t v;
	expr_eat_white(e);
	if (e->str[0]=='(') {
		e->str++;
		expr_eat_white(e);
		a=expr_or(e);
		expr_eat_white(e);
		if (e->str[0]==')') {
			e->str++;
			return a;
		} else {
			if ((int8_t)(e->str[0])>=32) {
				printf("parse error, closing round bracket expected, next char: '%c'\n",e->str[0]);
			} else {
				printf("parse error, closing round bracket expected, next code: 0x%02"PRIX8"\n",(uint8_t)(e->str[0]));
			}
			expr_rfree(a);
			e->erroroccured = 1;
			return NULL;
		}
	}
	if (e->str[0]=='[') {
		e->str++;
		expr_eat_white(e);
		a=expr_or(e);
		expr_eat_white(e);
		if (e->str[0]==']') {
			e->str++;
			return a;
		} else {
			if ((int8_t)(e->str[0])>=32) {
				printf("parse error, closing round bracket expected, next char: '%c'\n",e->str[0]);
			} else {
				printf("parse error, closing round bracket expected, next code: 0x%02"PRIX8"\n",(uint8_t)(e->str[0]));
			}
			expr_rfree(a);
			e->erroroccured = 1;
			return NULL;
		}
	}
	if (e->str[0]>='A' && e->str[0]<='Z') {
		v = e->str[0]-'A';
		e->str++;
		return newnode(SYM,v,NULL,NULL);
	}
	if (e->str[0]>='a' && e->str[0]<='z') {
		v = e->str[0]-'a';
		e->str++;
		return newnode(SYM,v,NULL,NULL);
	}
	if ((int8_t)(e->str[0])>=32) {
		printf("parse error, next char: '%c'\n",e->str[0]);
	} else {
		printf("parse error, next code: 0x%02"PRIX8"\n",(uint8_t)(e->str[0]));
	}
	e->erroroccured = 1;
	return NULL;
}
示例#3
0
文件: pass_cnf.c 项目: GJDuck/SMCHR
/*
 * CNF transformation one-level down.
 */
static expr_t cnf_expr_nextlevel(expr_t e, context_t context)
{
    if (expr_gettype(e) != EXPRTYPE_OP)
        return e;

    switch (expr_op(e))
    {
        case EXPROP_NOT:
        case EXPROP_OR:
        {
            expr_t or = expr_bool(false), k, v;
            for (expritr_t i = expritr(e); expr_getpair(i, &k, &v);
                    expr_next(i))
            {
                k = cnf_arg(k, context);
                if (v == expr_bool(true))
                    k = expr_not(k);
                or = expr_or(k, or);
            }
            return or;
        }
        default:
            e = cnf_arg(e, context);
            return e;
    }
}
示例#4
0
/* E -> '*' | S */
static inline node* expr_first(expr *e) {
	expr_eat_white(e);
	if (e->str[0]=='*') {
		e->str++;
		return newnode(ANY,0,NULL,NULL);
	}
	return expr_or(e);
}
示例#5
0
文件: pass_cnf.c 项目: GJDuck/SMCHR
/*
 * Eliminate <->s from an expression.
 */
static expr_t iffelim_expr(expr_t e, bool c)
{
    if (expr_gettype(e) != EXPRTYPE_OP)
        return e;

    exprop_t op = expr_op(e);
    switch (op)
    {
        case EXPROP_NOT: case EXPROP_AND: case EXPROP_OR:
        {
            expr_t acc = (op == EXPROP_OR? expr_bool(false): expr_bool(true));
            expr_t k, v;
            for (expritr_t i = expritr(e); expr_getpair(i, &k, &v);
                    expr_next(i))
            {
                bool d = (op != EXPROP_OR);
                d = (v == expr_bool(true)? !d: d);
                k = iffelim_expr(k, d);
                if (v == expr_bool(true))
                    k = expr_not(k);
                acc = (op == EXPROP_OR? expr_or(acc, k): expr_and(acc, k));
            }
            return acc;
        }
        case EXPROP_IFF:
        {
            expr_t x = iffelim_expr(expr_arg(e, 0), c);
            expr_t y = iffelim_expr(expr_arg(e, 1), c);
            if (c)
            {
                expr_t c1 = expr_or(expr_not(x), y);
                expr_t c2 = expr_or(x, expr_not(y));
                return expr_and(c1, c2);
            }
            else
            {
                expr_t c1 = expr_and(x, y);
                expr_t c2 = expr_and(expr_not(x), expr_not(y));
                return expr_or(c1, c2);
            }
        }
        default:
            return e;
    }
}
示例#6
0
/* S -> S '+' M | S '|' M | S '||' M | M */
static inline node* expr_or(expr *e) {
	node *a;
	node *b;
	expr_eat_white(e);
	a = expr_and(e);
	expr_eat_white(e);
	if (e->str[0]=='|' && e->str[1]=='|') {
		e->str += 2;
		b = expr_or(e);
		return newnode(OR,0,a,b);
	} else if (e->str[0]=='|' || e->str[0]=='+') {
		e->str ++;
		b = expr_or(e);
		return newnode(OR,0,a,b);
	} else {
		return a;
	}
}
示例#7
0
static void test_select()
{
    int a, b, c;
    Type ta, tb, tc;

    Rel *src = load("select_1");
    head_attr(src->head, "b", &b, &tb);
    Expr *expr = expr_eq(expr_real(1.01), expr_attr(b, tb));
    Rel *r = rel_select(src, expr);

    if (!equal(r, "select_1_res"))
        fail();

    src = load("select_2");
    head_attr(src->head, "a", &a, &ta);
    head_attr(src->head, "b", &b, &tb);
    head_attr(src->head, "c", &c, &tc);
    expr = expr_or(expr_gt(expr_attr(b, tb),
                           expr_real(4.00)),
                   expr_lt(expr_attr(a, ta),
                           expr_int(2)));
    expr = expr_or(expr,
                   expr_lt(expr_attr(c, tc),
                           expr_str("aab")));
    r = rel_select(src, expr);
    if (!equal(r, "select_2_res"))
        fail();

    src = load("select_3");
    head_attr(src->head, "a", &a, &ta);
    head_attr(src->head, "b", &b, &tb);
    expr = expr_and(expr_not(expr_attr(a, ta)),
                    expr_not(expr_eq(expr_attr(b, tb),
                                     expr_real(1.01))));
    r = rel_select(src, expr);
    
    if (!equal(r, "select_3_res"))
        fail();
}
示例#8
0
文件: expr.cpp 项目: jackbackrack/cad
Expr* expr_zbox(Expr* a, Expr* b) {
  Expr* za = expr_sub(a->zmax,a->zmin);
  Expr* zb = expr_sub(b->zmax,b->zmin);
  Expr* r  = expr_mul(expr_lit(0.5),expr_add(za,zb));
  auto tg  = expr_or(expr_zmov(expr_sub(expr_neg(r),a->zmin),a),
                     expr_zmov(expr_sub(expr_add(expr_neg(r),za),b->zmin),b));
  tg->zmin = expr_neg(r);
  tg->zmax = r;
  tg->xmin = expr_min(a->xmin, b->xmin);
  tg->xmax = expr_max(a->xmax, b->xmax);
  tg->ymin = expr_min(a->ymin, b->ymin);
  tg->ymax = expr_max(a->ymax, b->ymax);
  return tg;
}
示例#9
0
static void test_compound()
{
    char *names[] = {"a", "b", "c"};
    Type types[] = {Int, Real, String};

    int a, b, c;
    Type ta, tb, tc;
    Head *h = head_new(names, types, 3);
    head_attr(h, "a", &a, &ta);
    head_attr(h, "b", &b, &tb);
    head_attr(h, "c", &c, &tc);

    int v_int = 3;
    double v_real = 1.01;
    char *v_str = "bbb";

    Value vals[3];
    vals[0] = val_new_int(&v_int);
    vals[1] = val_new_real(&v_real);
    vals[2] = val_new_str(v_str);
    Tuple *t = tuple_new(vals, 3);

    Expr *expr = expr_or(expr_gt(expr_attr(b, Real),
                                 expr_real(4.00)),
                         expr_lt(expr_attr(a, Int),
                                 expr_int(2)));
    expr = expr_or(expr,
                   expr_lt(expr_attr(c, String),
                           expr_str("aab")));

    if (expr_bool_val(expr, t, NULL))
        fail();

    expr_free(expr);
    tuple_free(t);
    mem_free(h);
}
示例#10
0
文件: expr.cpp 项目: jackbackrack/cad
Expr* expr_ybox(Expr* a, Expr* b) {
  Expr* ha = expr_sub(a->ymax,a->ymin);
  Expr* hb = expr_sub(b->ymax,b->ymin);
  Expr* r = expr_mul(expr_lit(0.5),expr_add(ha,hb));
  auto tg = expr_or(expr_ymov(expr_sub(expr_neg(r),a->ymin),a),expr_ymov(expr_sub(expr_add(expr_neg(r),ha),b->ymin),b));
  tg->ymin = expr_neg(r);
  tg->ymax = r;
  tg->xmin = expr_min(a->xmin, b->xmin);
  tg->xmax = expr_max(a->xmax, b->xmax);
  if (a->zmin != NULL && b->zmin != NULL) {
    tg->zmin = expr_min(a->zmin, b->zmin);
    tg->zmax = expr_max(a->zmax, b->zmax);
  }
  return tg;
}
示例#11
0
文件: pass_cnf.c 项目: GJDuck/SMCHR
/*
 * CNF transformation on a Boolean argument.
 */
static expr_t cnf_arg(expr_t e, context_t context)
{
    if (expr_gettype(e) != EXPRTYPE_OP)
        return e;

    expr_t b = cnf_new_var(context), nb = expr_not(b);
    switch (expr_op(e))
    {
        case EXPROP_NOT:
        case EXPROP_AND:
        {
            expr_t clause = expr_bool(false), k, nk, v;
            for (expritr_t i = expritr(e); expr_getpair(i, &k, &v);
                    expr_next(i))
            {
                k = cnf_arg(k, context);
                nk = expr_not(k);
                if (v == expr_bool(true))
                {
                    expr_t tmp = k;
                    k = nk;
                    nk = tmp;
                }
                clause = expr_or(nk, clause);
                context_insertclause(context, expr_or(k, nb));
            }
            clause = expr_or(b, clause);
            context_insertclause(context, clause);
            return b;
        }
        case EXPROP_OR:
        {
            expr_t clause = expr_bool(false), k, nk, v;
            for (expritr_t i = expritr(e); expr_getpair(i, &k, &v);
                    expr_next(i))
            {
                k = cnf_arg(k, context);
                nk = expr_not(k);
                if (v == expr_bool(true))
                {
                    expr_t tmp = k;
                    k = nk;
                    nk = tmp;
                }
                clause = expr_or(k, clause);
                context_insertclause(context, expr_or(nk, b));
            }
            clause = expr_or(nb, clause);
            context_insertclause(context, clause);
            return b;
        }
        default:
            return context_insertiff(context, e, (expr_t)NULL);
    }
}
示例#12
0
int
b_expr(int argc, char** argv, Shbltin_t* context)
{
	State_t	state;
	Node_t	node;
	int	n;

	cmdinit(argc, argv, context, ERROR_CATALOG, 0);
	state.standard = !!conformance(0, 0);
#if 0
	if (state.standard)
		state.arglist = argv+1;
	else
#endif
	{
		while (n=optget(argv, usage))
		{
			/*
			 * NOTE: this loop ignores all but literal -- and -?
			 *	 out of kindness for obsolescent usage
			 *	 (and is ok with the standard) but strict
			 *	 getopt conformance would give usage for all
			 *	 unknown - options
			 */
			if(n=='?')
				error(ERROR_usage(2), "%s", opt_info.arg);
			if (opt_info.option[1] != '?')
				break;
			error(ERROR_usage(2), "%s", opt_info.arg);
		}
		if (error_info.errors)
			error(ERROR_usage(2),"%s",optusage((char*)0));
		state.arglist = argv+opt_info.index;
	}
	if (expr_or(&state, &node))
		error(ERROR_exit(2),"syntax error");
	if (node.type&T_STR)
	{
		if (*node.str)
			sfprintf(sfstdout,"%s\n",node.str);
	}
	else
		sfprintf(sfstdout,"%d\n",node.num);
	return numeric(&node)?node.num==0:*node.str==0;
}
示例#13
0
文件: expr.cpp 项目: jackbackrack/cad
Expr* polygonize (Nested<TV2> p) {
  Mesh mesh = triangulate(p);
  // printf("%d VERTICES %d INDICES\n", (int)mesh.vertices.size(), (int)mesh.indices.size());
  Expr* res = expr_none();
  Boxy box(vec( INFTY,  INFTY,  INFTY), vec(-INFTY, -INFTY, -INFTY));
  for (auto tri : mesh.soup->elements) {
    Vec p0 = mesh.points[tri.x];
    Vec p1 = mesh.points[tri.y];
    Vec p2 = mesh.points[tri.z];
    box = add(add(add(box, p0), p1), p2);
    res = expr_or(res, expr_triangle(expr_lit(p0.x), expr_lit(p0.y), expr_lit(p1.x), expr_lit(p1.y), expr_lit(p2.x), expr_lit(p2.y)));
  }
  res->xmin = expr_lit(box.lo.x);
  res->ymin = expr_lit(box.lo.y);
  res->zmin = expr_lit(box.lo.z);
  res->xmax = expr_lit(box.hi.x);
  res->ymax = expr_lit(box.hi.y);
  res->zmax = expr_lit(box.hi.z);
  return res;
}
示例#14
0
/*
 * Flattening transformation.
 */
static expr_t flatten(expr_t e, bool toplevel, context_t cxt)
{
    if (expr_gettype(e) != EXPRTYPE_OP)
        return e;

    exprop_t op = expr_op(e);
    switch (op)
    {
        case EXPROP_EQ:
        {
            expr_t x, y;
            if (expr_view_x_eq_func(e, &x, &y))
            {
                y = flatten(y, false, cxt);
                return flatten_eq_to_builtin(exprop_atom_make(ATOM_INT_EQ),
                    x, y, toplevel, cxt);

            }
            // Fall-through:
        }
        case EXPROP_NEQ: case EXPROP_LT: case EXPROP_LEQ: case EXPROP_GT:
        case EXPROP_GEQ:
        {
            // Check if already a flattened comparison:
            exprop_t binop, cmp;
            expr_t x, y, z;
            if (expr_view_x_cmp_y(e, &x, &cmp, &y))
                return flatten_x_cmp_y_to_builtin(x, cmp, y, cxt);
            if (expr_view_x_cmp_y_op_z(e, &x, &cmp, &y, &binop, &z))
            {
                y = expr_make(binop, y, z);
                return flatten_eq_to_builtin(exprop_atom_make(ATOM_INT_EQ),
                    x, y, toplevel, cxt);
            }

            e = expr_arg(e, 1);
            if (!expr_view_plus_sign_partition(e, &x, &y))
                panic("failed to partition (+) expression");
            if (op == EXPROP_EQ)
            {
                expr_t x0, x1;
                if (expr_view_plus_first_partition(x, &x0, &x1))
                {
                    x1 = flatten_to_primitive(x1, cxt);
                    y = flatten_to_var(y, cxt);
                    e = expr_make(EXPROP_ADD, x0, x1);
                    return flatten_eq_to_builtin(exprop_atom_make(ATOM_INT_EQ),
                        y, e, toplevel, cxt);
                }
                expr_t y0, y1;
                if (expr_view_plus_first_partition(y, &y0, &y1))
                {
                    y1 = flatten_to_primitive(y1, cxt);
                    x = flatten_to_var(x, cxt);
                    e = expr_make(EXPROP_ADD, y0, y1);
                    return flatten_eq_to_builtin(exprop_atom_make(ATOM_INT_EQ),
                        x, e, toplevel, cxt);
                }
                x = flatten_to_primitive(x, cxt);
                y = flatten_to_primitive(y, cxt);
                return flatten_eq_to_builtin(exprop_atom_make(ATOM_INT_EQ),
                    x, y, toplevel, cxt);
            }
            else
            {
                x = flatten_to_primitive(x, cxt);
                y = flatten_to_primitive(y, cxt);
                if (expr_gettype(y) == EXPRTYPE_NUM)
                {
                    num_t c = expr_getnum(y);
                    y = expr_num(c - 1);
                    e = flatten_x_cmp_y_to_builtin(x, cmp, y, cxt);
                    return expr_not(e);
                }
                else
                    return flatten_x_cmp_y_to_builtin(y, cmp, x, cxt);
            }
        }
        case EXPROP_NOT:
        {
            expr_t arg = expr_arg(e, 0);
            arg = flatten(arg, toplevel, cxt);
            return expr_not(arg);
        }
        case EXPROP_IFF:
        {
            expr_t arg0 = flatten(expr_arg(e, 0), false, cxt);
            expr_t arg1 = flatten(expr_arg(e, 1), false, cxt);
            return expr_iff(arg0, arg1);
        }
        case EXPROP_AND:
        {
            expr_t and = expr_bool(true), k, v;
            for (expritr_t i = expritr(e); expr_getpair(i, &k, &v);
                    expr_next(i))
            {
                k = flatten(k, toplevel, cxt);
                if (v == expr_bool(true))
                    k = expr_not(k);
                and = expr_and(k, and);
            }
            return and;
        }
        case EXPROP_OR:
        {
            expr_t or = expr_bool(false), k, v;
            for (expritr_t i = expritr(e); expr_getpair(i, &k, &v);
                    expr_next(i))
            {
                k = flatten(k, false, cxt);
                if (v == expr_bool(true))
                    k = expr_not(k);
                or = expr_or(k, or);
            }
            return or;
        }
        case EXPROP_ADD: case EXPROP_MUL:
        {
            size_t a = expr_arity(e);
            expr_t args[a];
            expr_args(e, args);
            for (size_t i = 0; i < a; i++)
                args[i] = flatten_to_primitive(args[i], cxt);
            e = expr(op, args);
            return e;
        }
        case EXPROP_POW:
        {
            expr_t arg1 = expr_arg(e, 1);
            if (expr_gettype(arg1) != EXPRTYPE_NUM)
            {
flatten_bad_pow:
                error("(%s: %zu) failed to flatten expression `!y%s!d'; "
                    "exponent must be a positive constant, found `!y%s!d'",
                    cxt->file, cxt->line, show(expr_term(e)),
                    show(expr_term(arg1)));
                cxt->error = true;
                return e;
            }
            num_t c = expr_getnum(arg1);
            if (c <= 1)
                goto flatten_bad_pow;
            expr_t arg0 = flatten_to_primitive(expr_arg(e, 0), cxt);
            expr_t e = expr_pow(arg0, arg1);
            return e;
        }
        default:
        {
            atom_t atom = expr_sym(e);
            if (atom == ATOM_NIL_EQ || atom == ATOM_STR_EQ ||
                atom == ATOM_ATOM_EQ || is_eq(atom))
            {
                expr_t x = expr_arg(e, 0), y = expr_arg(e, 1);
                x = flatten(x, false, cxt);
                y = flatten(y, false, cxt);
                return flatten_eq_to_builtin(expr_op(e), x, y, toplevel, cxt);
            }
            size_t a = expr_arity(e);
            expr_t args[a];
            expr_args(e, args);
            typesig_t sig = typeinst_get_decl((atom_t)op);
            for (size_t i = 0; i < a; i++)
            {
                typeinst_t t = typeinst_decl_arg(sig, i);
                if (t != typeinst_make_ground(t))
                    args[i] = flatten_to_var(args[i], cxt);
                else
                {
                    // Note: type check does not check instances; we check
                    //       here.
                    if (type(args[i]) == VAR || type(args[i]) == FUNC)
                    {
                        error("(%s: %zu) failed to flatten expression "
                            "`!y%s!d'; cannot flatten %s argument "
                            "`!y%s!d' to a ground term",  cxt->file,
                            cxt->line, show(expr_term(e)),
                            (type(args[i]) == VAR? "variable":
                                "function call"),
                            show(expr_term(args[i])));
                        cxt->error = true;
                    }
                }
            }
            e = expr(op, args);
            return e;
        }
    }
}
示例#15
0
static int getnode(State_t* state, Node_t *np)
{
	register char*	sp;
	register char*	cp;
	register int	i;
	register int	j;
	register int	k;
	register int	tok;
	char*		ep;

	if (!(cp = *state->arglist++))
		error(ERROR_exit(2), "argument expected");
	if (!state->standard)
		switch (cp[0])
		{
		case 'i':
			if (cp[1] == 'n' && !strcmp(cp, "index"))
			{
				if (!(cp = *state->arglist++))
					error(ERROR_exit(2), "string argument expected");
				if (!(ep = *state->arglist++))
					error(ERROR_exit(2), "chars argument expected");
				np->num = (ep = strpbrk(cp, ep)) ? (ep - cp + 1) : 0;
				np->type = T_NUM;
				goto next;
			}
			break;
		case 'l':
			if (cp[1] == 'e' && !strcmp(cp, "length"))
			{
				if (!(cp = *state->arglist++))
					error(ERROR_exit(2), "string argument expected");
				np->num = strlen(cp);
				np->type = T_NUM;
				goto next;
			}
			break;
		case 'm':
			if (cp[1] == 'a' && !strcmp(cp, "match"))
			{
				if (!(np->str = *state->arglist++))
					error(ERROR_exit(2), "pattern argument expected");
				np->type = T_STR;
				return ':';
			}
			break;
		case 'q':
			if (cp[1] == 'u' && !strcmp(cp, "quote") && !(cp = *state->arglist++))
				error(ERROR_exit(2), "string argument expected");
			break;
		case 's':
			if (cp[1] == 'u' && !strcmp(cp, "substr"))
			{
				if (!(sp = *state->arglist++))
					error(ERROR_exit(2), "string argument expected");
				if (!(cp = *state->arglist++))
					error(ERROR_exit(2), "position argument expected");
				i = strtol(cp, &ep, 10);
				if (*ep || --i < 0)
					i = -1;
				if (!(cp = *state->arglist++))
					error(ERROR_exit(2), "length argument expected");
				j = strtol(cp, &ep, 10);
				if (*ep)
					j = -1;
				k = strlen(sp);
				if (i < 0 || i >= k || j < 0)
					sp = "";
				else
				{
					sp += i;
					k -= i;
					if (j < k)
						sp[j] = 0;
				}
				np->type = T_STR;
				np->str = sp;
				goto next;
			}
			break;
		}
	if (*cp=='(' && cp[1]==0)
	{
		tok = expr_or(state, np);
		if (tok != ')')
			error(ERROR_exit(2),"closing parenthesis missing");
	}
	else
	{
		np->type = T_STR;
		np->str = cp;
		if (*cp)
		{
			np->num = strtol(np->str,&ep,10);
			if (!*ep)
				np->type |= T_NUM;
		}
	}
 next:
	if (!(cp = *state->arglist))
		return 0;
	state->arglist++;
	for (i=0; i < sizeof(optable)/sizeof(*optable); i++)
		if (*cp==optable[i].opname[0] && cp[1]==optable[i].opname[1])
			return optable[i].op;
	error(ERROR_exit(2),"%s: unknown operator argument",cp);
	return 0;
}
示例#16
0
文件: expr.cpp 项目: jackbackrack/cad
Expr* expr_capsule(Expr* xyrad, Expr* zrad) {
  return expr_or(expr_cylinder(xyrad, zrad),
                 expr_or(expr_zmov(expr_neg(zrad), expr_sphere(xyrad)), expr_zmov(zrad, expr_sphere(xyrad))));
}