// Copyright (c) 2016, 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.

// @dart = 2.9

import 'package:kernel/kernel.dart';
import 'type_parser.dart';
import 'package:test/test.dart';

final List<TestCase> testCases = <TestCase>[
  successCase('List<T>', 'List<String>', {'T': 'String'}),
  successCase('List<String>', 'List<T>', {'T': 'String'}),
  successCase('List<T>', 'List<T>', {'T': null}),
  successCase('List<S>', 'List<T>', {'S': 'T'}),
  successCase('List<S>', 'List<T>', {'T': 'S'}),
  successCase(
      'List<S>', 'List<T>', {'S': 'T', 'T': null}), // Require left bias.
  failureCase('List<S>', 'List<T>', []),

  failureCase('List<T>', 'T', ['T']),
  failureCase('List<List<T>>', 'List<T>', ['T']),
  failureCase('Map<S, T>', 'Map<List<T>, List<S>>', ['T', 'S']),

  failureCase('Map<Map<S,String>, Map<int,S>>',
      'Map<Map<int, S>, Map<S, String>>', ['S']),
  successCase('Map<Map<S, int>, Map<int, S>>', 'Map<Map<int, S>, Map<S, int>>',
      {'S': 'int'}),
  successCase('Map<Map<S, String>, Map<int, T>>',
      'Map<Map<int, T>, Map<S, String>>', {'S': 'int', 'T': 'String'}),

  successCase('Map<S, List<T>>', 'Map<T, List<S>>', {'S': 'T'}),
  successCase('Map<S, T>', 'Map<S, List<S>>', {'T': 'List<S>'}),
  successCase('Map<S, T>', 'Map<S, List<S>>', {'T': 'List<S>', 'S': null}),
  successCase('Map<List<S>, T>', 'Map<T, List<S>>', {'T': 'List<S>'}),
  successCase(
      'Map<List<S>, T>', 'Map<T, List<S>>', {'T': 'List<S>', 'S': null}),

  successCase('<E>(E) => E', '<T>(T) => T', {}),
  successCase('<E>(E, S) => E', '<T>(T, int) => T', {'S': 'int'}),
  failureCase('<E>(E, S) => E', '<T>(T, T) => T', ['S']),
  successCase(
      '<E>(E) => <T>(T) => Map<E,T>', '<E>(E) => <T>(T) => Map<E,T>', {}),
  successCase('<E>(E,_) => E', '<T>(T,_) => T', {}),

  successCase('(x:int,y:String) => int', '(y:String,x:int) => int', {}),
  successCase('<S,T>(x:S,y:T) => S', '<S,T>(y:T,x:S) => S', {}),
  successCase('(x:<T>(T)=>T,y:<S>(S)=>S) => int',
      '(y:<S>(S)=>S,x:<T>(T)=>T) => int', {}),
  successCase('(x:<T>(T)=>T,y:<S>(S,S,S)=>S) => int',
      '(y:<S>(S,S,S)=>S,x:<T>(T)=>T) => int', {}),
];

class TestCase {
  String type1;
  String type2;
  Iterable<String> quantifiedVariables;
  Map<String, String> expectedSubstitution; // Null if unification should fail.

  TestCase.success(this.type1, this.type2, this.expectedSubstitution) {
    quantifiedVariables = expectedSubstitution.keys;
  }

  TestCase.fail(this.type1, this.type2, this.quantifiedVariables);

  bool get shouldSucceed => expectedSubstitution != null;

  String toString() => '∃ ${quantifiedVariables.join(',')}. $type1 = $type2';
}

TestCase successCase(String type1, String type2, Map<String, String> expected,
    {bool debug: false}) {
  return new TestCase.success(type1, type2, expected);
}

TestCase failureCase(
    String type1, String type2, List<String> quantifiedVariables,
    {bool debug: false}) {
  return new TestCase.fail(type1, type2, quantifiedVariables);
}

void checkHashCodeEquality(DartType type1, DartType type2) {
  if (type1 == type2 && type1.hashCode != type2.hashCode) {
    fail('Equal types with different hash codes: $type1 and $type2');
  }
}

const int MinimumSmi = -(1 << 30);
const int MaximumSmi = (1 << 30) - 1;

bool isSmallInteger(int hash) {
  return MinimumSmi <= hash && hash <= MaximumSmi;
}

void checkHashCodeRange(DartType type) {
  int hash = type.hashCode;
  if (!isSmallInteger(hash)) {
    fail('Hash code for $type is not a SMI: $hash');
  }
}

void main() {
  for (var testCase in testCases) {
    test('$testCase', () {
      var env = new LazyTypeEnvironment();
      var type1 = env.parse(testCase.type1);
      var type2 = env.parse(testCase.type2);
      checkHashCodeEquality(type1, type2);
      checkHashCodeRange(type1);
      checkHashCodeRange(type2);
    });
  }
}
