// 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 "platform/globals.h"

#include "include/dart_debugger_api.h"
#include "vm/dart_api_impl.h"
#include "vm/dart_entry.h"
#include "vm/debugger.h"
#include "vm/globals.h"
#include "vm/message_handler.h"
#include "vm/object_id_ring.h"
#include "vm/os.h"
#include "vm/port.h"
#include "vm/service.h"
#include "vm/unit_test.h"

namespace dart {

// This flag is used in the Service_Flags test below.
DEFINE_FLAG(bool, service_testing_flag, false, "Comment");

class ServiceTestMessageHandler : public MessageHandler {
 public:
  ServiceTestMessageHandler() : _msg(NULL) {}

  ~ServiceTestMessageHandler() {
    free(_msg);
  }

  bool HandleMessage(Message* message) {
    if (_msg != NULL) {
      free(_msg);
    }

    // Parse the message.
    SnapshotReader reader(message->data(), message->len(),
                          Snapshot::kMessage, Isolate::Current());
    const Object& response_obj = Object::Handle(reader.ReadObject());
    String& response = String::Handle();
    response ^= response_obj.raw();
    _msg = strdup(response.ToCString());
    return true;
  }

  // Removes a given json key:value from _msg.
  void filterMsg(const char* key) {
    int key_len = strlen(key);
    int old_len = strlen(_msg);
    char* new_msg = reinterpret_cast<char*>(malloc(old_len + 1));
    int old_pos = 0;
    int new_pos = 0;
    while (_msg[old_pos] != '\0') {
      if (_msg[old_pos] == '\"') {
        old_pos++;
        if ((old_len - old_pos) > key_len &&
            strncmp(&_msg[old_pos], key, key_len) == 0 &&
            _msg[old_pos + key_len] == '\"') {
          old_pos += (key_len + 2);
          // Skip until next , or }.
          while (_msg[old_pos] != '\0' &&
                 _msg[old_pos] != ',' &&
                 _msg[old_pos] != '}') {
            old_pos++;
          }
          if (_msg[old_pos] == ',') {
            old_pos++;
          }
        } else {
          new_msg[new_pos] = '\"';;
          new_pos++;
        }
      } else {
        new_msg[new_pos] = _msg[old_pos];
        new_pos++;
        old_pos++;
      }
    }
    new_msg[new_pos] = '\0';
    free(_msg);
    _msg = new_msg;
  }

  const char* msg() const { return _msg; }

 private:
  char* _msg;
};


static RawArray* Eval(Dart_Handle lib, const char* expr) {
  Dart_Handle expr_val = Dart_EvaluateExpr(lib, NewString(expr));
  EXPECT_VALID(expr_val);
  Isolate* isolate = Isolate::Current();
  const GrowableObjectArray& value =
      Api::UnwrapGrowableObjectArrayHandle(isolate, expr_val);
  const Array& result = Array::Handle(Array::MakeArray(value));
  GrowableObjectArray& growable = GrowableObjectArray::Handle();
  growable ^= result.At(3);
  Array& array = Array::Handle(Array::MakeArray(growable));
  result.SetAt(3, array);
  growable ^= result.At(4);
  array = Array::MakeArray(growable);
  result.SetAt(4, array);
  return result.raw();
}


static RawArray* EvalF(Dart_Handle lib, const char* fmt, ...) {
  Isolate* isolate = Isolate::Current();

  va_list args;
  va_start(args, fmt);
  intptr_t len = OS::VSNPrint(NULL, 0, fmt, args);
  va_end(args);

  char* buffer = isolate->current_zone()->Alloc<char>(len + 1);
  va_list args2;
  va_start(args2, fmt);
  OS::VSNPrint(buffer, (len + 1), fmt, args2);
  va_end(args2);

  return Eval(lib, buffer);
}


// Search for the formatted string in buffer.
//
// TODO(turnidge): This function obscures the line number of failing
// EXPECTs.  Rework this.
static void ExpectSubstringF(const char* buff, const char* fmt, ...) {
  Isolate* isolate = Isolate::Current();

  va_list args;
  va_start(args, fmt);
  intptr_t len = OS::VSNPrint(NULL, 0, fmt, args);
  va_end(args);

  char* buffer = isolate->current_zone()->Alloc<char>(len + 1);
  va_list args2;
  va_start(args2, fmt);
  OS::VSNPrint(buffer, (len + 1), fmt, args2);
  va_end(args2);

  EXPECT_SUBSTRING(buffer, buff);
}


static RawFunction* GetFunction(const Class& cls, const char* name) {
  const Function& result = Function::Handle(cls.LookupDynamicFunction(
      String::Handle(String::New(name))));
  EXPECT(!result.IsNull());
  return result.raw();
}


static RawClass* GetClass(const Library& lib, const char* name) {
  const Class& cls = Class::Handle(
      lib.LookupClass(String::Handle(Symbols::New(name))));
  EXPECT(!cls.IsNull());  // No ambiguity error expected.
  return cls.raw();
}


TEST_CASE(Service_Isolate) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "main() {\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Get the isolate summary.
  service_msg = Eval(lib, "[0, port, [], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();

  JSONReader reader(handler.msg());

  const int kBufferSize = 128;
  char buffer[kBufferSize];

  // Check that the response string is somewhat sane.

  // type
  EXPECT(reader.Seek("type"));
  EXPECT_EQ(reader.Type(), JSONReader::kString);
  reader.GetDecodedValueChars(buffer, kBufferSize);
  EXPECT_STREQ("Isolate", buffer);

  // id
  EXPECT(reader.Seek("id"));
  EXPECT_EQ(reader.Type(), JSONReader::kString);
  reader.GetDecodedValueChars(buffer, kBufferSize);
  EXPECT_SUBSTRING("isolates/", buffer);

  // heap
  EXPECT(reader.Seek("heaps"));
  EXPECT_EQ(reader.Type(), JSONReader::kObject);
}


TEST_CASE(Service_StackTrace) {
  // TODO(turnidge): Extend this test to cover a non-trivial stack trace.
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "main() {\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Get the stacktrace.
  service_msg = Eval(lib, "[0, port, ['stacktrace'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ(
      "{\"type\":\"StackTrace\",\"id\":\"stacktrace\",\"members\":[]}",
      handler.msg());

  // Malformed request.
  service_msg = Eval(lib, "[0, port, ['stacktrace', 'jamboree'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ(
      "{\"type\":\"Error\",\"id\":\"\",\"message\":\"Command too long\","
      "\"request\":{\"arguments\":[\"stacktrace\",\"jamboree\"],"
      "\"option_keys\":[],\"option_values\":[]}}",
      handler.msg());
}


TEST_CASE(Service_DebugBreakpoints) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "main() {\n"   // We set breakpoint here.
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Add a breakpoint.
  service_msg = EvalF(lib,
                     "[0, port, ['libraries', '%" Pd "', "
                     "'scripts', 'test-lib', 'setBreakpoint'], "
                      "['line'], ['3']]",
                      vmlib.index());
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(
      handler.msg(),
      "{\"type\":\"Breakpoint\",\"id\":\"debug\\/breakpoints\\/1\","
      "\"breakpointNumber\":1,\"enabled\":true,\"resolved\":false,"
      "\"location\":{\"type\":\"Location\","
      "\"script\":{\"type\":\"@Script\","
      "\"id\":\"libraries\\/%" Pd "\\/scripts\\/test-lib\","
      "\"name\":\"test-lib\",\"kind\":\"script\"},"
      "\"tokenPos\":5}}",
      vmlib.index());

