diff options
author | Joel Fischer <joeljfischer@gmail.com> | 2020-02-11 10:43:07 -0500 |
---|---|---|
committer | Joel Fischer <joeljfischer@gmail.com> | 2020-02-11 10:43:07 -0500 |
commit | dca61a36fd2a8e45bda5068f648df5cdd7f51784 (patch) | |
tree | fc14d74c142e021fdc6ff0f09b06ff16eaa7e82d | |
parent | 73ad4212bf62d2afdaca13a6b4bbdab5b3242cbf (diff) | |
download | sdl_ios-dca61a36fd2a8e45bda5068f648df5cdd7f51784.tar.gz |
Remove, fix, and rearrange some code
-rw-r--r-- | SmartDeviceLink/SDLLifecycleManager.m | 10 | ||||
-rw-r--r-- | SmartDeviceLink/SDLSecondaryTransportManager.m | 278 |
2 files changed, 142 insertions, 146 deletions
diff --git a/SmartDeviceLink/SDLLifecycleManager.m b/SmartDeviceLink/SDLLifecycleManager.m index dfe18d397..6c571db81 100644 --- a/SmartDeviceLink/SDLLifecycleManager.m +++ b/SmartDeviceLink/SDLLifecycleManager.m @@ -161,7 +161,7 @@ NSString *const BackgroundTaskTransportName = @"com.sdl.transport.backgroundTask // Notifications [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(transportDidConnect) name:SDLTransportDidConnect object:_notificationDispatcher]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(transportDidDisconnect) name:SDLTransportDidDisconnect object:_notificationDispatcher]; - [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(hmiStatusDidChange:) name:SDLDidChangeHMIStatusNotification object: _notificationDispatcher]; + [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(hmiStatusDidChange:) name:SDLDidChangeHMIStatusNotification object:_notificationDispatcher]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(remoteHardwareDidUnregister:) name:SDLDidReceiveAppUnregisteredNotification object:_notificationDispatcher]; _backgroundTaskManager = [[SDLBackgroundTaskManager alloc] initWithBackgroundTaskName: BackgroundTaskTransportName]; @@ -244,13 +244,7 @@ NSString *const BackgroundTaskTransportName = @"com.sdl.transport.backgroundTask } else if (self.configuration.lifecycleConfig.allowedSecondaryTransports == SDLSecondaryTransportsNone) { self.proxy = [SDLProxy iapProxyWithListener:self.notificationDispatcher secondaryTransportManager:nil encryptionLifecycleManager:self.encryptionLifecycleManager]; } else { - if([self.configuration.lifecycleConfig.appType isEqualToEnum:SDLAppHMITypeNavigation] || - [self.configuration.lifecycleConfig.appType isEqualToEnum:SDLAppHMITypeProjection] || - [self.configuration.lifecycleConfig.additionalAppTypes containsObject:SDLAppHMITypeNavigation] || - [self.configuration.lifecycleConfig.additionalAppTypes containsObject:SDLAppHMITypeProjection]) { - // We reuse our queue to run secondary transport manager's state machine - self.secondaryTransportManager = [[SDLSecondaryTransportManager alloc] initWithStreamingProtocolDelegate:self serialQueue:self.lifecycleQueue]; - } + self.secondaryTransportManager = [[SDLSecondaryTransportManager alloc] initWithStreamingProtocolDelegate:self serialQueue:self.lifecycleQueue]; self.proxy = [SDLProxy iapProxyWithListener:self.notificationDispatcher secondaryTransportManager:self.secondaryTransportManager encryptionLifecycleManager:self.encryptionLifecycleManager]; } #pragma clang diagnostic pop diff --git a/SmartDeviceLink/SDLSecondaryTransportManager.m b/SmartDeviceLink/SDLSecondaryTransportManager.m index 3f0fb4a4c..b7e35125c 100644 --- a/SmartDeviceLink/SDLSecondaryTransportManager.m +++ b/SmartDeviceLink/SDLSecondaryTransportManager.m @@ -163,51 +163,76 @@ static const int TCPPortUnspecified = -1; [self.stateMachine transitionToState:SDLSecondaryTransportStateStopped]; } -// called from SDLProtocol's _receiveQueue of "primary" transport -- (void)onStartServiceAckReceived:(SDLControlFramePayloadRPCStartServiceAck *)payload { - NSMutableArray<SDLSecondaryTransportTypeBox *> *secondaryTransports = nil; - if (payload.secondaryTransports != nil) { - secondaryTransports = [NSMutableArray array]; - for (NSString *transportString in payload.secondaryTransports) { - SDLSecondaryTransportType transport = [self sdl_convertTransportType:transportString]; - [secondaryTransports addObject:@(transport)]; - } - } +#pragma mark - Manager Lifecycle - NSArray<SDLTransportClassBox *> *transportsForAudio = [self sdl_convertServiceTransports:payload.audioServiceTransports]; - NSArray<SDLTransportClassBox *> *transportsForVideo = [self sdl_convertServiceTransports:payload.videoServiceTransports]; +- (void)sdl_startManager { + [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(sdl_onAppStateUpdated:) name:UIApplicationDidBecomeActiveNotification object:nil]; + [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(sdl_onAppStateUpdated:) name:UIApplicationWillResignActiveNotification object:nil]; - SDLLogV(@"Secondary transports: %@, transports for audio: %@, transports for video: %@", secondaryTransports, transportsForAudio, transportsForVideo); + [self.primaryProtocolHandler start]; +} - dispatch_async(_stateMachineQueue, ^{ - [self sdl_configureManager:secondaryTransports availableTransportsForAudio:transportsForAudio availableTransportsForVideo:transportsForVideo]; - }); +- (void)sdl_stopManager { + SDLLogD(@"SDLSecondaryTransportManager stop"); + + [[NSNotificationCenter defaultCenter] removeObserver:self name:UIApplicationDidBecomeActiveNotification object:nil]; + [[NSNotificationCenter defaultCenter] removeObserver:self name:UIApplicationWillResignActiveNotification object:nil]; + + [self.primaryProtocolHandler stop]; + + self.streamingServiceTransportMap = [@{@(SDLServiceTypeAudio):@(SDLTransportClassInvalid), + @(SDLServiceTypeVideo):@(SDLTransportClassInvalid)} mutableCopy]; + self.secondaryTransportType = SDLSecondaryTransportTypeDisabled; + self.transportsForAudioService = @[]; + self.transportsForVideoService = @[]; + + self.ipAddress = nil; + self.tcpPort = TCPPortUnspecified; + self.shouldOpenConnection = NO; } -// called from SDLProtocol's _receiveQueue of "primary" transport -- (void)onTransportEventUpdateReceived:(SDLControlFramePayloadTransportEventUpdate *)payload { - dispatch_async(_stateMachineQueue, ^{ - BOOL updated = NO; +- (void)sdl_configureManager:(nullable NSArray<SDLSecondaryTransportTypeBox *> *)availableSecondaryTransports + availableTransportsForAudio:(nullable NSArray<SDLTransportClassBox *> *)availableTransportsForAudio + availableTransportsForVideo:(nullable NSArray<SDLTransportClassBox *> *)availableTransportsForVideo { + if (![self.stateMachine isCurrentState:SDLSecondaryTransportStateStarted]) { + SDLLogW(@"SecondaryTransportManager ignores duplicate Start Service ACK frame"); + return; + } - if (payload.tcpIpAddress != nil) { - if (![self.ipAddress isEqualToString:payload.tcpIpAddress]) { - self.ipAddress = payload.tcpIpAddress; - updated = YES; - SDLLogD(@"TCP transport IP address updated: %@", self.ipAddress); - } - } - if (payload.tcpPort != SDLControlFrameInt32NotFound) { - if (self.tcpPort != payload.tcpPort) { - self.tcpPort = payload.tcpPort; - updated = YES; - SDLLogD(@"TCP transport port number updated: %d", self.tcpPort); - } - } + // default values + self.secondaryTransportType = SDLSecondaryTransportTypeDisabled; + self.transportsForAudioService = @[@(SDLTransportClassPrimary)]; // If SDL Core did not send a transport list for the service, start it on Primary Transport. + self.transportsForVideoService = @[@(SDLTransportClassPrimary)]; + BOOL validConfig = YES; - if (updated) { - [self sdl_handleTransportEventUpdate]; - } - }); + if (availableSecondaryTransports.count > 0) { + // current proposal says the list should contain only one element + SDLSecondaryTransportTypeBox *transportType = availableSecondaryTransports[0]; + self.secondaryTransportType = [transportType integerValue]; + } else { + SDLLogW(@"Did not receive secondary transport type from system. Secondary transport is disabled."); + } + + SDLSecondaryTransportType primaryTransportType = [self sdl_getTransportTypeFromProtocol:self.primaryProtocol]; + if (self.secondaryTransportType == primaryTransportType) { + SDLLogW(@"Same transport is specified for both primary and secondary transport. Secondary transport is disabled."); + self.secondaryTransportType = SDLSecondaryTransportTypeDisabled; + validConfig = NO; // let audio and video services start on primary transport + } else if (self.secondaryTransportType == SDLSecondaryTransportTypeIAP) { + SDLLogW(@"Starting IAP as secondary transport, which does not usually happen"); + } + + if (availableTransportsForAudio != nil && validConfig) { + self.transportsForAudioService = availableTransportsForAudio; + } + if (availableTransportsForVideo != nil && validConfig) { + self.transportsForVideoService = availableTransportsForVideo; + } + + // this will trigger audio / video streaming if they are allowed on primary transport + [self sdl_handleTransportUpdateWithPrimaryAvailable:YES secondaryAvailable:NO]; + + [self.stateMachine transitionToState:SDLSecondaryTransportStateConfigured]; } #pragma mark - State machine @@ -294,105 +319,6 @@ static const int TCPPortUnspecified = -1; }); } -- (void)sdl_startManager { - [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(sdl_onAppStateUpdated:) name:UIApplicationDidBecomeActiveNotification object:nil]; - [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(sdl_onAppStateUpdated:) name:UIApplicationWillResignActiveNotification object:nil]; - - [self.primaryProtocolHandler start]; -} - -- (void)sdl_stopManager { - SDLLogD(@"SDLSecondaryTransportManager stop"); - - [[NSNotificationCenter defaultCenter] removeObserver:self name:UIApplicationDidBecomeActiveNotification object:nil]; - [[NSNotificationCenter defaultCenter] removeObserver:self name:UIApplicationWillResignActiveNotification object:nil]; - - [self.primaryProtocolHandler stop]; - - self.streamingServiceTransportMap = [@{@(SDLServiceTypeAudio):@(SDLTransportClassInvalid), - @(SDLServiceTypeVideo):@(SDLTransportClassInvalid)} mutableCopy]; - self.secondaryTransportType = SDLSecondaryTransportTypeDisabled; - self.transportsForAudioService = @[]; - self.transportsForVideoService = @[]; - - self.ipAddress = nil; - self.tcpPort = TCPPortUnspecified; - self.shouldOpenConnection = nil; -} - -- (void)sdl_configureManager:(nullable NSArray<SDLSecondaryTransportTypeBox *> *)availableSecondaryTransports - availableTransportsForAudio:(nullable NSArray<SDLTransportClassBox *> *)availableTransportsForAudio - availableTransportsForVideo:(nullable NSArray<SDLTransportClassBox *> *)availableTransportsForVideo { - if (![self.stateMachine isCurrentState:SDLSecondaryTransportStateStarted]) { - SDLLogW(@"SecondaryTransportManager ignores duplicate Start Service ACK frame"); - return; - } - - // default values - self.secondaryTransportType = SDLSecondaryTransportTypeDisabled; - self.transportsForAudioService = @[@(SDLTransportClassPrimary)]; // If SDL Core did not send a transport list for the service, start it on Primary Transport. - self.transportsForVideoService = @[@(SDLTransportClassPrimary)]; - BOOL validConfig = YES; - - if (availableSecondaryTransports.count > 0) { - // current proposal says the list should contain only one element - SDLSecondaryTransportTypeBox *transportType = availableSecondaryTransports[0]; - self.secondaryTransportType = [transportType integerValue]; - } else { - SDLLogW(@"Did not receive secondary transport type from system. Secondary transport is disabled."); - } - - SDLSecondaryTransportType primaryTransportType = [self sdl_getTransportTypeFromProtocol:self.primaryProtocol]; - if (self.secondaryTransportType == primaryTransportType) { - SDLLogW(@"Same transport is specified for both primary and secondary transport. Secondary transport is disabled."); - self.secondaryTransportType = SDLSecondaryTransportTypeDisabled; - validConfig = NO; // let audio and video services start on primary transport - } else if (self.secondaryTransportType == SDLSecondaryTransportTypeIAP) { - SDLLogW(@"Starting IAP as secondary transport, which does not usually happen"); - } - - if (availableTransportsForAudio != nil && validConfig) { - self.transportsForAudioService = availableTransportsForAudio; - } - if (availableTransportsForVideo != nil && validConfig) { - self.transportsForVideoService = availableTransportsForVideo; - } - - // this will trigger audio / video streaming if they are allowed on primary transport - [self sdl_handleTransportUpdateWithPrimaryAvailable:YES secondaryAvailable:NO]; - - [self.stateMachine transitionToState:SDLSecondaryTransportStateConfigured]; -} - -- (void)sdl_handleTransportEventUpdate { - if ([self.stateMachine isCurrentState:SDLSecondaryTransportStateStarted]) { - // The system sent Transport Event Update frame prior to Start Service ACK. Just keep the information and do nothing here. - SDLLogV(@"Received TCP transport information prior to Start Service ACK"); - return; - } - if (self.secondaryTransportType != SDLSecondaryTransportTypeTCP) { - SDLLogV(@"Received TCP transport information while the transport is not TCP"); - return; - } - - if ([self.stateMachine isCurrentState:SDLSecondaryTransportStateConfigured] && [self sdl_isTCPReady] && self.shouldOpenConnection) { - [self.stateMachine transitionToState:SDLSecondaryTransportStateConnecting]; - } else if ([self sdl_isTransportOpened]) { - // Disconnect current transport. If the IP address is available then we will reconnect immediately. - SDLLogD(@"TCP transport information updated, disconnecting current transport"); - [self.stateMachine transitionToState:SDLSecondaryTransportStateConfigured]; - } else if ([self.stateMachine isCurrentState:SDLSecondaryTransportStateReconnecting]) { - SDLLogD(@"TCP transport information updated, aborting reconnection timer"); - [self.stateMachine transitionToState:SDLSecondaryTransportStateConfigured]; - } -} - -- (BOOL)sdl_isTransportOpened { - return [self.stateMachine isCurrentState:SDLSecondaryTransportStateConnecting] - || [self.stateMachine isCurrentState:SDLSecondaryTransportStateRegistered]; -} - - #pragma mark - Starting / Stopping / Restarting services - (void)sdl_handleTransportUpdateWithPrimaryAvailable:(BOOL)primaryAvailable secondaryAvailable:(BOOL)secondaryAvailable { @@ -648,6 +574,76 @@ static const int TCPPortUnspecified = -1; }); } +// called from SDLProtocol's _receiveQueue of "primary" transport +- (void)onStartServiceAckReceived:(SDLControlFramePayloadRPCStartServiceAck *)payload { + NSMutableArray<SDLSecondaryTransportTypeBox *> *secondaryTransports = nil; + if (payload.secondaryTransports != nil) { + secondaryTransports = [NSMutableArray array]; + for (NSString *transportString in payload.secondaryTransports) { + SDLSecondaryTransportType transport = [self sdl_convertTransportType:transportString]; + [secondaryTransports addObject:@(transport)]; + } + } + + NSArray<SDLTransportClassBox *> *transportsForAudio = [self sdl_convertServiceTransports:payload.audioServiceTransports]; + NSArray<SDLTransportClassBox *> *transportsForVideo = [self sdl_convertServiceTransports:payload.videoServiceTransports]; + + SDLLogV(@"Secondary transports: %@, transports for audio: %@, transports for video: %@", secondaryTransports, transportsForAudio, transportsForVideo); + + dispatch_async(_stateMachineQueue, ^{ + [self sdl_configureManager:secondaryTransports availableTransportsForAudio:transportsForAudio availableTransportsForVideo:transportsForVideo]; + }); +} + +// called from SDLProtocol's _receiveQueue of "primary" transport +- (void)onTransportEventUpdateReceived:(SDLControlFramePayloadTransportEventUpdate *)payload { + dispatch_async(_stateMachineQueue, ^{ + BOOL updated = NO; + + if (payload.tcpIpAddress != nil) { + if (![self.ipAddress isEqualToString:payload.tcpIpAddress]) { + self.ipAddress = payload.tcpIpAddress; + updated = YES; + SDLLogD(@"TCP transport IP address updated: %@", self.ipAddress); + } + } + if (payload.tcpPort != SDLControlFrameInt32NotFound) { + if (self.tcpPort != payload.tcpPort) { + self.tcpPort = payload.tcpPort; + updated = YES; + SDLLogD(@"TCP transport port number updated: %d", self.tcpPort); + } + } + + if (updated) { + [self sdl_handleTransportEventUpdate]; + } + }); +} + +- (void)sdl_handleTransportEventUpdate { + if ([self.stateMachine isCurrentState:SDLSecondaryTransportStateStarted]) { + // The system sent Transport Event Update frame prior to Start Service ACK. Just keep the information and do nothing here. + SDLLogV(@"Received TCP transport information prior to Start Service ACK"); + return; + } + if (self.secondaryTransportType != SDLSecondaryTransportTypeTCP) { + SDLLogV(@"Received TCP transport information while the transport is not TCP"); + return; + } + + if ([self.stateMachine isCurrentState:SDLSecondaryTransportStateConfigured] && [self sdl_isTCPReady] && self.shouldOpenConnection) { + [self.stateMachine transitionToState:SDLSecondaryTransportStateConnecting]; + } else if ([self sdl_isTransportOpened]) { + // Disconnect current transport. If the IP address is available then we will reconnect immediately. + SDLLogD(@"TCP transport information updated, disconnecting current transport"); + [self.stateMachine transitionToState:SDLSecondaryTransportStateConfigured]; + } else if ([self.stateMachine isCurrentState:SDLSecondaryTransportStateReconnecting]) { + SDLLogD(@"TCP transport information updated, aborting reconnection timer"); + [self.stateMachine transitionToState:SDLSecondaryTransportStateConfigured]; + } +} + #pragma mark - App state handling - (void)sdl_onAppStateUpdated:(NSNotification *)notification { @@ -716,6 +712,12 @@ static const int TCPPortUnspecified = -1; } } +- (BOOL)sdl_isTransportOpened { + return [self.stateMachine isCurrentState:SDLSecondaryTransportStateConnecting] + || [self.stateMachine isCurrentState:SDLSecondaryTransportStateRegistered]; +} + +#pragma mark - RPC Notifications - (void)sdl_hmiStatusDidChange:(SDLRPCNotificationNotification *)notification { if (![notification isNotificationMemberOfClass:[SDLOnHMIStatus class]]) { return; @@ -723,7 +725,7 @@ static const int TCPPortUnspecified = -1; SDLOnHMIStatus *hmiStatusNotification = notification.notification; if(![hmiStatusNotification.hmiLevel isEqualToEnum:SDLHMILevelNone] && !self.shouldOpenConnection && [self.stateMachine isCurrentState:SDLSecondaryTransportStateConfigured]) { - self.shouldOpenConnection = true; + self.shouldOpenConnection = YES; if ((self.secondaryTransportType == SDLSecondaryTransportTypeTCP && [self sdl_isTCPReady]) || (self.secondaryTransportType == SDLSecondaryTransportTypeIAP)) { [self.stateMachine transitionToState:SDLSecondaryTransportStateConnecting]; |