Skip to content

Commit

Permalink
[fuchsia] Teach engine how to set up an isolate from a list of kernel…
Browse files Browse the repository at this point in the history
… files. (flutter#5210)
  • Loading branch information
rmacnak-google authored May 16, 2018
1 parent c95d432 commit 30c649d
Show file tree
Hide file tree
Showing 6 changed files with 109 additions and 10 deletions.
1 change: 1 addition & 0 deletions common/settings.h
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ struct Settings {

std::string application_library_path;
std::string application_kernel_asset;
std::string application_kernel_list_asset;

std::string main_dart_file_path;
std::string packages_file_path;
Expand Down
1 change: 1 addition & 0 deletions content_handler/application.cc
Original file line number Diff line number Diff line change
Expand Up @@ -138,6 +138,7 @@ Application::Application(

settings_.script_snapshot_path = "snapshot_blob.bin";
settings_.application_kernel_asset = "kernel_blob.dill";
settings_.application_kernel_list_asset = "app.dilplist";

settings_.log_tag = debug_label_ + std::string{"(flutter)"};

Expand Down
38 changes: 29 additions & 9 deletions runtime/dart_isolate.cc
Original file line number Diff line number Diff line change
Expand Up @@ -273,35 +273,50 @@ bool DartIsolate::PrepareForRunningFromPrecompiledCode() {
return true;
}

static bool LoadScriptSnapshot(std::shared_ptr<const fml::Mapping> mapping) {
static bool LoadScriptSnapshot(std::shared_ptr<const fml::Mapping> mapping,
bool last_piece) {
FXL_CHECK(last_piece) << "Script snapshots cannot be divided";
if (tonic::LogIfError(Dart_LoadScriptFromSnapshot(mapping->GetMapping(),
mapping->GetSize()))) {
return false;
}
return true;
}

static bool LoadKernelSnapshot(std::shared_ptr<const fml::Mapping> mapping) {
if (tonic::LogIfError(Dart_LoadScriptFromKernel(mapping->GetMapping(),
mapping->GetSize()))) {
static bool LoadKernelSnapshot(std::shared_ptr<const fml::Mapping> mapping,
bool last_piece) {
Dart_Handle library = Dart_LoadLibraryFromKernel(mapping->GetMapping(),
mapping->GetSize());
if (tonic::LogIfError(library)) {
return false;
}

if (!last_piece) {
// More to come.
return true;
}

Dart_SetRootLibrary(library);
if (tonic::LogIfError(Dart_FinalizeLoading(false))) {
return false;
}
return true;
}

static bool LoadSnapshot(std::shared_ptr<const fml::Mapping> mapping) {
static bool LoadSnapshot(std::shared_ptr<const fml::Mapping> mapping,
bool last_piece) {
if (Dart_IsKernel(mapping->GetMapping(), mapping->GetSize())) {
return LoadKernelSnapshot(std::move(mapping));
return LoadKernelSnapshot(std::move(mapping), last_piece);
} else {
return LoadScriptSnapshot(std::move(mapping));
return LoadScriptSnapshot(std::move(mapping), last_piece);
}
return false;
}

FXL_WARN_UNUSED_RESULT
bool DartIsolate::PrepareForRunningFromSnapshot(
std::shared_ptr<const fml::Mapping> mapping) {
std::shared_ptr<const fml::Mapping> mapping,
bool last_piece) {
TRACE_EVENT0("flutter", "DartIsolate::PrepareForRunningFromSnapshot");
if (phase_ != Phase::LibrariesSetup) {
return false;
Expand All @@ -321,10 +336,15 @@ bool DartIsolate::PrepareForRunningFromSnapshot(
return false;
}

if (!LoadSnapshot(mapping)) {
if (!LoadSnapshot(mapping, last_piece)) {
return false;
}

if (!last_piece) {
// More to come.
return true;
}

if (Dart_IsNull(Dart_RootLibrary())) {
return false;
}
Expand Down
3 changes: 2 additions & 1 deletion runtime/dart_isolate.h
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,8 @@ class DartIsolate : public UIDartState {

FXL_WARN_UNUSED_RESULT
bool PrepareForRunningFromSnapshot(
std::shared_ptr<const fml::Mapping> snapshot);
std::shared_ptr<const fml::Mapping> snapshot,
bool last_piece = true);

FXL_WARN_UNUSED_RESULT
bool PrepareForRunningFromSource(const std::string& main_source_file,
Expand Down
73 changes: 73 additions & 0 deletions shell/common/isolate_configuration.cc
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,35 @@ class SourceIsolateConfiguration final : public IsolateConfiguration {
FXL_DISALLOW_COPY_AND_ASSIGN(SourceIsolateConfiguration);
};

class KernelListIsolateConfiguration final : public IsolateConfiguration {
public:
KernelListIsolateConfiguration(
std::vector<std::unique_ptr<fml::Mapping>> kernel_pieces)
: kernel_pieces_(std::move(kernel_pieces)) {}

// |shell::IsolateConfiguration|
bool DoPrepareIsolate(blink::DartIsolate& isolate) override {
if (blink::DartVM::IsRunningPrecompiledCode()) {
return false;
}

for (size_t i = 0; i < kernel_pieces_.size(); i++) {
bool last_piece = i + 1 == kernel_pieces_.size();
if (!isolate.PrepareForRunningFromSnapshot(std::move(kernel_pieces_[i]),
last_piece)) {
return false;
}
}

return true;
}

private:
std::vector<std::unique_ptr<fml::Mapping>> kernel_pieces_;

FXL_DISALLOW_COPY_AND_ASSIGN(KernelListIsolateConfiguration);
};

std::unique_ptr<IsolateConfiguration> IsolateConfiguration::InferFromSettings(
const blink::Settings& settings,
fxl::RefPtr<blink::AssetManager> asset_manager) {
Expand All @@ -107,6 +136,7 @@ std::unique_ptr<IsolateConfiguration> IsolateConfiguration::InferFromSettings(

// Running from kernel snapshot.
{
// TODO(engine): Add AssetManager::GetAsMapping or such to avoid the copy.
std::vector<uint8_t> kernel;
if (asset_manager && asset_manager->GetAsBuffer(
settings.application_kernel_asset, &kernel)) {
Expand All @@ -117,6 +147,7 @@ std::unique_ptr<IsolateConfiguration> IsolateConfiguration::InferFromSettings(

// Running from script snapshot.
{
// TODO(engine): Add AssetManager::GetAsMapping or such to avoid the copy.
std::vector<uint8_t> script_snapshot;
if (asset_manager && asset_manager->GetAsBuffer(
settings.script_snapshot_path, &script_snapshot)) {
Expand All @@ -125,6 +156,42 @@ std::unique_ptr<IsolateConfiguration> IsolateConfiguration::InferFromSettings(
}
}

// Running from kernel divided into several pieces (for sharing).
{
// TODO(fuchsia): Add AssetManager::GetAsMapping or such to avoid the copy.
// TODO(fuchsia): Use async blobfs API once it becomes available.
std::vector<uint8_t> kernel_list;
if (asset_manager &&
asset_manager->GetAsBuffer(settings.application_kernel_list_asset,
&kernel_list)) {
std::vector<std::unique_ptr<fml::Mapping>> kernel_pieces;

size_t piece_path_start = 0;
while (piece_path_start < kernel_list.size()) {
size_t piece_path_end = piece_path_start;
while ((piece_path_end < kernel_list.size()) &&
(kernel_list[piece_path_end] != '\n')) {
piece_path_end++;
}

std::string piece_path(reinterpret_cast<const char*>(&kernel_list[piece_path_start]),
piece_path_end - piece_path_start);
std::vector<uint8_t> piece;
if (!asset_manager->GetAsBuffer(piece_path, &piece)) {
FXL_LOG(ERROR) << "Failed to load: " << piece_path;
return nullptr;
}

kernel_pieces.emplace_back(
std::make_unique<fml::DataMapping>(std::move(piece)));

piece_path_start = piece_path_end + 1;
}

return CreateForKernelList(std::move(kernel_pieces));
}
}

return nullptr;
}

Expand All @@ -145,4 +212,10 @@ std::unique_ptr<IsolateConfiguration> IsolateConfiguration::CreateForSource(
std::move(packages_path));
}

std::unique_ptr<IsolateConfiguration> IsolateConfiguration::CreateForKernelList(
std::vector<std::unique_ptr<fml::Mapping>> kernel_pieces) {
return std::make_unique<KernelListIsolateConfiguration>(
std::move(kernel_pieces));
}

} // namespace shell
3 changes: 3 additions & 0 deletions shell/common/isolate_configuration.h
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,9 @@ class IsolateConfiguration {
std::string main_path,
std::string packages_path);

static std::unique_ptr<IsolateConfiguration> CreateForKernelList(
std::vector<std::unique_ptr<fml::Mapping>> kernel_pieces);

IsolateConfiguration();

virtual ~IsolateConfiguration();
Expand Down

0 comments on commit 30c649d

Please sign in to comment.