  // Get the breakpoint list.
  service_msg = Eval(lib, "[0, port, ['debug', 'breakpoints'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(
      handler.msg(),
      "{\"type\":\"BreakpointList\",\"id\":\"debug\\/breakpoints\","
      "\"breakpoints\":["
      "{\"type\":\"Breakpoint\",\"id\":\"debug\\/breakpoints\\/1\","
      "\"breakpointNumber\":1,\"enabled\":true,\"resolved\":false,"
      "\"location\":{\"type\":\"Location\","
      "\"script\":{\"type\":\"@Script\","
      "\"id\":\"libraries\\/%" Pd "\\/scripts\\/test-lib\","
      "\"name\":\"test-lib\",\"kind\":\"script\"},"
      "\"tokenPos\":5}}]}",
      vmlib.index());

  // Lookup individual breakpoint.
  service_msg = Eval(lib, "[0, port, ['debug', 'breakpoints', '1'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(
      handler.msg(),
      "{\"type\":\"Breakpoint\",\"id\":\"debug\\/breakpoints\\/1\","
      "\"breakpointNumber\":1,\"enabled\":true,\"resolved\":false,"
      "\"location\":{\"type\":\"Location\","
      "\"script\":{\"type\":\"@Script\","
      "\"id\":\"libraries\\/%" Pd "\\/scripts\\/test-lib\","
      "\"name\":\"test-lib\",\"kind\":\"script\"},"
      "\"tokenPos\":5}}",
      vmlib.index());

