// Copyright (c) 2020, 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.
//
// SharedObjects=ffi_test_functions
// VMOptions=--enable-testing-pragmas

import 'dart:ffi';

import 'package:expect/expect.dart';

import 'dylib_utils.dart';

void main() {
  testHandle();
  testReadField();
  testTrueHandle();
  testClosureCallback();
  testReturnHandleInCallback();
  testPropagateError();
  testCallbackReturnException();
  testDeepException();
  testDeepException2();
  testNull();
  testDeepRecursive();
  testNoHandlePropagateError();
}

void testHandle() {
  print("testHandle");
  final s = SomeClass(123);
  print("passObjectToC($s)");
  final result = passObjectToC(s);
  print("result = $result");
  Expect.isTrue(identical(s, result));
}

void testReadField() {
  final s = SomeClass(123);
  final result = handleReadFieldValue(s);
  Expect.equals(s.a, result);
}

void testTrueHandle() {
  final result = trueHandle();
  Expect.isTrue(result);
}

int globalCounter = 0;

void increaseCounter() {
  print("increaseCounter");
  globalCounter++;
}

void doClosureCallback(Object callback) {
  print("doClosureCallback");
  print(callback.runtimeType);
  print(callback);
  final callback_as_function = callback as void Function();
  callback_as_function();
}

final closureCallbackPointer =
    Pointer.fromFunction<Void Function(Handle)>(doClosureCallback);

void testClosureCallback() {
  print("testClosureCallback $closureCallbackPointer");
  Expect.equals(0, globalCounter);
  closureCallbackThroughHandle(closureCallbackPointer, increaseCounter);
  Expect.equals(1, globalCounter);
  closureCallbackThroughHandle(closureCallbackPointer, increaseCounter);
  Expect.equals(2, globalCounter);
}

final someObject = SomeClass(12356789);

Object returnHandleCallback() {
  print("returnHandleCallback returning $someObject");
  return someObject;
}

final returnHandleCallbackPointer =
    Pointer.fromFunction<Handle Function()>(returnHandleCallback);

void testReturnHandleInCallback() {
  print("testReturnHandleInCallback");
  final result = returnHandleInCallback(returnHandleCallbackPointer);
  Expect.isTrue(identical(someObject, result));
}

class SomeClass {
  // We use this getter in the native api, don't tree shake it.
  @pragma("vm:entry-point")
  final int a;
  SomeClass(this.a);
}

void testPropagateError() {
  final s = SomeOtherClass(123);
  Expect.throws(() => handleReadFieldValue(s));
}

class SomeOtherClass {
  final int notA;
  SomeOtherClass(this.notA);
}

final someException = Exception("exceptionHandleCallback exception");

Object exceptionHandleCallback() {
  print("exceptionHandleCallback throwing ($someException)");
  throw someException;
}

final exceptionHandleCallbackPointer =
    Pointer.fromFunction<Handle Function()>(exceptionHandleCallback);

void testCallbackReturnException() {
  print("testCallbackReturnException");
  bool throws = false;
  try {
    final result = returnHandleInCallback(exceptionHandleCallbackPointer);
    print(result);
  } catch (e) {
    throws = true;
    print("caught ($e)");
    Expect.isTrue(identical(someException, e));
  }
  Expect.isTrue(throws);
}

Object callCAgainFromCallback() {
  print("callCAgainFromCallback");
  final s = SomeOtherClass(123);
  Expect.throws(() => handleReadFieldValue(s));
  return someObject;
}

final callCAgainFromCallbackPointer =
    Pointer.fromFunction<Handle Function()>(callCAgainFromCallback);

void testDeepException() {
  print("testDeepException");
  final result = returnHandleInCallback(callCAgainFromCallbackPointer);
  Expect.isTrue(identical(someObject, result));
}

Object callCAgainFromCallback2() {
  print("callCAgainFromCallback2");
  final s = SomeOtherClass(123);
  handleReadFieldValue(s); // throws.
  return someObject;
}

final callCAgainFromCallbackPointer2 =
    Pointer.fromFunction<Handle Function()>(callCAgainFromCallback2);

void testDeepException2() {
  print("testDeepException2");
  Expect.throws(() => returnHandleInCallback(callCAgainFromCallbackPointer2));
}

Object returnNullHandleCallback() {
  print("returnHandleCallback returning null");
  return null;
}

final returnNullHandleCallbackPointer =
    Pointer.fromFunction<Handle Function()>(returnNullHandleCallback);

void testNull() {
  print("testNull");
  final result = passObjectToC(null);
  Expect.isNull(result);

  final result2 = returnHandleInCallback(returnNullHandleCallbackPointer);
  Expect.isNull(result2);
}

Object recurseAbove0(int i) {
  print("recurseAbove0($i)");
  if (i == 0) {
    print("throwing");
    throw someException;
  }
  if (i < 0) {
    print("returning");
    return someObject;
  }
  final result =
      handleRecursion(SomeClassWithMethod(), recurseAbove0Pointer, i - 1);
  print("return $i");
  return result;
}

final recurseAbove0Pointer =
    Pointer.fromFunction<Handle Function(Int64)>(recurseAbove0);

class SomeClassWithMethod {
  // We use this method in the native api, don't tree shake it.
  @pragma("vm:entry-point")
  Object a(int i) => recurseAbove0(i);
}

void testDeepRecursive() {
  // works on arm.
  Expect.throws(() {
    handleRecursion(123, recurseAbove0Pointer, 1);
  });

  Expect.throws(() {
    handleRecursion(SomeClassWithMethod(), recurseAbove0Pointer, 1);
  });

  Expect.throws(() {
    recurseAbove0(100);
  });

  final result = recurseAbove0(101);
  Expect.isTrue(identical(someObject, result));
}

void testNoHandlePropagateError() {
  bool throws = false;
  try {
    final result = propagateErrorWithoutHandle(exceptionHandleCallbackPointer);
    print(result);
  } catch (e) {
    throws = true;
    print("caught ($e)");
    Expect.isTrue(identical(someException, e));
  }
  Expect.isTrue(throws);
}

final testLibrary = dlopenPlatformSpecific("ffi_test_functions");

final passObjectToC = testLibrary.lookupFunction<Handle Function(Handle),
    Object Function(Object)>("PassObjectToC");

final handleReadFieldValue =
    testLibrary.lookupFunction<Int64 Function(Handle), int Function(Object)>(
        "HandleReadFieldValue");

final trueHandle = testLibrary
    .lookupFunction<Handle Function(), Object Function()>("TrueHandle");

final closureCallbackThroughHandle = testLibrary.lookupFunction<
    Void Function(Pointer<NativeFunction<Void Function(Handle)>>, Handle),
    void Function(Pointer<NativeFunction<Void Function(Handle)>>,
        Object)>("ClosureCallbackThroughHandle");

final returnHandleInCallback = testLibrary.lookupFunction<
    Handle Function(Pointer<NativeFunction<Handle Function()>>),
    Object Function(
        Pointer<NativeFunction<Handle Function()>>)>("ReturnHandleInCallback");

final handleRecursion = testLibrary.lookupFunction<
    Handle Function(
        Handle, Pointer<NativeFunction<Handle Function(Int64)>>, Int64),
    Object Function(Object, Pointer<NativeFunction<Handle Function(Int64)>>,
        int)>("HandleRecursion");

final propagateErrorWithoutHandle = testLibrary.lookupFunction<
        Int64 Function(Pointer<NativeFunction<Handle Function()>>),
        int Function(Pointer<NativeFunction<Handle Function()>>)>(
    "PropagateErrorWithoutHandle");
