示例#1
0
/**
 * Creates a ddv of size equal to the maximal loop depth of the source
 * and target of the statement, according to the dependence polyhedron.
 *
 */
static
CandlDDV*
candl_ddv_create_from_dep(CandlDependence* dep, int loop_id, int ddv_size)
{
  int i, j;
  int pos;
  CandlMatrix* mat = dep->domain;
  CandlStatement* src = dep->source;
  CandlDDV* dv = candl_ddv_alloc(ddv_size);
  dv->loop_id = loop_id;
  dv->deptype = dep->type;

  // Create the template of the system to operate on.
  // Add one dimension at the beginning, and one row for the extra constraint.
  int nb_par = src->domain->NbColumns - 2 - src->depth;
  CandlMatrix* testsyst =
    candl_matrix_malloc(mat->NbRows + 1, mat->NbColumns + 1);
  for (pos = 0; pos < mat->NbRows; ++pos)
    {
      CANDL_assign(testsyst->p[pos][0], mat->p[pos][0]);
      for (j = 1; j < mat->NbColumns; ++j)
	CANDL_assign(testsyst->p[pos][j + 1], mat->p[pos][j]);
    }
  int has_eq, has_pos, has_neg, has_cst;
  int scal1, scal2;
  for (i = 1; i <= ddv_size; ++i)
    {
      // Test for '='.
      CANDL_set_si(testsyst->p[pos][0], 0);
      CANDL_set_si(testsyst->p[pos][1 + i], 1);
      CANDL_set_si(testsyst->p[pos][1 + i + src->depth], -1);
      CANDL_set_si(testsyst->p[pos][testsyst->NbColumns - 1], 0);
      has_eq = candl_ddv_has_point(testsyst);

      // Test for '>'.
      CANDL_set_si(testsyst->p[pos][0], 1);
      CANDL_set_si(testsyst->p[pos][1 + i], 1);
      CANDL_set_si(testsyst->p[pos][1 + i + src->depth], -1);
      CANDL_set_si(testsyst->p[pos][testsyst->NbColumns - 1], -1);
      has_pos = candl_ddv_has_point(testsyst);

      // Test for '<'.
      CANDL_set_si(testsyst->p[pos][0], 1);
      CANDL_set_si(testsyst->p[pos][1 + i], -1);
      CANDL_set_si(testsyst->p[pos][1 + i + src->depth], 1);
      CANDL_set_si(testsyst->p[pos][testsyst->NbColumns - 1], -1);
      has_neg = candl_ddv_has_point(testsyst);

      // Test for constant distance.
      // min(x_R^i - x_S^i)
      // max(x_R^i - x_S^i) = - min(- x_R^i + x_S^i)
      CANDL_set_si(testsyst->p[pos][0], 0);
      CANDL_set_si(testsyst->p[pos][1], 1);
      CANDL_set_si(testsyst->p[pos][1 + i], -1);
      CANDL_set_si(testsyst->p[pos][1 + i + src->depth], 1);
      CANDL_set_si(testsyst->p[pos][testsyst->NbColumns - 1], 0);
      has_cst = candl_ddv_constant_val(testsyst, &scal1, nb_par);

      if (has_cst)
	{
	  CANDL_set_si(testsyst->p[pos][1 + i], 1);
	  CANDL_set_si(testsyst->p[pos][1 + i + src->depth], -1);
	  CANDL_set_si(testsyst->p[pos][1], 1);
	  has_cst = candl_ddv_constant_val(testsyst, &scal2, nb_par);
	  scal2 *= -1;
	  if (has_cst)
	    has_cst = (scal1 == scal2);
	}

      if (has_cst && scal1 != 0)
	{
	  candl_ddv_set_type_at (dv, candl_dv_scalar, i - 1);
	  candl_ddv_set_value_at (dv, scal1, i - 1);
	}
      else if (has_pos && has_neg)
	candl_ddv_set_type_at (dv, candl_dv_star, i - 1);
      else if (has_pos)
	candl_ddv_set_type_at (dv, candl_dv_plus, i - 1);
      else if (has_neg)
	candl_ddv_set_type_at (dv, candl_dv_minus, i - 1);
      else if (has_eq)
	{
	  candl_ddv_set_type_at (dv, candl_dv_eq, i - 1);
	  candl_ddv_set_value_at (dv, 0, i - 1);
	}

      // Reset the constraint.
      CANDL_set_si(testsyst->p[pos][0], 0);
      CANDL_set_si(testsyst->p[pos][1], 0);
      CANDL_set_si(testsyst->p[pos][1 + i], 0);
      CANDL_set_si(testsyst->p[pos][1 + i + src->depth], 0);
      CANDL_set_si(testsyst->p[pos][testsyst->NbColumns - 1], 0);
    }

  return dv;
}
示例#2
0
文件: ddv.c 项目: Ced/candl
/**
 * Creates a ddv of size equal to the maximal loop depth of the source
 * and target of the statement, according to the dependence polyhedron.
 *
 */