  // Unrecognized breakpoint subcommand.
  service_msg =
      Eval(lib, "[0, port, ['debug', 'breakpoints', '1', 'green'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ("{\"type\":\"Error\",\"id\":\"\","
                "\"message\":\"Unrecognized subcommand: green\","
                "\"request\":{\"arguments\":[\"debug\",\"breakpoints\","
                                            "\"1\",\"green\"],"
                             "\"option_keys\":[],\"option_values\":[]}}",
               handler.msg());

  // Clear breakpoint.
  service_msg =
      Eval(lib, "[0, port, ['debug', 'breakpoints', '1', 'clear'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ("{\"type\":\"Success\",\"id\":\"\"}",
               handler.msg());

  // Get the breakpoint list.
  service_msg = Eval(lib, "[0, port, ['debug', 'breakpoints'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ(
      "{\"type\":\"BreakpointList\",\"id\":\"debug\\/breakpoints\","
      "\"breakpoints\":[]}",
      handler.msg());

  // Missing sub-command.
  service_msg = Eval(lib, "[0, port, ['debug'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ(
      "{\"type\":\"Error\",\"id\":\"\","
       "\"message\":\"Must specify a subcommand\","
       "\"request\":{\"arguments\":[\"debug\"],\"option_keys\":[],"
                    "\"option_values\":[]}}",
      handler.msg());

  // Unrecognized breakpoint.
  service_msg = Eval(lib,
                     "[0, port, ['debug', 'breakpoints', '1111'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ("{\"type\":\"Error\",\"id\":\"\","
                "\"message\":\"Unrecognized breakpoint id: 1111\","
                "\"request\":{"
                    "\"arguments\":[\"debug\",\"breakpoints\",\"1111\"],"
                    "\"option_keys\":[],\"option_values\":[]}}",
               handler.msg());

  // Unrecognized subcommand.
  service_msg = Eval(lib, "[0, port, ['debug', 'nosferatu'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ("{\"type\":\"Error\",\"id\":\"\","
                "\"message\":\"Unrecognized subcommand 'nosferatu'\","
                "\"request\":{\"arguments\":[\"debug\",\"nosferatu\"],"
                             "\"option_keys\":[],\"option_values\":[]}}",
               handler.msg());
}


// Globals used to communicate with HandlerPausedEvent.
static intptr_t pause_line_number = 0;
static Dart_Handle saved_lib;
static ServiceTestMessageHandler* saved_handler = NULL;

static void HandlePausedEvent(Dart_IsolateId isolate_id,
                              intptr_t bp_id,
                              const Dart_CodeLocation& loc) {
  Isolate* isolate = Isolate::Current();
  Debugger* debugger = isolate->debugger();

  // The debugger knows that it is paused, and why.
  EXPECT(debugger->IsPaused());
  const DebuggerEvent* event = debugger->PauseEvent();
  EXPECT(event != NULL);
  EXPECT(event->type() == DebuggerEvent::kBreakpointReached);

  // Save the last line number seen by this handler.
  pause_line_number = event->top_frame()->LineNumber();

  // Single step
  Array& service_msg = Array::Handle();
  service_msg = Eval(saved_lib,
                     "[0, port, ['debug', 'resume'], "
                     "['step'], ['into']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  saved_handler->HandleNextMessage();
  EXPECT_STREQ("{\"type\":\"Success\",\"id\":\"\"}",
               saved_handler->msg());
}


TEST_CASE(Service_Stepping) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "var value = 0;\n"
      "\n"
      "main() {\n"   // We set breakpoint here.
      "  value++;\n"
      "  value++;\n"
      "  value++;\n"
      "}";           // We step up to here.

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  saved_lib = lib;

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  saved_handler = &handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Add a breakpoint.
  service_msg = EvalF(lib,
                      "[0, port, ['libraries', '%" Pd "', "
                      "'scripts', 'test-lib', 'setBreakpoint'], "
                      "['line'], ['4']]",
                      vmlib.index());
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(
      handler.msg(),
      "{\"type\":\"Breakpoint\",\"id\":\"debug\\/breakpoints\\/1\","
      "\"breakpointNumber\":1,\"enabled\":true,\"resolved\":false,"
      "\"location\":{\"type\":\"Location\","
      "\"script\":{\"type\":\"@Script\","
      "\"id\":\"libraries\\/%" Pd "\\/scripts\\/test-lib\","
      "\"name\":\"test-lib\",\"kind\":\"script\"},"
      "\"tokenPos\":11}}",
      vmlib.index());

  pause_line_number = -1;
  Dart_SetPausedEventHandler(HandlePausedEvent);

  // Run the program.
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);

  // We were able to step to the last line in main.
  EXPECT_EQ(8, pause_line_number);
}


TEST_CASE(Service_Objects) {
  // TODO(turnidge): Extend this test to cover a non-trivial stack trace.
  const char* kScript =
      "var port;\n"     // Set to our mock port by C++.
      "var validId;\n"  // Set to a valid object id by C++.
      "\n"
      "main() {\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  ObjectIdRing* ring = isolate->object_id_ring();
  const Array& arr = Array::Handle(Array::New(1, Heap::kOld));
  {
    HANDLESCOPE(isolate);
    const String& str = String::Handle(String::New("value", Heap::kOld));
    arr.SetAt(0, str);
  }
  intptr_t arr_id = ring->GetIdForObject(arr.raw());
  Dart_Handle valid_id = Dart_NewInteger(arr_id);
  EXPECT_VALID(valid_id);
  EXPECT_VALID(Dart_SetField(lib, NewString("validId"), valid_id));

  Array& service_msg = Array::Handle();

  // null
  service_msg = Eval(lib, "[0, port, ['objects', 'null'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_SUBSTRING(
      "{\"type\":\"null\",\"id\":\"objects\\/null\","
      "\"valueAsString\":\"null\",\"class\":",
      handler.msg());

  // not initialized
  service_msg = Eval(lib, "[0, port, ['objects', 'not-initialized'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"Sentinel\",\"id\":\"objects\\/not-initialized\","
      "\"valueAsString\":\"<not initialized>\"}",
      handler.msg());

  // being initialized
  service_msg = Eval(lib,
                     "[0, port, ['objects', 'being-initialized'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"Sentinel\",\"id\":\"objects\\/being-initialized\","
      "\"valueAsString\":\"<being initialized>\"}",
      handler.msg());

  // optimized out
  service_msg = Eval(lib, "[0, port, ['objects', 'optimized-out'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"Sentinel\",\"id\":\"objects\\/optimized-out\","
      "\"valueAsString\":\"<optimized out>\"}",
      handler.msg());

  // collected
  service_msg = Eval(lib, "[0, port, ['objects', 'collected'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"Sentinel\",\"id\":\"objects\\/collected\","
      "\"valueAsString\":\"<collected>\"}",
      handler.msg());

  // expired
  service_msg = Eval(lib, "[0, port, ['objects', 'expired'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"Sentinel\",\"id\":\"objects\\/expired\","
      "\"valueAsString\":\"<expired>\"}",
      handler.msg());

  // bool
  service_msg = Eval(lib, "[0, port, ['objects', 'bool-true'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  handler.filterMsg("size");
  EXPECT_STREQ(
      "{\"type\":\"bool\","
      "\"class\":{\"type\":\"@Class\",\"id\":\"classes\\/46\","
      "\"name\":\"bool\"},"
      "\"fields\":[],\"id\":\"objects\\/bool-true\","
      "\"valueAsString\":\"true\"}",
      handler.msg());

  // int
  service_msg = Eval(lib, "[0, port, ['objects', 'int-123'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"int\",\"_vmType\":\"Smi\","
      "\"class\":{\"type\":\"@Class\",\"id\":\"classes\\/42\","
      "\"name\":\"_Smi\",},"
      "\"fields\":[],"
      "\"id\":\"objects\\/int-123\","
      "\"valueAsString\":\"123\"}",
      handler.msg());

  // object id ring / valid
  service_msg = Eval(lib, "[0, port, ['objects', '$validId'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  handler.filterMsg("size");
  handler.filterMsg("id");
  EXPECT_STREQ(
      "{\"type\":\"List\",\"_vmType\":\"Array\","
      "\"class\":{\"type\":\"@Class\",\"name\":\"_List\",},"
      "\"fields\":[],"
      "\"length\":1,"
      "\"elements\":[{"
          "\"index\":0,"
          "\"value\":{\"type\":\"@String\","
          "\"class\":{\"type\":\"@Class\",\"name\":\"_OneByteString\",},"
          "\"valueAsString\":\"value\"}}]}",
      handler.msg());

  // object id ring / invalid => expired
  service_msg = Eval(lib, "[0, port, ['objects', '99999999'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"Sentinel\",\"id\":\"objects\\/expired\","
      "\"valueAsString\":\"<expired>\"}",
      handler.msg());

  // expired/eval => error
  service_msg = Eval(lib, "[0, port, ['objects', 'expired', 'eval'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"Error\",\"id\":\"\","
      "\"message\":\"expected at most 2 arguments but found 3\\n\","
      "\"request\":{\"arguments\":[\"objects\",\"expired\",\"eval\"],"
      "\"option_keys\":[],\"option_values\":[]}}",
      handler.msg());

  // int/eval => good
  service_msg = Eval(lib,
                     "[0, port, ['objects', 'int-123', 'eval'], "
                     "['expr'], ['this+99']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"@int\",\"_vmType\":\"@Smi\","
      "\"class\":{\"type\":\"@Class\",\"id\":\"classes\\/42\","
      "\"name\":\"_Smi\",},"
      "\"id\":\"objects\\/int-222\","
      "\"valueAsString\":\"222\"}",
      handler.msg());

  // eval returning null works
  service_msg = Eval(lib,
                     "[0, port, ['objects', 'int-123', 'eval'], "
                     "['expr'], ['null']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"@null\",\"id\":\"objects\\/null\","
      "\"valueAsString\":\"null\"}",
      handler.msg());

  // object id ring / invalid => expired
  service_msg = Eval(lib, "[0, port, ['objects', '99999999', 'eval'], "
                     "['expr'], ['this']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"Error\",\"id\":\"\",\"kind\":\"EvalExpired\","
      "\"message\":\"attempt to evaluate against expired object\\n\","
      "\"request\":{\"arguments\":[\"objects\",\"99999999\",\"eval\"],"
      "\"option_keys\":[\"expr\"],\"option_values\":[\"this\"]}}",
      handler.msg());

  // Extra arg to eval.
  service_msg = Eval(lib,
                     "[0, port, ['objects', 'int-123', 'eval', 'foo'], "
                     "['expr'], ['this+99']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"Error\",\"id\":\"\","
      "\"message\":\"expected at most 3 arguments but found 4\\n\","
      "\"request\":{\"arguments\":[\"objects\",\"int-123\",\"eval\",\"foo\"],"
      "\"option_keys\":[\"expr\"],\"option_values\":[\"this+99\"]}}",
      handler.msg());

  // Retained by single instance.
  service_msg = Eval(lib,
                     "[0, port, ['objects', '$validId', 'retained'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  ExpectSubstringF(handler.msg(),
                   "\"id\":\"objects\\/int-%" Pd "\"",
                   arr.raw()->Size() + arr.At(0)->Size());

  // Retaining path to 'arr', limit 1.
  service_msg = Eval(
      lib,
      "[0, port, ['objects', '$validId', 'retaining_path'], ['limit'], ['1']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(
      handler.msg(),
      "{\"type\":\"RetainingPath\",\"id\":\"retaining_path\",\"length\":1,"
      "\"elements\":[{\"index\":0,\"value\":{\"type\":\"@List\"");

  // Retaining path missing limit.
  service_msg = Eval(
      lib,
      "[0, port, ['objects', '$validId', 'retaining_path'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(), "{\"type\":\"Error\"");

  // eval against list containing an internal object.
  Object& internal_object = Object::Handle();
  internal_object = LiteralToken::New();
  arr.SetAt(0, internal_object);
  service_msg = Eval(lib,
                     "[0, port, ['objects', '$validId', 'eval'], "
                     "['expr'], ['toString()']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(), "\"type\":\"Error\"");
  ExpectSubstringF(
      handler.msg(),
      "\"message\":\"attempt to evaluate against internal VM object\\n\"");
}


TEST_CASE(Service_RetainingPath) {
  const char* kScript =
      "var port;\n"    // Set to our mock port by C++.
      "var id0;\n"     // Set to an object id by C++.
      "var id1;\n"     // Ditto.
      "var idElem;\n"  // Ditto.
      "class Foo {\n"
      "  String f0;\n"
      "  String f1;\n"
      "}\n"
      "Foo foo;\n"
      "List<String> lst;\n"
      "main() {\n"
      "  foo = new Foo();\n"
      "  lst = new List<String>(100);\n"
      "}\n";
  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  const Class& class_foo = Class::Handle(GetClass(vmlib, "Foo"));
  EXPECT(!class_foo.IsNull());
  Dart_Handle foo = Dart_GetField(lib, NewString("foo"));
  Dart_Handle lst = Dart_GetField(lib, NewString("lst"));
  const intptr_t kElemIndex = 42;
  {
    Dart_EnterScope();
    ObjectIdRing* ring = isolate->object_id_ring();
    {
      const String& foo0 = String::Handle(String::New("foo0", Heap::kOld));
      Dart_Handle h_foo0 = Api::NewHandle(isolate, foo0.raw());
      EXPECT_VALID(Dart_SetField(foo, NewString("f0"), h_foo0));
      Dart_Handle id0 = Dart_NewInteger(ring->GetIdForObject(foo0.raw()));
      EXPECT_VALID(id0);
      EXPECT_VALID(Dart_SetField(lib, NewString("id0"), id0));
    }
    {
      const String& foo1 = String::Handle(String::New("foo1", Heap::kOld));
      Dart_Handle h_foo1 = Api::NewHandle(isolate, foo1.raw());
      EXPECT_VALID(Dart_SetField(foo, NewString("f1"), h_foo1));
      Dart_Handle id1 = Dart_NewInteger(ring->GetIdForObject(foo1.raw()));
      EXPECT_VALID(id1);
      EXPECT_VALID(Dart_SetField(lib, NewString("id1"), id1));
    }
    {
      const String& elem = String::Handle(String::New("elem", Heap::kOld));
      Dart_Handle h_elem = Api::NewHandle(isolate, elem.raw());
      EXPECT_VALID(Dart_ListSetAt(lst, kElemIndex, h_elem));
      Dart_Handle idElem = Dart_NewInteger(ring->GetIdForObject(elem.raw()));
      EXPECT_VALID(idElem);
      EXPECT_VALID(Dart_SetField(lib, NewString("idElem"), idElem));
    }
    Dart_ExitScope();
  }

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));
  Array& service_msg = Array::Handle();

  // Retaining path to 'foo0', limit 2.
  service_msg = Eval(
      lib,
      "[0, port, ['objects', '$id0', 'retaining_path'], ['limit'], ['2']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(
      handler.msg(),
      "{\"type\":\"RetainingPath\",\"id\":\"retaining_path\",\"length\":2,"
      "\"elements\":[{\"index\":0,\"value\":{\"type\":\"@String\"");
  ExpectSubstringF(handler.msg(), "\"parentField\":{\"type\":\"@Field\"");
  ExpectSubstringF(handler.msg(), "\"name\":\"f0\"");
  ExpectSubstringF(handler.msg(),
      "{\"index\":1,\"value\":{\"type\":\"@Instance\"");

  // Retaining path to 'foo1', limit 2.
  service_msg = Eval(
      lib,
      "[0, port, ['objects', '$id1', 'retaining_path'], ['limit'], ['2']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(
      handler.msg(),
      "{\"type\":\"RetainingPath\",\"id\":\"retaining_path\",\"length\":2,"
      "\"elements\":[{\"index\":0,\"value\":{\"type\":\"@String\"");
  ExpectSubstringF(handler.msg(), "\"parentField\":{\"type\":\"@Field\"");
  ExpectSubstringF(handler.msg(), "\"name\":\"f1\"");
  ExpectSubstringF(handler.msg(),
      "{\"index\":1,\"value\":{\"type\":\"@Instance\"");

  // Retaining path to 'elem', limit 2.
  service_msg = Eval(
      lib,
      "[0, port, ['objects', '$idElem', 'retaining_path'], ['limit'], ['2']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(
      handler.msg(),
      "{\"type\":\"RetainingPath\",\"id\":\"retaining_path\",\"length\":2,"
      "\"elements\":[{\"index\":0,\"value\":{\"type\":\"@String\"");
  ExpectSubstringF(handler.msg(), "\"parentListIndex\":%" Pd, kElemIndex);
  ExpectSubstringF(handler.msg(),
      "{\"index\":1,\"value\":{\"type\":\"@List\"");
}


TEST_CASE(Service_Libraries) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "var libVar = 54321;\n"
      "\n"
      "main() {\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Request library.
  service_msg = EvalF(lib,
                      "[0, port, ['libraries', '%" Pd "'], [], []]",
                      vmlib.index());
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Library\"", handler.msg());
  EXPECT_SUBSTRING("\"url\":\"test-lib\"", handler.msg());

  // Evaluate an expression from a library.
  service_msg = EvalF(lib,
                      "[0, port, ['libraries', '%" Pd "', 'eval'], "
                      "['expr'], ['libVar - 1']]",
                      vmlib.index());
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"@int\",\"_vmType\":\"@Smi\","
      "\"class\":{\"type\":\"@Class\",\"id\":\"classes\\/42\","
      "\"name\":\"_Smi\",},\"id\":\"objects\\/int-54320\","
      "\"valueAsString\":\"54320\"}",
      handler.msg());
}


TEST_CASE(Service_Classes) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "class A {\n"
      "  var a;\n"
      "  static var cobra = 11235;\n"
      "  dynamic b() {}\n"
      "  dynamic c() {\n"
      "    var d = () { b(); };\n"
      "    return d;\n"
      "  }\n"
      "}\n"
      "class B { static int i = 42; }\n"
      "main() {\n"
      "  var z = new A();\n"
      "  var x = z.c();\n"
      "  x();\n"
      "  ++B.i;\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);
  const Class& class_a = Class::Handle(GetClass(vmlib, "A"));
  EXPECT(!class_a.IsNull());
  intptr_t cid = class_a.id();

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Request an invalid class id.
  service_msg = Eval(lib, "[0, port, ['classes', '999999'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ(
    "{\"type\":\"Error\",\"id\":\"\","
    "\"message\":\"999999 is not a valid class id.\","
    "\"request\":{\"arguments\":[\"classes\",\"999999\"],"
    "\"option_keys\":[],\"option_values\":[]}}", handler.msg());

