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

#include "vm/dart.h"

#include "vm/code_observers.h"
#include "vm/cpu.h"
#include "vm/dart_api_state.h"
#include "vm/dart_entry.h"
#include "vm/debugger.h"
#include "vm/flags.h"
#include "vm/freelist.h"
#include "vm/handles.h"
#include "vm/heap.h"
#include "vm/isolate.h"
#include "vm/metrics.h"
#include "vm/object.h"
#include "vm/object_store.h"
#include "vm/object_id_ring.h"
#include "vm/port.h"
#include "vm/profiler.h"
#include "vm/service_isolate.h"
#include "vm/simulator.h"
#include "vm/snapshot.h"
#include "vm/stub_code.h"
#include "vm/symbols.h"
#include "vm/thread_interrupter.h"
#include "vm/thread_pool.h"
#include "vm/virtual_memory.h"
#include "vm/zone.h"

namespace dart {

DEFINE_FLAG(int, new_gen_semi_max_size, (kWordSize <= 4) ? 16 : 32,
            "Max size of new gen semi space in MB");
DEFINE_FLAG(int, old_gen_heap_size, 0,
            "Max size of old gen heap size in MB, or 0 for unlimited,"
            "e.g: --old_gen_heap_size=1024 allows up to 1024MB old gen heap");
DEFINE_FLAG(int, external_max_size, (kWordSize <= 4) ? 512 : 1024,
            "Max total size of external allocations in MB, or 0 for unlimited,"
            "e.g: --external_max_size=1024 allows up to 1024MB of externals");

DEFINE_FLAG(bool, keep_code, false,
            "Keep deoptimized code for profiling.");

DECLARE_FLAG(bool, print_class_table);
DECLARE_FLAG(bool, trace_isolates);

Isolate* Dart::vm_isolate_ = NULL;
ThreadPool* Dart::thread_pool_ = NULL;
DebugInfo* Dart::pprof_symbol_generator_ = NULL;
ReadOnlyHandles* Dart::predefined_handles_ = NULL;

// Structure for managing read-only global handles allocation used for
// creating global read-only handles that are pre created and initialized
// for use across all isolates. Having these global pre created handles
// stored in the vm isolate ensures that we don't constantly create and
// destroy handles for read-only objects referred in the VM code
// (e.g: symbols, null object, empty array etc.)
// The ReadOnlyHandles C++ Wrapper around VMHandles which is a ValueObject is
// to ensure that the handles area is not trashed by automatic running of C++
// static destructors when 'exit()" is called by any isolate. There might be
// other isolates running at the same time and trashing the handles area will
// have unintended consequences.
class ReadOnlyHandles {
 public:
  ReadOnlyHandles() { }

 private:
  VMHandles handles_;

