Index: sky/engine/bindings/builtin.cc |
diff --git a/sky/engine/bindings/builtin.cc b/sky/engine/bindings/builtin.cc |
index d57ea814eb31a2999c8c1c040eb616564af699c2..8cb25fc8f9d3b9425120e58426dbe1825a438e04 100644 |
--- a/sky/engine/bindings/builtin.cc |
+++ b/sky/engine/bindings/builtin.cc |
@@ -16,46 +16,129 @@ |
namespace blink { |
namespace { |
+const char* mojo_core_patch_resource_names_[] = { |
+ "/core/buffer_patch.dart", |
+ "/core/data_pipe_patch.dart", |
+ "/core/handle_patch.dart", |
+ "/core/handle_watcher_patch.dart", |
+ "/core/message_pipe_patch.dart", |
+ NULL, |
+}; |
+ |
struct LibraryDescriptor { |
const char* url; |
bool has_natives; |
Dart_NativeEntrySymbol native_symbol; |
Dart_NativeEntryResolver native_resolver; |
+ const char* patch_url; |
+ const char** patch_resources; |
}; |
const LibraryDescriptor kBuiltinLibraries[] = { |
- /* { url_, has_natives_, native_symbol_, native_resolver_ } */ |
- {"dart:sky_builtin", true, BuiltinNatives::NativeSymbol, BuiltinNatives::NativeLookup}, |
- {"dart:sky", true, skySnapshotSymbolizer, skySnapshotResolver}, |
- {"mojo:bindings", false, nullptr, nullptr}, |
- {"mojo:core", true, MojoNativeSymbol, MojoNativeLookup}, |
+ /* { url, has_natives, native_symbol, native_resolver, |
+ patch_url, patch_paths } */ |
+ {"dart:sky_builtin", |
+ true, |
+ BuiltinNatives::NativeSymbol, |
+ BuiltinNatives::NativeLookup, |
+ nullptr, |
+ nullptr}, |
+ {"dart:sky", |
+ true, |
+ skySnapshotSymbolizer, |
+ skySnapshotResolver, |
+ nullptr, |
+ nullptr}, |
+ {"mojo:bindings", false, nullptr, nullptr, nullptr, nullptr}, |
+ {"mojo:core", |
+ true, |
+ MojoNativeSymbol, |
+ MojoNativeLookup, |
+ "mojo:core-patch", |
+ mojo_core_patch_resource_names_}, |
}; |
} // namespace |
-void Builtin::SetNativeResolver(BuiltinLibraryId id) { |
+struct ResourcesEntry { |
+ const char* path_; |
+ const char* resource_; |
+ int length_; |
+}; |
+ |
+extern ResourcesEntry __dart_embedder_patch_resources_[]; |
+ |
+// Returns -1 if resource could not be found. |
+int Builtin::FindResource(const char* path, const uint8_t** resource) { |
+ ResourcesEntry* table = &__dart_embedder_patch_resources_[0]; |
+ for (int i = 0; table[i].path_ != NULL; i++) { |
+ const ResourcesEntry& entry = table[i]; |
+ if (strcmp(path, entry.path_) == 0) { |
+ *resource = reinterpret_cast<const uint8_t*>(entry.resource_); |
+ DCHECK(entry.length_ > 0); |
+ return entry.length_; |
+ } |
+ } |
+ *resource = NULL; |
+ return -1; |
+} |
+ |
+Dart_Handle Builtin::GetStringResource(const char* resource_name) { |
+ const uint8_t* resource_string; |
+ int resource_length = FindResource(resource_name, &resource_string); |
+ if (resource_length > 0) { |
+ return Dart_NewStringFromUTF8(resource_string, resource_length); |
+ } |
+ return Dart_Null(); |
+} |
+ |
+// Patch all the specified patch files in the array 'patch_resources' into the |
+// library specified in 'library'. |
+void Builtin::LoadPatchFiles(Dart_Handle library, |
+ const char* patch_uri, |
+ const char** patch_resources) { |
+ for (intptr_t j = 0; patch_resources[j] != NULL; j++) { |
+ Dart_Handle patch_src = GetStringResource(patch_resources[j]); |
+ if (Dart_IsNull(patch_src)) { |
+ LOG(ERROR) << "Could not load resource " << patch_resources[j]; |
+ return; |
+ } |
+ // Prepend the patch library URI to form a unique script URI for the patch. |
+ intptr_t len = snprintf(NULL, 0, "%s%s", patch_uri, patch_resources[j]); |
+ char* patch_filename = reinterpret_cast<char*>(malloc(len + 1)); |
+ snprintf(patch_filename, len + 1, "%s%s", patch_uri, patch_resources[j]); |
+ Dart_Handle patch_file_uri = Dart_NewStringFromCString(patch_filename); |
+ DART_CHECK_VALID(patch_file_uri); |
+ free(patch_filename); |
+ DART_CHECK_VALID(Dart_LibraryLoadPatch(library, patch_file_uri, patch_src)); |
+ } |
+} |
+ |
+Dart_Handle Builtin::GetLibrary(BuiltinLibraryId id) { |
static_assert(arraysize(kBuiltinLibraries) == kInvalidLibrary, |
"Unexpected number of builtin libraries"); |
DCHECK_GE(id, kBuiltinLibrary); |
DCHECK_LT(id, kInvalidLibrary); |
+ Dart_Handle library = DartBuiltin::LookupLibrary(kBuiltinLibraries[id].url); |
+ DART_CHECK_VALID(library); |
+ return library; |
+} |
+ |
+void Builtin::PrepareLibrary(BuiltinLibraryId id) { |
+ Dart_Handle library = GetLibrary(id); |
+ DCHECK(!Dart_IsError(library)); |
if (kBuiltinLibraries[id].has_natives) { |
- Dart_Handle library = DartBuiltin::LookupLibrary(kBuiltinLibraries[id].url); |
// Setup the native resolver for built in library functions. |
DART_CHECK_VALID( |
Dart_SetNativeResolver(library, |
kBuiltinLibraries[id].native_resolver, |
kBuiltinLibraries[id].native_symbol)); |
} |
-} |
- |
-Dart_Handle Builtin::LoadAndCheckLibrary(BuiltinLibraryId id) { |
- static_assert(arraysize(kBuiltinLibraries) == kInvalidLibrary, |
- "Unexpected number of builtin libraries"); |
- DCHECK_GE(id, kBuiltinLibrary); |
- DCHECK_LT(id, kInvalidLibrary); |
- Dart_Handle library = DartBuiltin::LookupLibrary(kBuiltinLibraries[id].url); |
- DART_CHECK_VALID(library); |
- return library; |
+ if (kBuiltinLibraries[id].patch_url != nullptr) { |
+ DCHECK(kBuiltinLibraries[id].patch_resources != nullptr); |
+ LoadPatchFiles(library, kBuiltinLibraries[id].patch_url, |
+ kBuiltinLibraries[id].patch_resources); |
+ } |
} |
} // namespace blink |