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

import 'dart:convert';
import 'dart:io';
import 'dart:ffi';
import 'dart:async';

import 'package:expect/expect.dart';
import 'package:native_stack_traces/elf.dart';
import 'package:path/path.dart' as path;

import 'use_flag_test_helper.dart';

const int headerSize = 8;
final int compressedWordSize =
    sizeOf<Pointer>() == 8 && !Platform.executable.contains('64C') ? 8 : 4;
const int wordSize = 8; // analyze_snapshot is not supported on arm32

// Used to ensure we don't have multiple equivalent calls to test.
final _seenDescriptions = <String>{};

Future<void> testAOT(
  String dillPath, {
  bool useAsm = false,
  bool forceDrops = false,
  bool stripUtil = false, // Note: forced true if useAsm.
  bool stripFlag = false,
  bool disassemble = false,
}) async {
  const isProduct = const bool.fromEnvironment('dart.vm.product');
  if (isProduct && disassemble) {
    Expect.isFalse(disassemble, 'no use of disassembler in PRODUCT mode');
  }

  final analyzeSnapshot = path.join(buildDir, 'analyze_snapshot');

  // For assembly, we can't test the sizes of the snapshot sections, since we
  // don't have a Mach-O reader for Mac snapshots and for ELF, the assembler
  // merges the text/data sections and the VM/isolate section symbols may not
  // have length information. Thus, we force external stripping so we can test
  // the approximate size of the stripped snapshot.
  if (useAsm) {
    stripUtil = true;
  }

  final descriptionBuilder = StringBuffer()..write(useAsm ? 'assembly' : 'elf');
  if (forceDrops) {
    descriptionBuilder.write('-dropped');
  }
  if (stripFlag) {
    descriptionBuilder.write('-intstrip');
  }
  if (stripUtil) {
    descriptionBuilder.write('-extstrip');
  }
  if (disassemble) {
    descriptionBuilder.write('-disassembled');
  }

  final description = descriptionBuilder.toString();
  Expect.isTrue(
    _seenDescriptions.add(description),
    "test configuration $description would be run multiple times",
  );

  await withTempDir('analyze_snapshot_binary-$description', (
    String tempDir,
  ) async {
    // Generate the snapshot
    final snapshotPath = path.join(tempDir, 'test.snap');
    final commonSnapshotArgs = [
      if (stripFlag) '--strip', //  gen_snapshot specific and not a VM flag.
      if (forceDrops) ...[
        '--dwarf-stack-traces',
        '--no-retain-function-objects',
        '--no-retain-code-objects',
      ],
      if (disassemble) '--disassemble', // Not defined in PRODUCT mode.
      dillPath,
    ];

    if (useAsm) {
      final assemblyPath = path.join(tempDir, 'test.S');

      await (disassemble ? runSilent : run)(genSnapshot, <String>[
        '--snapshot-kind=app-aot-assembly',
        '--assembly=$assemblyPath',
        ...commonSnapshotArgs,
      ]);

      await assembleSnapshot(assemblyPath, snapshotPath);
    } else {
      await (disassemble ? runSilent : run)(genSnapshot, <String>[
        '--snapshot-kind=app-aot-elf',
        '--elf=$snapshotPath',
        ...commonSnapshotArgs,
      ]);
    }

    print("Snapshot generated at $snapshotPath.");

    // May not be ELF, but another format.
    final elf = Elf.fromFile(snapshotPath);
    if (!useAsm) {
      Expect.isNotNull(elf);
    }

    if (elf != null) {
      // Verify some ELF file format parameters.
      final textSections = elf.namedSections(".text");
      Expect.isNotEmpty(textSections);
      Expect.isTrue(
        textSections.length <= 2,
        "More text sections than expected",
      );
      final dataSections = elf.namedSections(".rodata");
      Expect.isNotEmpty(dataSections);
      Expect.isTrue(
        dataSections.length <= 2,
        "More data sections than expected",
      );
    }

    final analyzerOutputPath = path.join(tempDir, 'analyze_test.json');

    // This will throw if exit code is not 0.
    await run(analyzeSnapshot, <String>[
      '--out=$analyzerOutputPath',
      '$snapshotPath',
    ]);

    final analyzerJsonBytes = await readFile(analyzerOutputPath);
    final analyzerJson = json.decode(analyzerJsonBytes);
    Expect.isFalse(analyzerJson.isEmpty);
    Expect.isTrue(
      analyzerJson.keys.toSet().containsAll([
        'snapshot_data',
        'objects',
        'metadata',
      ]),
    );

    final objects = (analyzerJson['objects'] as List)
        .map((o) => o as Map)
        .toList();
    final classes = objects.where((o) => o['type'] == 'Class').toList();
    final classnames = <int, String>{};
    final superclass = <int, int>{};
    final implementedInterfaces = <int, List<int>>{};
    for (final klass in classes) {
      final id = klass['id'];
      superclass[id] = klass['super_class'] as int;
      classnames[id] = klass['name'];
      implementedInterfaces[id] = [
        for (final superTypeId in klass['interfaces'] as List? ?? [])
          objects[superTypeId]['type_class']!,
      ];
    }

    // Find MethodChannel class.
    final methodChannelId = classnames.entries
        .singleWhere((e) => e.value == 'MethodChannel')
        .key;

    // Find string instance.
    final stringList = objects
        .where((o) => o['type'] == 'String' && o['value'] == 'constChannel1')
        .toList();
    Expect.isTrue(
      stringList.length == 1,
      'one "constChannel1" string must exist in output',
    );
    final int stringObjId = stringList.first['id'];

    // Find MethodChannel instance.
    final instanceList = objects
        .where(
          (o) =>
              o['type'] == 'Instance' &&
              o['class'] == methodChannelId &&
              o['references'].contains(stringObjId),
        )
        .toList();
    Expect.isTrue(instanceList.length == 1, '''one instance of MethodChannel
        with reference to "constChannel1" must exist in output''');

    // Test class hierarchy information
    final myBaseClassId = classnames.entries
        .singleWhere((e) => e.value == 'MyBase')
        .key;
    final mySubClassId = classnames.entries
        .singleWhere((e) => e.value == 'MySub')
        .key;
    final myInterfaceClassId = classnames.entries
        .singleWhere((e) => e.value == 'MyInterface')
        .key;

    Expect.equals(myBaseClassId, superclass[mySubClassId]);
    Expect.equals(
      myInterfaceClassId,
      implementedInterfaces[mySubClassId]!.single,
    );

    // Ensure instance fields of classes are reported.
    final baseClass =
        objects[classnames.entries
            .singleWhere((e) => e.value == 'FieldTestBase')
            .key];
    final subClass =
        objects[classnames.entries
            .singleWhere((e) => e.value == 'FieldTestSub')
            .key];
    final baseFieldIds = baseClass['fields'];
    final baseFields = [for (final int id in baseFieldIds) objects[id]];
    final baseSlots = baseClass['instance_slots']
        .map<Map>((e) => e as Map)
        .toList();
    final subFieldIds = subClass['fields'];
    final subFields = [for (final int id in subFieldIds) objects[id]];
    final subSlots = subClass['instance_slots'];

    // We have:
    //   class Base {
    //     static int baseS0 = int.parse('1');
    //     static int baseS1 = int.parse('2');
    //     int base0;
    //     double base1;
    //     Object? base2;
    //     Float32x4 base3;
    //     Float64x2 base4;
    //   }
    //
    // This static field is never tree shaken.
    expectField(baseFields[0], name: 'baseS0', flags: ['static']);
    expectField(baseFields[1], name: 'baseS1', flags: ['static']);

    // Neighboring static fields should always be one word away
    final int staticFieldOffset0 = baseFields[0]["static_field_offset"];
    final int staticFieldOffset1 = baseFields[1]["static_field_offset"];
    Expect.equals(staticFieldOffset1 - staticFieldOffset0, wordSize);

    if (isProduct) {
      // Most [Field] objests are tree shaken.
      Expect.equals(2, baseFields.length);

      int slotOffset = 0;
      slotOffset += expectUnknown8Bytes(
        baseSlots.skip(slotOffset),
        offsetReferences: 0,
        offsetBytes: 0,
      );
      slotOffset += expectUnknown8Bytes(
        baseSlots.skip(slotOffset),
        offsetReferences: 0,
        offsetBytes: 8,
      );
      slotOffset += expectUnknownReference(
        baseSlots[slotOffset],
        offsetReferences: 0,
        offsetBytes: 16,
      );
      slotOffset += expectUnknown16Bytes(
        baseSlots.skip(slotOffset),
        offsetReferences: 1,
        offsetBytes: 16,
      );
      slotOffset += expectUnknown16Bytes(
        baseSlots.skip(slotOffset),
        offsetReferences: 1,
        offsetBytes: 32,
      );
    } else {
      // We don't tree shake [Field] objects in non-product builds.
      Expect.equals(7, baseFields.length);
      expectField(
        baseFields[2],
        name: 'base0',
        isReference: false,
        unboxedType: 'int',
      );
      expectField(
        baseFields[3],
        name: 'base1',
        isReference: false,
        unboxedType: 'double',
      );
      expectField(baseFields[4], name: 'base2');
      expectField(
        baseFields[5],
        name: 'base3',
        isReference: false,
        unboxedType: 'Float32x4',
      );
      expectField(
        baseFields[6],
        name: 'base4',
        isReference: false,
        unboxedType: 'Float64x2',
      );
      int slotOffset = 0;
      slotOffset += expectInstanceSlot(
        baseSlots[slotOffset],
        offsetReferences: 0,
        offsetBytes: 0,
        isReference: false,
        fieldId: baseFieldIds[2],
      );
      slotOffset += expectInstanceSlot(
        baseSlots[slotOffset],
        offsetReferences: 0,
        offsetBytes: 8,
        isReference: false,
        fieldId: baseFieldIds[3],
      );
      slotOffset += expectInstanceSlot(
        baseSlots[slotOffset],
        offsetReferences: 0,
        offsetBytes: 16,
        fieldId: baseFieldIds[4],
      );
      slotOffset += expectInstanceSlot(
        baseSlots[slotOffset],
        offsetReferences: 1,
        offsetBytes: 16,
        isReference: false,
        fieldId: baseFieldIds[5],
      );
      slotOffset += expectInstanceSlot(
        baseSlots[slotOffset],
        offsetReferences: 1,
        offsetBytes: 32,
        isReference: false,
        fieldId: baseFieldIds[6],
      );
    }
    // We have:
    //   class Sub<T> extends Base{
    //     late int subL1 = int.parse('1');
    //     late final double subL2 = double.parse('1.2');
    //   }
    // These late instance fields are never tree shaken.
    expectField(subFields[0], name: 'subL1', flags: ['late']);
    expectField(subFields[1], name: 'subL2', flags: ['final', 'late']);
    expectTypeArgumentsSlot(
      subSlots[0],
      offsetReferences: 1,
      offsetBytes: 8 + 8 + 16 + 16,
    );
    expectSlot(
      subSlots[1],
      offsetReferences: 2,
      offsetBytes: 8 + 8 + 16 + 16,
      type: 'instance_field',
      fieldId: subFieldIds[0],
    );
    expectSlot(
      subSlots[2],
      offsetReferences: 3,
      offsetBytes: 8 + 8 + 16 + 16,
      type: 'instance_field',
      fieldId: subFieldIds[1],
    );

    Expect.isTrue(
      analyzerJson['metadata'].containsKey('analyzer_version'),
      'snapshot analyzer version must be reported',
    );
    Expect.isTrue(
      analyzerJson['metadata']['analyzer_version'] == 2,
      'invalid snapshot analyzer version',
    );
  });
}

