@@ -14,7 +14,7 @@ use windows::Win32::UI::WindowsAndMessaging::{
1414
1515use crate :: type_description:: build_runtime_type_descriptor;
1616use crate :: dotnet:: { bin_write_str16, bin_write_str32} ;
17- use crate :: { normalize_js_path, proxy_manifests, throw_js_error, try_resolve_with_known_extensions, Runtime , ASYNC_PUMP_HOOK } ;
17+ use crate :: { normalize_js_path, proxy_manifests, throw_js_error, try_resolve_with_known_extensions, ASYNC_PUMP_HOOK } ;
1818use std:: cell:: RefCell ;
1919use std:: ffi:: c_void;
2020
@@ -209,23 +209,29 @@ fn default_auto_capture_path() -> PathBuf {
209209 PathBuf :: from ( "sbg_output" ) . join ( "sbg_metadata.json" )
210210}
211211
212+ /// Delivered as a `messageerror`.
213+ fn worker_error < ' s > ( scope : & mut v8:: PinScope < ' s , ' _ > , error : & str ) -> Option < v8:: Local < ' s , v8:: Value > > {
214+ let obj = v8:: Object :: new ( scope) ;
215+ if let Some ( key) = v8:: String :: new ( scope, "__workerError" ) {
216+ if let Some ( val) = v8:: String :: new ( scope, error) {
217+ obj. set ( scope, key. into ( ) , val. into ( ) ) ;
218+ }
219+ }
220+ Some ( obj. into ( ) )
221+ }
222+
212223fn polled_event_to_v8 < ' s > (
213224 scope : & mut v8:: PinScope < ' s , ' _ > ,
214225 event : crate :: worker_threads:: PolledWorkerEvent ,
215226) -> Option < v8:: Local < ' s , v8:: Value > > {
216227 match event {
217- crate :: worker_threads:: PolledWorkerEvent :: Message ( bytes) => {
218- Runtime :: deserialize_value ( scope, & bytes)
219- }
220- crate :: worker_threads:: PolledWorkerEvent :: Error ( error) => {
221- let obj = v8:: Object :: new ( scope) ;
222- if let Some ( key) = v8:: String :: new ( scope, "__workerError" ) {
223- if let Some ( val) = v8:: String :: new ( scope, error. as_str ( ) ) {
224- obj. set ( scope, key. into ( ) , val. into ( ) ) ;
225- }
228+ crate :: worker_threads:: PolledWorkerEvent :: Message ( message) => {
229+ match crate :: transfer:: deserialize ( scope, message) {
230+ Ok ( value) => Some ( value) ,
231+ Err ( error) => worker_error ( scope, & error) ,
226232 }
227- Some ( obj. into ( ) )
228233 }
234+ crate :: worker_threads:: PolledWorkerEvent :: Error ( error) => worker_error ( scope, & error) ,
229235 crate :: worker_threads:: PolledWorkerEvent :: Exited => {
230236 let obj = v8:: Object :: new ( scope) ;
231237 if let Some ( key) = v8:: String :: new ( scope, "__workerExit" ) {
@@ -919,6 +925,11 @@ pub(crate) fn handle_resolve_module_path(
919925 throw_js_error ( scope, "__nsResolveModulePath: module specifier is empty" ) ;
920926 return ;
921927 }
928+ // The app directory, as NativeScript's webpack worker loader names worker chunks.
929+ let specifier = match specifier. strip_prefix ( "~/" ) {
930+ Some ( rest) => rest. to_string ( ) ,
931+ None => specifier,
932+ } ;
922933 let parent_path = if args. length ( ) >= 2 {
923934 value_to_string ( scope, args. get ( 1 ) )
924935 } else {
@@ -1061,7 +1072,7 @@ pub(crate) fn handle_worker_post_message(
10611072 if args. length ( ) < 2 {
10621073 throw_js_error (
10631074 scope,
1064- "__nsWorkerPostMessage(workerId, value) expects 2 arguments" ,
1075+ "__nsWorkerPostMessage(workerId, value, transfer? ) expects 2 arguments" ,
10651076 ) ;
10661077 return ;
10671078 }
@@ -1070,16 +1081,38 @@ pub(crate) fn handle_worker_post_message(
10701081 throw_js_error ( scope, "Invalid worker id" ) ;
10711082 return ;
10721083 }
1073- let value = args. get ( 1 ) ;
1074- let Some ( bytes) = Runtime :: serialize_value ( scope, value) else {
1075- throw_js_error ( scope, "DataCloneError: value could not be cloned." ) ;
1084+ // On failure the exception is pending.
1085+ let Some ( message) = crate :: transfer:: serialize ( scope, args. get ( 1 ) , args. get ( 2 ) ) else {
10761086 return ;
10771087 } ;
1078- if let Err ( err) = crate :: worker_threads:: post_message ( worker_id as u64 , bytes ) {
1088+ if let Err ( err) = crate :: worker_threads:: post_message ( worker_id as u64 , message ) {
10791089 throw_js_error ( scope, err. as_str ( ) ) ;
10801090 }
10811091}
10821092
1093+ /// A dispatcher the runtime made itself only runs when its host pumps messages: there a worker's
1094+ /// replies only arrive by polling.
1095+ pub ( crate ) fn handle_worker_pushes_messages (
1096+ _scope : & mut v8:: PinScope < ' _ , ' _ > ,
1097+ _args : v8:: FunctionCallbackArguments ,
1098+ mut retval : v8:: ReturnValue ,
1099+ ) {
1100+ let isolate = crate :: DELEGATE_ISOLATE_PTR . with ( |c| c. get ( ) ) as usize ;
1101+ let xaml_host = crate :: ui_dispatcher:: is_initialized ( ) && !crate :: ui_dispatcher:: needs_win32_pump ( ) ;
1102+ retval. set_bool ( crate :: worker_threads:: is_worker_isolate ( isolate) || xaml_host) ;
1103+ }
1104+
1105+ /// Cloned and transferred now, as on the web; sent once the current job is done.
1106+ pub ( crate ) fn handle_worker_queue_message (
1107+ scope : & mut v8:: PinScope < ' _ , ' _ > ,
1108+ args : v8:: FunctionCallbackArguments ,
1109+ _retval : v8:: ReturnValue ,
1110+ ) {
1111+ if let Some ( message) = crate :: transfer:: serialize ( scope, args. get ( 0 ) , args. get ( 1 ) ) {
1112+ crate :: worker_threads:: queue_outgoing ( message) ;
1113+ }
1114+ }
1115+
10831116/// Runs on a worker's creating thread when the worker has queued messages: hands them to that
10841117/// `Worker` object (`__nsWorkerDeliver`, installed by the Worker shim).
10851118pub ( crate ) fn deliver_worker_events ( worker_id : u64 ) {
@@ -5788,6 +5821,8 @@ pub(crate) fn init_async_helpers(
57885821 register ! ( "__nsDescribeWinRTType" , handle_describe_winrt_type) ;
57895822 register ! ( "__nsWorkerCreateThreaded" , handle_worker_create_threaded) ;
57905823 register ! ( "__nsWorkerPostMessage" , handle_worker_post_message) ;
5824+ register ! ( "__nsWorkerQueueMessage" , handle_worker_queue_message) ;
5825+ register ! ( "__nsWorkerPushesMessages" , handle_worker_pushes_messages) ;
57915826 register ! ( "__nsWorkerPollMessages" , handle_worker_poll_messages) ;
57925827 register ! ( "__nsWorkerTerminate" , handle_worker_terminate) ;
57935828 register ! (
@@ -5879,6 +5914,7 @@ pub(crate) fn init_async_helpers(
58795914 }
58805915
58815916 crate :: message_port:: install_message_port_runtime ( scope) ;
5917+ crate :: transfer:: install_transfer_runtime ( scope) ;
58825918 crate :: worker_support:: install_worker_runtime ( scope) ;
58835919 crate :: hmr_support:: install_hmr_support ( scope) ;
58845920 crate :: livesync:: install_livesync_support ( scope) ;
0 commit comments