// Copyright (c) 2011, 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 "dart:collection";
import "dart:typed_data";
import "package:expect/expect.dart";

void main() {
  // Growable lists. Initial length 0.
  testConcurrentModification(new List());
  testConcurrentModification(new List<int>().toList());
  testConcurrentModification(new List<int>(0).toList());
  testConcurrentModification(new List.filled(0, null, growable: true));
  testConcurrentModification([]);
  testConcurrentModification(new List.from(const []));
  testConcurrentModification(new MyList([]));
  testConcurrentModification(new MyList<int>([]).toList());

  testConcurrentModification(new Uint8List(0).toList());
  testConcurrentModification(new Int8List(0).toList());
  testConcurrentModification(new Uint16List(0).toList());
  testConcurrentModification(new Int16List(0).toList());
  testConcurrentModification(new Uint32List(0).toList());
  testConcurrentModification(new Int32List(0).toList());
}

void testConcurrentModification(List<int> list) {
  // add, removeLast.
  list.clear();
  list.addAll([1, 2, 3, 2, 7, 9, 9, 7, 2, 3, 2, 1]);

  // Operations that change the length cause ConcurrentModificationError.
  void testModification(action()) {
    testIterator(int when) {
      list.length = 4;
      list.setAll(0, [0, 1, 2, 3]);
      Expect.throws(() {
        for (var element in list) {
          if (element == when) action();
        }
      }, (e) => e is ConcurrentModificationError);
    }

    testForEach(int when) {
      list.length = 4;
      list.setAll(0, [0, 1, 2, 3]);
      Expect.throws(() {
        list.forEach((var element) {
          if (element == when) action();
        });
      }, (e) => e is ConcurrentModificationError);
    }

    // Test the change at different points of the iteration.
    testIterator(0);
    testIterator(1);
    testIterator(3);
    testForEach(0);
    testForEach(1);
    testForEach(3);
  }

  testModification(() => list.add(5));
  testModification(() => list.addAll([5, 6]));
  testModification(() => list.removeLast());
  for (int i = 0; i < 4; i++) {
    testModification(() => list.remove(i));
    testModification(() => list.removeAt(i));
    testModification(() => list.removeWhere((x) => x == i));
    testModification(() => list.retainWhere((x) => x != i));
    testModification(() => list.insert(i, 5));
    testModification(() => list.insertAll(i, [5, 6]));
    testModification(() => list.removeRange(i, i + 1));
    testModification(() => list.replaceRange(i, i + 1, [5, 6]));
  }
}

class MyList<E> extends ListBase<E> {
  List<E> _source;
  MyList(this._source);
  int get length => _source.length;
  void set length(int length) {
    _source.length = length;
  }

  E operator [](int index) => _source[index];
  void operator []=(int index, E value) {
    _source[index] = value;
  }
}
