コード例 #1
0
/*
 * Reset to the empty table
 */
void reset_intern_tbl(intern_tbl_t *tbl) {
  reset_int32_array(&tbl->map);
  reset_int32_array(&tbl->type);
  reset_uint8_array(&tbl->rank);

  if (tbl->cache != NULL) {
    int_hset_reset(tbl->cache);
  }

  if (tbl->queue != NULL) {
    int_queue_reset(tbl->queue);
  }
}
コード例 #2
0
ファイル: flattening.c プロジェクト: polazarus/ocamlyices2
/*
 * Reset queue/cache and vector
 */
void reset_flattener(flattener_t *flat) {
  int_queue_reset(&flat->queue);
  int_hset_reset(&flat->cache);
  ivector_reset(&flat->resu);
}
コード例 #3
0
/*
 * Check whether t occurs in v
 * - t must be a free root
 * - v must be a valid term
 */
static bool bfs_occurs_check(intern_tbl_t *tbl, term_t t, term_t v) {
  term_table_t *terms;
  int_queue_t *queue;
  int_hset_t *cache;
  int32_t x;
  bool found;

  assert(intern_tbl_root_is_free(tbl, t));
  assert(is_pos_term(t) && term_kind(tbl->terms, t) == UNINTERPRETED_TERM);

  terms = tbl->terms;
  queue = intern_tbl_get_queue(tbl);
  cache = intern_tbl_get_cache(tbl);

  assert(int_queue_is_empty(queue) && int_hset_is_empty(cache));

  bfs_visit_term(tbl, v);
  found = false;

  do {
    x = int_queue_pop(queue);

    switch (kind_for_idx(terms, x)) {
    case CONSTANT_TERM:
    case ARITH_CONSTANT:
    case BV64_CONSTANT:
    case BV_CONSTANT:
    case VARIABLE:
      break;

    case UNINTERPRETED_TERM:
      if (x == index_of(t)) {
        // found a cycle
        found = true;
        goto done;
      }
      break;

    case ARITH_EQ_ATOM:
    case ARITH_GE_ATOM:
      bfs_visit_term(tbl, integer_value_for_idx(terms, x));
      break;

    case ITE_TERM:
    case ITE_SPECIAL:
    case APP_TERM:
    case UPDATE_TERM:
    case TUPLE_TERM:
    case EQ_TERM:
    case DISTINCT_TERM:
    case FORALL_TERM:
    case LAMBDA_TERM:
    case OR_TERM:
    case XOR_TERM:
    case ARITH_BINEQ_ATOM:
    case BV_ARRAY:
    case BV_DIV:
    case BV_REM:
    case BV_SDIV:
    case BV_SREM:
    case BV_SMOD:
    case BV_SHL:
    case BV_LSHR:
    case BV_ASHR:
    case BV_EQ_ATOM:
    case BV_GE_ATOM:
    case BV_SGE_ATOM:
      bfs_visit_composite(tbl, composite_for_idx(terms, x));
      break;

    case BIT_TERM:
    case SELECT_TERM:
      bfs_visit_term(tbl, select_for_idx(terms, x)->arg);
      break;

    case POWER_PRODUCT:
      bfs_visit_pprod(tbl, pprod_for_idx(terms, x));
      break;

    case ARITH_POLY:
      bfs_visit_poly(tbl, polynomial_for_idx(terms, x));
      break;

    case BV64_POLY:
      bfs_visit_bvpoly64(tbl, bvpoly64_for_idx(terms, x));
      break;

    case BV_POLY:
      bfs_visit_bvpoly(tbl, bvpoly_for_idx(terms, x));
      break;

    default:
      assert(false);
      abort();
      break;
    }

  } while (! int_queue_is_empty(queue));

 done:
  int_hset_reset(cache);
  int_queue_reset(queue);

  return found;
}
コード例 #4
0
/*
 * Check whether f is a range constraint
 * - if so return a term t and fill in vector v with the formula's constants
 * - otherwise, return NULL_TERM
 *
 * Side effect: use queue and cache.
 * v may be modified even if the function returns NULL_TERM.
 */
static term_t formula_is_range_constraint(sym_breaker_t *breaker, term_t f, ivector_t *v) {
  int_queue_t *queue;
  int_hset_t *cache;
  term_table_t *terms;
  intern_tbl_t *intern;
  term_t r, t;
  term_t x, a, y, b;
  uint32_t neqs;

  queue = &breaker->queue;
  cache = &breaker->cache;
  terms = breaker->terms;
  intern = &breaker->ctx->intern;

  assert(int_queue_is_empty(queue) && int_hset_is_empty(cache));
  push_term(queue, cache, f);

  neqs = 0;
  t = NULL_TERM;

  y = NULL_TERM; // prevent GCC warning
  b = NULL_TERM; // prevent GCC warning

  /*
   * Invariants:
   * - neqs = number of equality atoms seen so far
   * - if neq == 1, then the first equality is stored as (y == b) where b is a constant
   * - if neq >= 2, then all equalities seen so far were of the form (x == constant)
   */
  do {
    // r := root of the first term in the queue
    r = intern_tbl_get_root(intern, int_queue_pop(queue));

    switch (match_term(breaker->ctx, r, &a, &x)) {
    case MATCH_FALSE: // skip false terms
      break;

    case MATCH_OR:
      push_children(queue, cache, or_term_desc(terms, r));
      break;

    case MATCH_EQ:
      assert(term_is_constant(terms, a));
      if (neqs == 0) {
	y = x; b = a;
      } else if (neqs == 1) {
	/*
	 * First equality: (y == b). Second equality: (x == a)
	 */
	if (y == x) {
	  // y is the common term, a and b are constant
	  ivector_push(v, b);
	  ivector_push(v, a);
	} else if (y == a && term_is_uconst(terms, x)) {
	  // y is the common term, b and x are constant
	  ivector_push(v, b);
	  ivector_push(v, a);
	} else if (x == b && term_is_uconst(terms, y)) {
	  // b is the common term, y and a are constant
	  ivector_push(v, y);
	  ivector_push(v, a);
	  y = b;
	} else if (a == b && term_is_uconst(terms, y) && term_is_uconst(terms, x)) {
	  // b is the common term, y and x are constant
	  ivector_push(v, y);
	  ivector_push(v, x);
	  y = b;
	} else {
	  // abort
	  goto done;
	}

      } else {
	/*
	 * All equalities so far have the form (y == constant)
	 * - the current equality is (x == a)
	 */
	if (y == x) {
	  ivector_push(v, a); // match
	} else if (y == a && term_is_constant(terms, x)) {
	  ivector_push(v, x); // swap a and x
	} else {
	  // no match
	  goto done;
	}
      }
      neqs ++;
      break;

    case MATCH_IFF:
      /*
       * the returned term x is equivalent to t
       */
      push_term(queue, cache, x);
      break;

    default:
      // abort
      goto done;
    }
  } while (! int_queue_is_empty(queue));

  assert(y != NULL_TERM && t == NULL_TERM);

  if (neqs >= 2) {
    assert(v->size == neqs);
    t = y;
  }

 done:
  int_queue_reset(queue);
  int_hset_reset(cache);

  return t;
}