  // Request the class A over the service.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "'], [], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Class\"", handler.msg());
  ExpectSubstringF(handler.msg(),
                   "\"id\":\"classes\\/%" Pd "\",\"name\":\"A\",", cid);
  ExpectSubstringF(handler.msg(), "\"allocationStats\":");
  ExpectSubstringF(handler.msg(), "\"tokenPos\":");
  ExpectSubstringF(handler.msg(), "\"endTokenPos\":");

  // Evaluate an expression from class A.
  service_msg = EvalF(lib,
                      "[0, port, ['classes', '%" Pd "', 'eval'], "
                      "['expr'], ['cobra + 100000']]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  handler.filterMsg("_vmName");
  EXPECT_STREQ(
      "{\"type\":\"@int\",\"_vmType\":\"@Smi\","
      "\"class\":{\"type\":\"@Class\",\"id\":\"classes\\/42\","
      "\"name\":\"_Smi\",},"
      "\"id\":\"objects\\/int-111235\","
      "\"valueAsString\":\"111235\"}",
      handler.msg());

  // Request function 'b' from class A.
  service_msg = EvalF(lib,
                      "[0, port, ['classes', '%" Pd "', 'functions', 'b'],"
                      "[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Function\"", handler.msg());
  ExpectSubstringF(handler.msg(),
                   "\"id\":\"classes\\/%" Pd "\\/functions\\/b\","
                   "\"name\":\"b\",", cid);

  // Request field 0 from class A.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "', 'fields', '0'],"
                      "[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Field\"", handler.msg());
  ExpectSubstringF(handler.msg(),
                   "\"id\":\"classes\\/%" Pd "\\/fields\\/0\","
                   "\"name\":\"a\",", cid);

