Index: Source/bindings/dart/DartService.cpp |
diff --git a/Source/bindings/dart/DartService.cpp b/Source/bindings/dart/DartService.cpp |
index 62ecfe3686d6fc9ef35e04460ab81b4fc6daf8ab..cab40176874767b1572f0dd5c1a959ff9df67df6 100644 |
--- a/Source/bindings/dart/DartService.cpp |
+++ b/Source/bindings/dart/DartService.cpp |
@@ -9,195 +9,50 @@ |
#include "DartApplicationLoader.h" |
#include "DartController.h" |
#include "DartDocument.h" |
-#include "DartServiceInternal.h" |
#include "DartUtilities.h" |
#include "DartWindow.h" |
-// These must be kept in sync with vmservice/constants.dart |
-// TODO(johnmccutchan): Put these constants in one place. |
-#define VM_SERVICE_ISOLATE_STARTUP_MESSAGE_ID 1 |
-#define VM_SERVICE_ISOLATE_SHUTDOWN_MESSAGE_ID 2 |
- |
-// The following Resources class is used in combination with a generated |
-// source file that expects underscores in names. The NOLINT tags are |
-// used to suppress the errors. |
-// TODO(johnmccutchan): Move VM service source into runtime and out of bin. |
-namespace dart { |
-namespace bin { |
-class Resources { |
-public: |
- static const int kNoSuchInstance = -1; |
- |
- static int ResourceLookup(const char* path, const char** resource) |
- { |
- for (int i = 0; i < get_resource_count(); i++) { |
- resource_map_entry* entry = get_resource(i); |
- if (!strcmp(path, entry->path_)) { |
- *resource = entry->resource_; |
- ASSERT(entry->length_ > 0); |
- return entry->length_; |
- } |
- } |
- return kNoSuchInstance; |
- } |
- |
- static intptr_t get_resource_count() // NOLINT. |
- { |
- return builtin_resources_count_; |
- } |
- |
- static const char* get_resource_path(intptr_t i) // NOLINT. |
- { |
- return get_resource(i)->path_; |
- } |
- |
-private: |
- struct resource_map_entry { // NOLINT. |
- const char* path_; // NOLINT. |
- const char* resource_; // NOLINT. |
- intptr_t length_; // NOLINT. |
- }; |
- |
- // These fields are generated by resources_gen.cc. |
- static resource_map_entry builtin_resources_[]; // NOLINT. |
- static const intptr_t builtin_resources_count_; // NOLINT. |
- |
- static resource_map_entry* get_resource(int i) // NOLINT. |
- { |
- ASSERT(i >= 0 && i < builtin_resources_count_); |
- return &builtin_resources_[i]; |
- } |
- |
- DISALLOW_IMPLICIT_CONSTRUCTORS(Resources); |
-}; |
- |
-} |
-} |
namespace WebCore { |
-#define SHUTDOWN_ON_ERROR(handle) \ |
- if (Dart_IsError(handle)) { \ |
- m_errorMsg = strdup(Dart_GetError(handle)); \ |
- goto error; \ |
+#define SHUTDOWN_ON_ERROR(handle) \ |
+ if (Dart_IsError(handle)) { \ |
+ m_errorMsg = strdup(Dart_GetError(handle)); \ |
+ Dart_ExitScope(); \ |
+ Dart_ShutdownIsolate(); \ |
+ return false; \ |
} |
-static const char* kScriptUri = "vmservice:"; |
-#define kLibraryResourceNamePrefix "/vmservice" |
-static const char* kVMServiceDartiumLibraryScriptResourceName = |
- kLibraryResourceNamePrefix "/vmservice_dartium.dart"; |
-static const char* kVMServiceLibraryName = |
- kLibraryResourceNamePrefix "/vmservice.dart"; |
- |
- |
-Dart_Isolate DartService::m_isolate = 0; |
-Dart_Port DartService::m_port = ILLEGAL_PORT; |
-Dart_Port DartService::m_requestPort = ILLEGAL_PORT; |
const char* DartService::m_errorMsg = 0; |
- |
+Dart_Isolate DartService::m_isolate = 0; |
bool DartService::Start(Document* document) |
{ |
if (m_isolate) { |
- // Already running. |
- return true; |
- } |
- { |
- char* error = 0; |
- |
- m_isolate = DartController::createIsolate(kScriptUri, "main", document, true, &error); |
- if (!m_isolate) { |
- m_errorMsg = error; |
- return false; |
- } |
- |
- Dart_EnterScope(); |
- // Set up the library tag handler for this isolate. |
- Dart_Handle result = Dart_SetLibraryTagHandler(LibraryTagHandler); |
- SHUTDOWN_ON_ERROR(result); |
- |
- { |
- // Load source into service isolate. |
- Dart_Handle library = |
- LoadScript(kVMServiceDartiumLibraryScriptResourceName); |
- SHUTDOWN_ON_ERROR(library); |
- result = Dart_SetNativeResolver(library, DartService::NativeResolver); |
- SHUTDOWN_ON_ERROR(result); |
- } |
- // Make the isolate runnable so that it is ready to handle messages. |
- Dart_ExitScope(); |
- Dart_ExitIsolate(); |
- |
- bool retval = Dart_IsolateMakeRunnable(m_isolate); |
- if (!retval) { |
- Dart_EnterIsolate(m_isolate); |
- Dart_ShutdownIsolate(); |
- m_errorMsg = "Invalid isolate state - Unable to make it runnable."; |
- return false; |
- } |
- |
- Dart_EnterIsolate(m_isolate); |
- Dart_EnterScope(); |
- |
- // Invoke main. |
- Dart_Handle library = Dart_RootLibrary(); |
- Dart_Handle entryFunctioName = Dart_NewStringFromCString("main"); |
- SHUTDOWN_ON_ERROR(entryFunctioName); |
- result = Dart_Invoke(library, entryFunctioName, 0, 0); |
- SHUTDOWN_ON_ERROR(result); |
- |
- // Retrieve the ReceivePort that the service is waiting on. The _receivePort |
- // variable is setup in the call to main. |
- Dart_Handle portFieldName = Dart_NewStringFromCString("_receivePort"); |
- SHUTDOWN_ON_ERROR(portFieldName); |
- Dart_Handle receivePort = Dart_GetField(library, portFieldName); |
- SHUTDOWN_ON_ERROR(receivePort); |
- |
- m_port = DartServiceInternal::GetPortIdFromPort(receivePort); |
- if (m_port == ILLEGAL_PORT) { |
- Dart_ExitScope(); |
- Dart_ShutdownIsolate(); |
- m_errorMsg = "Invalid isolate state - Unable to get receivePort"; |
- return false; |
- } |
- |
- { |
- // Retrieve the ReceivePort that the service is waiting on. The _receivePort |
- // variable is setup in the call to main. |
- Dart_Handle portFieldName = Dart_NewStringFromCString("_requestPort"); |
- SHUTDOWN_ON_ERROR(portFieldName); |
- Dart_Handle receivePort = Dart_GetField(library, portFieldName); |
- SHUTDOWN_ON_ERROR(receivePort); |
- m_requestPort = DartServiceInternal::GetPortIdFromPort(receivePort); |
- ASSERT(m_requestPort != ILLEGAL_PORT); |
- } |
- |
- Dart_ExitScope(); |
- Dart_ExitIsolate(); |
+ // Already started. |
return true; |
} |
-error: |
- Dart_ExitScope(); |
- Dart_ShutdownIsolate(); |
- m_isolate = 0; |
- m_port = ILLEGAL_PORT; |
- m_requestPort = ILLEGAL_PORT; |
- return false; |
-} |
- |
- |
-bool DartService::Stop() |
-{ |
- if (!m_isolate) { |
- // Already shutdown. |
- return true; |
+ ASSERT(!Dart_CurrentIsolate()); |
+ Dart_Isolate isolate = Dart_GetServiceIsolate(document); |
+ if (!isolate) { |
+ m_errorMsg = "Could not get service isolate from VM."; |
+ return false; |
} |
- m_port = ILLEGAL_PORT; |
- m_requestPort = ILLEGAL_PORT; |
- Dart_Isolate isolate = m_isolate; |
- m_isolate = 0; |
Dart_EnterIsolate(isolate); |
- DartController::shutdownIsolate(isolate); |
+ Dart_EnterScope(); |
+ Dart_Handle result; |
+ Dart_Handle library = LoadScript(); |
+ // Expect a library. |
+ ASSERT(Dart_IsLibrary(library)); |
+ SHUTDOWN_ON_ERROR(library); |
+ library = Dart_RootLibrary(); |
+ result = Dart_SetNativeResolver(library, NativeResolver); |
+ SHUTDOWN_ON_ERROR(result); |
+ result = Dart_Invoke(library, Dart_NewStringFromCString("main"), 0, 0); |
+ SHUTDOWN_ON_ERROR(result); |
+ Dart_ExitScope(); |
+ Dart_ExitIsolate(); |
+ m_isolate = isolate; |
return true; |
} |
@@ -208,65 +63,6 @@ const char* DartService::GetErrorMessage() |
} |
-Dart_Port DartService::port() |
-{ |
- return m_port; |
-} |
- |
- |
-bool DartService::IsRunning() |
-{ |
- return m_port != ILLEGAL_PORT; |
-} |
- |
- |
-static Dart_Handle MakeServiceControlMessage(Dart_Port portId, intptr_t code, Dart_Handle name) |
-{ |
- Dart_Handle result; |
- UNUSED_PARAM(result); |
- Dart_Handle list = Dart_NewList(4); |
- ASSERT(!Dart_IsError(list)); |
- Dart_Handle codeHandle = Dart_NewInteger(code); |
- ASSERT(!Dart_IsError(codeHandle)); |
- result = Dart_ListSetAt(list, 0, codeHandle); |
- ASSERT(!Dart_IsError(result)); |
- Dart_Handle portIdHandle = Dart_NewInteger(portId); |
- ASSERT(!Dart_IsError(portIdHandle)); |
- result = Dart_ListSetAt(list, 1, portIdHandle); |
- ASSERT(!Dart_IsError(result)); |
- Dart_Handle sendPort = Dart_NewSendPort(portId); |
- ASSERT(!Dart_IsError(sendPort)); |
- result = Dart_ListSetAt(list, 2, sendPort); |
- ASSERT(!Dart_IsError(result)); |
- result = Dart_ListSetAt(list, 3, name); |
- ASSERT(!Dart_IsError(result)); |
- return list; |
-} |
- |
- |
-bool DartService::SendIsolateStartupMessage() |
-{ |
- if (!IsRunning()) { |
- return false; |
- } |
- Dart_Handle name = Dart_DebugName(); |
- ASSERT(!Dart_IsError(name)); |
- Dart_Handle list = MakeServiceControlMessage(Dart_GetMainPortId(), VM_SERVICE_ISOLATE_STARTUP_MESSAGE_ID, name); |
- ASSERT(!Dart_IsError(list)); |
- return Dart_Post(m_port, list); |
-} |
- |
- |
-bool DartService::SendIsolateShutdownMessage() |
-{ |
- if (!IsRunning()) |
- return false; |
- Dart_Handle list = MakeServiceControlMessage(Dart_GetMainPortId(), VM_SERVICE_ISOLATE_SHUTDOWN_MESSAGE_ID, Dart_Null()); |
- ASSERT(!Dart_IsError(list)); |
- return Dart_Post(m_port, list); |
-} |
- |
- |
DartServiceRequest::DartServiceRequest(const String& request) : m_request(request) |
{ |
} |
@@ -276,7 +72,6 @@ DartServiceRequest::~DartServiceRequest() |
} |
- |
// The format of the message is: |
// [request string, address of DartServiceRequest]. |
static Dart_Handle MakeServiceRequestMessage(DartServiceRequest* request) |
@@ -307,145 +102,87 @@ void DartService::MakeServiceRequest(DartServiceRequest* request) |
DartIsolateScope isolateScope(m_isolate); |
DartApiScope apiScope; |
Dart_Handle message = MakeServiceRequestMessage(request); |
- Dart_Post(m_requestPort, message); |
-} |
- |
- |
-Dart_Handle DartService::GetSource(const char* name) |
-{ |
- const char* vmserviceSource = 0; |
- int result = dart::bin::Resources::ResourceLookup(name, &vmserviceSource); |
- UNUSED_PARAM(result); |
- ASSERT(result != dart::bin::Resources::kNoSuchInstance); |
- return Dart_NewStringFromCString(vmserviceSource); |
-} |
- |
- |
-Dart_Handle DartService::LoadScript(const char* name) |
-{ |
- Dart_Handle url = Dart_NewStringFromCString(name); |
- Dart_Handle source = GetSource(name); |
- return Dart_LoadScript(url, source, 0, 0); |
-} |
- |
- |
-Dart_Handle DartService::LoadSource(Dart_Handle library, const char* name) |
-{ |
- Dart_Handle url = Dart_NewStringFromCString(name); |
- Dart_Handle source = GetSource(name); |
- return Dart_LoadSource(library, url, source); |
-} |
- |
- |
-Dart_Handle DartService::LoadSources(Dart_Handle library, const char* names[]) |
-{ |
- Dart_Handle result = Dart_Null(); |
- for (int i = 0; names[i]; i++) { |
- result = LoadSource(library, names[i]); |
- if (Dart_IsError(result)) |
- break; |
+ if (Dart_IsError(message)) { |
+ return; |
} |
- return result; |
-} |
- |
- |
-static bool IsVMServiceURL(const char* url) |
-{ |
- static const intptr_t kLibraryResourceNamePrefixLen = strlen(kLibraryResourceNamePrefix); |
- return !strncmp(kLibraryResourceNamePrefix, url, kLibraryResourceNamePrefixLen); |
-} |
- |
- |
-static bool IsVMServiceLibrary(const char* url) |
-{ |
- return !strcmp(kVMServiceLibraryName, url); |
-} |
- |
-static bool IsDartLibrary(const char* url) |
-{ |
- static const char* kDartPrefix = "dart:"; |
- static const intptr_t kDartPrefixLen = strlen(kDartPrefix); |
- return !strncmp(kDartPrefix, url, kDartPrefixLen); |
-} |
- |
-static Dart_Handle Canonicalize(const char* url) |
-{ |
- if (IsVMServiceURL(url)) { |
- // Already canonicalized. |
- return Dart_NewStringFromCString(url); |
+ Dart_Handle library = Dart_RootLibrary(); |
+ if (Dart_IsError(library)) { |
+ return; |
} |
- String path = String(kLibraryResourceNamePrefix) + String("/") + String(url); |
- return DartUtilities::stringToDartString(path); |
-} |
- |
- |
-Dart_Handle DartService::LibraryTagHandler(Dart_LibraryTag tag, Dart_Handle library, Dart_Handle url) |
-{ |
- if (!Dart_IsLibrary(library)) |
- return Dart_NewApiError("not a library"); |
- if (!Dart_IsString(url)) |
- return Dart_NewApiError("url is not a string"); |
- const char* urlString = 0; |
- Dart_Handle result = Dart_StringToCString(url, &urlString); |
- if (Dart_IsError(result)) |
- return result; |
- Dart_Handle libraryUrl = Dart_LibraryUrl(library); |
- const char* libraryUrlString = 0; |
- result = Dart_StringToCString(libraryUrl, &libraryUrlString); |
- if (Dart_IsError(result)) |
- return result; |
- if (IsDartLibrary(urlString)) |
- return DartApplicationLoader::libraryTagHandlerCallback(tag, library, url); |
- switch (tag) { |
- case Dart_kCanonicalizeUrl: |
- return Canonicalize(urlString); |
- break; |
- case Dart_kImportTag: { |
- Dart_Handle source = GetSource(urlString); |
- if (Dart_IsError(source)) |
- return source; |
- Dart_Handle lib = Dart_LoadLibrary(url, source); |
- if (Dart_IsError(lib)) |
- return lib; |
- if (IsVMServiceLibrary(urlString)) { |
- // Install native resolver for this library. |
- result = Dart_SetNativeResolver(lib, DartService::NativeResolver); |
- if (Dart_IsError(result)) |
- return result; |
- } |
- return lib; |
- } |
- break; |
- case Dart_kSourceTag: { |
- Dart_Handle source = GetSource(urlString); |
- if (Dart_IsError(source)) |
- return source; |
- return Dart_LoadSource(library, url, source); |
- } |
- break; |
- default: |
- DART_UNIMPLEMENTED(); |
- break; |
+ Dart_Handle requestPortFieldName = Dart_NewStringFromCString("requestPort"); |
+ Dart_Handle requestPort = Dart_GetField(library, requestPortFieldName); |
+ if (Dart_IsError(requestPort)) { |
+ return; |
} |
- ASSERT_NOT_REACHED(); |
- return result; |
+ Dart_PostMessage(requestPort, message); |
+} |
+ |
+ |
+Dart_Handle DartService::LoadScript() |
+{ |
+ const char* kScriptChars = "\n" |
+"library vmservice_dartium;\n" |
+"\n" |
+"import 'dart:isolate';\n" |
+"import 'dart:vmservice';\n" |
+"\n" |
+"\n" |
+"// The receive port that service request messages are delivered on.\n" |
+"SendPort requestPort;\n" |
+"\n" |
+"// The native method that is called to post the response back to DevTools.\n" |
+"void postResponse(String response, int cookie) native \"VMService_PostResponse\";\n" |
+"\n" |
+"/// Dartium Service receives messages through the requestPort and posts\n" |
+"/// responses via postResponse. It has a single persistent client.\n" |
+"class DartiumClient extends Client {\n" |
+" DartiumClient(port, service) : super(service) {\n" |
+" port.listen((message) {\n" |
+" if (message == null) {\n" |
+" return;\n" |
+" }\n" |
+" if (message is! List) {\n" |
+" return;\n" |
+" }\n" |
+" if (message.length != 2) {\n" |
+" return;\n" |
+" }\n" |
+" if (message[0] is! String) {\n" |
+" return;\n" |
+" }\n" |
+" var uri = Uri.parse(message[0]);\n" |
+" var cookie = message[1];\n" |
+" onMessage(cookie, new Message.fromUri(uri));\n" |
+" });\n" |
+" }\n" |
+"\n" |
+" void post(var seq, String response) {\n" |
+" postResponse(response, seq);\n" |
+" }\n" |
+"\n" |
+" dynamic toJson() {\n" |
+" var map = super.toJson();\n" |
+" map['type'] = 'DartiumClient';\n" |
+" }\n" |
+"}\n" |
+"\n" |
+"\n" |
+"main() {\n" |
+" // Get VMService.\n" |
+" var service = new VMService();\n" |
+" var receivePort = new ReceivePort();\n" |
+" requestPort = receivePort.sendPort;\n" |
+" new DartiumClient(receivePort, service);\n" |
+"}\n"; |
siva
2014/01/14 18:57:34
Maybe you could move this string out into a global
Cutch
2014/01/14 21:17:18
Done.
|
+ Dart_Handle url = Dart_NewStringFromCString("dart:vmservice_dartium"); |
+ ASSERT(!Dart_IsError(url)); |
+ Dart_Handle source = Dart_NewStringFromCString(kScriptChars); |
siva
2014/01/14 18:57:34
Ditto comment about using Dart_NewStringFromUTF8 i
Cutch
2014/01/14 21:17:18
Done.
|
+ ASSERT(!Dart_IsError(source)); |
+ Dart_Handle library = Dart_LoadScript(url, source, 0, 0); |
+ return library; |
} |
-void DartService::VmServiceShutdownCallback(void* callbackData) |
-{ |
- ASSERT(Dart_CurrentIsolate()); |
- DartApiScope apiScope; |
- SendIsolateShutdownMessage(); |
-} |
- |
-static void SendServiceMessage(Dart_NativeArguments args) |
-{ |
- Dart_Handle sp = Dart_GetNativeArgument(args, 0); |
- Dart_Handle message = Dart_GetNativeArgument(args, 1); |
- DartServiceInternal::PostOOB(sp, message); |
-} |
- |
static void PostResponse(Dart_NativeArguments args) |
{ |
Dart_Handle result; |
@@ -468,6 +205,7 @@ static void PostResponse(Dart_NativeArguments args) |
request->ResponseReady(responseString); |
} |
+ |
struct VmServiceNativeEntry { |
const char* name; |
int numArguments; |
@@ -476,7 +214,6 @@ struct VmServiceNativeEntry { |
static VmServiceNativeEntry VmServiceNativeEntries[] = { |
- {"VMService_SendServiceMessage", 2, SendServiceMessage}, |
{"VMService_PostResponse", 2, PostResponse} |
}; |