From bbcc9babb8e3950dfacbfb2deacb7fa38d6383bd Mon Sep 17 00:00:00 2001 From: Jason Simmons Date: Mon, 7 Jul 2025 09:34:35 -0700 Subject: [PATCH] [dart:io] Update dart::bin::CleanupDartIo and no-SSL mode to support recent changes to IOService https://dart-review.googlesource.com/c/sdk/+/437160 changed how the IOService port is created. The Flutter engine calls dart::bin::CleanupDartIo during shutdown of the Dart VM. That API now needs to clean up the IOService. This PR also adds support for the IOService port change when building Dart with secure sockets disabled. TEST=building the Flutter engine Change-Id: I2d61713cfbe3feddb7d361605c25229d05dd61a3 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/438605 Reviewed-by: Alexander Markov Reviewed-by: Siva Annamalai Commit-Queue: Jason Simmons --- runtime/bin/dart_embedder_api_impl.cc | 4 ++++ runtime/bin/dart_io_api_impl.cc | 6 ++++++ runtime/bin/io_service_no_ssl.cc | 16 ++++++++++++++-- runtime/bin/io_service_no_ssl.h | 4 ++++ 4 files changed, 28 insertions(+), 2 deletions(-) diff --git a/runtime/bin/dart_embedder_api_impl.cc b/runtime/bin/dart_embedder_api_impl.cc index c280fc8e2df..ce1b89ab34a 100644 --- a/runtime/bin/dart_embedder_api_impl.cc +++ b/runtime/bin/dart_embedder_api_impl.cc @@ -6,7 +6,11 @@ #include "bin/dartutils.h" #include "bin/eventhandler.h" +#if defined(DART_IO_SECURE_SOCKET_DISABLED) +#include "bin/io_service_no_ssl.h" +#else // defined(DART_IO_SECURE_SOCKET_DISABLED) #include "bin/io_service.h" +#endif // defined(DART_IO_SECURE_SOCKET_DISABLED) #include "bin/isolate_data.h" #include "bin/process.h" #include "bin/secure_socket_filter.h" diff --git a/runtime/bin/dart_io_api_impl.cc b/runtime/bin/dart_io_api_impl.cc index 369bf2d4a1c..d6acd6f3829 100644 --- a/runtime/bin/dart_io_api_impl.cc +++ b/runtime/bin/dart_io_api_impl.cc @@ -8,6 +8,11 @@ #include "bin/directory.h" #include "bin/eventhandler.h" #include "bin/io_natives.h" +#if defined(DART_IO_SECURE_SOCKET_DISABLED) +#include "bin/io_service_no_ssl.h" +#else // defined(DART_IO_SECURE_SOCKET_DISABLED) +#include "bin/io_service.h" +#endif // defined(DART_IO_SECURE_SOCKET_DISABLED) #include "bin/platform.h" #include "bin/process.h" #if !defined(DART_IO_SECURE_SOCKET_DISABLED) @@ -36,6 +41,7 @@ void CleanupDartIo() { SSLFilter::Cleanup(); #endif Process::Cleanup(); + IOService::Cleanup(); } void SetSystemTempDirectory(const char* system_temp) { diff --git a/runtime/bin/io_service_no_ssl.cc b/runtime/bin/io_service_no_ssl.cc index 406ad89b6df..d456cdf68f1 100644 --- a/runtime/bin/io_service_no_ssl.cc +++ b/runtime/bin/io_service_no_ssl.cc @@ -53,10 +53,22 @@ void IOServiceCallback(Dart_Port dest_port_id, Dart_CObject* message) { } intptr_t IOService::max_concurrency_ = 32; +std::atomic IOService::port_ = ILLEGAL_PORT; Dart_Port IOService::GetServicePort() { - return Dart_NewConcurrentNativePort("IOService", IOServiceCallback, - max_concurrency_); + Dart_Port port = port_; + if (port == ILLEGAL_PORT) { + port = Dart_NewConcurrentNativePort("IOService", IOServiceCallback, + max_concurrency_); + Dart_Port expected = ILLEGAL_PORT; + if (!port_.compare_exchange_strong(expected, port)) { + // Lost the initialization race. Use the winner's port and close our port. + // The winner's port is eventually implicitly closed by VM shutdown. + Dart_CloseNativePort(port); + return expected; + } + } + return port; } void FUNCTION_NAME(IOService_NewServicePort)(Dart_NativeArguments args) { diff --git a/runtime/bin/io_service_no_ssl.h b/runtime/bin/io_service_no_ssl.h index 9ab2762e6ad..db22cfde17d 100644 --- a/runtime/bin/io_service_no_ssl.h +++ b/runtime/bin/io_service_no_ssl.h @@ -9,6 +9,8 @@ #error "io_service_no_ssl.h can only be included on builds with IO enabled" #endif +#include + #include "bin/builtin.h" #include "bin/utils.h" @@ -70,12 +72,14 @@ class IOService { enum { IO_SERVICE_REQUEST_LIST(DECLARE_REQUEST) }; static Dart_Port GetServicePort(); + static void Cleanup() { port_ = ILLEGAL_PORT; } static intptr_t max_concurrency() { return max_concurrency_; } static void set_max_concurrency(intptr_t value) { max_concurrency_ = value; } private: static intptr_t max_concurrency_; + static std::atomic port_; DISALLOW_ALLOCATION(); DISALLOW_IMPLICIT_CONSTRUCTORS(IOService);