  // Invalid sub command.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "', 'huh', '0'],"
                      "[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(),
    "{\"type\":\"Error\",\"id\":\"\",\"message\":\"Invalid sub collection huh\""
    ",\"request\":"
    "{\"arguments\":[\"classes\",\"%" Pd "\",\"huh\",\"0\"],\"option_keys\":[],"
    "\"option_values\":[]}}", cid);

  // Invalid field request.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "', 'fields', '9'],"
                      "[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(),
    "{\"type\":\"Error\",\"id\":\"\",\"message\":\"Field 9 not found\","
    "\"request\":{\"arguments\":[\"classes\",\"%" Pd "\",\"fields\",\"9\"],"
    "\"option_keys\":[],\"option_values\":[]}}", cid);

  // Invalid function request.
  service_msg = EvalF(lib,
                      "[0, port, ['classes', '%" Pd "', 'functions', '9'],"
                      "[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(),
    "{\"type\":\"Error\",\"id\":\"\",\"message\":\"Function 9 not found\","
    "\"request\":{\"arguments\":[\"classes\",\"%" Pd "\",\"functions\",\"9\"],"
    "\"option_keys\":[],\"option_values\":[]}}", cid);


  // Invalid field subcommand.
  service_msg = EvalF(lib,
                      "[0, port, ['classes', '%" Pd "', 'fields', '9', 'x']"
                      ",[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(),
    "{\"type\":\"Error\",\"id\":\"\",\"message\":\"Command too long\","
    "\"request\":"
    "{\"arguments\":[\"classes\",\"%" Pd "\",\"fields\",\"9\",\"x\"],"
    "\"option_keys\":[],\"option_values\":[]}}", cid);

  // Invalid function command.
  service_msg = EvalF(lib,
                      "[0, port, ['classes', '%" Pd "', 'functions', '0',"
                      "'x', 'y'], [], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(),
    "{\"type\":\"Error\",\"id\":\"\","
    "\"message\":\"Command should have 4 or 5 arguments\","
    "\"request\":"
    "{\"arguments\":[\"classes\",\"%" Pd "\",\"functions\",\"0\",\"x\",\"y\"],"
    "\"option_keys\":[],\"option_values\":[]}}", cid);

  // Invalid function subcommand with valid function id.
  service_msg = EvalF(lib,
                      "[0, port, ['classes', '%" Pd "', 'functions', 'b',"
                      "'x'], [], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(),
    "{\"type\":\"Error\",\"id\":\"\",\"message\":\"Invalid sub command x\","
    "\"request\":"
    "{\"arguments\":[\"classes\",\"%" Pd "\",\"functions\",\"b\",\"x\"],"
    "\"option_keys\":[],\"option_values\":[]}}", cid);

  // Retained size of all instances of class B.
  const Class& class_b = Class::Handle(GetClass(vmlib, "B"));
  EXPECT(!class_b.IsNull());
  const Instance& b0 = Instance::Handle(Instance::New(class_b));
  const Instance& b1 = Instance::Handle(Instance::New(class_b));
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "', 'retained'],"
                      "[], []]", class_b.id());
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(),
                   "\"id\":\"objects\\/int-%" Pd "\"",
                   b0.raw()->Size() + b1.raw()->Size());
  // ... and list the instances of class B.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "', 'instances'],"
                      "['limit'], ['3']]", class_b.id());
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(), "\"type\":\"InstanceSet\"");
  ExpectSubstringF(handler.msg(), "\"totalCount\":2");
  ExpectSubstringF(handler.msg(), "\"sampleCount\":2");
  // TODO(koda): Actually parse the response.
  static const intptr_t kInstanceListId = 0;
  ExpectSubstringF(handler.msg(), "\"id\":\"objects\\/%" Pd "\",\"length\":2",
                   kInstanceListId);
  Array& list = Array::Handle();
  ObjectIdRing::LookupResult kind;
  list ^= isolate->object_id_ring()->GetObjectForId(kInstanceListId, &kind);
  EXPECT_EQ(2, list.Length());
  // The list should contain {b0, b1}.
  EXPECT((list.At(0) == b0.raw() && list.At(1) == b1.raw()) ||
         (list.At(0) == b1.raw() && list.At(1) == b0.raw()));
  // ... and if limit is 1, we one get one of them.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "', 'instances'],"
                      "['limit'], ['1']]", class_b.id());
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(), "\"totalCount\":2");
  ExpectSubstringF(handler.msg(), "\"sampleCount\":1");
}


TEST_CASE(Service_SetSource) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "class A {\n"
      "  a() { return 1; }\n"
      "  b() { return 0; }\n"
      "  c(String f) { return f.length; }\n"
      "}\n"
      "main() {\n"
      "  var z = new A();\n"
      "  return z.a();\n"
      "}\n"
      "runB() {\n"
      "  var z = new A();\n"
      "  return z.b();\n"
      "}\n"
      "runC() {\n"
      "  var z = new A();\n"
      "  return z.c();\n"
      "}\n";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);
  const Class& class_a = Class::Handle(GetClass(vmlib, "A"));
  EXPECT(!class_a.IsNull());
  intptr_t cid = class_a.id();

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Request the class A over the service.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "'], [], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Class\"", handler.msg());
  ExpectSubstringF(handler.msg(),
                   "\"id\":\"classes\\/%" Pd "\",\"name\":\"A\",", cid);
  ExpectSubstringF(handler.msg(), "\"allocationStats\":");
  ExpectSubstringF(handler.msg(), "\"tokenPos\":");
  ExpectSubstringF(handler.msg(), "\"endTokenPos\":");

  // Request function 'b' from class A.
  service_msg = EvalF(lib,
                      "[0, port, ['classes', '%" Pd "', 'functions', 'b'],"
                      "[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Function\"", handler.msg());
  ExpectSubstringF(handler.msg(),
                   "\"id\":\"classes\\/%" Pd "\\/functions\\/b\","
                   "\"name\":\"b\",", cid);

  // Invalid set source of function 'b' from class A.
  service_msg = EvalF(
    lib,
    "[0, port, ['classes', '%" Pd "', 'functions', 'b', 'set_source'],"
    "[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Error\"", handler.msg());
  EXPECT_SUBSTRING("set_source expects a 'source' option", handler.msg());

  // Set source (with syntax error) of function 'b' from class A.
  service_msg = EvalF(
    lib,
    "[0, port, ['classes', '%" Pd "', 'functions', 'b', 'set_source'],"
    "['source'], ['b() { return 4 }']]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Error\"", handler.msg());

  // Set source of function 'b' from class A.
  service_msg = EvalF(
    lib,
    "[0, port, ['classes', '%" Pd "', 'functions', 'b', 'set_source'],"
    "['source'], ['b() { return 4; }']]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("Success", handler.msg());

  // Run function 'b' see that it is executing replaced code.
  result = Dart_Invoke(lib, NewString("runB"), 0, NULL);
  EXPECT_VALID(result);
  ASSERT(Dart_IsInteger(result));
  int64_t r;
  result = Dart_IntegerToInt64(result, &r);
  EXPECT_VALID(result);
  EXPECT_EQ(4, r);

  // Set source of function 'c' from class A, changing its signature.
  service_msg = EvalF(
    lib,
    "[0, port, ['classes', '%" Pd "', 'functions', 'c', 'set_source'],"
    "['source'], ['c() { return 99; }']]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("Success", handler.msg());

  // Run function 'c' see that it is executing replaced code.
  result = Dart_Invoke(lib, NewString("runC"), 0, NULL);
  EXPECT_VALID(result);
  ASSERT(Dart_IsInteger(result));
  result = Dart_IntegerToInt64(result, &r);
  EXPECT_VALID(result);
  EXPECT_EQ(99, r);
}


TEST_CASE(Service_Types) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "class A<T> { }\n"
      "\n"
      "main() {\n"
      "  new A<A<bool>>();\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);
  const Class& class_a = Class::Handle(GetClass(vmlib, "A"));
  EXPECT(!class_a.IsNull());
  intptr_t cid = class_a.id();

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Request the class A over the service.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "'], [], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Class\"", handler.msg());
  EXPECT_SUBSTRING("\"name\":\"A\"", handler.msg());
  ExpectSubstringF(handler.msg(),
                   "\"id\":\"classes\\/%" Pd "\"", cid);

  // Request canonical type 0 from class A.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "', 'types', '0'],"
                              "[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Type\"", handler.msg());
  EXPECT_SUBSTRING("\"name\":\"A<bool>\"", handler.msg());
  ExpectSubstringF(handler.msg(),
                   "\"id\":\"classes\\/%" Pd "\\/types\\/0\"", cid);

  // Request canonical type 1 from class A.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "', 'types', '1'],"
                              "[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Type\"", handler.msg());
  EXPECT_SUBSTRING("\"name\":\"A<A<bool>>\"", handler.msg());
  ExpectSubstringF(handler.msg(),
                   "\"id\":\"classes\\/%" Pd "\\/types\\/1\"", cid);

  // Request for non-existent canonical type from class A.
  service_msg = EvalF(lib, "[0, port, ['classes', '%" Pd "', 'types', '42'],"
                      "[], []]", cid);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  ExpectSubstringF(handler.msg(),
    "{\"type\":\"Error\",\"id\":\"\","
    "\"message\":\"Canonical type 42 not found\""
    ",\"request\":"
    "{\"arguments\":[\"classes\",\"%" Pd "\",\"types\",\"42\"],"
    "\"option_keys\":[],\"option_values\":[]}}", cid);

  // Request canonical type arguments. Expect <A<bool>> to be listed.
  service_msg = EvalF(lib, "[0, port, ['typearguments'],"
                      "[], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"TypeArgumentsList\"", handler.msg());
  ExpectSubstringF(handler.msg(), "\"name\":\"<A<bool>>\",");

  // Request canonical type arguments with instantiations.
  service_msg = EvalF(lib,
                      "[0, port, ['typearguments', 'withinstantiations'],"
                      "[], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"TypeArgumentsList\"", handler.msg());
}


