// Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

library dart2js.constant_system;

import '../common_elements.dart' show CommonElements;
import '../elements/operators.dart';
import '../elements/types.dart';
import 'values.dart';

abstract class Operation {
  String get name;
}

abstract class UnaryOperation extends Operation {
  /// Returns [:null:] if it was unable to fold the operation.
  ConstantValue fold(ConstantValue constant);
}

abstract class BinaryOperation extends Operation {
  /// Returns [:null:] if it was unable to fold the operation.
  ConstantValue fold(ConstantValue left, ConstantValue right);
  apply(left, right);
}

/// A [ConstantSystem] is responsible for creating constants and folding them.
abstract class ConstantSystem {
  BinaryOperation get add;
  BinaryOperation get bitAnd;
  UnaryOperation get bitNot;
  BinaryOperation get bitOr;
  BinaryOperation get bitXor;
  BinaryOperation get booleanAnd;
  BinaryOperation get booleanOr;
  BinaryOperation get divide;
  BinaryOperation get equal;
  BinaryOperation get greaterEqual;
  BinaryOperation get greater;
  BinaryOperation get identity;
  BinaryOperation get ifNull;
  BinaryOperation get lessEqual;
  BinaryOperation get less;
  BinaryOperation get modulo;
  BinaryOperation get multiply;
  UnaryOperation get negate;
  UnaryOperation get not;
  BinaryOperation get remainder;
  BinaryOperation get shiftLeft;
  BinaryOperation get shiftRight;
  BinaryOperation get subtract;
  BinaryOperation get truncatingDivide;

  BinaryOperation get codeUnitAt;
  UnaryOperation get round;
  UnaryOperation get abs;

  const ConstantSystem();

  ConstantValue createInt(BigInt i);
  ConstantValue createIntFromInt(int i) => createInt(new BigInt.from(i));
  ConstantValue createDouble(double d);
  ConstantValue createString(String string);
  ConstantValue createBool(bool value);
  ConstantValue createNull();
  ConstantValue createList(InterfaceType type, List<ConstantValue> values);
  ConstantValue createMap(CommonElements commonElements, InterfaceType type,
      List<ConstantValue> keys, List<ConstantValue> values);
  ConstantValue createType(CommonElements commonElements, DartType type);
  ConstantValue createSymbol(CommonElements commonElements, String text);

  // We need to special case the subtype check for JavaScript constant
  // system because an int is a double at runtime.
  bool isSubtype(DartTypes types, DartType s, DartType t);

  /// Returns true if the [constant] is an integer at runtime.
  bool isInt(ConstantValue constant);

  /// Returns true if the [constant] is a double at runtime.
  bool isDouble(ConstantValue constant);

  /// Returns true if the [constant] is a string at runtime.
  bool isString(ConstantValue constant);

  /// Returns true if the [constant] is a boolean at runtime.
  bool isBool(ConstantValue constant);

  /// Returns true if the [constant] is null at runtime.
  bool isNull(ConstantValue constant);

  UnaryOperation lookupUnary(UnaryOperator operator) {
    switch (operator.kind) {
      case UnaryOperatorKind.COMPLEMENT:
        return bitNot;
      case UnaryOperatorKind.NEGATE:
        return negate;
      case UnaryOperatorKind.NOT:
        return not;
      default:
        return null;
    }
  }

  BinaryOperation lookupBinary(BinaryOperator operator) {
    switch (operator.kind) {
      case BinaryOperatorKind.ADD:
        return add;
      case BinaryOperatorKind.SUB:
        return subtract;
      case BinaryOperatorKind.MUL:
        return multiply;
      case BinaryOperatorKind.DIV:
        return divide;
      case BinaryOperatorKind.MOD:
        return modulo;
      case BinaryOperatorKind.IDIV:
        return truncatingDivide;
      case BinaryOperatorKind.OR:
        return bitOr;
      case BinaryOperatorKind.AND:
        return bitAnd;
      case BinaryOperatorKind.XOR:
        return bitXor;
      case BinaryOperatorKind.LOGICAL_OR:
        return booleanOr;
      case BinaryOperatorKind.LOGICAL_AND:
        return booleanAnd;
      case BinaryOperatorKind.SHL:
        return shiftLeft;
      case BinaryOperatorKind.SHR:
        return shiftRight;
      case BinaryOperatorKind.LT:
        return less;
      case BinaryOperatorKind.LTEQ:
        return lessEqual;
      case BinaryOperatorKind.GT:
        return greater;
      case BinaryOperatorKind.GTEQ:
        return greaterEqual;
      case BinaryOperatorKind.EQ:
        return equal;
      case BinaryOperatorKind.IF_NULL:
        return ifNull;
      default:
        return null;
    }
  }
}
