Skip to content

Commit 86e3ebb

Browse files
authored
Allow embedders to specify arbitrary data to the isolate on launch. (flutter#13047)
Since this is currently only meant to be used by the embedding internally, the setter in Objective-C is only exposed via the FlutterDartProject private class extension. Unit tests have been added to the shell_unittests harness. Fixes flutter#37641
1 parent 5162413 commit 86e3ebb

File tree

16 files changed

+184
-34
lines changed

16 files changed

+184
-34
lines changed

DEPS

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -145,7 +145,7 @@ deps = {
145145
# and not have to specific specific hashes.
146146

147147
'src/third_party/tonic':
148-
Var('fuchsia_git') + '/tonic' + '@' + 'bd27b4549199df72fcaeefd259ebc12a31c2e4ee',
148+
Var('fuchsia_git') + '/tonic' + '@' + '1a8ed9be2e2b56b32e888266d6db465d36012df4',
149149

150150
'src/third_party/benchmark':
151151
Var('fuchsia_git') + '/third_party/benchmark' + '@' + 'a779ffce872b4c811beef482e18bd0b63626aa42',

ci/licenses_golden/licenses_third_party

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
Signature: 500cc19ee17ba4703537a9ae9ac78b8f
1+
Signature: a2d49b14022a4fb8fc74726a0861087f
22

33
UNUSED LICENSES:
44

common/settings.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -183,6 +183,14 @@ struct Settings {
183183
// soon as a frame is rasterized.
184184
FrameRasterizedCallback frame_rasterized_callback;
185185

186+
// This data will be available to the isolate immediately on launch via the
187+
// Window.getPersistentIsolateData callback. This is meant for information
188+
// that the isolate cannot request asynchronously (platform messages can be
189+
// used for that purpose). This data is held for the lifetime of the shell and
190+
// is available on isolate restarts in the the shell instance. Due to this,
191+
// the buffer must be as small as possible.
192+
std::shared_ptr<const fml::Mapping> persistent_isolate_data;
193+
186194
std::string ToString() const;
187195
};
188196

fml/mapping.cc

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44

55
#include "flutter/fml/mapping.h"
66

7+
#include <algorithm>
78
#include <sstream>
89

910
namespace fml {
@@ -67,6 +68,9 @@ std::unique_ptr<FileMapping> FileMapping::CreateReadExecute(
6768

6869
DataMapping::DataMapping(std::vector<uint8_t> data) : data_(std::move(data)) {}
6970

71+
DataMapping::DataMapping(const std::string& string)
72+
: data_(string.begin(), string.end()) {}
73+
7074
DataMapping::~DataMapping() = default;
7175

7276
size_t DataMapping::GetSize() const {

fml/mapping.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,8 @@ class DataMapping final : public Mapping {
8686
public:
8787
DataMapping(std::vector<uint8_t> data);
8888

89+
DataMapping(const std::string& string);
90+
8991
~DataMapping() override;
9092

9193
// |Mapping|

lib/ui/window.dart

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1176,6 +1176,18 @@ class Window {
11761176
registrationZone.runUnaryGuarded(callback, data);
11771177
};
11781178
}
1179+
1180+
1181+
/// The embedder can specify data that the isolate can request synchronously
1182+
/// on launch. This accessor fetches that data.
1183+
///
1184+
/// This data is persistent for the duration of the Flutter application and is
1185+
/// available even after isolate restarts. Because of this lifecycle, the size
1186+
/// of this data must be kept to a minimum.
1187+
///
1188+
/// For asynchronous communication between the embedder and isolate, a
1189+
/// platform channel may be used.
1190+
ByteData getPersistentIsolateData() native 'Window_getPersistentIsolateData';
11791191
}
11801192

11811193
/// Additional accessibility features that may be enabled by the platform.

lib/ui/window/window.cc

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -142,6 +142,20 @@ void _RespondToPlatformMessage(Dart_NativeArguments args) {
142142
tonic::DartCallStatic(&RespondToPlatformMessage, args);
143143
}
144144

145+
void GetPersistentIsolateData(Dart_NativeArguments args) {
146+
auto persistent_isolate_data =
147+
UIDartState::Current()->window()->client()->GetPersistentIsolateData();
148+
149+
if (!persistent_isolate_data) {
150+
Dart_SetReturnValue(args, Dart_Null());
151+
return;
152+
}
153+
154+
Dart_SetReturnValue(
155+
args, tonic::DartByteData::Create(persistent_isolate_data->GetMapping(),
156+
persistent_isolate_data->GetSize()));
157+
}
158+
145159
} // namespace
146160

147161
Dart_Handle ToByteData(const std::vector<uint8_t>& buffer) {
@@ -398,6 +412,7 @@ void Window::RegisterNatives(tonic::DartLibraryNatives* natives) {
398412
{"Window_setIsolateDebugName", SetIsolateDebugName, 2, true},
399413
{"Window_reportUnhandledException", ReportUnhandledException, 2, true},
400414
{"Window_setNeedsReportTimings", SetNeedsReportTimings, 2, true},
415+
{"Window_getPersistentIsolateData", GetPersistentIsolateData, 1, true},
401416
});
402417
}
403418

lib/ui/window/window.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,7 @@ class WindowClient {
5757
virtual void UpdateIsolateDescription(const std::string isolate_name,
5858
int64_t isolate_port) = 0;
5959
virtual void SetNeedsReportTimings(bool value) = 0;
60+
virtual std::shared_ptr<const fml::Mapping> GetPersistentIsolateData() = 0;
6061

6162
protected:
6263
virtual ~WindowClient();

lib/web_ui/lib/src/ui/window.dart

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -995,6 +995,8 @@ abstract class Window {
995995
String _initialLifecycleState;
996996

997997
void setIsolateDebugName(String name) {}
998+
999+
ByteData getPersistentIsolateData() => null;
9981000
}
9991001

10001002
VoidCallback webOnlyScheduleFrameCallback;

runtime/runtime_controller.cc

Lines changed: 24 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,8 @@ RuntimeController::RuntimeController(
2626
std::string p_advisory_script_entrypoint,
2727
std::function<void(int64_t)> p_idle_notification_callback,
2828
fml::closure p_isolate_create_callback,
29-
fml::closure p_isolate_shutdown_callback)
29+
fml::closure p_isolate_shutdown_callback,
30+
std::shared_ptr<const fml::Mapping> p_persistent_isolate_data)
3031
: RuntimeController(p_client,
3132
p_vm,
3233
std::move(p_isolate_snapshot),
@@ -39,7 +40,8 @@ RuntimeController::RuntimeController(
3940
p_idle_notification_callback,
4041
WindowData{/* default window data */},
4142
p_isolate_create_callback,
42-
p_isolate_shutdown_callback) {}
43+
p_isolate_shutdown_callback,
44+
std::move(p_persistent_isolate_data)) {}
4345

4446
RuntimeController::RuntimeController(
4547
RuntimeDelegate& p_client,
@@ -54,7 +56,8 @@ RuntimeController::RuntimeController(
5456
std::function<void(int64_t)> idle_notification_callback,
5557
WindowData p_window_data,
5658
fml::closure p_isolate_create_callback,
57-
fml::closure p_isolate_shutdown_callback)
59+
fml::closure p_isolate_shutdown_callback,
60+
std::shared_ptr<const fml::Mapping> p_persistent_isolate_data)
5861
: client_(p_client),
5962
vm_(p_vm),
6063
isolate_snapshot_(std::move(p_isolate_snapshot)),
@@ -67,7 +70,8 @@ RuntimeController::RuntimeController(
6770
idle_notification_callback_(idle_notification_callback),
6871
window_data_(std::move(p_window_data)),
6972
isolate_create_callback_(p_isolate_create_callback),
70-
isolate_shutdown_callback_(p_isolate_shutdown_callback) {
73+
isolate_shutdown_callback_(p_isolate_shutdown_callback),
74+
persistent_isolate_data_(std::move(p_persistent_isolate_data)) {
7175
// Create the root isolate as soon as the runtime controller is initialized.
7276
// It will be run at a later point when the engine provides a run
7377
// configuration and then runs the isolate.
@@ -144,7 +148,8 @@ std::unique_ptr<RuntimeController> RuntimeController::Clone() const {
144148
idle_notification_callback_, //
145149
window_data_, //
146150
isolate_create_callback_, //
147-
isolate_shutdown_callback_ //
151+
isolate_shutdown_callback_, //
152+
persistent_isolate_data_ //
148153
));
149154
}
150155

@@ -296,42 +301,56 @@ Window* RuntimeController::GetWindowIfAvailable() {
296301
return root_isolate ? root_isolate->window() : nullptr;
297302
}
298303

304+
// |WindowClient|
299305
std::string RuntimeController::DefaultRouteName() {
300306
return client_.DefaultRouteName();
301307
}
302308

309+
// |WindowClient|
303310
void RuntimeController::ScheduleFrame() {
304311
client_.ScheduleFrame();
305312
}
306313

314+
// |WindowClient|
307315
void RuntimeController::Render(Scene* scene) {
308316
client_.Render(scene->takeLayerTree());
309317
}
310318

319+
// |WindowClient|
311320
void RuntimeController::UpdateSemantics(SemanticsUpdate* update) {
312321
if (window_data_.semantics_enabled) {
313322
client_.UpdateSemantics(update->takeNodes(), update->takeActions());
314323
}
315324
}
316325

326+
// |WindowClient|
317327
void RuntimeController::HandlePlatformMessage(
318328
fml::RefPtr<PlatformMessage> message) {
319329
client_.HandlePlatformMessage(std::move(message));
320330
}
321331

332+
// |WindowClient|
322333
FontCollection& RuntimeController::GetFontCollection() {
323334
return client_.GetFontCollection();
324335
}
325336

337+
// |WindowClient|
326338
void RuntimeController::UpdateIsolateDescription(const std::string isolate_name,
327339
int64_t isolate_port) {
328340
client_.UpdateIsolateDescription(isolate_name, isolate_port);
329341
}
330342

343+
// |WindowClient|
331344
void RuntimeController::SetNeedsReportTimings(bool value) {
332345
client_.SetNeedsReportTimings(value);
333346
}
334347

348+
// |WindowClient|
349+
std::shared_ptr<const fml::Mapping>
350+
RuntimeController::GetPersistentIsolateData() {
351+
return persistent_isolate_data_;
352+
}
353+
335354
Dart_Port RuntimeController::GetMainPort() {
336355
std::shared_ptr<DartIsolate> root_isolate = root_isolate_.lock();
337356
return root_isolate ? root_isolate->main_port() : ILLEGAL_PORT;

0 commit comments

Comments
 (0)