TEST_CASE(Service_Code) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "class A {\n"
      "  var a;\n"
      "  dynamic b() {}\n"
      "  dynamic c() {\n"
      "    var d = () { b(); };\n"
      "    return d;\n"
      "  }\n"
      "}\n"
      "main() {\n"
      "  var z = new A();\n"
      "  var x = z.c();\n"
      "  x();\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);
  const Class& class_a = Class::Handle(GetClass(vmlib, "A"));
  EXPECT(!class_a.IsNull());
  const Function& function_c = Function::Handle(GetFunction(class_a, "c"));
  EXPECT(!function_c.IsNull());
  const Code& code_c = Code::Handle(function_c.CurrentCode());
  EXPECT(!code_c.IsNull());
  // Use the entry of the code object as it's reference.
  uword entry = code_c.EntryPoint();
  int64_t compile_timestamp = code_c.compile_timestamp();
  EXPECT_GT(code_c.Size(), 16);
  uword last = entry + code_c.Size();

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Request an invalid code object.
  service_msg = Eval(lib, "[0, port, ['code', '0'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ(
    "{\"type\":\"Error\",\"id\":\"\",\"message\":\"Malformed code id: 0\","
    "\"request\":{\"arguments\":[\"code\",\"0\"],"
    "\"option_keys\":[],\"option_values\":[]}}", handler.msg());

  // The following test checks that a code object can be found only
  // at compile_timestamp()-code.EntryPoint().
  service_msg = EvalF(lib, "[0, port, ['code', '%" Px64"-%" Px "'], [], []]",
                      compile_timestamp,
                      entry);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  {
    // Only perform a partial match.
    const intptr_t kBufferSize = 512;
    char buffer[kBufferSize];
    OS::SNPrint(buffer, kBufferSize-1,
                "{\"type\":\"Code\",\"id\":\"code\\/%" Px64 "-%" Px "\",",
                compile_timestamp,
                entry);
    EXPECT_SUBSTRING(buffer, handler.msg());
  }

  // Request code object at compile_timestamp-code.EntryPoint() + 16
  // Expect this to fail because the address is not the entry point.
  uintptr_t address = entry + 16;
  service_msg = EvalF(lib, "[0, port, ['code', '%" Px64"-%" Px "'], [], []]",
                      compile_timestamp,
                      address);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  {
    // Only perform a partial match.
    const intptr_t kBufferSize = 512;
    char buffer[kBufferSize];
    OS::SNPrint(buffer, kBufferSize-1,
                "Could not find code with id: %" Px64 "-%" Px "",
                compile_timestamp,
                address);
    EXPECT_SUBSTRING(buffer, handler.msg());
  }

  // Request code object at (compile_timestamp - 1)-code.EntryPoint()
  // Expect this to fail because the timestamp is wrong.
  address = entry;
  service_msg = EvalF(lib, "[0, port, ['code', '%" Px64"-%" Px "'], [], []]",
                      compile_timestamp - 1,
                      address);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  {
    // Only perform a partial match.
    const intptr_t kBufferSize = 512;
    char buffer[kBufferSize];
    OS::SNPrint(buffer, kBufferSize-1,
                "Could not find code with id: %" Px64 "-%" Px "",
                compile_timestamp - 1,
                address);
    EXPECT_SUBSTRING(buffer, handler.msg());
  }

  // Request native code at address. Expect the null code object back.
  address = last;
  service_msg = EvalF(lib, "[0, port, ['code', 'native-%" Px "'], [], []]",
                      address);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("{\"type\":\"null\",\"id\":\"objects\\/null\","
                   "\"valueAsString\":\"null\"",
                   handler.msg());

  // Request malformed native code.
  service_msg = EvalF(lib, "[0, port, ['code', 'native%" Px "'], [], []]",
                      address);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"message\":\"Malformed code id:", handler.msg());
}


TEST_CASE(Service_TokenStream) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "main() {\n"
      "}";

  Isolate* isolate = Isolate::Current();

  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());

  const String& script_name = String::Handle(String::New("test-lib"));
  EXPECT(!script_name.IsNull());
  const Script& script = Script::Handle(vmlib.LookupScript(script_name));
  EXPECT(!script.IsNull());

  const TokenStream& token_stream = TokenStream::Handle(script.tokens());
  EXPECT(!token_stream.IsNull());
  ObjectIdRing* ring = isolate->object_id_ring();
  intptr_t id = ring->GetIdForObject(token_stream.raw());

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Fetch object.
  service_msg = EvalF(lib, "[0, port, ['objects', '%" Pd "'], [], []]", id);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();

  // Check type.
  EXPECT_SUBSTRING("\"type\":\"Object\"", handler.msg());
  EXPECT_SUBSTRING("\"_vmType\":\"TokenStream\"", handler.msg());
  // Check for members array.
  EXPECT_SUBSTRING("\"members\":[", handler.msg());
}


TEST_CASE(Service_PcDescriptors) {
  const char* kScript =
    "var port;\n"  // Set to our mock port by C++.
    "\n"
    "class A {\n"
    "  var a;\n"
    "  dynamic b() {}\n"
    "  dynamic c() {\n"
    "    var d = () { b(); };\n"
    "    return d;\n"
    "  }\n"
    "}\n"
    "main() {\n"
    "  var z = new A();\n"
    "  var x = z.c();\n"
    "  x();\n"
    "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);
  const Class& class_a = Class::Handle(GetClass(vmlib, "A"));
  EXPECT(!class_a.IsNull());
  const Function& function_c = Function::Handle(GetFunction(class_a, "c"));
  EXPECT(!function_c.IsNull());
  const Code& code_c = Code::Handle(function_c.CurrentCode());
  EXPECT(!code_c.IsNull());

  const PcDescriptors& descriptors =
      PcDescriptors::Handle(code_c.pc_descriptors());
  EXPECT(!descriptors.IsNull());
  ObjectIdRing* ring = isolate->object_id_ring();
  intptr_t id = ring->GetIdForObject(descriptors.raw());

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Fetch object.
  service_msg = EvalF(lib, "[0, port, ['objects', '%" Pd "'], [], []]", id);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  // Check type.
  EXPECT_SUBSTRING("\"type\":\"Object\"", handler.msg());
  EXPECT_SUBSTRING("\"_vmType\":\"PcDescriptors\"", handler.msg());
  // Check for members array.
  EXPECT_SUBSTRING("\"members\":[", handler.msg());
}


TEST_CASE(Service_LocalVarDescriptors) {
  const char* kScript =
    "var port;\n"  // Set to our mock port by C++.
    "\n"
    "class A {\n"
    "  var a;\n"
    "  dynamic b() {}\n"
    "  dynamic c() {\n"
    "    var d = () { b(); };\n"
    "    return d;\n"
    "  }\n"
    "}\n"
    "main() {\n"
    "  var z = new A();\n"
    "  var x = z.c();\n"
    "  x();\n"
    "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);
  const Class& class_a = Class::Handle(GetClass(vmlib, "A"));
  EXPECT(!class_a.IsNull());
  const Function& function_c = Function::Handle(GetFunction(class_a, "c"));
  EXPECT(!function_c.IsNull());
  const Code& code_c = Code::Handle(function_c.CurrentCode());
  EXPECT(!code_c.IsNull());

  const LocalVarDescriptors& descriptors =
      LocalVarDescriptors::Handle(code_c.var_descriptors());
  // Generate an ID for this object.
  ObjectIdRing* ring = isolate->object_id_ring();
  intptr_t id = ring->GetIdForObject(descriptors.raw());

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();

  // Fetch object.
  service_msg = EvalF(lib, "[0, port, ['objects', '%" Pd "'], [], []]", id);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  // Check type.
  EXPECT_SUBSTRING("\"type\":\"Object\"", handler.msg());
  EXPECT_SUBSTRING("\"_vmType\":\"LocalVarDescriptors\"", handler.msg());
  // Check for members array.
  EXPECT_SUBSTRING("\"members\":[", handler.msg());
}