void expectField(
  Map fieldJson, {
  required String name,
  List<String> flags = const [],
  bool isReference = true,
  String? unboxedType,
}) {
  Expect.equals(name, fieldJson['name']);
  Expect.equals(isReference, fieldJson['is_reference']);
  Expect.listEquals(flags, fieldJson['flags']);
  if (unboxedType != null) {
    Expect.equals(unboxedType, fieldJson['unboxed_type']);
  } else {
    Expect.isFalse(fieldJson.containsKey('unboxed_type'));
  }
}

void expectSlot(
  Map slotJson, {
  required int offsetReferences,
  required int offsetBytes,
  required String type,
  bool isReference = true,
  int? fieldId,
}) {
  Expect.equals(type, slotJson['slot_type']);
  if (fieldId != null) {
    Expect.equals(fieldId, slotJson['field']);
  } else {
    Expect.isFalse(slotJson.containsKey('field'));
  }
  final int offset =
      headerSize + offsetReferences * compressedWordSize + offsetBytes;
  Expect.equals(offset, slotJson['offset']);
  Expect.equals(isReference, slotJson['is_reference']);
}

int expectInstanceSlot(
  Map slotJson, {
  required int offsetReferences,
  required int offsetBytes,
  bool isReference = true,
  int? fieldId,
}) {
  expectSlot(
    slotJson,
    isReference: isReference,
    fieldId: fieldId,
    offsetReferences: offsetReferences,
    offsetBytes: offsetBytes,
    type: 'instance_field',
  );
  return 1;
}