static
CandlDDV*
candl_ddv_create_from_dep(osl_dependence_p dep, int loop_id, int ddv_size) {
  osl_relation_p mat = dep->domain;
  osl_statement_p src = dep->stmt_source_ptr;
  candl_statement_usr_p usr = src->usr;
  CandlDDV* dv = candl_ddv_alloc(ddv_size);
  int precision = src->domain->precision;
  int i, j;
  int pos;
  
  dv->loop_id = loop_id;
  dv->deptype = dep->type;

  // Create the template of the system to operate on.
  // Add one dimension at the beginning, and one row for the extra constraint.
  int nb_par = src->domain->nb_parameters;
  osl_relation_p testsyst = osl_relation_pmalloc(precision,
                                                 mat->nb_rows + 1,
                                                 mat->nb_columns + 1);
  for (pos = 0; pos < mat->nb_rows; ++pos) {
    osl_int_assign(precision, &testsyst->m[pos][0], mat->m[pos][0]);
    for (j = 1; j < mat->nb_columns; ++j)
      osl_int_assign(precision, &testsyst->m[pos][j + 1],mat->m[pos][j]);
  }
  
  int has_eq, has_pos, has_neg, has_cst;
  int scal1, scal2;
  for (i = 1; i <= ddv_size; ++i) {
    // Test for '='.
    osl_int_set_si(precision, &testsyst->m[pos][0], 0);
    osl_int_set_si(precision, &testsyst->m[pos][1 + i], 1);
    osl_int_set_si(precision, &testsyst->m[pos][1 + i + usr->depth], -1);
    osl_int_set_si(precision, &testsyst->m[pos][testsyst->nb_columns-1], 0);
    has_eq = pip_has_rational_point(testsyst, NULL, 1);

    // Test for '>'.
    osl_int_set_si(precision, &testsyst->m[pos][0], 1);
    osl_int_set_si(precision, &testsyst->m[pos][1 + i], 1);
    osl_int_set_si(precision, &testsyst->m[pos][1 + i + usr->depth], -1);
    osl_int_set_si(precision, &testsyst->m[pos][testsyst->nb_columns-1], -1);
    has_pos = pip_has_rational_point(testsyst, NULL, 1);

    // Test for '<'.
    osl_int_set_si(precision, &testsyst->m[pos][0], 1);
    osl_int_set_si(precision, &testsyst->m[pos][1 + i], -1);
    osl_int_set_si(precision, &testsyst->m[pos][1 + i + usr->depth], 1);
    osl_int_set_si(precision, &testsyst->m[pos][testsyst->nb_columns-1], -1);
    has_neg = pip_has_rational_point(testsyst, NULL, 1);

    // Test for constant distance.
    // min(x_R^i - x_S^i)
    // max(x_R^i - x_S^i) = - min(- x_R^i + x_S^i)
    osl_int_set_si(precision, &testsyst->m[pos][0], 0);
    osl_int_set_si(precision, &testsyst->m[pos][1], 1);
    osl_int_set_si(precision, &testsyst->m[pos][1 + i], -1);
    osl_int_set_si(precision, &testsyst->m[pos][1 + i + usr->depth], 1);
    osl_int_set_si(precision, &testsyst->m[pos][testsyst->nb_columns-1], 0);
    has_cst = candl_ddv_constant_val(testsyst, &scal1, nb_par);

    if (has_cst) {
      osl_int_set_si(precision, &testsyst->m[pos][1 + i], 1);
      osl_int_set_si(precision, &testsyst->m[pos][1 + i + usr->depth], -1);
      osl_int_set_si(precision, &testsyst->m[pos][1], 1);
      has_cst = candl_ddv_constant_val(testsyst, &scal2, nb_par);
      scal2 *= -1;
      if (has_cst)
        has_cst = (scal1 == scal2);
    }

    if (has_cst && scal1 != 0) {
      candl_ddv_set_type_at(dv, candl_dv_scalar, i - 1);
      candl_ddv_set_value_at(dv, scal1, i - 1);
    }
    else if (has_pos && has_neg)
      candl_ddv_set_type_at(dv, candl_dv_star, i - 1);
    else if (has_pos)
      candl_ddv_set_type_at(dv, candl_dv_plus, i - 1);
    else if (has_neg)
      candl_ddv_set_type_at(dv, candl_dv_minus, i - 1);
    else if (has_eq) {
      candl_ddv_set_type_at(dv, candl_dv_eq, i - 1);
      candl_ddv_set_value_at(dv, 0, i - 1);
    }

    // Reset the constraint.
    osl_int_set_si(precision, &testsyst->m[pos][0], 0);
    osl_int_set_si(precision, &testsyst->m[pos][1], 0);
    osl_int_set_si(precision, &testsyst->m[pos][1 + i], 0);
    osl_int_set_si(precision, &testsyst->m[pos][1 + i + usr->depth], 0);
    osl_int_set_si(precision, &testsyst->m[pos][testsyst->nb_columns-1], 0);
  }

  return dv;
}