TEST_CASE(Service_VM) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "main() {\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, "[0, port, ['vm'], [], []]");

  Service::HandleRootMessage(service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"VM\",\"id\":\"vm\"", handler.msg());
  EXPECT_SUBSTRING("\"targetCPU\"", handler.msg());
  EXPECT_SUBSTRING("\"hostCPU\"", handler.msg());
  EXPECT_SUBSTRING("\"version\"", handler.msg());
  EXPECT_SUBSTRING("\"uptime\"", handler.msg());
  EXPECT_SUBSTRING("\"isolates\"", handler.msg());
}


TEST_CASE(Service_Flags) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "main() {\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, "[0, port, ['flags'], [], []]");

  // Make sure we can get the FlagList.
  Service::HandleRootMessage(service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"FlagList\",\"id\":\"flags\"", handler.msg());
  EXPECT_SUBSTRING(
      "\"name\":\"service_testing_flag\",\"comment\":\"Comment\","
      "\"flagType\":\"bool\",\"valueAsString\":\"false\"",
      handler.msg());

  // Modify a flag through the vm service.
  service_msg = Eval(lib,
                     "[0, port, ['flags', 'set'], "
                     "['name', 'value'], ['service_testing_flag', 'true']]");
  Service::HandleRootMessage(service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("Success", handler.msg());

  // Make sure that the flag changed.
  service_msg = Eval(lib, "[0, port, ['flags'], [], []]");
  Service::HandleRootMessage(service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING(
      "\"name\":\"service_testing_flag\",\"comment\":\"Comment\","
      "\"flagType\":\"bool\",\"valueAsString\":\"true\"",
      handler.msg());
}


TEST_CASE(Service_Scripts) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "main() {\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();
  char buf[1024];
  OS::SNPrint(buf, sizeof(buf),
      "[0, port, ['libraries', '%" Pd "', 'scripts', 'test-lib'], [], []]",
      vmlib.index());

  service_msg = Eval(lib, buf);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  OS::SNPrint(buf, sizeof(buf),
      "{\"type\":\"Script\","
      "\"id\":\"libraries\\/%" Pd "\\/scripts\\/test-lib\","
      "\"name\":\"test-lib\","
      "\"kind\":\"script\","
      "\"owningLibrary\":{\"type\":\"@Library\","
      "\"id\":\"libraries\\/%" Pd "\",\"name\":\"\","
      "\"url\":\"test-lib\"},"
      "\"source\":\"var port;\\n\\nmain() {\\n}\","
      "\"tokenPosTable\":[[1,0,1,1,5,2,9],[3,5,1,6,5,7,6,8,8],[4,10,1]]}",
      vmlib.index(), vmlib.index());
  EXPECT_STREQ(buf, handler.msg());
}


// TODO(zra): Remove when tests are ready to enable.
#if !defined(TARGET_ARCH_ARM64)

TEST_CASE(Service_Coverage) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "var x = 7;\n"
      "main() {\n"
      "  x = x * x;\n"
      "  x = x / 13;\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, "[0, port, ['coverage'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();

  char buf[1024];
  OS::SNPrint(buf, sizeof(buf),
              "{\"source\":\"test-lib\",\"script\":{\"type\":\"@Script\","
              "\"id\":\"libraries\\/%" Pd "\\/scripts\\/test-lib\","
              "\"name\":\"test-lib\","
              "\"kind\":\"script\"},\"hits\":"
              "[5,1,6,1]}",
              vmlib.index());
  EXPECT_SUBSTRING(buf, handler.msg());
}


TEST_CASE(Service_LibrariesScriptsCoverage) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "var x = 7;\n"
      "main() {\n"
      "  x = x * x;\n"
      "  x = x / 13;\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();
  char buf[1024];
  OS::SNPrint(buf, sizeof(buf),
      "[0, port, ['libraries', '%" Pd  "', 'scripts', 'test-lib', 'coverage'], "
      "[], []]",
      vmlib.index());

  service_msg = Eval(lib, buf);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  OS::SNPrint(buf, sizeof(buf),
      "{\"type\":\"CodeCoverage\",\"id\":\"coverage\",\"coverage\":["
      "{\"source\":\"test-lib\",\"script\":{\"type\":\"@Script\","
      "\"id\":\"libraries\\/%" Pd "\\/scripts\\/test-lib\","
      "\"name\":\"test-lib\","
      "\"kind\":\"script\"},\"hits\":[5,1,6,1]}]}", vmlib.index());
  EXPECT_STREQ(buf, handler.msg());
}


TEST_CASE(Service_LibrariesCoverage) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "var x = 7;\n"
      "main() {\n"
      "  x = x * x;\n"
      "  x = x / 13;\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  char buf[1024];
  OS::SNPrint(buf, sizeof(buf),
              "[0, port, ['libraries', '%" Pd "', 'coverage'], [], []]",
              vmlib.index());

  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, buf);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  OS::SNPrint(buf, sizeof(buf),
              "{\"type\":\"CodeCoverage\",\"id\":\"coverage\",\"coverage\":["
              "{\"source\":\"test-lib\",\"script\":{\"type\":\"@Script\","
              "\"id\":\"libraries\\/%" Pd "\\/scripts\\/test-lib\","
              "\"name\":\"test-lib\","
              "\"kind\":\"script\"},\"hits\":[5,1,6,1]}]}",
              vmlib.index());
  EXPECT_STREQ(buf, handler.msg());
}


TEST_CASE(Service_ClassesCoverage) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "class Foo {\n"
      "  var x;\n"
      "  Foo(this.x);\n"
      "  bar() {\n"
      "    x = x * x;\n"
      "    x = x / 13;\n"
      "  }\n"
      "}\n"
      "main() {\n"
      "  var foo = new Foo(7);\n"
      "  foo.bar();\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  // Look up the service id of Foo.
  const Class& cls = Class::Handle(
      vmlib.LookupClass(String::Handle(String::New("Foo"))));
  ASSERT(!cls.IsNull());
  ClassTable* table = isolate->class_table();
  intptr_t i;
  for (i = 1; i < table->NumCids(); i++) {
    if (table->HasValidClassAt(i) && table->At(i) == cls.raw()) {
      break;
    }
  }
  ASSERT(i != table->NumCids());
  char buf[1024];
  OS::SNPrint(buf, sizeof(buf),
              "[0, port, ['classes', '%" Pd "', 'coverage'], [], []]", i);

  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, buf);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  OS::SNPrint(buf, sizeof(buf),
              "{\"type\":\"CodeCoverage\",\"id\":\"coverage\",\"coverage\":["
              "{\"source\":\"test-lib\",\"script\":{\"type\":\"@Script\","
              "\"id\":\"libraries\\/%" Pd "\\/scripts\\/test-lib\","
              "\"name\":\"test-lib\","
              "\"kind\":\"script\"},\"hits\":[5,1,7,4,8,3]}]}",
              vmlib.index());
  EXPECT_STREQ(buf, handler.msg());
}