int expectUnknownReference(
  Map slotJson, {
  required int offsetReferences,
  required int offsetBytes,
}) {
  expectSlot(
    slotJson,
    offsetReferences: offsetReferences,
    offsetBytes: offsetBytes,
    type: 'unknown_slot',
  );
  return 1;
}

int expectTypeArgumentsSlot(
  Map slotJson, {
  required int offsetReferences,
  required int offsetBytes,
}) {
  expectSlot(
    slotJson,
    offsetReferences: offsetReferences,
    offsetBytes: offsetBytes,
    type: 'type_arguments_field',
  );
  return 1;
}

int expectUnknown8Bytes(
  Iterable<Map> slotJson, {
  required int offsetReferences,
  required int offsetBytes,
}) {
  final it = slotJson.iterator;
  Expect.isTrue(it.moveNext());
  expectSlot(
    it.current,
    isReference: false,
    offsetReferences: offsetReferences,
    offsetBytes: offsetBytes,
    type: 'unknown_slot',
  );
  if (compressedWordSize == 8) {
    return 1;
  }
  Expect.isTrue(it.moveNext());
  expectSlot(
    it.current,
    isReference: false,
    offsetReferences: offsetReferences,
    offsetBytes: offsetBytes + compressedWordSize,
    type: 'unknown_slot',
  );
  return 2;
}

