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

// ignore_for_file: hash_and_equals

// Benchmark for `Object.hash` and `Object.hashAll`.

import 'dart:math';

import 'package:benchmark_harness/benchmark_harness.dart';

int get nextHash => Random().nextInt(0x20000000);

// An object with a fast hashCode.
class Leaf {
  @override
  final int hashCode = nextHash;
}

abstract class Node5 {
  final item1 = Leaf();
  final item2 = Leaf();
  final item3 = Leaf();
  final item4 = Random().nextBool();
  final item5 = nextHash;
}

class Node5Hash extends Node5 {
  // This is the main subject of the benchmark - a typical use of `Object.hash`.
  @override
  int get hashCode => Object.hash(item1, item2, item3, item4, item5);
}

class Node5Manual extends Node5 {
  // This is a similar quality hashCode but with statically resolvable
  // `hashCode` calls and a 0 seed (instead of loading a unique random seed from
  // global late-final variable).
  @override
  int get hashCode => _SystemHash.hash5(item1.hashCode, item2.hashCode,
      item3.hashCode, item4.hashCode, item5.hashCode, 0);
}

class Node5List extends Node5 {
  // This is a pattern that is sometimes used, especially for large numbers of
  // items.
  @override
  int get hashCode => Object.hashAll([item1, item2, item3, item4, item5]);
}

/// Returns a list with most values created by [makeValue], and a few objects of
/// different types so that the `hashCode` calls are polymorphic, like the ones
/// in the hashed collections.
List generateData(Object Function(int) makeValue) {
  final List data = List.generate(1000, makeValue);
  final exceptions = [
    Leaf(),
    Node5Hash(),
    Node5Manual(),
    Node5List(),
    '',
    true,
    false,
    123,
    Object()
  ];
  data.setRange(1, 1 + exceptions.length, exceptions);
  return data;
}

class BenchmarkNode5Hash extends BenchmarkBase {
  final List data = generateData((_) => Node5Hash());

  BenchmarkNode5Hash() : super('ObjectHash.hash.5');

  @override
  void run() {
    for (final e in data) {
      sink = e.hashCode;
    }
  }
}

class BenchmarkNode5Manual extends BenchmarkBase {
  final List data = generateData((_) => Node5Manual());

  BenchmarkNode5Manual() : super('ObjectHash.manual.5');

  @override
  void run() {
    for (final e in data) {
      sink = e.hashCode;
    }
  }
}

class BenchmarkNode5List extends BenchmarkBase {
  final List data = generateData((_) => Node5List());

  BenchmarkNode5List() : super('ObjectHash.list.5');

  @override
  void run() {
    for (final e in data) {
      sink = e.hashCode;
    }
  }
}

class BenchmarkNode5HashHashAll extends BenchmarkBase {
  final List data = generateData((_) => Node5Hash());

  BenchmarkNode5HashHashAll() : super('ObjectHash.hash.5.hashAll');

  @override
  void run() {
    sink = Object.hashAll(data);
  }
}

class BenchmarkNode5ManualHashAll extends BenchmarkBase {
  final List data = generateData((_) => Node5Manual());

  BenchmarkNode5ManualHashAll() : super('ObjectHash.manual.5.hashAll');

  @override
  void run() {
    sink = Object.hashAll(data);
  }
}

Object? sink;

void main() {
  generalUses();

  final benchmarks = [
    BenchmarkNode5Hash.new,
    BenchmarkNode5Manual.new,
    BenchmarkNode5List.new,
    BenchmarkNode5HashHashAll.new,
    BenchmarkNode5ManualHashAll.new,
  ];

  // Warmup all benchmarks so that JIT compilers see full polymorphism before
  // measuring.
  for (var benchmark in benchmarks) {
    benchmark().warmup();
  }

  if (sink == null) throw StateError('sink unassigned');

  generalUses();

  for (var benchmark in benchmarks) {
    benchmark().report();
  }
}