  friend class Dart;
  DISALLOW_COPY_AND_ASSIGN(ReadOnlyHandles);
};


const char* Dart::InitOnce(Dart_IsolateCreateCallback create,
                           Dart_IsolateInterruptCallback interrupt,
                           Dart_IsolateUnhandledExceptionCallback unhandled,
                           Dart_IsolateShutdownCallback shutdown,
                           Dart_FileOpenCallback file_open,
                           Dart_FileReadCallback file_read,
                           Dart_FileWriteCallback file_write,
                           Dart_FileCloseCallback file_close,
                           Dart_EntropySource entropy_source) {
  // TODO(iposva): Fix race condition here.
  if (vm_isolate_ != NULL || !Flags::Initialized()) {
    return "VM already initialized or flags not initialized.";
  }
  Isolate::SetFileCallbacks(file_open, file_read, file_write, file_close);
  Isolate::SetEntropySourceCallback(entropy_source);
  OS::InitOnce();
  VirtualMemory::InitOnce();
  Thread::InitOnce();
  Isolate::InitOnce();
  PortMap::InitOnce();
  FreeListElement::InitOnce();
  Api::InitOnce();
  CodeObservers::InitOnce();
  ThreadInterrupter::InitOnce();
  Profiler::InitOnce();
  SemiSpace::InitOnce();
  Metric::InitOnce();

#if defined(USING_SIMULATOR)
  Simulator::InitOnce();
#endif
  // Create the read-only handles area.
  ASSERT(predefined_handles_ == NULL);
  predefined_handles_ = new ReadOnlyHandles();
  // Create the VM isolate and finish the VM initialization.
  ASSERT(thread_pool_ == NULL);
  thread_pool_ = new ThreadPool();
  {
    ASSERT(vm_isolate_ == NULL);
    ASSERT(Flags::Initialized());
    const bool is_vm_isolate = true;
    vm_isolate_ = Isolate::Init("vm-isolate", is_vm_isolate);
    StackZone zone(vm_isolate_);
    HandleScope handle_scope(vm_isolate_);
    Heap::Init(vm_isolate_,
               0,  // New gen size 0; VM isolate should only allocate in old.
               FLAG_old_gen_heap_size * MBInWords,
               FLAG_external_max_size * MBInWords);
    ObjectStore::Init(vm_isolate_);
    TargetCPUFeatures::InitOnce();
    Object::InitOnce(vm_isolate_);
    ArgumentsDescriptor::InitOnce();
    StubCode::InitOnce();
    // Now that the needed stub has been generated, set the stack limit.
    vm_isolate_->InitializeStackLimit();
    Symbols::InitOnce(vm_isolate_);
    Scanner::InitOnce();
#if defined(TARGET_ARCH_IA32) || defined(TARGET_ARCH_X64)
    // Dart VM requires at least SSE2.
    if (!TargetCPUFeatures::sse2_supported()) {
      return "SSE2 is required.";
    }
#endif
    Object::FinalizeVMIsolate(vm_isolate_);
  }
  // There is a planned and known asymmetry here: We enter one scope for the VM
  // isolate so that we can allocate the "persistent" scoped handles for the
  // predefined API values (such as Dart_True, Dart_False and Dart_Null).
  Dart_EnterScope();
  Api::InitHandles();

  Isolate::SetCurrent(NULL);  // Unregister the VM isolate from this thread.
  Isolate::SetCreateCallback(create);
  Isolate::SetInterruptCallback(interrupt);
  Isolate::SetUnhandledExceptionCallback(unhandled);
  Isolate::SetShutdownCallback(shutdown);

  ServiceIsolate::Run();

  return NULL;
}


const char* Dart::Cleanup() {
  // Shutdown the service isolate before shutting down the thread pool.
  ServiceIsolate::Shutdown();
#if 0
  // Ideally we should shutdown the VM isolate here, but the thread pool
  // shutdown does not seem to ensure that all the threads have stopped
  // execution before it terminates, this results in racing isolates.
  if (vm_isolate_ == NULL) {
    return "VM already terminated.";
  }

  ASSERT(Isolate::Current() == NULL);

  delete thread_pool_;
  thread_pool_ = NULL;

  // Set the VM isolate as current isolate.
  Isolate::SetCurrent(vm_isolate_);

  // There is a planned and known asymmetry here: We exit one scope for the VM
  // isolate to account for the scope that was entered in Dart_InitOnce.
  Dart_ExitScope();

  ShutdownIsolate();
  vm_isolate_ = NULL;

  TargetCPUFeatures::Cleanup();
#endif

  Profiler::Shutdown();
  CodeObservers::DeleteAll();

  return NULL;
}


Isolate* Dart::CreateIsolate(const char* name_prefix) {
  // Create a new isolate.
  Isolate* isolate = Isolate::Init(name_prefix);
  ASSERT(isolate != NULL);
  return isolate;
}


RawError* Dart::InitializeIsolate(const uint8_t* snapshot_buffer, void* data) {
  // Initialize the new isolate.
  Isolate* isolate = Isolate::Current();
  TIMERSCOPE(isolate, time_isolate_initialization);
  ASSERT(isolate != NULL);
  StackZone zone(isolate);
  HandleScope handle_scope(isolate);
  Heap::Init(isolate,
             FLAG_new_gen_semi_max_size * MBInWords,
             FLAG_old_gen_heap_size * MBInWords,
             FLAG_external_max_size * MBInWords);
  ObjectIdRing::Init(isolate);
  ObjectStore::Init(isolate);

  // Setup for profiling.
  Profiler::InitProfilingForIsolate(isolate);

  if (snapshot_buffer == NULL) {
    const Error& error = Error::Handle(Object::Init(isolate));
    if (!error.IsNull()) {
      return error.raw();
    }
  } else {
    // Initialize from snapshot (this should replicate the functionality
    // of Object::Init(..) in a regular isolate creation path.
    Object::InitFromSnapshot(isolate);

    // TODO(turnidge): Remove once length is not part of the snapshot.
    const Snapshot* snapshot = Snapshot::SetupFromBuffer(snapshot_buffer);
    if (snapshot == NULL) {
      const String& message = String::Handle(
          String::New("Invalid snapshot."));
      return ApiError::New(message);
    }
    ASSERT(snapshot->kind() == Snapshot::kFull);
    if (FLAG_trace_isolates) {
      OS::Print("Size of isolate snapshot = %" Pd "\n", snapshot->length());
    }
    SnapshotReader reader(snapshot->content(), snapshot->length(),
                          Snapshot::kFull, isolate, zone.GetZone());
    const Error& error = Error::Handle(reader.ReadFullSnapshot());
    if (!error.IsNull()) {
      return error.raw();
    }
    if (FLAG_trace_isolates) {
      isolate->heap()->PrintSizes();
      isolate->megamorphic_cache_table()->PrintSizes();
    }
  }

  Object::VerifyBuiltinVtables();

  StubCode::Init(isolate);
  if (snapshot_buffer == NULL) {
    if (!isolate->object_store()->PreallocateObjects()) {
      return isolate->object_store()->sticky_error();
    }
  }
  isolate->megamorphic_cache_table()->InitMissHandler();

  isolate->heap()->EnableGrowthControl();
  isolate->set_init_callback_data(data);
  Api::SetupAcquiredError(isolate);
  if (FLAG_print_class_table) {
    isolate->class_table()->Print();
  }

  ServiceIsolate::MaybeInjectVMServiceLibrary(isolate);

  ServiceIsolate::SendIsolateStartupMessage();
  isolate->debugger()->NotifyIsolateCreated();

  // Create tag table.
  isolate->set_tag_table(
      GrowableObjectArray::Handle(GrowableObjectArray::New()));
  // Set up default UserTag.
  const UserTag& default_tag = UserTag::Handle(UserTag::DefaultTag());
  isolate->set_current_tag(default_tag);

  if (FLAG_keep_code) {
    isolate->set_deoptimized_code_array(
      GrowableObjectArray::Handle(GrowableObjectArray::New()));
  }
  return Error::null();
}


void Dart::RunShutdownCallback() {
  Isolate* isolate = Isolate::Current();
  void* callback_data = isolate->init_callback_data();
  Dart_IsolateShutdownCallback callback = Isolate::ShutdownCallback();
  ServiceIsolate::SendIsolateShutdownMessage();
  if (callback != NULL) {
    (callback)(callback_data);
  }
}


void Dart::ShutdownIsolate() {
  Isolate* isolate = Isolate::Current();
  isolate->Shutdown();
  delete isolate;
}


uword Dart::AllocateReadOnlyHandle() {
  ASSERT(Isolate::Current() == Dart::vm_isolate());
  ASSERT(predefined_handles_ != NULL);
  return predefined_handles_->handles_.AllocateScopedHandle();
}


bool Dart::IsReadOnlyHandle(uword address) {
  ASSERT(predefined_handles_ != NULL);
  return predefined_handles_->handles_.IsValidScopedHandle(address);
}

}  // namespace dart