int expectUnknown16Bytes(
  Iterable<Map> slotJson, {
  required int offsetReferences,
  required int offsetBytes,
}) {
  int slots = 0;
  slots += expectUnknown8Bytes(
    slotJson,
    offsetReferences: offsetReferences,
    offsetBytes: offsetBytes,
  );
  slots += expectUnknown8Bytes(
    slotJson.skip(slots),
    offsetReferences: offsetReferences,
    offsetBytes: offsetBytes + 8,
  );
  return slots;
}

main() async {
  void printSkip(String description) => print(
    'Skipping $description for ${path.basename(buildDir)} '
            'on ${Platform.operatingSystem}' +
        (clangBuildToolsDir == null ? ' without //buildtools' : ''),
  );

  // We don't have access to the SDK on Android.
  if (Platform.isAndroid) {
    printSkip('all tests');
    return;
  }

  await withTempDir('analyze_snapshot_binary', (String tempDir) async {
    // We only need to generate the dill file once for all JIT tests.
    final thisTestPath = path.join(
      sdkDir,
      'runtime',
      'tests',
      'vm',
      'dart',
      'analyze_snapshot_program.dart',
    );

    // We only need to generate the dill file once for all AOT tests.
    final aotDillPath = path.join(tempDir, 'aot_test.dill');
    await run(genKernel, <String>[
      '--aot',
      '--platform',
      platformDill,
      ...Platform.executableArguments.where(
        (arg) =>
            arg.startsWith('--enable-experiment=') ||
            arg == '--sound-null-safety' ||
            arg == '--no-sound-null-safety',
      ),
      '-o',
      aotDillPath,
      thisTestPath,
    ]);

    // Just as a reminder for AOT tests:
    // * If useAsm is true, then stripUtil is forced (as the assembler may add
    //   extra information that needs stripping), so no need to specify
    //   stripUtil for useAsm tests.

    await Future.wait([
      // Test unstripped ELF generation directly.
      testAOT(aotDillPath),
      testAOT(aotDillPath, forceDrops: true),

      // Test flag-stripped ELF generation.
      testAOT(aotDillPath, stripFlag: true),
    ]);

    // Since we can't force disassembler support after the fact when running
    // in PRODUCT mode, skip any --disassemble tests. Do these tests last as
    // they have lots of output and so the log will be truncated.
    if (!const bool.fromEnvironment('dart.vm.product')) {
      // Regression test for dartbug.com/41149.
      await Future.wait([testAOT(aotDillPath, disassemble: true)]);
    }

    // Test unstripped ELF generation that is then externally stripped.
    await Future.wait([testAOT(aotDillPath, stripUtil: true)]);

    // Dont test assembled snapshot for simulated platforms or macos
    if (!buildDir.endsWith("SIMARM64") &&
        !buildDir.endsWith("SIMARM64C") &&
        !Platform.isMacOS) {
      await Future.wait([
        // Test unstripped assembly generation that is then externally stripped.
        testAOT(aotDillPath, useAsm: true),
        // Test stripped assembly generation that is then externally stripped.
        testAOT(aotDillPath, useAsm: true, stripFlag: true),
      ]);
    }
  });
}

Future<String> readFile(String file) {
  return new File(file).readAsString();
}
