diff --git a/packages/react-native/Libraries/Image/RCTImageLoader.mm b/packages/react-native/Libraries/Image/RCTImageLoader.mm index 9dab28583942..75362da2dd43 100644 --- a/packages/react-native/Libraries/Image/RCTImageLoader.mm +++ b/packages/react-native/Libraries/Image/RCTImageLoader.mm @@ -1323,22 +1323,6 @@ - (void)queryCache:(NSArray *)uris resolve:(RCTPromiseResolveBlock)resolve rejec } @end -/** - * DEPRECATED!! DO NOT USE - * Instead use `[_bridge moduleForClass:[RCTImageLoader class]]` - */ -@implementation RCTBridge (RCTImageLoader) - -- (RCTImageLoader *)imageLoader -{ - RCTLogWarn( - @"Calling bridge.imageLoader is deprecated and will not work in newer versions of RN. Please update to the " - "moduleForClass API or turboModuleRegistry API."); - return [self moduleForClass:[RCTImageLoader class]]; -} - -@end - @implementation RCTBridgeProxy (RCTImageLoader) - (RCTImageLoader *)imageLoader diff --git a/packages/react-native/Libraries/Image/RCTImageStoreManager.mm b/packages/react-native/Libraries/Image/RCTImageStoreManager.mm index 393034c53d03..76b0ab7ece1f 100644 --- a/packages/react-native/Libraries/Image/RCTImageStoreManager.mm +++ b/packages/react-native/Libraries/Image/RCTImageStoreManager.mm @@ -248,15 +248,6 @@ - (void)getImageForTag:(NSString *)imageTag withBlock:(void (^)(UIImage *image)) @end -@implementation RCTBridge (RCTImageStoreManager) - -- (RCTImageStoreManager *)imageStoreManager -{ - return [self moduleForClass:[RCTImageStoreManager class]]; -} - -@end - @implementation RCTBridgeProxy (RCTImageStoreManager) - (RCTImageStoreManager *)imageStoreManager diff --git a/packages/react-native/Libraries/Network/RCTNetworking.mm b/packages/react-native/Libraries/Network/RCTNetworking.mm index 95e531d4e49a..d9c78b10e685 100644 --- a/packages/react-native/Libraries/Network/RCTNetworking.mm +++ b/packages/react-native/Libraries/Network/RCTNetworking.mm @@ -856,15 +856,6 @@ - (void)clearCookies:(RCTResponseSenderBlock)responseSender @end -@implementation RCTBridge (RCTNetworking) - -- (RCTNetworking *)networking -{ - return [self moduleForClass:[RCTNetworking class]]; -} - -@end - @implementation RCTBridgeProxy (RCTNetworking) - (RCTNetworking *)networking diff --git a/packages/react-native/Package.swift b/packages/react-native/Package.swift index bc51dadab45c..ac1611c59c07 100644 --- a/packages/react-native/Package.swift +++ b/packages/react-native/Package.swift @@ -454,7 +454,6 @@ let reactCore = RNTarget( path: "React", searchPaths: [ "React/I18n", - "React/Profiler", "ReactCommon/react/runtime/platform/ios", // explicit header search path to break circular dependency. RCTHost imports `RCTDefines.h` in ReactCore, ReacCore needs to import RCTHost ], linkedFrameworks: ["CoreServices"], diff --git a/packages/react-native/React/Base/RCTBridge+Private.h b/packages/react-native/React/Base/RCTBridge+Private.h index 88d68cd925b6..4f717ab3412b 100644 --- a/packages/react-native/React/Base/RCTBridge+Private.h +++ b/packages/react-native/React/Base/RCTBridge+Private.h @@ -8,7 +8,6 @@ #import @class RCTModuleRegistry; -@class RCTModuleData; @protocol RCTJavaScriptExecutor; #if !defined(RCT_REMOVE_LEGACY_MODULE_INTEROP) || !defined(RCT_REMOVE_LEGACY_COMPONENT_INTEROP) @@ -18,23 +17,9 @@ RCT_EXTERN void RCTRegisterModule(Class); @interface RCTBridge () -// Used for the profiler flow events between JS and native -@property (nonatomic, assign) int64_t flowID; -@property (nonatomic, assign) CFMutableDictionaryRef flowIDMap; -@property (nonatomic, strong) NSLock *flowIDMapLock; - -// Used by RCTDevMenu -@property (nonatomic, copy) NSString *bridgeDescription; - + (instancetype)currentBridge; + (void)setCurrentBridge:(RCTBridge *)bridge; -/** - * Bridge setup code - creates an instance of RCTBachedBridge. Exposed for - * test only - */ -- (void)setUp; - /** * This method is used to invoke a callback that was registered in the * JavaScript application context. Safe to call from any thread. @@ -48,17 +33,6 @@ RCT_EXTERN void RCTRegisterModule(Class); */ @property (atomic, strong) RCTBridge *batchedBridge; -/** - * The block that creates the modules' instances to be added to the bridge. - * Exposed for RCTCxxBridge - */ -@property (nonatomic, copy, readonly) RCTBridgeModuleListProvider moduleProvider; - -/** - * Used by RCTDevMenu to override the `hot` param of the current bundleURL. - */ -@property (nonatomic, strong, readwrite) NSURL *bundleURL; - /** * An object that allows one to require NativeModules/TurboModules. * RCTModuleRegistry is implemented in bridgeless mode and bridge mode. @@ -70,17 +44,6 @@ RCT_EXTERN void RCTRegisterModule(Class); @interface RCTBridge (RCTCxxBridge) -/** - * Used by RCTModuleData - */ - -@property (nonatomic, weak, readonly) RCTBridge *parentBridge; - -/** - * Used by RCTModuleData - */ -@property (nonatomic, assign, readonly) BOOL moduleSetupComplete; - /** * Called on the child bridge to run the executor and start loading. */ @@ -92,41 +55,9 @@ RCT_EXTERN void RCTRegisterModule(Class); */ - (void)dispatchBlock:(dispatch_block_t)block queue:(dispatch_queue_t)queue; -/** - * Get the module data for a given module name. Used by UIManager to implement - * the `dispatchViewManagerCommand` method. - */ -- (RCTModuleData *)moduleDataForName:(NSString *)moduleName; - /** * Registers additional classes with the ModuleRegistry. */ - (void)registerAdditionalModuleClasses:(NSArray *)newModules; -/** - * Updates the ModuleRegistry with a pre-initialized instance. - */ -- (void)updateModuleWithInstance:(id)instance; - -/** - * Systrace profiler toggling methods exposed for the RCTDevMenu - */ -- (void)startProfiling; -- (void)stopProfiling:(void (^)(NSData *))callback; - -/** - * Synchronously call a specific native module's method and return the result - */ -- (id)callNativeModule:(NSUInteger)moduleID method:(NSUInteger)methodID params:(NSArray *)params; - -/** - * Hook exposed for RCTLog to send logs to JavaScript when not running in JSC - */ -- (void)logMessage:(NSString *)message level:(NSString *)level; - -/** - * Allow super fast, one time, timers to skip the queue and be directly executed - */ -- (void)_immediatelyCallTimer:(NSNumber *)timer; - @end diff --git a/packages/react-native/React/Base/RCTBridge.mm b/packages/react-native/React/Base/RCTBridge.mm index b2258a62c0b9..f46ded1db8fd 100644 --- a/packages/react-native/React/Base/RCTBridge.mm +++ b/packages/react-native/React/Base/RCTBridge.mm @@ -27,7 +27,6 @@ #import "RCTModuleData.h" #import "RCTPausedInDebuggerOverlayController.h" #import "RCTPerformanceLogger.h" -#import "RCTProfile.h" #import "RCTReloadCommand.h" #import "RCTUtils.h" diff --git a/packages/react-native/React/Base/RCTDisplayLink.m b/packages/react-native/React/Base/RCTDisplayLink.m index ebb430f42d93..afb1b4da566c 100644 --- a/packages/react-native/React/Base/RCTDisplayLink.m +++ b/packages/react-native/React/Base/RCTDisplayLink.m @@ -12,7 +12,6 @@ #import "RCTAssert.h" #import "RCTFrameUpdate.h" -#import "RCTProfile.h" #define RCTAssertRunLoop() \ RCTAssert(_runLoop == [NSRunLoop currentRunLoop], @"This method must be called on the CADisplayLink run loop") @@ -81,8 +80,6 @@ - (void)_jsThreadUpdate:(CADisplayLink *)displayLink { RCTAssertRunLoop(); - RCT_PROFILE_BEGIN_EVENT(RCTProfileTagAlways, @"-[RCTDisplayLink _jsThreadUpdate:]", nil); - // This always runs on the JS thread run loop, which is the queue the frame // update observer expects its callbacks on, so dispatch inline. RCTFrameUpdate *frameUpdate = [[RCTFrameUpdate alloc] initWithDisplayLink:displayLink]; @@ -91,10 +88,6 @@ - (void)_jsThreadUpdate:(CADisplayLink *)displayLink } [self updateJSDisplayLinkState]; - - RCTProfileImmediateEvent(RCTProfileTagAlways, @"JS Thread Tick", displayLink.timestamp, 'g'); - - RCT_PROFILE_END_EVENT(RCTProfileTagAlways, @"objc_call"); } - (void)updateJSDisplayLinkState diff --git a/packages/react-native/React/Base/RCTEventDispatcher.m b/packages/react-native/React/Base/RCTEventDispatcher.m index d779006e7e90..0c3c8806b6e4 100644 --- a/packages/react-native/React/Base/RCTEventDispatcher.m +++ b/packages/react-native/React/Base/RCTEventDispatcher.m @@ -20,15 +20,6 @@ return eventName; } -@implementation RCTBridge (RCTEventDispatcher) - -- (id)eventDispatcher -{ - return [self moduleForName:@"EventDispatcher" lazilyLoadIfNecessary:YES]; -} - -@end - @implementation RCTBridgeProxy (RCTEventDispatcher) - (id)eventDispatcher diff --git a/packages/react-native/React/Base/RCTModuleMethod.mm b/packages/react-native/React/Base/RCTModuleMethod.mm index 4dda9e0ff7ce..b853608e5f60 100644 --- a/packages/react-native/React/Base/RCTModuleMethod.mm +++ b/packages/react-native/React/Base/RCTModuleMethod.mm @@ -17,7 +17,6 @@ #import "RCTLog.h" #import "RCTManagedPointer.h" #import "RCTParserUtils.h" -#import "RCTProfile.h" #import "RCTUtils.h" typedef BOOL (^RCTArgumentBlock)(RCTBridge *, NSUInteger, id); @@ -471,12 +470,7 @@ - (void)processMethodSignature - (SEL)selector { if (_selector == NULL) { - RCT_PROFILE_BEGIN_EVENT( - RCTProfileTagAlways, - @"", - (@{@"module" : NSStringFromClass(_moduleClass), @"method" : @(_methodInfo->objcName)})); [self processMethodSignature]; - RCT_PROFILE_END_EVENT(RCTProfileTagAlways, @""); } return _selector; diff --git a/packages/react-native/React/Base/RCTPerformanceLogger.mm b/packages/react-native/React/Base/RCTPerformanceLogger.mm index e1c40ff51064..f31d1df4e6c1 100644 --- a/packages/react-native/React/Base/RCTPerformanceLogger.mm +++ b/packages/react-native/React/Base/RCTPerformanceLogger.mm @@ -12,14 +12,12 @@ #import "RCTLog.h" #import "RCTPerformanceLogger.h" #import "RCTPerformanceLoggerLabels.h" -#import "RCTProfile.h" #import "RCTRootView.h" using namespace facebook::react; @interface RCTPerformanceLogger () { int64_t _data[RCTPLSize][2]; - NSInteger _cookies[RCTPLSize]; } @end @@ -46,12 +44,6 @@ @implementation RCTPerformanceLogger - (void)markStartForTag:(RCTPLTag)tag { -#if RCT_PROFILE - if (RCTProfileIsProfiling()) { - NSString *label = RCTPLLabelForTag(tag); - _cookies[tag] = RCTProfileBeginAsyncEvent(RCTProfileTagAlways, label, nil); - } -#endif const NSTimeInterval currentTime = CACurrentMediaTime() * 1000; _data[tag][0] = currentTime; _data[tag][1] = 0; @@ -65,12 +57,6 @@ - (void)markStartForTag:(RCTPLTag)tag - (void)markStopForTag:(RCTPLTag)tag { -#if RCT_PROFILE - if (RCTProfileIsProfiling()) { - NSString *label = RCTPLLabelForTag(tag); - RCTProfileEndAsyncEvent(RCTProfileTagAlways, @"native", _cookies[tag], label, @"RCTPerformanceLogger"); - } -#endif const NSTimeInterval currentTime = CACurrentMediaTime() * 1000; if (_data[tag][0] != 0 && _data[tag][1] == 0) { _data[tag][1] = currentTime; diff --git a/packages/react-native/React/Base/RCTRootView.m b/packages/react-native/React/Base/RCTRootView.m index 976be1e92312..178fa0f76f3d 100644 --- a/packages/react-native/React/Base/RCTRootView.m +++ b/packages/react-native/React/Base/RCTRootView.m @@ -15,7 +15,6 @@ #import "RCTKeyCommands.h" #import "RCTLog.h" #import "RCTPerformanceLogger.h" -#import "RCTProfile.h" #import "RCTTouchHandler.h" #import "RCTUIManager.h" #import "RCTUIManagerUtils.h" diff --git a/packages/react-native/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm b/packages/react-native/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm index 4e4101a6c6ed..bddc3b863912 100644 --- a/packages/react-native/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm +++ b/packages/react-native/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm @@ -13,7 +13,6 @@ #import "RCTBridge.h" #import "RCTLog.h" #import "RCTPerformanceLogger.h" -#import "RCTProfile.h" #import "RCTRootViewDelegate.h" #import "RCTSurface.h" #import "UIView+React.h" diff --git a/packages/react-native/React/CoreModules/RCTAccessibilityManager.mm b/packages/react-native/React/CoreModules/RCTAccessibilityManager.mm index b40e36614038..dee5e643c758 100644 --- a/packages/react-native/React/CoreModules/RCTAccessibilityManager.mm +++ b/packages/react-native/React/CoreModules/RCTAccessibilityManager.mm @@ -486,15 +486,6 @@ void RCTAccessibilityManagerSetIsVoiceOverEnabled( @end -@implementation RCTBridge (RCTAccessibilityManager) - -- (RCTAccessibilityManager *)accessibilityManager -{ - return [self moduleForClass:[RCTAccessibilityManager class]]; -} - -@end - @implementation RCTBridgeProxy (RCTAccessibilityManager) - (RCTAccessibilityManager *)accessibilityManager diff --git a/packages/react-native/React/CoreModules/RCTDevMenu.mm b/packages/react-native/React/CoreModules/RCTDevMenu.mm index bd946190df6b..695c42e2e0ca 100644 --- a/packages/react-native/React/CoreModules/RCTDevMenu.mm +++ b/packages/react-native/React/CoreModules/RCTDevMenu.mm @@ -616,19 +616,6 @@ + (instancetype)buttonItemWithTitleBlock:(NSString * (^)(void))titleBlock handle #endif -@implementation RCTBridge (RCTDevMenu) - -- (RCTDevMenu *)devMenu -{ -#if RCT_DEV_MENU - return [self moduleForClass:[RCTDevMenu class]]; -#else - return nil; -#endif -} - -@end - @implementation RCTBridgeProxy (RCTDevMenu) - (RCTDevMenu *)devMenu diff --git a/packages/react-native/React/CoreModules/RCTDevSettings.mm b/packages/react-native/React/CoreModules/RCTDevSettings.mm index abe2897dec27..89a7b0c793e6 100644 --- a/packages/react-native/React/CoreModules/RCTDevSettings.mm +++ b/packages/react-native/React/CoreModules/RCTDevSettings.mm @@ -552,21 +552,6 @@ - (void)addHandler:(id)handler forPackagerMethod:(NSStr #endif // #if RCT_DEV_MENU -@implementation RCTBridge (RCTDevSettings) - -- (RCTDevSettings *)devSettings -{ -#if RCT_REMOTE_PROFILE - return [self moduleForClass:[RCTDevSettings class]]; -#elif RCT_DEV_MENU - return devSettingsMenuEnabled ? [self moduleForClass:[RCTDevSettings class]] : nil; -#else - return nil; -#endif -} - -@end - @implementation RCTBridgeProxy (RCTDevSettings) - (RCTDevSettings *)devSettings diff --git a/packages/react-native/React/CoreModules/RCTEventDispatcher.mm b/packages/react-native/React/CoreModules/RCTEventDispatcher.mm index 6bf4508067b8..5a64e1d8622b 100644 --- a/packages/react-native/React/CoreModules/RCTEventDispatcher.mm +++ b/packages/react-native/React/CoreModules/RCTEventDispatcher.mm @@ -9,7 +9,6 @@ #import #import -#import #import #import diff --git a/packages/react-native/React/CoreModules/RCTWebSocketModule.mm b/packages/react-native/React/CoreModules/RCTWebSocketModule.mm index c588c616d1b7..44f62bd3adcd 100644 --- a/packages/react-native/React/CoreModules/RCTWebSocketModule.mm +++ b/packages/react-native/React/CoreModules/RCTWebSocketModule.mm @@ -288,15 +288,6 @@ - (void)webSocket:(SRWebSocket *)webSocket @end -@implementation RCTBridge (RCTWebSocketModule) - -- (RCTWebSocketModule *)webSocketModule -{ - return [self moduleForClass:[RCTWebSocketModule class]]; -} - -@end - @implementation RCTBridgeProxy (RCTWebSocketModule) - (RCTWebSocketModule *)webSocketModule diff --git a/packages/react-native/React/Modules/RCTSurfacePresenterStub.m b/packages/react-native/React/Modules/RCTSurfacePresenterStub.m index 07524d583ea4..a03450b9a877 100644 --- a/packages/react-native/React/Modules/RCTSurfacePresenterStub.m +++ b/packages/react-native/React/Modules/RCTSurfacePresenterStub.m @@ -7,20 +7,6 @@ #import "RCTSurfacePresenterStub.h" -@implementation RCTBridge (RCTSurfacePresenterStub) - -- (id)surfacePresenter -{ - return objc_getAssociatedObject(self, @selector(surfacePresenter)); -} - -- (void)setSurfacePresenter:(id)surfacePresenter -{ - objc_setAssociatedObject(self, @selector(surfacePresenter), surfacePresenter, OBJC_ASSOCIATION_RETAIN); -} - -@end - @implementation RCTBridgeProxy (RCTSurfacePresenterStub) - (id)surfacePresenter diff --git a/packages/react-native/React/Modules/RCTUIManager.mm b/packages/react-native/React/Modules/RCTUIManager.mm index 3764fffef7c4..3e7eba4aae4a 100644 --- a/packages/react-native/React/Modules/RCTUIManager.mm +++ b/packages/react-native/React/Modules/RCTUIManager.mm @@ -24,7 +24,6 @@ #import "RCTLog.h" #import "RCTModuleData.h" #import "RCTModuleMethod.h" -#import "RCTProfile.h" #import "RCTScrollableProtocol.h" #import "RCTShadowView.h" #import "RCTSurfaceRootShadowView.h" diff --git a/packages/react-native/React/Profiler/RCTMacros.h b/packages/react-native/React/Profiler/RCTMacros.h deleted file mode 100644 index b636f9a831d4..000000000000 --- a/packages/react-native/React/Profiler/RCTMacros.h +++ /dev/null @@ -1,16 +0,0 @@ -/* - * Copyright (c) Meta Platforms, Inc. and affiliates. - * - * This source code is licensed under the MIT license found in the - * LICENSE file in the root directory of this source tree. - */ - -#define _CONCAT(A, B) A##B -#define CONCAT(A, B) _CONCAT(A, B) - -#if !defined(PIC_MODIFIER) -#define PIC_MODIFIER -#endif - -#define SYMBOL_NAME(name) CONCAT(__USER_LABEL_PREFIX__, name) -#define SYMBOL_NAME_PIC(name) CONCAT(SYMBOL_NAME(name), PIC_MODIFIER) diff --git a/packages/react-native/React/Profiler/RCTProfile.h b/packages/react-native/React/Profiler/RCTProfile.h deleted file mode 100644 index a2780535de62..000000000000 --- a/packages/react-native/React/Profiler/RCTProfile.h +++ /dev/null @@ -1,268 +0,0 @@ -/* - * Copyright (c) Meta Platforms, Inc. and affiliates. - * - * This source code is licensed under the MIT license found in the - * LICENSE file in the root directory of this source tree. - */ - -#import - -#import -#import - -/** - * RCTProfile - * - * This file provides a set of functions and macros for performance profiling - * - * NOTE: This API is a work in progress, please consider carefully before - * using it. - */ - -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wdeprecated" - -RCT_EXTERN __deprecated_msg("This API will be removed along with the legacy architecture.") NSString *const - RCTProfileDidStartProfiling; -RCT_EXTERN __deprecated_msg("This API will be removed along with the legacy architecture.") NSString *const - RCTProfileDidEndProfiling; - -RCT_EXTERN __deprecated_msg("This API will be removed along with the legacy architecture.") const uint64_t - RCTProfileTagAlways; - -#if RCT_PROFILE - -@class RCTBridge; - -#define RCTProfileBeginFlowEvent() \ - _Pragma("clang diagnostic push") _Pragma("clang diagnostic ignored \"-Wshadow\"") NSUInteger __rct_profile_flow_id = \ - _RCTProfileBeginFlowEvent(); \ - _Pragma("clang diagnostic pop") - -#define RCTProfileEndFlowEvent() _RCTProfileEndFlowEvent(__rct_profile_flow_id) - -RCT_EXTERN dispatch_queue_t RCTProfileGetQueue(void) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -RCT_EXTERN NSUInteger _RCTProfileBeginFlowEvent(void) - __deprecated_msg("This API will be removed along with the legacy architecture."); -RCT_EXTERN void _RCTProfileEndFlowEvent(NSUInteger /*cookie*/) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * Returns YES if the profiling information is currently being collected - */ -RCT_EXTERN BOOL RCTProfileIsProfiling(void) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * Start collecting profiling information - */ -RCT_EXTERN void RCTProfileInit(RCTBridge * /*bridge*/) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * Stop profiling and return a JSON string of the collected data - The data - * returned is compliant with google's trace event format - the format used - * as input to trace-viewer - */ -RCT_EXTERN void RCTProfileEnd(RCTBridge * /*bridge*/, void (^/*callback*/)(NSString *)) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * Route the RCT_PROFILE_BEGIN_EVENT hooks to our loom tracing. - */ -#ifdef WITH_LOOM_TRACE -RCT_EXTERN BOOL _RCTLoomIsProfiling(void); -RCT_EXTERN void -_RCTLoomBeginEvent(NSString *name, const char *file, size_t line, NSDictionary *args); -RCT_EXTERN void _RCTLoomEndEvent(); -#else -#define _RCTLoomIsProfiling(...) NO -#define _RCTLoomBeginEvent(...) -#define _RCTLoomEndEvent(...) -#endif - -/** - * Collects the initial event information for the event and returns a reference ID - */ -RCT_EXTERN void _RCTProfileBeginEvent( - NSThread *calleeThread, - NSTimeInterval time, - uint64_t tag, - NSString *name, - NSDictionary *args) - __deprecated_msg("This API will be removed along with the legacy architecture."); -#define RCT_PROFILE_BEGIN_EVENT(tag, name, args) \ - do { \ - if (_RCTLoomIsProfiling()) { \ - _RCTLoomBeginEvent(name, __FILE__, __LINE__, args); \ - } \ - if (RCTProfileIsProfiling()) { \ - NSThread *__calleeThread = [NSThread currentThread]; \ - NSTimeInterval __time = CACurrentMediaTime(); \ - _RCTProfileBeginEvent(__calleeThread, __time, tag, name, args); \ - } \ - } while (0) - -/** - * The ID returned by BeginEvent should then be passed into EndEvent, with the - * rest of the event information. Just at this point the event will actually be - * registered - */ -RCT_EXTERN void -_RCTProfileEndEvent(NSThread *calleeThread, NSString *threadName, NSTimeInterval time, uint64_t tag, NSString *category) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -#define RCT_PROFILE_END_EVENT(tag, category) \ - do { \ - if (_RCTLoomIsProfiling()) { \ - _RCTLoomEndEvent(); \ - } \ - if (RCTProfileIsProfiling()) { \ - NSThread *__calleeThread = [NSThread currentThread]; \ - NSString *__threadName = RCTCurrentThreadName(); \ - NSTimeInterval __time = CACurrentMediaTime(); \ - _RCTProfileEndEvent(__calleeThread, __threadName, __time, tag, category); \ - } \ - } while (0) - -/** - * Collects the initial event information for the event and returns a reference ID - */ -RCT_EXTERN NSUInteger -RCTProfileBeginAsyncEvent(uint64_t tag, NSString *name, NSDictionary *args) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * The ID returned by BeginEvent should then be passed into EndEvent, with the - * rest of the event information. Just at this point the event will actually be - * registered - */ -RCT_EXTERN void -RCTProfileEndAsyncEvent(uint64_t tag, NSString *category, NSUInteger cookie, NSString *name, NSString *threadName) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * An event that doesn't have a duration (i.e. Notification, VSync, etc) - */ -RCT_EXTERN void RCTProfileImmediateEvent(uint64_t tag, NSString *name, NSTimeInterval time, char scope) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * Helper to profile the duration of the execution of a block. This method uses - * self and _cmd to name this event for simplicity sake. - * - * NOTE: The block can't expect any argument - * - * DEPRECATED: this approach breaks debugging and stepping through instrumented block functions - */ -#define RCTProfileBlock(block, tag, category, arguments) \ - ^{ \ - RCT_PROFILE_BEGIN_EVENT(tag, @(__PRETTY_FUNCTION__), nil); \ - block(); \ - RCT_PROFILE_END_EVENT(tag, category, arguments); \ - } - -/** - * Hook into a bridge instance to log all bridge module's method calls - */ -RCT_EXTERN void RCTProfileHookModules(RCTBridge * /*bridge*/) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * Unhook from a given bridge instance's modules - */ -RCT_EXTERN void RCTProfileUnhookModules(RCTBridge * /*bridge*/) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * Hook into all of a module's methods - */ -RCT_EXTERN void RCTProfileHookInstance(id instance) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * Send systrace or cpu profiling information to the packager - * to present to the user - */ -RCT_EXTERN void RCTProfileSendResult(RCTBridge *bridge, NSString *route, NSData *profileData) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * Systrace gluecode - * - * allow to use systrace to back RCTProfile - */ - -typedef struct { - const char *key; - unsigned long key_len; - const char *value; - unsigned long value_len; -} systrace_arg_t __deprecated_msg("This API will be removed along with the legacy architecture."); - -typedef struct { - char *(*start)(void); - void (*stop)(void); - - void (*begin_section)(uint64_t tag, const char *name, size_t numArgs, systrace_arg_t *args); - void (*end_section)(uint64_t tag, size_t numArgs, systrace_arg_t *args); - - void (*begin_async_section)(uint64_t tag, const char *name, int cookie, size_t numArgs, systrace_arg_t *args); - void (*end_async_section)(uint64_t tag, const char *name, int cookie, size_t numArgs, systrace_arg_t *args); - - void (*instant_section)(uint64_t tag, const char *name, char scope); - - void (*begin_async_flow)(uint64_t tag, const char *name, int cookie); - void (*end_async_flow)(uint64_t tag, const char *name, int cookie); -} RCTProfileCallbacks __deprecated_msg("This API will be removed along with the legacy architecture."); - -RCT_EXTERN void RCTProfileRegisterCallbacks(RCTProfileCallbacks * /*cb*/) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -/** - * Systrace control window - */ -RCT_EXTERN void RCTProfileShowControls(void) - __deprecated_msg("This API will be removed along with the legacy architecture."); -RCT_EXTERN void RCTProfileHideControls(void) - __deprecated_msg("This API will be removed along with the legacy architecture."); - -#else - -#define RCTProfileBeginFlowEvent() -#define _RCTProfileBeginFlowEvent() @0 - -#define RCTProfileEndFlowEvent() -#define _RCTProfileEndFlowEvent(...) - -#define RCTProfileIsProfiling(...) NO -#define RCTProfileInit(...) -#define RCTProfileEnd(...) @"" - -#define _RCTProfileBeginEvent(...) -#define _RCTProfileEndEvent(...) - -#define RCT_PROFILE_BEGIN_EVENT(...) -#define RCT_PROFILE_END_EVENT(...) - -#define RCTProfileBeginAsyncEvent(...) 0 -#define RCTProfileEndAsyncEvent(...) - -#define RCTProfileImmediateEvent(...) - -#define RCTProfileBlock(block, ...) block - -#define RCTProfileHookModules(...) -#define RCTProfileHookInstance(...) -#define RCTProfileUnhookModules(...) - -#define RCTProfileSendResult(...) - -#define RCTProfileShowControls(...) -#define RCTProfileHideControls(...) - -#endif - -#pragma clang diagnostic pop diff --git a/packages/react-native/React/Profiler/RCTProfile.m b/packages/react-native/React/Profiler/RCTProfile.m deleted file mode 100644 index 47e2c86ac6f3..000000000000 --- a/packages/react-native/React/Profiler/RCTProfile.m +++ /dev/null @@ -1,811 +0,0 @@ -/* - * Copyright (c) Meta Platforms, Inc. and affiliates. - * - * This source code is licensed under the MIT license found in the - * LICENSE file in the root directory of this source tree. - */ - -#import "RCTProfile.h" - -#import -#import -#import -#import -#import - -#import -#import - -#import "RCTAssert.h" -#import "RCTBridge+Private.h" -#import "RCTBridge.h" -#import "RCTComponentData.h" -#import "RCTLog.h" -#import "RCTModuleData.h" -#import "RCTReloadCommand.h" -#import "RCTUIManager.h" -#import "RCTUIManagerUtils.h" -#import "RCTUtils.h" - -NSString *const RCTProfileDidStartProfiling = @"RCTProfileDidStartProfiling"; -NSString *const RCTProfileDidEndProfiling = @"RCTProfileDidEndProfiling"; - -const uint64_t RCTProfileTagAlways = 1L << 0; - -#if RCT_PROFILE - -#pragma mark - Constants - -static NSString *const kProfileTraceEvents = @"traceEvents"; -static NSString *const kProfileSamples = @"samples"; -static NSString *const kProfilePrefix = @"rct_profile_"; - -#pragma mark - Variables - -static atomic_bool RCTProfileProfiling = NO; - -static NSDictionary *RCTProfileInfo; -static NSMutableDictionary *RCTProfileOngoingEvents; -static NSTimeInterval RCTProfileStartTime; -static NSUInteger RCTProfileEventID = 0; -static CADisplayLink *RCTProfileDisplayLink; -static __weak RCTBridge *_RCTProfilingBridge; -static UIWindow *RCTProfileControlsWindow; - -#pragma mark - Macros - -#define RCTProfileAddEvent(type, props...) \ - [RCTProfileInfo[type] addObject:@{@"pid" : @([[NSProcessInfo processInfo] processIdentifier]), props}]; - -#define CHECK(...) \ - if (!RCTProfileIsProfiling()) { \ - return __VA_ARGS__; \ - } - -#pragma mark - systrace glue code - -static RCTProfileCallbacks *callbacks; -static char *systrace_buffer; - -static systrace_arg_t *newSystraceArgsFromDictionary(NSDictionary *args) -{ - if (args.count == 0) { - return NULL; - } - - systrace_arg_t *systrace_args = malloc(sizeof(systrace_arg_t) * args.count); - if (systrace_args) { - __block size_t i = 0; - [args enumerateKeysAndObjectsUsingBlock:^(NSString *key, NSString *value, __unused BOOL *stop) { - systrace_args[i].key = [key UTF8String]; - systrace_args[i].key_len = [key length]; - systrace_args[i].value = [value UTF8String]; - systrace_args[i].value_len = [value length]; - i++; - }]; - } - return systrace_args; -} - -void RCTProfileRegisterCallbacks(RCTProfileCallbacks *cb) -{ - callbacks = cb; -} - -#pragma mark - Private Helpers - -static RCTBridge *RCTProfilingBridge(void) -{ - return _RCTProfilingBridge ?: [RCTBridge currentBridge]; -} - -static NSNumber *RCTProfileTimestamp(NSTimeInterval timestamp) -{ - return @((timestamp - RCTProfileStartTime) * 1e6); -} - -static NSString *RCTProfileMemory(vm_size_t memory) -{ - double mem = ((double)memory) / 1024 / 1024; - return [NSString stringWithFormat:@"%.2lfmb", mem]; -} - -static NSDictionary *RCTProfileGetMemoryUsage(void) -{ - struct task_basic_info info; - mach_msg_type_number_t size = sizeof(info); - kern_return_t kerr = task_info(mach_task_self(), TASK_BASIC_INFO, (task_info_t)&info, &size); - if (kerr == KERN_SUCCESS) { - return @{ - @"suspend_count" : @(info.suspend_count), - @"virtual_size" : RCTProfileMemory(info.virtual_size), - @"resident_size" : RCTProfileMemory(info.resident_size), - }; - } else { - return @{}; - } -} - -#pragma mark - Module hooks - -static const char *RCTProfileProxyClassName(Class class) -{ - return [kProfilePrefix stringByAppendingString:NSStringFromClass(class)].UTF8String; -} - -static dispatch_group_t RCTProfileGetUnhookGroup(void) -{ - static dispatch_group_t unhookGroup; - static dispatch_once_t onceToken; - dispatch_once(&onceToken, ^{ - unhookGroup = dispatch_group_create(); - }); - - return unhookGroup; -} - -// Used by RCTProfileTrampoline assembly file to call libc`malloc -RCT_EXTERN void *RCTProfileMalloc(size_t size); -void *RCTProfileMalloc(size_t size) -{ - return malloc(size); -} - -// Used by RCTProfileTrampoline assembly file to call libc`free -RCT_EXTERN void RCTProfileFree(void *buf); -void RCTProfileFree(void *buf) -{ - free(buf); -} - -RCT_EXTERN IMP RCTProfileGetImplementation(id obj, SEL cmd); -IMP RCTProfileGetImplementation(id obj, SEL cmd) -{ - return class_getMethodImplementation([obj class], cmd); -} - -/** - * For the profiling we have to execute some code before and after every - * function being profiled, the only way of doing that with pure Objective-C is - * by using `-forwardInvocation:`, which is slow and could skew the profile - * results. - * - * The alternative in assembly is much simpler, we just need to store all the - * state at the beginning of the function, start the profiler, restore all the - * state, call the actual function we want to profile and stop the profiler. - * - * The implementation can be found in RCTProfileTrampoline-.s where arch - * is one of: i386, x86_64, arm, arm64. - */ -#if defined(__i386__) || defined(__x86_64__) || defined(__arm__) || defined(__arm64__) - -RCT_EXTERN void RCTProfileTrampoline(void); -#else -static void *RCTProfileTrampoline = NULL; -#endif - -RCT_EXTERN void RCTProfileTrampolineStart(id /*self*/, SEL /*cmd*/); -void RCTProfileTrampolineStart(id self, SEL cmd) -{ - /** - * This call might be during dealloc, so we shouldn't retain the object in the - * block. - */ - Class klass = [self class]; - RCT_PROFILE_BEGIN_EVENT( - RCTProfileTagAlways, ([NSString stringWithFormat:@"-[%s %s]", class_getName(klass), sel_getName(cmd)]), nil); -} - -RCT_EXTERN void RCTProfileTrampolineEnd(void); -void RCTProfileTrampolineEnd(void) -{ - RCT_PROFILE_END_EVENT(RCTProfileTagAlways, @"objc_call,modules,auto"); -} - -static UIView *(*originalCreateView)(RCTComponentData *, SEL, NSNumber *, NSNumber *); -static UIView *RCTProfileCreateView(RCTComponentData *self, SEL _cmd, NSNumber *tag, NSNumber *rootTag) -{ - UIView *view = originalCreateView(self, _cmd, tag, rootTag); - RCTProfileHookInstance(view); - return view; -} - -static void RCTProfileHookUIManager(RCTUIManager *uiManager) -{ - dispatch_async(dispatch_get_main_queue(), ^{ - for (id view in [uiManager valueForKey:@"viewRegistry"]) { - RCTProfileHookInstance([uiManager viewForReactTag:view]); - } - - Method createView = class_getInstanceMethod([RCTComponentData class], @selector(createViewWithTag:rootTag:)); - - if (method_getImplementation(createView) != (IMP)RCTProfileCreateView) { - originalCreateView = (typeof(originalCreateView))method_getImplementation(createView); - method_setImplementation(createView, (IMP)RCTProfileCreateView); - } - }); -} - -void RCTProfileHookInstance(id instance) -{ - Class moduleClass = object_getClass(instance); - - /** - * We swizzle the instance -class method to return the original class, but - * object_getClass will return the actual class. - * - * If they are different, it means that the object is returning the original - * class, but it's actual class is the proxy subclass we created. - */ - if ([instance class] != moduleClass) { - return; - } - - Class proxyClass = objc_allocateClassPair(moduleClass, RCTProfileProxyClassName(moduleClass), 0); - - if (!proxyClass) { - proxyClass = objc_getClass(RCTProfileProxyClassName(moduleClass)); - if (proxyClass) { - object_setClass(instance, proxyClass); - } - return; - } - - unsigned int methodCount; - Method *methods = class_copyMethodList(moduleClass, &methodCount); - for (NSUInteger i = 0; i < methodCount; i++) { - Method method = methods[i]; - SEL selector = method_getName(method); - - /** - * Bail out on struct returns (except arm64) - we don't use it enough - * to justify writing a stret version - */ -#ifdef __arm64__ - BOOL returnsStruct = NO; -#else - const char *typeEncoding = method_getTypeEncoding(method); - // bail out on structs and unions (since they might contain structs) - BOOL returnsStruct = typeEncoding[0] == '{' || typeEncoding[0] == '('; -#endif - - /** - * Avoid hooking into NSObject methods, methods generated by React Native - * and special methods that start `.` (e.g. .cxx_destruct) - */ - if ([NSStringFromSelector(selector) hasPrefix:@"rct"] || [NSObject instancesRespondToSelector:selector] || - sel_getName(selector)[0] == '.' || returnsStruct) { - continue; - } - - const char *types = method_getTypeEncoding(method); - class_addMethod(proxyClass, selector, (IMP)RCTProfileTrampoline, types); - } - free(methods); - - class_replaceMethod( - object_getClass(proxyClass), - @selector(initialize), - imp_implementationWithBlock(^{ - }), - "v@:"); - - for (Class cls in @[ proxyClass, object_getClass(proxyClass) ]) { - Method oldImp = class_getInstanceMethod(cls, @selector(class)); - class_replaceMethod( - cls, - @selector(class), - imp_implementationWithBlock(^{ - return moduleClass; - }), - method_getTypeEncoding(oldImp)); - } - - objc_registerClassPair(proxyClass); - object_setClass(instance, proxyClass); - - if (moduleClass == [RCTUIManager class]) { - RCTProfileHookUIManager((RCTUIManager *)instance); - } -} - -void RCTProfileHookModules(RCTBridge *bridge) -{ - _RCTProfilingBridge = bridge; - -#pragma clang diagnostic push -#pragma clang diagnostic ignored "-Wtautological-pointer-compare" -#pragma clang diagnostic ignored "-Wunreachable-code-return" - if (RCTProfileTrampoline == NULL) { - return; - } -#pragma clang diagnostic pop - - RCT_PROFILE_BEGIN_EVENT(RCTProfileTagAlways, @"RCTProfileHookModules", nil); - for (RCTModuleData *moduleData in [bridge valueForKey:@"moduleDataByID"]) { - // Only hook modules with an instance, to prevent initializing everything - if ([moduleData hasInstance]) { - [bridge - dispatchBlock:^{ - RCTProfileHookInstance(moduleData.instance); - } - queue:moduleData.methodQueue]; - } - } - RCT_PROFILE_END_EVENT(RCTProfileTagAlways, @""); -} - -static void RCTProfileUnhookInstance(id instance) -{ - if ([instance class] != object_getClass(instance)) { - object_setClass(instance, [instance class]); - } -} - -void RCTProfileUnhookModules(RCTBridge *bridge) -{ - _RCTProfilingBridge = nil; - - dispatch_group_enter(RCTProfileGetUnhookGroup()); - - NSDictionary *moduleDataByID = [bridge valueForKey:@"moduleDataByID"]; - for (RCTModuleData *moduleData in moduleDataByID) { - if ([moduleData hasInstance]) { - RCTProfileUnhookInstance(moduleData.instance); - } - } - - if ([bridge moduleIsInitialized:[RCTUIManager class]]) { - dispatch_async(dispatch_get_main_queue(), ^{ - for (id view in [bridge.uiManager valueForKey:@"viewRegistry"]) { - RCTProfileUnhookInstance([bridge.uiManager viewForReactTag:view]); - } - - dispatch_group_leave(RCTProfileGetUnhookGroup()); - }); - } -} - -#pragma mark - Private ObjC class only used for the vSYNC CADisplayLink target - -@interface RCTProfile : NSObject -@end - -@implementation RCTProfile - -+ (void)vsync:(CADisplayLink *)displayLink -{ - RCTProfileImmediateEvent(RCTProfileTagAlways, @"VSYNC", displayLink.timestamp, 'g'); -} - -+ (void)reload -{ - RCTTriggerReloadCommandListeners(@"Profiling controls"); -} - -+ (void)toggle:(UIButton *)target -{ - BOOL isProfiling = RCTProfileIsProfiling(); - - // Start and Stop are switched here, since we're going to toggle isProfiling - [target setTitle:isProfiling ? @"Start" : @"Stop" forState:UIControlStateNormal]; - - if (isProfiling) { - RCTProfileEnd(RCTProfilingBridge(), ^(NSString *result) { - NSString *outFile = [NSTemporaryDirectory() stringByAppendingString:@"tmp_trace.json"]; - [result writeToFile:outFile atomically:YES encoding:NSUTF8StringEncoding error:nil]; -#if !TARGET_OS_TV - UIActivityViewController *activityViewController = - [[UIActivityViewController alloc] initWithActivityItems:@[ [NSURL fileURLWithPath:outFile] ] - applicationActivities:nil]; - activityViewController.completionWithItemsHandler = - ^(__unused UIActivityType activityType, - __unused BOOL completed, - __unused NSArray *items, - __unused NSError *error) { - RCTProfileControlsWindow.hidden = NO; - }; - RCTProfileControlsWindow.hidden = YES; - dispatch_async(dispatch_get_main_queue(), ^{ - [[RCTKeyWindow() rootViewController] presentViewController:activityViewController animated:YES completion:nil]; - }); -#else - RCTProfileControlsWindow.hidden = NO; -#endif - }); - } else { - RCTProfileInit(RCTProfilingBridge()); - } -} - -+ (void)drag:(UIPanGestureRecognizer *)gestureRecognizer -{ - CGPoint translation = [gestureRecognizer translationInView:RCTProfileControlsWindow]; - RCTProfileControlsWindow.center = - CGPointMake(RCTProfileControlsWindow.center.x + translation.x, RCTProfileControlsWindow.center.y + translation.y); - [gestureRecognizer setTranslation:CGPointMake(0, 0) inView:RCTProfileControlsWindow]; -} - -@end - -#pragma mark - Public Functions - -dispatch_queue_t RCTProfileGetQueue(void) -{ - static dispatch_queue_t queue; - static dispatch_once_t onceToken; - dispatch_once(&onceToken, ^{ - queue = dispatch_queue_create("com.facebook.react.Profiler", DISPATCH_QUEUE_SERIAL); - }); - return queue; -} - -BOOL RCTProfileIsProfiling(void) -{ - return atomic_load(&RCTProfileProfiling); -} - -void RCTProfileInit(RCTBridge *bridge) -{ - // TODO: enable assert JS thread from any file (and assert here) - BOOL wasProfiling = atomic_fetch_or(&RCTProfileProfiling, 1); - if (wasProfiling) { - return; - } - - if (callbacks != NULL) { - systrace_buffer = callbacks->start(); - } else { - NSTimeInterval time = CACurrentMediaTime(); - dispatch_async(RCTProfileGetQueue(), ^{ - RCTProfileStartTime = time; - RCTProfileOngoingEvents = [NSMutableDictionary new]; - RCTProfileInfo = @{ - kProfileTraceEvents : [NSMutableArray new], - kProfileSamples : [NSMutableArray new], - }; - }); - } - - // Set up thread ordering - dispatch_async(RCTProfileGetQueue(), ^{ - NSArray *orderedThreads = - @[ @"JS async", @"RCTPerformanceLogger", @"com.facebook.react.JavaScript", @(RCTUIManagerQueueName), @"main" ]; - [orderedThreads enumerateObjectsUsingBlock:^(NSString *thread, NSUInteger idx, __unused BOOL *stop) { - RCTProfileAddEvent( - kProfileTraceEvents, - @"ph" : @"M", // metadata event - @"name" : @"thread_sort_index", - @"tid" : thread, - @"args" : - @{@"sort_index" : @(-1000 + (NSInteger)idx)}); - }]; - }); - - RCTProfileHookModules(bridge); - - RCTProfileDisplayLink = [CADisplayLink displayLinkWithTarget:[RCTProfile class] selector:@selector(vsync:)]; - [RCTProfileDisplayLink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes]; - - [[NSNotificationCenter defaultCenter] postNotificationName:RCTProfileDidStartProfiling object:bridge]; -} - -void RCTProfileEnd(RCTBridge *bridge, void (^callback)(NSString *)) -{ - // assert JavaScript thread here again - BOOL wasProfiling = atomic_fetch_and(&RCTProfileProfiling, 0); - if (!wasProfiling) { - return; - } - - [[NSNotificationCenter defaultCenter] postNotificationName:RCTProfileDidEndProfiling object:bridge]; - - [RCTProfileDisplayLink invalidate]; - RCTProfileDisplayLink = nil; - - RCTProfileUnhookModules(bridge); - - if (callbacks != NULL) { - if (systrace_buffer) { - callbacks->stop(); - callback(@(systrace_buffer)); - } - } else { - dispatch_async(RCTProfileGetQueue(), ^{ - NSString *log = RCTJSONStringify(RCTProfileInfo, NULL); - RCTProfileEventID = 0; - RCTProfileInfo = nil; - RCTProfileOngoingEvents = nil; - - callback(log); - }); - } -} - -static NSMutableArray *RCTProfileGetThreadEvents(NSThread *thread) -{ - static NSString *const RCTProfileThreadEventsKey = @"RCTProfileThreadEventsKey"; - NSMutableArray *threadEvents = thread.threadDictionary[RCTProfileThreadEventsKey]; - if (!threadEvents) { - threadEvents = [NSMutableArray new]; - thread.threadDictionary[RCTProfileThreadEventsKey] = threadEvents; - } - return threadEvents; -} - -void _RCTProfileBeginEvent( - NSThread *calleeThread, - NSTimeInterval time, - uint64_t tag, - NSString *name, - NSDictionary *args) -{ - CHECK(); - - if (callbacks != NULL) { - systrace_arg_t *systraceArgs = newSystraceArgsFromDictionary(args); - callbacks->begin_section(tag, name.UTF8String, args.count, systraceArgs); - free(systraceArgs); - return; - } - - dispatch_async(RCTProfileGetQueue(), ^{ - NSMutableArray *events = RCTProfileGetThreadEvents(calleeThread); - [events addObject:@[ - RCTProfileTimestamp(time), - name, - RCTNullIfNil(args), - ]]; - }); -} - -void _RCTProfileEndEvent( - NSThread *calleeThread, - NSString *threadName, - NSTimeInterval time, - uint64_t tag, - NSString *category) -{ - CHECK(); - - if (callbacks != NULL) { - callbacks->end_section(tag, 0, nil); - return; - } - - dispatch_async(RCTProfileGetQueue(), ^{ - NSMutableArray *events = RCTProfileGetThreadEvents(calleeThread); - NSArray *event = events.lastObject; - [events removeLastObject]; - - if (!event) { - return; - } - - NSNumber *start = event[0]; - RCTProfileAddEvent( - kProfileTraceEvents, - @"tid" : threadName, - @"name" : event[1], - @"cat" : category, - @"ph" : @"X", - @"ts" : start, - @"dur" : @(RCTProfileTimestamp(time).doubleValue - start.doubleValue), - @"args" : event[2], ); - }); -} - -NSUInteger RCTProfileBeginAsyncEvent(uint64_t tag, NSString *name, NSDictionary *args) -{ - CHECK(0); - - static NSUInteger eventID = 0; - - NSTimeInterval time = CACurrentMediaTime(); - NSUInteger currentEventID = ++eventID; - - if (callbacks != NULL) { - systrace_arg_t *systraceArgs = newSystraceArgsFromDictionary(args); - callbacks->begin_async_section(tag, name.UTF8String, (int)(currentEventID % INT_MAX), args.count, systraceArgs); - free(systraceArgs); - } else { - dispatch_async(RCTProfileGetQueue(), ^{ - RCTProfileOngoingEvents[@(currentEventID)] = @[ - RCTProfileTimestamp(time), - name, - RCTNullIfNil(args), - ]; - }); - } - - return currentEventID; -} - -void RCTProfileEndAsyncEvent(uint64_t tag, NSString *category, NSUInteger cookie, NSString *name, NSString *threadName) -{ - CHECK(); - - if (callbacks != NULL) { - callbacks->end_async_section(tag, name.UTF8String, (int)(cookie % INT_MAX), 0, nil); - return; - } - - NSTimeInterval time = CACurrentMediaTime(); - - dispatch_async(RCTProfileGetQueue(), ^{ - NSArray *event = RCTProfileOngoingEvents[@(cookie)]; - - if (event) { - NSNumber *endTimestamp = RCTProfileTimestamp(time); - - RCTProfileAddEvent( - kProfileTraceEvents, - @"tid" : threadName, - @"name" : event[1], - @"cat" : category, - @"ph" : @"X", - @"ts" : event[0], - @"dur" : @(endTimestamp.doubleValue - [event[0] doubleValue]), - @"args" : event[2], ); - [RCTProfileOngoingEvents removeObjectForKey:@(cookie)]; - } - }); -} - -void RCTProfileImmediateEvent(uint64_t tag, NSString *name, NSTimeInterval time, char scope) -{ - CHECK(); - - if (callbacks != NULL) { - callbacks->instant_section(tag, name.UTF8String, scope); - return; - } - - NSString *threadName = RCTCurrentThreadName(); - - dispatch_async(RCTProfileGetQueue(), ^{ - RCTProfileAddEvent( - kProfileTraceEvents, - @"tid" : threadName, - @"name" : name, - @"ts" : RCTProfileTimestamp(time), - @"scope" : @(scope), - @"ph" : @"i", - @"args" : RCTProfileGetMemoryUsage(), ); - }); -} - -NSUInteger _RCTProfileBeginFlowEvent(void) -{ - static NSUInteger flowID = 0; - - CHECK(0); - - NSUInteger cookie = ++flowID; - if (callbacks != NULL) { - callbacks->begin_async_flow(1, "flow", (int)cookie); - return cookie; - } - - NSTimeInterval time = CACurrentMediaTime(); - NSString *threadName = RCTCurrentThreadName(); - - dispatch_async(RCTProfileGetQueue(), ^{ - RCTProfileAddEvent( - kProfileTraceEvents, - @"tid" : threadName, - @"name" : @"flow", - @"id" : @(cookie), - @"cat" : @"flow", - @"ph" : @"s", - @"ts" : RCTProfileTimestamp(time), ); - }); - - return cookie; -} - -void _RCTProfileEndFlowEvent(NSUInteger cookie) -{ - CHECK(); - - if (callbacks != NULL) { - callbacks->end_async_flow(1, "flow", (int)cookie); - return; - } - - NSTimeInterval time = CACurrentMediaTime(); - NSString *threadName = RCTCurrentThreadName(); - - dispatch_async(RCTProfileGetQueue(), ^{ - RCTProfileAddEvent( - kProfileTraceEvents, - @"tid" : threadName, - @"name" : @"flow", - @"id" : @(cookie), - @"cat" : @"flow", - @"ph" : @"f", - @"ts" : RCTProfileTimestamp(time), ); - }); -} - -void RCTProfileSendResult(RCTBridge *bridge, NSString *route, NSData *data) -{ - if (![bridge.bundleURL.scheme hasPrefix:@"http"]) { - RCTLogWarn( - @"Cannot upload profile information because you're not connected to the packager. The profiling data is still saved in the app container."); - return; - } - - NSURL *URL = [NSURL URLWithString:[@"/" stringByAppendingString:route] relativeToURL:bridge.bundleURL]; - - NSMutableURLRequest *URLRequest = [NSMutableURLRequest requestWithURL:URL]; - URLRequest.HTTPMethod = @"POST"; - [URLRequest setValue:@"application/json" forHTTPHeaderField:@"Content-Type"]; - - NSURLSessionTask *task = [[NSURLSession sharedSession] - uploadTaskWithRequest:URLRequest - fromData:data - completionHandler:^(NSData *responseData, __unused NSURLResponse *response, NSError *error) { - if (error) { - RCTLogError(@"%@", error.localizedDescription); - } else { - NSString *message = [[NSString alloc] initWithData:responseData encoding:NSUTF8StringEncoding]; - - if (message.length) { - dispatch_async(dispatch_get_main_queue(), ^{ - UIAlertController *alertController = - [UIAlertController alertControllerWithTitle:@"Profile" - message:message - preferredStyle:UIAlertControllerStyleAlert]; - [alertController addAction:[UIAlertAction actionWithTitle:@"OK" - style:UIAlertActionStyleCancel - handler:nil]]; - [RCTPresentedViewController() presentViewController:alertController animated:YES completion:nil]; - }); - } - } - }]; - - [task resume]; -} - -void RCTProfileShowControls(void) -{ - static const CGFloat height = 30; - static const CGFloat width = 60; - - UIWindow *window = [[UIWindow alloc] initWithFrame:CGRectMake(20, 80, width * 2, height)]; - window.windowLevel = UIWindowLevelAlert + 1000; - window.hidden = NO; - window.backgroundColor = [UIColor lightGrayColor]; - window.layer.borderColor = [UIColor grayColor].CGColor; - window.layer.borderWidth = 1; - window.alpha = 0.8; - - UIButton *startOrStop = [[UIButton alloc] initWithFrame:CGRectMake(0, 0, width, height)]; - [startOrStop setTitle:RCTProfileIsProfiling() ? @"Stop" : @"Start" forState:UIControlStateNormal]; - [startOrStop addTarget:[RCTProfile class] action:@selector(toggle:) forControlEvents:UIControlEventTouchUpInside]; - startOrStop.titleLabel.font = [UIFont systemFontOfSize:12]; - - UIButton *reload = [[UIButton alloc] initWithFrame:CGRectMake(width, 0, width, height)]; - [reload setTitle:@"Reload" forState:UIControlStateNormal]; - [reload addTarget:[RCTProfile class] action:@selector(reload) forControlEvents:UIControlEventTouchUpInside]; - reload.titleLabel.font = [UIFont systemFontOfSize:12]; - - [window addSubview:startOrStop]; - [window addSubview:reload]; - - UIPanGestureRecognizer *gestureRecognizer = [[UIPanGestureRecognizer alloc] initWithTarget:[RCTProfile class] - action:@selector(drag:)]; - [window addGestureRecognizer:gestureRecognizer]; - - RCTProfileControlsWindow = window; -} - -void RCTProfileHideControls(void) -{ - RCTProfileControlsWindow.hidden = YES; - RCTProfileControlsWindow = nil; -} - -#endif diff --git a/packages/react-native/React/Profiler/RCTProfileTrampoline-arm.S b/packages/react-native/React/Profiler/RCTProfileTrampoline-arm.S deleted file mode 100644 index c7b8e414c1d0..000000000000 --- a/packages/react-native/React/Profiler/RCTProfileTrampoline-arm.S +++ /dev/null @@ -1,96 +0,0 @@ -/** - * Copyright (c) Meta Platforms, Inc. and affiliates. - * - * This source code is licensed under the MIT license found in the - * LICENSE file in the root directory of this source tree. - */ - -#include -#include "RCTMacros.h" - -#if RCT_PROFILE && defined(__arm__) - - .thumb - .thumb_func - .globl SYMBOL_NAME(RCTProfileTrampoline) -SYMBOL_NAME(RCTProfileTrampoline): - /** - * The explanation here is shorter, refer to the x86_64 implementation to a - * richer explanation - */ - - /** - * Save the parameter registers (r0-r3), r7 (frame pointer) and lr (link - * register (contains the address of the caller of RCTProfileTrampoline) - */ - push {r0-r3, r7, lr} - - /** - * Allocate memory to store values across function calls: 12-bytes are - * allocated to store 3 values: the previous value of the callee saved - * register used to save the pointer to the allocated memory, the caller of - * RCTProfileTrampoline and the address of the actual function we want to - * profile - */ - mov r0, #0xc - bl SYMBOL_NAME(RCTProfileMalloc) - /** - * r4 is the callee saved register we'll use to refer to the allocated memory, - * store its initial value, so we can restore it later - */ - str r4, [r0] - mov r4, r0 - - /** - * void RCTProfileGetImplementation(id object, SEL selector) in RCTProfile.m - * - * Load the first 2 argumenters (self and _cmd) used to call - * RCTProfileTrampoline from the stack and put them on the appropriate registers. - */ - ldr r0, [sp] - ldr r1, [sp, #0x4] - bl SYMBOL_NAME(RCTProfileGetImplementation) - // store the actual function address in the allocated memory - str r0, [r4, #0x4] - - /** - * void RCTProfileGetImplementation(id object, SEL selector) in RCTProfile.m - * - * Load the first 2 arguments again to start the profiler - */ - ldr r0, [sp] - ldr r1, [sp, #0x4] - bl SYMBOL_NAME(RCTProfileTrampolineStart) - - /** - * Restore the state to call the actual function we want to profile: pop - * all the registers - */ - pop {r0-r3, r7, lr} - - // store lr (the caller) since it'll be overridden by `blx` (call) - str lr, [r4, #0x8] - ldr r12, [r4, #0x4] // load the function address - blx r12 // call it - push {r0} // save return value - - // void RCTProfileTrampolineEnd(void) in RCTProfile.m - just ends this profile - bl SYMBOL_NAME(RCTProfileTrampolineEnd) - - /** - * Save the value we still need from the allocated memory (caller address), - * restore r4 and free the allocated memory (put its address in r0) - */ - mov r0, r4 - ldr r1, [r4, #0x8] - ldr r4, [r4] - push {r1} // save the caller on the stack - bl SYMBOL_NAME(RCTProfileFree) - - pop {lr} // pop the caller - pop {r0} // pop the return value - bx lr // jump to the caller - - trap - -#endif diff --git a/packages/react-native/React/Profiler/RCTProfileTrampoline-arm64.S b/packages/react-native/React/Profiler/RCTProfileTrampoline-arm64.S deleted file mode 100644 index 1e04fb00801f..000000000000 --- a/packages/react-native/React/Profiler/RCTProfileTrampoline-arm64.S +++ /dev/null @@ -1,125 +0,0 @@ -/** - * Copyright (c) Meta Platforms, Inc. and affiliates. - * - * This source code is licensed under the MIT license found in the - * LICENSE file in the root directory of this source tree. - */ - -#include -#include "RCTMacros.h" - -#if RCT_PROFILE && defined(__arm64__) - - .align 5 - .globl SYMBOL_NAME(RCTProfileTrampoline) -SYMBOL_NAME(RCTProfileTrampoline): - /** - * The explanation here is shorter, refer to the x86_64 implementation to a - * richer explanation - */ - - // Basic prolog: save the frame pointer and the link register (caller address) - stp fp, lr, [sp, #-16]! - mov fp, sp - - /** - * Store the value of all the parameter registers (x0-x8, q0-q7) so we can - * restore everything to the initial state at the time of the actual function - * call - */ - sub sp, sp, #(10*8 + 8*16) - stp q0, q1, [sp, #(0*16)] - stp q2, q3, [sp, #(2*16)] - stp q4, q5, [sp, #(4*16)] - stp q6, q7, [sp, #(6*16)] - stp x0, x1, [sp, #(8*16+0*8)] - stp x2, x3, [sp, #(8*16+2*8)] - stp x4, x5, [sp, #(8*16+4*8)] - stp x6, x7, [sp, #(8*16+6*8)] - str x8, [sp, #(8*16+8*8)] - - /** - * Allocate 16-bytes for the values that have to be preserved across the call - * to the actual function, since the stack has to be in the exact initial - * state. During its lifetime we use it to store the initial value of the - * callee saved registers we use to point the memory, the actual address of - * the implementation and the caller address. - */ - mov x0, #0x10 - bl SYMBOL_NAME(RCTProfileMalloc) - // store the initial value of r19, the callee saved register we'll use - str x19, [x0] - mov x19, x0 - - /** - * void RCTProfileGetImplementation(id object, SEL selector) - * - * Load the 2 first arguments from the stack, they are the same used to call - * this function - */ - ldp x0, x1, [sp, #(8*16+0*8)] - bl SYMBOL_NAME(RCTProfileGetImplementation) - str x0, [x19, #0x8] // store the actual function address - - /** - * void RCTProfileTrampolineStart(id, SEL) in RCTProfile.m - * - * start the profile, it takes the same first 2 arguments as above. - */ - ldp x0, x1, [sp, #(8*16+0*8)] - bl SYMBOL_NAME(RCTProfileTrampolineStart) - - // Restore all the parameter registers to the initial state. - ldp q0, q1, [sp, #(0*16)] - ldp q2, q3, [sp, #(2*16)] - ldp q4, q5, [sp, #(4*16)] - ldp q6, q7, [sp, #(6*16)] - ldp x0, x1, [sp, #(8*16+0*8)] - ldp x2, x3, [sp, #(8*16+2*8)] - ldp x4, x5, [sp, #(8*16+4*8)] - ldp x6, x7, [sp, #(8*16+6*8)] - ldr x8, [sp, #(8*16+8*8)] - - // Restore the stack pointer, frame pointer and link register - mov sp, fp - ldp fp, lr, [sp], #16 - - - ldr x9, [x19, #0x8] // Load the function - str lr, [x19, #0x8] // store the address of the caller - - blr x9 // call the actual function - - /** - * allocate 32-bytes on the stack, for the 2 return values + the caller - * address that has to preserved across the call to `free` - */ - sub sp, sp, #0x20 - str q0, [sp, #0x0] // 16-byte return value - str x0, [sp, #0x10] // 8-byte return value - - // void RCTProfileTrampolineEnd(void) in RCTProfile.m - just ends this profile - bl SYMBOL_NAME(RCTProfileTrampolineEnd) - - /** - * restore the callee saved registers, move the values we still need to the - * stack and free the allocated memory - */ - mov x0, x19 // move the address of the memory to x0, first argument - ldr x10, [x19, #0x8] // load the caller address - ldr x19, [x19] // restore x19 - str x10, [sp, #0x18] // store x10 on the stack space allocated above - bl SYMBOL_NAME(RCTProfileFree) - - // Load both return values and link register from the stack - ldr q0, [sp, #0x0] - ldr x0, [sp, #0x10] - ldr lr, [sp, #0x18] - - // restore the stack pointer - add sp, sp, #0x20 - - // jump to the caller, without a link - br lr - -#endif diff --git a/packages/react-native/React/Profiler/RCTProfileTrampoline-i386.S b/packages/react-native/React/Profiler/RCTProfileTrampoline-i386.S deleted file mode 100644 index 8d3fdce28f7f..000000000000 --- a/packages/react-native/React/Profiler/RCTProfileTrampoline-i386.S +++ /dev/null @@ -1,97 +0,0 @@ -/** - * Copyright (c) Meta Platforms, Inc. and affiliates. - * - * This source code is licensed under the MIT license found in the - * LICENSE file in the root directory of this source tree. - */ - -#include -#include "RCTMacros.h" - -#if RCT_PROFILE && defined(__i386__) - - .globl SYMBOL_NAME(RCTProfileTrampoline) -SYMBOL_NAME(RCTProfileTrampoline): - /** - * The x86 version is much simpler, since all the arguments are passed in the - * stack, so we just have to preserve the stack pointer (%esp) and the callee - * saved register used to keep the memory allocated - * - * The explanation here is also shorter, refer to the x86_64 implementation to - * a richer explanation - */ - - /** - * Allocate memory to save the caller of RCTProfileTrampoline (used afterwards - * to return at the end of the function) and the initial value for the callee - * saved register (%edi) that will be used to point to the memory allocated. - */ - subl $0x8, %esp // stack padding (16-byte alignment for function calls) - pushl $0xc // allocate 12-bytes - calll SYMBOL_NAME(RCTProfileMalloc) - addl $0xc, %esp // restore stack (8-byte padding + 4-byte argument) - - /** - * actually store the values in the memory allocated - */ - movl %edi, 0x0(%eax) // previous value of edi - popl 0x4(%eax) // caller of RCTProfileTrampoline - - // save the pointer to the allocated memory in %edi - movl %eax, %edi - - /** - * void RCTProfileGetImplementation(id object, SEL selector) in RCTProfile.m - * - * Get the address of the actual C function we have to profile - */ - calll SYMBOL_NAME(RCTProfileGetImplementation) - movl %eax, 0x8(%edi) // Save it in the allocated memory - - /** - * void RCTProfileTrampolineStart(id, SEL) in RCTProfile.m - * - * start profile - the arguments are already in the right position in the - * stack since it takes the same first 2 arguments as the any ObjC function - - * "self" and "_cmd" - */ - calll SYMBOL_NAME(RCTProfileTrampolineStart) - - /** - * Call the actual function and save it's return value, since it should be the - * return value of RCTProfileTrampoline - */ - calll *0x8(%edi) - pushl %eax - - // Align stack and end profile - subl $0xc, %esp - calll SYMBOL_NAME(RCTProfileTrampolineEnd) - addl $0xc, %esp // restore the stack - - /** - * Move the values from the allocated memory to the stack, restore the - * value of %edi, and prepare to free the allocated memory. - */ - pushl 0x4(%edi) // caller of RCTProfileTrampoline - subl $0x4, %esp // Stack padding - pushl %edi // push the memory address - movl 0x0(%edi), %edi // restore the value of %edi - - /** - * Actually free the memory used to store the values across function calls, - * the stack has already been padded and the first and only argument, the - * memory address, is already in the bottom of the stack. - */ - calll SYMBOL_NAME(RCTProfileFree) - addl $0x8, %esp - - /** - * pop the caller address to %ecx and the actual function return value to - * %eax, so it's the return value of RCTProfileTrampoline - */ - popl %ecx - popl %eax - jmpl *%ecx - -#endif diff --git a/packages/react-native/React/Profiler/RCTProfileTrampoline-x86_64.S b/packages/react-native/React/Profiler/RCTProfileTrampoline-x86_64.S deleted file mode 100644 index d5bcb50d4e6e..000000000000 --- a/packages/react-native/React/Profiler/RCTProfileTrampoline-x86_64.S +++ /dev/null @@ -1,190 +0,0 @@ -/** - * Copyright (c) Meta Platforms, Inc. and affiliates. - * - * This source code is licensed under the MIT license found in the - * LICENSE file in the root directory of this source tree. - */ - -#include -#include "RCTMacros.h" - -#if RCT_PROFILE && defined(__x86_64__) - - .globl SYMBOL_NAME(RCTProfileTrampoline) -SYMBOL_NAME(RCTProfileTrampoline): - - /** - * Saves all the state so we can restore it before calling the functions being - * profiled. Registers have the same value at the point of the function call, - * the only thing we can change is the return value, so we return to - * `RCTProfileTrampoline` rather than to its caller. - * - * Save all the parameters registers (%rdi, %rsi, %rdx, %rcx, %r8, %r9), they - * have the 6 first arguments of the function call, and %rax which in special - * cases might be a pointer used for struct returns. - * - * We have to save %r12 since its value should be preserved across function - * calls and we'll use it to keep the stack pointer - */ - subq $0x80+8, %rsp // 8 x 16-bytes xmm registers + 8-bytes alignment - movdqa %xmm0, 0x70(%rsp) - movdqa %xmm1, 0x60(%rsp) - movdqa %xmm2, 0x50(%rsp) - movdqa %xmm3, 0x40(%rsp) - movdqa %xmm4, 0x30(%rsp) - movdqa %xmm5, 0x20(%rsp) - movdqa %xmm6, 0x10(%rsp) - movdqa %xmm7, 0x00(%rsp) - pushq %rdi - pushq %rsi - pushq %rdx - pushq %rcx - pushq %r8 - pushq %r9 - pushq %rax - pushq %r12 - - /** - * Store the stack pointer in the callee saved register %r12 and align the - * stack - it has to 16-byte aligned at the point of the function call - */ - movq %rsp, %r12 - andq $-0x10, %rsp - - /** - * void RCTProfileGetImplementation(id object, SEL selector) - * - * This is a C function defined in `RCTProfile.m`, the object and the selector - * already have to be on %rdi and %rsi respectively, as in any ObjC call. - */ - callq SYMBOL_NAME_PIC(RCTProfileGetImplementation) - - // Restore/unalign the stack pointer, so we can access the registers we stored - movq %r12, %rsp - - /** - * pop %r12 before pushing %rax, which contains the address of the actual - * function we have to call, than we keep %r12 at the bottom of the stack to - * reference the stack pointer - */ - popq %r12 - pushq %rax - pushq %r12 - - // align stack - movq %rsp, %r12 - andq $-0x10, %rsp - - /** - * Allocate memory to save parent before start profiling: the address is put - * at the bottom of the stack at the function call, so ret can actually return - * to the caller. In this case it has the address of RCTProfileTrampoline's - * caller where we'll have to return to after we're finished. - * - * We can't store it on the stack or in any register, since we have to be in - * the exact same state we were at the moment we were called, so the solution - * is to allocate a tiny bit of memory to save this address - */ - - // allocate 16 bytes - movq $0x10, %rdi - callq SYMBOL_NAME_PIC(RCTProfileMalloc) - - // store the initial value of caller saved registers %r13 and %r14 - movq %r13, 0x0(%rax) - movq %r14, 0x8(%rax) - - // mov the pointers we need to the callee saved registers - movq 0xd8(%rsp), %r13 // caller of RCTProfileTrampoline (0xd8 is stack top) - movq %rax, %r14 // allocated memory's address - - /** - * Move self and cmd back to the registers and call start profile: it uses - * the object and the selector to label the call in the profile. - */ - movq 0x40(%r12), %rdi // object - movq 0x38(%r12), %rsi // selector - - // void RCTProfileTrampolineStart(id, SEL) in RCTProfile.m - callq SYMBOL_NAME_PIC(RCTProfileTrampolineStart) - - // unalign the stack and restore %r12 - movq %r12, %rsp - popq %r12 - - // Restore registers for actual function call - popq %r11 - popq %rax - popq %r9 - popq %r8 - popq %rcx - popq %rdx - popq %rsi - popq %rdi - movdqa 0x00(%rsp), %xmm7 - movdqa 0x10(%rsp), %xmm6 - movdqa 0x20(%rsp), %xmm5 - movdqa 0x30(%rsp), %xmm4 - movdqa 0x40(%rsp), %xmm3 - movdqa 0x50(%rsp), %xmm2 - movdqa 0x60(%rsp), %xmm1 - movdqa 0x70(%rsp), %xmm0 - addq $0x80+8, %rsp - - /** - * delete parent caller (saved in %r13) `call` will add the new address so - * we return to RCTProfileTrampoline rather than to its caller - */ - addq $0x8, %rsp - - // call the actual function and save the return value - callq *%r11 - pushq %rax - pushq %rdx - subq $0x20, %rsp // 2 16-bytes xmm register - movdqa %xmm0, 0x00(%rsp) - movdqa %xmm1, 0x10(%rsp) - - // void RCTProfileTrampolineEnd(void) in RCTProfile.m - just ends this profile - callq SYMBOL_NAME_PIC(RCTProfileTrampolineEnd) - - /** - * Restore the initial value of the callee saved registers, saved in the - * memory allocated. - */ - movq %r13, %rcx - movq %r14, %rdi - movq 0x0(%r14), %r13 - movq 0x8(%r14), %r14 - - /** - * save caller address and actual function return (previously in the allocated - * memory) and align the stack - */ - pushq %rcx - pushq %r12 - movq %rsp, %r12 - andq $-0x10, %rsp - - // Free the memory allocated to stash callee saved registers - callq SYMBOL_NAME_PIC(RCTProfileFree) - - // unalign stack and restore %r12 - movq %r12, %rsp - popq %r12 - - /** - * pop the caller address to %rcx and the actual function return value(s) - * so it's the return value of RCTProfileTrampoline - */ - popq %rcx - movdqa 0x00(%rsp), %xmm0 - movdqa 0x10(%rsp), %xmm1 - addq $0x20, %rsp - popq %rdx - popq %rax - - // jump to caller - jmpq *%rcx - -#endif diff --git a/packages/react-native/ReactCommon/react/nativemodule/core/platform/ios/ReactCommon/RCTTurboModule.h b/packages/react-native/ReactCommon/react/nativemodule/core/platform/ios/ReactCommon/RCTTurboModule.h index 2050b7bcee89..4e9a4f094bf1 100644 --- a/packages/react-native/ReactCommon/react/nativemodule/core/platform/ios/ReactCommon/RCTTurboModule.h +++ b/packages/react-native/ReactCommon/react/nativemodule/core/platform/ios/ReactCommon/RCTTurboModule.h @@ -200,16 +200,3 @@ class JSI_EXPORT ObjCTurboModule : public TurboModule { @optional - (void)setEventEmitterCallback:(EventEmitterCallbackWrapper *)eventEmitterCallbackWrapper; @end - -/** - * These methods are all implemented by RCTCxxBridge, which subclasses RCTBridge. Hence, they must only be used in - * contexts where the concrete class of an RCTBridge instance is RCTCxxBridge. This happens, for example, when - * [RCTCxxBridgeDelegate jsExecutorFactoryForBridge:(RCTBridge *)] is invoked by RCTCxxBridge. - * - * TODO: Consolidate this extension with the one in RCTSurfacePresenter. - */ -@interface RCTBridge (RCTTurboModule) -- (std::shared_ptr)jsCallInvoker; -- (std::shared_ptr)decorateNativeMethodCallInvoker: - (std::shared_ptr)nativeMethodCallInvoker; -@end diff --git a/packages/react-native/scripts/ios-prebuild/__tests__/setup-test.js b/packages/react-native/scripts/ios-prebuild/__tests__/setup-test.js index a0a66f27721d..ae77c15cbed1 100644 --- a/packages/react-native/scripts/ios-prebuild/__tests__/setup-test.js +++ b/packages/react-native/scripts/ios-prebuild/__tests__/setup-test.js @@ -282,6 +282,18 @@ describe('createHeaderLinker', () => { ]); }); + it('warns and skips a source folder that no longer exists', () => { + const warn = jest.spyOn(console, 'warn').mockImplementation(() => {}); + + expect(() => stage('React/Profiler', 'React')).not.toThrow(); + + expect(warn).toHaveBeenCalledWith( + expect.stringContaining('React/Profiler'), + ); + expect(log).not.toHaveBeenCalled(); + expect(fs.existsSync(staged('React'))).toBe(false); + }); + it.each(['__tests__', 'tests', 'platform'])( 'does not stage headers from a %s subfolder', folder => { diff --git a/packages/react-native/scripts/ios-prebuild/setup.js b/packages/react-native/scripts/ios-prebuild/setup.js index c8d6ef4a5324..84e054e04c96 100644 --- a/packages/react-native/scripts/ios-prebuild/setup.js +++ b/packages/react-native/scripts/ios-prebuild/setup.js @@ -67,7 +67,6 @@ async function setup( link('React/CoreModules', 'React'); link('React/Modules', 'React'); link('React/Fabric', 'React'); - link('React/Profiler', 'React'); link('React/CoreModules', 'React'); link('React/Runtime', 'React'); link('React/Views/ScrollView', 'React'); @@ -186,11 +185,26 @@ function createHeaderLinker( const source = path.resolve(root, fromPath); const target = path.resolve(linksFolder, includePath ?? fromPath); + let entries; + try { + entries = fs.readdirSync(source, {withFileTypes: true}); + } catch (e) { + if (e.code === 'ENOENT') { + // A source folder was deleted without updating the link() list below. + // Warn instead of crashing the whole prebuild (and OSS builds with it). + console.warn( + `Skipping missing source folder ${path.relative(root, source)} ` + + `— remove its link() entry from setup.js if the deletion was intentional.`, + ); + return; + } + throw e; + } + createFolderIfNotExists(target); let linkedFiles = 0; - const entries = fs.readdirSync(source, {withFileTypes: true}); if ( entries.some( dirent => dirent.isFile() && /\.(h|hpp)$/.test(String(dirent.name)), diff --git a/scripts/cxx-api/api-snapshots/ReactAppleDebugCxx.api b/scripts/cxx-api/api-snapshots/ReactAppleDebugCxx.api index 863038207ad0..5a9b3277706e 100644 --- a/scripts/cxx-api/api-snapshots/ReactAppleDebugCxx.api +++ b/scripts/cxx-api/api-snapshots/ReactAppleDebugCxx.api @@ -43,11 +43,6 @@ category RCTBridge(RCTSurfacePresenterStub) { public virtual void setSurfacePresenter:(id presenter); } -category RCTBridge(RCTTurboModule) { - public virtual std::shared_ptr jsCallInvoker(); - public virtual std::shared_ptr decorateNativeMethodCallInvoker:(std::shared_ptr nativeMethodCallInvoker); -} - category RCTBridge(RCTUIManager) { public @property (assign, readonly) RCTUIManager* uiManager; } diff --git a/scripts/cxx-api/api-snapshots/ReactAppleFrameworksCxx.api b/scripts/cxx-api/api-snapshots/ReactAppleFrameworksCxx.api index dece37c06a37..86fa6aceda5b 100644 --- a/scripts/cxx-api/api-snapshots/ReactAppleFrameworksCxx.api +++ b/scripts/cxx-api/api-snapshots/ReactAppleFrameworksCxx.api @@ -43,11 +43,6 @@ category RCTBridge(RCTSurfacePresenterStub) { public virtual void setSurfacePresenter:(id presenter); } -category RCTBridge(RCTTurboModule) { - public virtual std::shared_ptr jsCallInvoker(); - public virtual std::shared_ptr decorateNativeMethodCallInvoker:(std::shared_ptr nativeMethodCallInvoker); -} - category RCTBridge(RCTUIManager) { public @property (assign, readonly) RCTUIManager* uiManager; } diff --git a/scripts/cxx-api/api-snapshots/ReactAppleNewarchCxx.api b/scripts/cxx-api/api-snapshots/ReactAppleNewarchCxx.api index 3e9a7b4744fc..3047aa3a310d 100644 --- a/scripts/cxx-api/api-snapshots/ReactAppleNewarchCxx.api +++ b/scripts/cxx-api/api-snapshots/ReactAppleNewarchCxx.api @@ -43,11 +43,6 @@ category RCTBridge(RCTSurfacePresenterStub) { public virtual void setSurfacePresenter:(id presenter); } -category RCTBridge(RCTTurboModule) { - public virtual std::shared_ptr jsCallInvoker(); - public virtual std::shared_ptr decorateNativeMethodCallInvoker:(std::shared_ptr nativeMethodCallInvoker); -} - category RCTBridge(RCTUIManager) { public @property (assign, readonly) RCTUIManager* uiManager; } diff --git a/scripts/cxx-api/api-snapshots/ReactAppleReleaseCxx.api b/scripts/cxx-api/api-snapshots/ReactAppleReleaseCxx.api index a692b6489f17..1b31bd51a474 100644 --- a/scripts/cxx-api/api-snapshots/ReactAppleReleaseCxx.api +++ b/scripts/cxx-api/api-snapshots/ReactAppleReleaseCxx.api @@ -43,11 +43,6 @@ category RCTBridge(RCTSurfacePresenterStub) { public virtual void setSurfacePresenter:(id presenter); } -category RCTBridge(RCTTurboModule) { - public virtual std::shared_ptr jsCallInvoker(); - public virtual std::shared_ptr decorateNativeMethodCallInvoker:(std::shared_ptr nativeMethodCallInvoker); -} - category RCTBridge(RCTUIManager) { public @property (assign, readonly) RCTUIManager* uiManager; }