Example #1
0
  private SemanticType propagate(
      Expr.Nary e,
      HashMap<String, SemanticType> environment,
      HashSet<String> generics,
      WyalFile.Context context) {
    Expr[] e_operands = e.operands;
    SemanticType[] op_types = new SemanticType[e_operands.length];

    for (int i = 0; i != e_operands.length; ++i) {
      op_types[i] = propagate(e_operands[i], environment, generics, context);
    }

    switch (e.op) {
      case AND:
      case OR:
        for (int i = 0; i != e_operands.length; ++i) {
          checkIsSubtype(SemanticType.Bool, op_types[i], e_operands[i]);
        }
        return SemanticType.Bool;
      case TUPLE:
        return SemanticType.Tuple(op_types);
      case SET:
        if (op_types.length == 0) {
          return SemanticType.Set(true, SemanticType.Void);
        } else {
          return SemanticType.Set(true, SemanticType.Or(op_types));
        }
      case LIST:
        if (op_types.length == 0) {
          return SemanticType.Set(true, SemanticType.Void);
        } else {
          return SemanticType.Set(
              true, SemanticType.Tuple(SemanticType.Int, SemanticType.Or(op_types)));
        }
    }

    internalFailure("unknown nary expression encountered (" + e + ")", filename, e);
    return null; // deadcode
  }
Example #2
0
  private SemanticType propagate(
      Expr.Binary e,
      HashMap<String, SemanticType> environment,
      HashSet<String> generics,
      WyalFile.Context context) {
    SemanticType lhs_type = propagate(e.leftOperand, environment, generics, context);
    SemanticType rhs_type = propagate(e.rightOperand, environment, generics, context);

    switch (e.op) {
      case ADD:
      case SUB:
      case MUL:
      case DIV:
      case REM:
        checkIsSubtype(SemanticType.IntOrReal, lhs_type, e.leftOperand);
        checkIsSubtype(SemanticType.IntOrReal, rhs_type, e.rightOperand);
        return SemanticType.Or(lhs_type, rhs_type);
      case EQ:
      case NEQ:
        return SemanticType.Or(lhs_type, rhs_type);
      case IMPLIES:
      case IFF:
        checkIsSubtype(SemanticType.Bool, lhs_type, e.leftOperand);
        checkIsSubtype(SemanticType.Bool, rhs_type, e.rightOperand);
        return SemanticType.Bool;
      case LT:
      case LTEQ:
      case GT:
      case GTEQ:
        checkIsSubtype(SemanticType.IntOrReal, lhs_type, e.leftOperand);
        checkIsSubtype(SemanticType.IntOrReal, rhs_type, e.rightOperand);
        return SemanticType.Or(lhs_type, rhs_type);
      case IN:
        {
          checkIsSubtype(SemanticType.SetAny, rhs_type, e.rightOperand);
          SemanticType.Set s = (SemanticType.Set) rhs_type;
          return s;
        }
      case SUBSET:
      case SUBSETEQ:
      case SUPSET:
      case SUPSETEQ:
        {
          checkIsSubtype(SemanticType.SetAny, lhs_type, e.leftOperand);
          checkIsSubtype(SemanticType.SetAny, rhs_type, e.rightOperand);
          // following can cause some problems
          // checkIsSubtype(lhs_type,rhs_type,e);
          return SemanticType.Or(lhs_type, rhs_type);
        }
      case SETUNION:
        {
          checkIsSubtype(SemanticType.SetAny, lhs_type, e.leftOperand);
          checkIsSubtype(SemanticType.SetAny, rhs_type, e.rightOperand);
          SemanticType.Set l = (SemanticType.Set) lhs_type;
          SemanticType.Set r = (SemanticType.Set) rhs_type;
          return SemanticType.Set(true, SemanticType.Or(l.element(), r.element()));
        }
      case SETINTERSECTION:
        {
          checkIsSubtype(SemanticType.SetAny, lhs_type, e.leftOperand);
          checkIsSubtype(SemanticType.SetAny, rhs_type, e.rightOperand);
          // TODO: the following gives a more accurate type, but there are
          // some outstanding issues related to the type system reduction
          // rules.
          // return SemanticType.And(lhs_type,rhs_type);
          SemanticType.Set l = (SemanticType.Set) lhs_type;
          SemanticType.Set r = (SemanticType.Set) rhs_type;
          return SemanticType.Set(true, SemanticType.Or(l.element(), r.element()));
        }
      case LISTAPPEND:
        {
          checkIsSubtype(SemanticType.SetTupleAnyAny, lhs_type, e.leftOperand);
          checkIsSubtype(SemanticType.SetTupleAnyAny, rhs_type, e.rightOperand);
          SemanticType.Set l = (SemanticType.Set) lhs_type;
          SemanticType.Set r = (SemanticType.Set) rhs_type;
          return SemanticType.Set(true, SemanticType.Or(l.element(), r.element()));
        }
      case RANGE:
        {
          checkIsSubtype(SemanticType.Int, lhs_type, e.leftOperand);
          checkIsSubtype(SemanticType.Int, rhs_type, e.rightOperand);
          return SemanticType.Set(true, SemanticType.Tuple(SemanticType.Int, SemanticType.Int));
        }
    }

    internalFailure("unknown binary expression encountered (" + e + ")", filename, e);
    return null; // deadcode
  }