// Copyright 2013 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#import "flutter/shell/platform/darwin/ios/framework/Source/profiler_metrics_ios.h"

#import <Foundation/Foundation.h>

#import "flutter/shell/platform/darwin/common/framework/Headers/FlutterMacros.h"
#import "flutter/shell/platform/darwin/ios/framework/Source/IOKit.h"

FLUTTER_ASSERT_ARC

namespace {

// RAII holder for `thread_array_t` this is so any early returns in
// `ProfilerMetricsIOS::CpuUsage` don't leak them.
class MachThreads {
 public:
  thread_array_t threads = NULL;
  mach_msg_type_number_t thread_count = 0;

  MachThreads() = default;

  ~MachThreads() {
    kern_return_t kernel_return_code = vm_deallocate(
        mach_task_self(), reinterpret_cast<vm_offset_t>(threads), thread_count * sizeof(thread_t));
    FML_CHECK(kernel_return_code == KERN_SUCCESS) << "Failed to deallocate thread infos.";
  }

 private:
  FML_DISALLOW_COPY_AND_ASSIGN(MachThreads);
};

}  // namespace

namespace flutter {
namespace {

#if FLUTTER_RUNTIME_MODE == FLUTTER_RUNTIME_MODE_DEBUG || \
    FLUTTER_RUNTIME_MODE == FLUTTER_RUNTIME_MODE_PROFILE

template <typename T>
T ClearValue() {
  return nullptr;
}

template <>
io_object_t ClearValue<io_object_t>() {
  return 0;
}

template <typename T>
/// Generic RAII wrapper like unique_ptr but gives access to its handle.
class Scoped {
 public:
  typedef void (*Deleter)(T);
  explicit Scoped(Deleter deleter) : object_(ClearValue<T>()), deleter_(deleter) {}
  Scoped(T object, Deleter deleter) : object_(object), deleter_(deleter) {}
  ~Scoped() {
    if (object_) {
      deleter_(object_);
    }
  }
  T* handle() {
    if (object_) {
      deleter_(object_);
      object_ = ClearValue<T>();
    }
    return &object_;
  }
  T get() { return object_; }
  void reset(T new_value) {
    if (object_) {
      deleter_(object_);
    }
    object_ = new_value;
  }

 private:
  FML_DISALLOW_COPY_ASSIGN_AND_MOVE(Scoped);
  T object_;
  Deleter deleter_;
};

void DeleteCF(CFMutableDictionaryRef value) {
  CFRelease(value);
}

void DeleteIO(io_object_t value) {
  IOObjectRelease(value);
}

std::optional<GpuUsageInfo> FindGpuUsageInfo(io_iterator_t iterator) {
  for (Scoped<io_registry_entry_t> regEntry(IOIteratorNext(iterator), DeleteIO); regEntry.get();
       regEntry.reset(IOIteratorNext(iterator))) {
    Scoped<CFMutableDictionaryRef> serviceDictionary(DeleteCF);
    if (IORegistryEntryCreateCFProperties(regEntry.get(), serviceDictionary.handle(),
                                          kCFAllocatorDefault, kNilOptions) != kIOReturnSuccess) {
      continue;
    }

    NSDictionary* dictionary =
        ((__bridge NSDictionary*)serviceDictionary.get())[@"PerformanceStatistics"];
    NSNumber* utilization = dictionary[@"Device Utilization %"];
    if (utilization) {
      return (GpuUsageInfo){.percent_usage = [utilization doubleValue]};
    }
  }
  return std::nullopt;
}

[[maybe_unused]] std::optional<GpuUsageInfo> FindSimulatorGpuUsageInfo() {
  Scoped<io_iterator_t> iterator(DeleteIO);
  if (IOServiceGetMatchingServices(kIOMasterPortDefault, IOServiceNameMatching("IntelAccelerator"),
                                   iterator.handle()) == kIOReturnSuccess) {
    return FindGpuUsageInfo(iterator.get());
  }
  return std::nullopt;
}

[[maybe_unused]] std::optional<GpuUsageInfo> FindDeviceGpuUsageInfo() {
  Scoped<io_iterator_t> iterator(DeleteIO);
  if (IOServiceGetMatchingServices(kIOMasterPortDefault, IOServiceNameMatching("sgx"),
                                   iterator.handle()) == kIOReturnSuccess) {
    for (Scoped<io_registry_entry_t> regEntry(IOIteratorNext(iterator.get()), DeleteIO);
         regEntry.get(); regEntry.reset(IOIteratorNext(iterator.get()))) {
      Scoped<io_iterator_t> innerIterator(DeleteIO);
      if (IORegistryEntryGetChildIterator(regEntry.get(), kIOServicePlane,
                                          innerIterator.handle()) == kIOReturnSuccess) {
        std::optional<GpuUsageInfo> result = FindGpuUsageInfo(innerIterator.get());
        if (result.has_value()) {
          return result;
        }
      }
    }
  }
  return std::nullopt;
}

#endif  // FLUTTER_RUNTIME_MODE == FLUTTER_RUNTIME_MODE_DEBUG ||
        // FLUTTER_RUNTIME_MODE == FLUTTER_RUNTIME_MODE_PROFILE

std::optional<GpuUsageInfo> PollGpuUsage() {
#if (FLUTTER_RUNTIME_MODE == FLUTTER_RUNTIME_MODE_RELEASE || \
     FLUTTER_RUNTIME_MODE == FLUTTER_RUNTIME_MODE_JIT_RELEASE)
  return std::nullopt;
#elif TARGET_IPHONE_SIMULATOR
  return FindSimulatorGpuUsageInfo();
#elif TARGET_OS_IOS
  return FindDeviceGpuUsageInfo();
#endif  // TARGET_IPHONE_SIMULATOR
}
}  // namespace