/// Does a variety of calls to `Object.hash` to ensure the compiler does not
/// over-specialize the code on a few benchmark inputs.
void generalUses() {
  void check(int a, int b) {
    if (a != b) throw StateError('inconsistent');
  }

  // Exercise arity dispatch.
  check(Object.hash(1, 2), Object.hash(1, 2));
  check(Object.hash(1, 2, 3), Object.hash(1, 2, 3));
  check(Object.hash(1, 2, 3, 4), Object.hash(1, 2, 3, 4));
  check(Object.hash(1, 2, 3, 4, 5), Object.hash(1, 2, 3, 4, 5));
  check(Object.hash(1, 2, 3, 4, 5, 6), Object.hash(1, 2, 3, 4, 5, 6));
  check(Object.hash(1, 2, 3, 4, 5, 6, 7), Object.hash(1, 2, 3, 4, 5, 6, 7));

  final xs = Iterable.generate(20).toList();
  check(Function.apply(Object.hash, xs), Function.apply(Object.hash, xs));

  // Exercise internal hashCode dispatch.
  final a1 = 123;
  final a2 = 'hello';
  final a3 = true;
  final a4 = Object();
  final a5 = StringBuffer();
  const a6 = Point<int>(1, 2);
  const a7 = Rectangle<int>(100, 200, 1, 1);

  check(Object.hash(a1, a2, a3, a4, a5), Object.hash(a1, a2, a3, a4, a5));
  check(Object.hash(a2, a3, a4, a5, a6), Object.hash(a2, a3, a4, a5, a6));
  check(Object.hash(a3, a4, a5, a6, a7), Object.hash(a3, a4, a5, a6, a7));
  check(Object.hash(a4, a5, a6, a7, a1), Object.hash(a4, a5, a6, a7, a1));
  check(Object.hash(a5, a6, a7, a1, a2), Object.hash(a5, a6, a7, a1, a2));
  check(Object.hash(a6, a7, a1, a2, a3), Object.hash(a6, a7, a1, a2, a3));
  check(Object.hash(a7, a1, a2, a3, a4), Object.hash(a7, a1, a2, a3, a4));

  check(_SystemHash.hash2(1, 2, 0), _SystemHash.hash2(1, 2, 0));
  check(_SystemHash.hash3(1, 2, 3, 0), _SystemHash.hash3(1, 2, 3, 0));
  check(_SystemHash.hash4(1, 2, 3, 4, 0), _SystemHash.hash4(1, 2, 3, 4, 0));
  check(
      _SystemHash.hash5(1, 2, 3, 4, 5, 0), _SystemHash.hash5(1, 2, 3, 4, 5, 0));

  // Pollute hashAll argument type.
  check(Object.hashAll({}), Object.hashAll([]));
  check(Object.hashAll({}.values), Object.hashAll({}.keys));
  check(Object.hashAll(''.codeUnits), Object.hashAll(const Iterable.empty()));
  check(Object.hashAll(const [0]), Object.hashAll(Iterable.generate(1)));
}

// Partial copy of dart:internal `SystemHash` that is used by `Object.hash` so
// that we can create comparable manual hashCode methods.
class _SystemHash {
  static int combine(int hash, int value) {
    hash = 0x1fffffff & (hash + value);
    hash = 0x1fffffff & (hash + ((0x0007ffff & hash) << 10));
    return hash ^ (hash >> 6);
  }

  static int finish(int hash) {
    hash = 0x1fffffff & (hash + ((0x03ffffff & hash) << 3));
    hash = hash ^ (hash >> 11);
    return 0x1fffffff & (hash + ((0x00003fff & hash) << 15));
  }

  static int hash2(int v1, int v2, int seed) {
    int hash = seed;
    hash = combine(hash, v1);
    hash = combine(hash, v2);
    return finish(hash);
  }

  static int hash3(int v1, int v2, int v3, int seed) {
    int hash = seed;
    hash = combine(hash, v1);
    hash = combine(hash, v2);
    hash = combine(hash, v3);
    return finish(hash);
  }

  static int hash4(int v1, int v2, int v3, int v4, int seed) {
    int hash = seed;
    hash = combine(hash, v1);
    hash = combine(hash, v2);
    hash = combine(hash, v3);
    hash = combine(hash, v4);
    return finish(hash);
  }

  static int hash5(int v1, int v2, int v3, int v4, int v5, int seed) {
    int hash = seed;
    hash = combine(hash, v1);
    hash = combine(hash, v2);
    hash = combine(hash, v3);
    hash = combine(hash, v4);
    hash = combine(hash, v5);
    return finish(hash);
  }
}