TEST_CASE(Service_ClassesFunctionsCoverage) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "class Foo {\n"
      "  var x;\n"
      "  Foo(this.x);\n"
      "  bar() {\n"
      "    x = x * x;\n"
      "    x = x / 13;\n"
      "  }\n"
      "  badum(var a) => 4 + a;\n"
      "}\n"
      "main() {\n"
      "  var foo = new Foo(7);\n"
      "  foo.bar();\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Library& vmlib = Library::Handle();
  vmlib ^= Api::UnwrapHandle(lib);
  EXPECT(!vmlib.IsNull());
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  // Look up the service id of Foo.
  const Class& cls = Class::Handle(
      vmlib.LookupClass(String::Handle(String::New("Foo"))));
  ASSERT(!cls.IsNull());
  ClassTable* table = isolate->class_table();
  intptr_t i;
  for (i = 1; i < table->NumCids(); i++) {
    if (table->HasValidClassAt(i) && table->At(i) == cls.raw()) {
      break;
    }
  }
  ASSERT(i != table->NumCids());

  // Look up the service if of the function Foo.bar.
  const Function& func = Function::Handle(
      cls.LookupFunction(String::Handle(String::New("bar"))));
  ASSERT(!func.IsNull());

  char buf[1024];
  OS::SNPrint(buf, sizeof(buf),
              "[0, port, ['classes', '%" Pd "', 'functions',"
              "'bar', 'coverage'], [], []]", i);

  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, buf);
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  OS::SNPrint(buf, sizeof(buf),
      "{\"type\":\"CodeCoverage\",\"id\":\"coverage\",\"coverage\":["
      "{\"source\":\"test-lib\",\"script\":{\"type\":\"@Script\","
      "\"id\":\"libraries\\/%" Pd "\\/scripts\\/test-lib\","
      "\"name\":\"test-lib\","
      "\"kind\":\"script\"},\"hits\":[7,4,8,3]}]}", vmlib.index());
  EXPECT_STREQ(buf, handler.msg());
}

#endif


TEST_CASE(Service_AllocationProfile) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "var x = 7;\n"
      "main() {\n"
      "  x = x * x;\n"
      "  x = x / 13;\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, "[0, port, ['allocationprofile'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"AllocationProfile\"", handler.msg());

  // Too long.
  service_msg = Eval(lib, "[0, port, ['allocationprofile', 'foo'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Error\"", handler.msg());

  // Bad gc option.
  service_msg = Eval(lib,
                     "[0, port, ['allocationprofile'], ['gc'], ['cat']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Error\"", handler.msg());

  // Bad reset option.
  service_msg = Eval(lib,
                     "[0, port, ['allocationprofile'], ['reset'], ['ff']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"Error\"", handler.msg());

  // Good reset.
  service_msg =
      Eval(lib, "[0, port, ['allocationprofile'], ['reset'], ['true']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"AllocationProfile\"", handler.msg());

  // Good GC.
  service_msg =
      Eval(lib, "[0, port, ['allocationprofile'], ['gc'], ['full']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"AllocationProfile\"", handler.msg());

  // Good GC and reset.
  service_msg = Eval(lib,
      "[0, port, ['allocationprofile'], ['gc', 'reset'], ['full', 'true']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"AllocationProfile\"", handler.msg());
}


TEST_CASE(Service_HeapMap) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "main() {\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, "[0, port, ['heapmap'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_SUBSTRING("\"type\":\"HeapMap\"", handler.msg());
  EXPECT_SUBSTRING("\"pages\":[", handler.msg());
}


TEST_CASE(Service_Address) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "main() {\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  const String& str = String::Handle(String::New("foobar", Heap::kOld));
  Array& service_msg = Array::Handle();
  // Note: If we ever introduce old space compaction, this test might fail.
  uword start_addr = RawObject::ToAddr(str.raw());
  // Expect to find 'str', also from internal addresses.
  for (int offset = 0; offset < kObjectAlignment; ++offset) {
    uword addr = start_addr + offset;
    char buf[1024];
    bool ref = offset % 2 == 0;
    OS::SNPrint(buf, sizeof(buf),
                ref ? "[0, port, ['address', '%" Px "'], ['ref'], ['true']]" :
                      "[0, port, ['address', '%" Px "', ], [], []]",
                addr);
    service_msg = Eval(lib, buf);
    Service::HandleIsolateMessage(isolate, service_msg);
    handler.HandleNextMessage();
    EXPECT_SUBSTRING(ref ? "\"type\":\"@String\"" :
                           "\"type\":\"String\"",
                     handler.msg());
    EXPECT_SUBSTRING("foobar", handler.msg());
  }
  // Expect null when no object is found.
  service_msg = Eval(lib, "[0, port, ['address', '7'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  // TODO(turnidge): Should this be a ServiceException instead?
  EXPECT_SUBSTRING("{\"type\":\"null\",\"id\":\"objects\\/null\","
                   "\"valueAsString\":\"null\"",
               handler.msg());
}


static const char* alpha_callback(
    const char* name,
    const char** arguments,
    intptr_t num_arguments,
    const char** option_keys,
    const char** option_values,
    intptr_t num_options,
    void* user_data) {
  return strdup("alpha");
}


static const char* beta_callback(
    const char* name,
    const char** arguments,
    intptr_t num_arguments,
    const char** option_keys,
    const char** option_values,
    intptr_t num_options,
    void* user_data) {
  return strdup("beta");
}


TEST_CASE(Service_EmbedderRootHandler) {
  const char* kScript =
    "var port;\n"  // Set to our mock port by C++.
    "\n"
    "var x = 7;\n"
    "main() {\n"
    "  x = x * x;\n"
    "  x = x / 13;\n"
    "}";

  Dart_RegisterRootServiceRequestCallback("alpha", alpha_callback, NULL);
  Dart_RegisterRootServiceRequestCallback("beta", beta_callback, NULL);

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));


  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, "[0, port, ['alpha'], [], []]");
  Service::HandleRootMessage(service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ("alpha", handler.msg());
  service_msg = Eval(lib, "[0, port, ['beta'], [], []]");
  Service::HandleRootMessage(service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ("beta", handler.msg());
}

TEST_CASE(Service_EmbedderIsolateHandler) {
  const char* kScript =
    "var port;\n"  // Set to our mock port by C++.
    "\n"
    "var x = 7;\n"
    "main() {\n"
    "  x = x * x;\n"
    "  x = x / 13;\n"
    "}";

  Dart_RegisterIsolateServiceRequestCallback("alpha", alpha_callback, NULL);
  Dart_RegisterIsolateServiceRequestCallback("beta", beta_callback, NULL);

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, "[0, port, ['alpha'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ("alpha", handler.msg());
  service_msg = Eval(lib, "[0, port, ['beta'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  EXPECT_STREQ("beta", handler.msg());
}


// TODO(zra): Remove when tests are ready to enable.
#if !defined(TARGET_ARCH_ARM64)

TEST_CASE(Service_Profile) {
  const char* kScript =
      "var port;\n"  // Set to our mock port by C++.
      "\n"
      "var x = 7;\n"
      "main() {\n"
      "  x = x * x;\n"
      "  x = x / 13;\n"
      "}";

  Isolate* isolate = Isolate::Current();
  Dart_Handle lib = TestCase::LoadTestScript(kScript, NULL);
  EXPECT_VALID(lib);
  Dart_Handle result = Dart_Invoke(lib, NewString("main"), 0, NULL);
  EXPECT_VALID(result);

  // Build a mock message handler and wrap it in a dart port.
  ServiceTestMessageHandler handler;
  Dart_Port port_id = PortMap::CreatePort(&handler);
  Dart_Handle port = Api::NewHandle(isolate, SendPort::New(port_id));
  EXPECT_VALID(port);
  EXPECT_VALID(Dart_SetField(lib, NewString("port"), port));

  Array& service_msg = Array::Handle();
  service_msg = Eval(lib, "[0, port, ['profile'], [], []]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  // Expect profile
  EXPECT_SUBSTRING("\"type\":\"Profile\"", handler.msg());

  service_msg = Eval(lib, "[0, port, ['profile'], ['tags'], ['hide']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  // Expect profile
  EXPECT_SUBSTRING("\"type\":\"Profile\"", handler.msg());

  service_msg = Eval(lib, "[0, port, ['profile'], ['tags'], ['hidden']]");
  Service::HandleIsolateMessage(isolate, service_msg);
  handler.HandleNextMessage();
  // Expect error.
  EXPECT_SUBSTRING("\"type\":\"Error\"", handler.msg());
}

#endif  // !defined(TARGET_ARCH_ARM64)

}  // namespace dart