ProfileSample ProfilerMetricsIOS::GenerateSample() {
  return {.cpu_usage = CpuUsage(), .memory_usage = MemoryUsage(), .gpu_usage = PollGpuUsage()};
}

std::optional<CpuUsageInfo> ProfilerMetricsIOS::CpuUsage() {
  kern_return_t kernel_return_code;
  MachThreads mach_threads = MachThreads();

  // Get threads in the task
  kernel_return_code =
      task_threads(mach_task_self(), &mach_threads.threads, &mach_threads.thread_count);
  if (kernel_return_code != KERN_SUCCESS) {
    FML_LOG(ERROR) << "Error retrieving task information: "
                   << mach_error_string(kernel_return_code);
    return std::nullopt;
  }

  double total_cpu_usage = 0.0;
  uint32_t num_threads = mach_threads.thread_count;

  // Add the CPU usage for each thread. It should be noted that there may be some CPU usage missing
  // from this calculation. If a thread ends between calls to this routine, then its info will be
  // lost. We could solve this by installing a callback using pthread_key_create. The callback would
  // report the thread is ending and allow the code to get the CPU usage. But we need to call
  // pthread_setspecific in each thread to set the key's value to a non-null value for the callback
  // to work. If we really need this information and if we have a good mechanism for calling
  // pthread_setspecific in every thread, then we can include that value in the CPU usage.
  for (mach_msg_type_number_t i = 0; i < mach_threads.thread_count; i++) {
    thread_basic_info_data_t basic_thread_info;
    mach_msg_type_number_t thread_info_count = THREAD_BASIC_INFO_COUNT;
    kernel_return_code =
        thread_info(mach_threads.threads[i], THREAD_BASIC_INFO,
                    reinterpret_cast<thread_info_t>(&basic_thread_info), &thread_info_count);
    switch (kernel_return_code) {
      case KERN_SUCCESS: {
        const double current_thread_cpu_usage =
            basic_thread_info.cpu_usage / static_cast<float>(TH_USAGE_SCALE);
        total_cpu_usage += current_thread_cpu_usage;
        break;
      }
      case MACH_SEND_TIMEOUT:
      case MACH_SEND_TIMED_OUT:
      case MACH_SEND_INVALID_DEST:
        // Ignore as this thread been destroyed. The possible return codes are not really well
        // documented. This handling is inspired from the following sources:
        // - https://opensource.apple.com/source/xnu/xnu-4903.221.2/tests/task_inspect.c.auto.html
        // - https://github.com/apple/swift-corelibs-libdispatch/blob/main/src/queue.c#L6617
        num_threads--;
        break;
      default:
        FML_LOG(ERROR) << "Error retrieving thread information: "
                       << mach_error_string(kernel_return_code);
        return std::nullopt;
    }
  }

  flutter::CpuUsageInfo cpu_usage_info = {.num_threads = num_threads,
                                          .total_cpu_usage = total_cpu_usage * 100.0};
  return cpu_usage_info;
}

std::optional<MemoryUsageInfo> ProfilerMetricsIOS::MemoryUsage() {
  kern_return_t kernel_return_code;
  task_vm_info_data_t task_memory_info;
  mach_msg_type_number_t task_memory_info_count = TASK_VM_INFO_COUNT;

  kernel_return_code =
      task_info(mach_task_self(), TASK_VM_INFO, reinterpret_cast<task_info_t>(&task_memory_info),
                &task_memory_info_count);
  if (kernel_return_code != KERN_SUCCESS) {
    FML_LOG(ERROR) << " Error retrieving task memory information: "
                   << mach_error_string(kernel_return_code);
    return std::nullopt;
  }

  // `phys_footprint` is Apple's recommended way to measure app's memory usage. It provides the
  // best approximate to xcode memory gauge. According to its source code explanation, the physical
  // footprint mainly consists of app's internal memory data and IOKit mappings. `resident_size`
  // is the total physical memory used by the app, so we simply do `resident_size - phys_footprint`
  // to obtain the shared memory usage.
  const double dirty_memory_usage =
      static_cast<double>(task_memory_info.phys_footprint) / 1024.0 / 1024.0;
  const double owned_shared_memory_usage =
      static_cast<double>(task_memory_info.resident_size) / 1024.0 / 1024.0 - dirty_memory_usage;
  flutter::MemoryUsageInfo memory_usage_info = {
      .dirty_memory_usage = dirty_memory_usage,
      .owned_shared_memory_usage = owned_shared_memory_usage};
  return memory_usage_info;
}

}  // namespace flutter
