diff --git a/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTMessageService.h b/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTMessageService.h index 99d24a9b7c..7f3d013a62 100644 --- a/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTMessageService.h +++ b/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTMessageService.h @@ -31,6 +31,7 @@ - (void)mtProto:(MTProto *)mtProto protocolErrorReceived:(int32_t)errorCode; - (bool)mtProto:(MTProto *)mtProto shouldRequestMessageWithId:(int64_t)responseMessageId inResponseToMessageId:(int64_t)messageId currentTransactionId:(id)currentTransactionId; - (void)mtProto:(MTProto *)mtProto updateReceiveProgressForToken:(id)progressToken progress:(float)progress packetLength:(NSInteger)packetLength; +- (void)mtProtoTransportActivityUpdated:(MTProto *)mtProto; - (void)mtProtoNetworkAvailabilityChanged:(MTProto *)mtProto isNetworkAvailable:(bool)isNetworkAvailable; - (void)mtProtoConnectionStateChanged:(MTProto *)mtProto isConnected:(bool)isConnected; diff --git a/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTRequest.h b/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTRequest.h index 3cc58bf6ab..5f5d3d1248 100644 --- a/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTRequest.h +++ b/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTRequest.h @@ -22,6 +22,7 @@ @property (nonatomic) bool hasHighPriority; @property (nonatomic) bool dependsOnPasswordEntry; @property (nonatomic) bool passthroughPasswordEntryError; +@property (nonatomic) bool needsTimeoutTimer; @property (nonatomic, copy) void (^completed)(id result, NSTimeInterval completionTimestamp, MTRpcError *error); @property (nonatomic, copy) void (^progressUpdated)(float progress, NSUInteger packetLength); diff --git a/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTTransport.h b/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTTransport.h index 9349935610..156fe128c3 100644 --- a/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTTransport.h +++ b/submodules/MtProtoKit/PublicHeaders/MtProtoKit/MTTransport.h @@ -32,6 +32,8 @@ - (void)transportDecodeProgressToken:(MTTransport * _Nonnull)transport scheme:(MTTransportScheme * _Nonnull)scheme data:(NSData * _Nonnull)data token:(int64_t)token completion:(void (^ _Nonnull)(int64_t token, id _Nonnull progressToken))completion; - (void)transportUpdatedDataReceiveProgress:(MTTransport * _Nonnull)transport progressToken:(id _Nonnull)progressToken packetLength:(NSInteger)packetLength progress:(float)progress; +- (void)transportActivityUpdated:(MTTransport * _Nonnull)transport; + @end @interface MTTransport : NSObject diff --git a/submodules/MtProtoKit/Sources/MTProto.m b/submodules/MtProtoKit/Sources/MTProto.m index 77f47d8df3..4b02c06b50 100644 --- a/submodules/MtProtoKit/Sources/MTProto.m +++ b/submodules/MtProtoKit/Sources/MTProto.m @@ -1926,6 +1926,20 @@ static const NSUInteger MTMaxUnacknowledgedMessageCount = 64; }]; } +- (void)transportActivityUpdated:(MTTransport * _Nonnull)transport { + [[MTProto managerQueue] dispatchOnQueue:^ + { + if (transport != _transport) + return; + + for (id messageService in _messageServices) + { + if ([messageService respondsToSelector:@selector(mtProtoTransportActivityUpdated:)]) + [messageService mtProtoTransportActivityUpdated:self]; + } + }]; +} + - (void)transportTransactionsSucceeded:(NSArray *)transactionIds { [[MTProto managerQueue] dispatchOnQueue:^ diff --git a/submodules/MtProtoKit/Sources/MTRequestMessageService.m b/submodules/MtProtoKit/Sources/MTRequestMessageService.m index 80a4348bbb..c4214f6b34 100644 --- a/submodules/MtProtoKit/Sources/MTRequestMessageService.m +++ b/submodules/MtProtoKit/Sources/MTRequestMessageService.m @@ -36,6 +36,7 @@ NSMutableArray *_dropReponseContexts; MTTimer *_requestsServiceTimer; + MTTimer *_requestsTimeoutTimer; } @end @@ -72,6 +73,10 @@ [_requestsServiceTimer invalidate]; _requestsServiceTimer = nil; } + if (_requestsTimeoutTimer != nil) { + [_requestsTimeoutTimer invalidate]; + _requestsTimeoutTimer = nil; + } } - (void)addRequest:(MTRequest *)request @@ -147,6 +152,7 @@ } [self updateRequestsTimer]; + [self updateRequestsTimeoutTimerWithReset:false]; }]; } @@ -267,6 +273,75 @@ [mtProto requestTransportTransaction]; } +- (void)updateRequestsTimeoutTimerWithReset:(bool)reset { + CFAbsoluteTime currentTime = MTAbsoluteSystemTime(); + + bool needTimer = false; + + for (MTRequest *request in _requests) { + if (!request.needsTimeoutTimer) { + continue; + } + if (request.errorContext != nil) { + if (request.errorContext.waitingForRequestToComplete != nil) { + bool foundDependency = false; + for (MTRequest *anotherRequest in _requests) { + if (request.errorContext.waitingForRequestToComplete == anotherRequest.internalId) { + foundDependency = true; + break; + } + } + + if (!foundDependency) { + needTimer = true; + } + } + + if (request.requestContext == nil) { + if (request.errorContext.minimalExecuteTime > currentTime + DBL_EPSILON) { + } else { + request.errorContext.minimalExecuteTime = 0.0; + needTimer = true; + } + } + } else { + needTimer = true; + } + } + + if (needTimer) { + if (reset) { + if (_requestsTimeoutTimer != nil) { + [_requestsTimeoutTimer invalidate]; + _requestsTimeoutTimer = nil; + } + } + + if (_requestsTimeoutTimer == nil) { + __weak MTRequestMessageService *weakSelf = self; + _requestsTimeoutTimer = [[MTTimer alloc] initWithTimeout:5.0 repeat:false completion:^ + { + __strong MTRequestMessageService *strongSelf = weakSelf; + [strongSelf requestTimerTimeoutEvent]; + } queue:_queue.nativeQueue]; + [_requestsTimeoutTimer start]; + } + } else { + if (_requestsTimeoutTimer != nil) { + [_requestsTimeoutTimer invalidate]; + _requestsTimeoutTimer = nil; + } + } +} + +- (void)requestTimerTimeoutEvent { + MTProto *mtProto = _mtProto; + if (mtProto) { + [mtProto requestSecureTransportReset]; + [mtProto requestTransportTransaction]; + } +} + - (void)mtProtoWillAddService:(MTProto *)mtProto { _queue = [mtProto messageServiceQueue]; @@ -824,6 +899,7 @@ } [self updateRequestsTimer]; + [self updateRequestsTimeoutTimerWithReset:false]; } } } @@ -840,6 +916,10 @@ } } +- (void)mtProtoTransportActivityUpdated:(MTProto *) __unused mtProto { + [self updateRequestsTimeoutTimerWithReset:true]; +} + - (void)mtProto:(MTProto *)__unused mtProto messageDeliveryConfirmed:(NSArray *)messageIds { for (NSNumber *nMessageId in messageIds) diff --git a/submodules/MtProtoKit/Sources/MTTcpConnection.h b/submodules/MtProtoKit/Sources/MTTcpConnection.h index cbc8c5886e..872eea7981 100644 --- a/submodules/MtProtoKit/Sources/MTTcpConnection.h +++ b/submodules/MtProtoKit/Sources/MTTcpConnection.h @@ -17,6 +17,7 @@ - (void)tcpConnectionReceivedQuickAck:(MTTcpConnection *)connection quickAck:(int32_t)quickAck; - (void)tcpConnectionDecodePacketProgressToken:(MTTcpConnection *)connection data:(NSData *)data token:(int64_t)token completion:(void (^)(int64_t token, id packetProgressToken))completion; - (void)tcpConnectionProgressUpdated:(MTTcpConnection *)connection packetProgressToken:(id)packetProgressToken packetLength:(NSUInteger)packetLength progress:(float)progress; +- (void)tcpConnectionDownloadActivityUpdated:(MTTcpConnection *)connection; @end diff --git a/submodules/MtProtoKit/Sources/MTTcpConnection.m b/submodules/MtProtoKit/Sources/MTTcpConnection.m index 594f53330d..9cc61b7fcd 100644 --- a/submodules/MtProtoKit/Sources/MTTcpConnection.m +++ b/submodules/MtProtoKit/Sources/MTTcpConnection.m @@ -606,6 +606,118 @@ struct ctr_state { @end +@protocol MTTcpConnectionInterface; + +@protocol MTTcpConnectionInterfaceDelegate + +- (void)connectionInterface:(id)connectionInterface didReadPartialDataOfLength:(NSUInteger)partialLength tag:(long)tag; +- (void)connectionInterface:(id)connectionInterface didReadData:(NSData *)rawData withTag:(long)tag; +- (void)connectionInterface:(id)connectionInterface didConnectToHost:(NSString *)host port:(uint16_t)port; +- (void)connectionInterfaceDidDisconnect:(id)connectionInterface withError:(NSError *)error; + +@end + +@protocol MTTcpConnectionInterface + +- (void)setGetLogPrefix:(NSString *(^)())getLogPrefix; +- (void)setUsageCalculationInfo:(MTNetworkUsageCalculationInfo *)usageCalculationInfo; +- (bool)connectToHost:(NSString *)inHost + onPort:(uint16_t)port + viaInterface:(NSString *)inInterface + withTimeout:(NSTimeInterval)timeout + error:(NSError **)errPtr; +- (void)writeData:(NSData *)data; +- (void)readDataToLength:(NSUInteger)length withTimeout:(NSTimeInterval)timeout tag:(long)tag; +- (void)disconnect; +- (void)resetDelegate; + +@end + +@interface MTGcdAsyncSocketTcpConnectionInterface: NSObject { + GCDAsyncSocket *_socket; + __weak id _delegate; +} + +@end + +@implementation MTGcdAsyncSocketTcpConnectionInterface + +- (instancetype)initWithDelegate:(id)delegate delegateQueue:(dispatch_queue_t)delegateQueue { + self = [super init]; + if (self != nil) { + _delegate = delegate; + _socket = [[GCDAsyncSocket alloc] initWithDelegate:self delegateQueue:delegateQueue]; + } + return self; +} + +- (void)setGetLogPrefix:(NSString *(^)())getLogPrefix { + _socket.getLogPrefix = getLogPrefix; +} + +- (void)setUsageCalculationInfo:(MTNetworkUsageCalculationInfo *)usageCalculationInfo { + _socket.usageCalculationInfo = usageCalculationInfo; +} + +- (bool)connectToHost:(NSString *)inHost + onPort:(uint16_t)port + viaInterface:(NSString *)inInterface + withTimeout:(NSTimeInterval)timeout + error:(NSError **)errPtr { + return [_socket connectToHost:inHost onPort:port viaInterface:inInterface withTimeout:timeout error:errPtr]; +} + +- (void)writeData:(NSData *)data { + [_socket writeData:data withTimeout:-1.0 tag:0]; +} + +- (void)readDataToLength:(NSUInteger)length withTimeout:(NSTimeInterval)timeout tag:(long)tag { + [_socket readDataToLength:length withTimeout:timeout tag:tag]; +} + +- (void)disconnect { + [_socket disconnect]; +} + +- (void)resetDelegate { + _socket.delegate = nil; + +} + +- (void)socket:(GCDAsyncSocket *)socket didReadPartialDataOfLength:(NSUInteger)partialLength tag:(long)tag { + id delegate = _delegate; + if (delegate) { + [delegate connectionInterface:self didReadPartialDataOfLength:partialLength tag:tag]; + } +} + +- (void)socket:(GCDAsyncSocket *)socket didReadData:(NSData *)rawData withTag:(long)tag { + id delegate = _delegate; + if (delegate) { + [delegate connectionInterface:self didReadData:rawData withTag:tag]; + } +} + +- (void)socket:(GCDAsyncSocket *)socket didConnectToHost:(NSString *)host port:(uint16_t)port { + id delegate = _delegate; + if (delegate) { + [delegate connectionInterface:self didConnectToHost:host port:port]; + } +} + +- (void)socketDidDisconnect:(GCDAsyncSocket *)socket withError:(NSError *)error { + id delegate = _delegate; + if (delegate) { + [delegate connectionInterfaceDidDisconnect:self withError:error]; + } +} + +- (NSTimeInterval)socket:(GCDAsyncSocket *)sock shouldTimeoutReadWithTag:(long)tag elapsed:(NSTimeInterval)elapsed bytesDone:(NSUInteger)length { + return -1.0; +} + +@end + @interface MTTcpReceiveData : NSObject @property (nonatomic, readonly) int tag; @@ -626,11 +738,11 @@ struct ctr_state { @end -@interface MTTcpConnection () +@interface MTTcpConnection () { id _encryptionProvider; - GCDAsyncSocket *_socket; + id _socket; bool _closed; bool _useIntermediateFormat; @@ -786,7 +898,7 @@ struct ctr_state { - (void)setUsageCalculationInfo:(MTNetworkUsageCalculationInfo *)usageCalculationInfo { [[MTTcpConnection tcpQueue] dispatchOnQueue:^{ _usageCalculationInfo = usageCalculationInfo; - _socket.usageCalculationInfo = usageCalculationInfo; + [_socket setUsageCalculationInfo:usageCalculationInfo]; }]; } @@ -805,9 +917,10 @@ struct ctr_state { { if (_socket == nil) { - _socket = [[GCDAsyncSocket alloc] initWithDelegate:self delegateQueue:[[MTTcpConnection tcpQueue] nativeQueue]]; - _socket.getLogPrefix = _getLogPrefix; - _socket.usageCalculationInfo = _usageCalculationInfo; + _socket = [[MTGcdAsyncSocketTcpConnectionInterface alloc] initWithDelegate:self delegateQueue:[[MTTcpConnection tcpQueue] nativeQueue]]; + + [_socket setGetLogPrefix:_getLogPrefix]; + [_socket setUsageCalculationInfo:_usageCalculationInfo]; NSString *addressIp = _scheme.address.ip; MTSignal *resolveSignal = [MTSignal single:[[MTTcpConnectionData alloc] initWithIp:addressIp port:_scheme.address.port isSocks:false]]; @@ -990,7 +1103,7 @@ struct ctr_state { _helloRandom = [[NSData alloc] initWithBytes:cHMAC length:32]; memcpy(((uint8_t *)helloData.mutableBytes) + 11, cHMAC, 32); - [strongSelf->_socket writeData:helloData withTimeout:-1 tag:0]; + [strongSelf->_socket writeData:helloData]; [strongSelf->_socket readDataToLength:5 withTimeout:-1 tag:MTTcpSocksReceiveHelloResponse]; } else { strongSelf->_readyToSendData = true; @@ -1011,7 +1124,7 @@ struct ctr_state { req.NumberOfMethods += 1; req.Methods[1] = 0x02; } - [strongSelf->_socket writeData:[NSData dataWithBytes:&req length:2 + req.NumberOfMethods] withTimeout:-1 tag:0]; + [strongSelf->_socket writeData:[NSData dataWithBytes:&req length:2 + req.NumberOfMethods]]; [strongSelf->_socket readDataToLength:sizeof(struct socks5_ident_resp) withTimeout:-1 tag:MTTcpSocksLogin]; } }]; @@ -1038,7 +1151,7 @@ struct ctr_state { _closed = true; [_socket disconnect]; - _socket.delegate = nil; + [_socket resetDelegate]; _socket = nil; if (_connectionClosed) @@ -1232,9 +1345,9 @@ struct ctr_state { offset += partLength; } - [_socket writeData:partitionedCompleteData withTimeout:-1 tag:0]; + [_socket writeData:partitionedCompleteData]; } else { - [_socket writeData:completeData withTimeout:-1 tag:0]; + [_socket writeData:completeData]; } } @@ -1294,7 +1407,7 @@ struct ctr_state { [self closeAndNotifyWithError:true]; } -- (void)socket:(GCDAsyncSocket *)__unused socket didReadPartialDataOfLength:(NSUInteger)partialLength tag:(long)__unused tag +- (void)connectionInterface:(id)__unused connectionInterface didReadPartialDataOfLength:(NSUInteger)partialLength tag:(long)__unused tag { if (_closed) return; @@ -1313,6 +1426,9 @@ struct ctr_state { [delegate tcpConnectionProgressUpdated:self packetProgressToken:_packetProgressToken packetLength:_packetRestLength progress:currentApproximateProgress / 100.0f]; } } + + id delegate = _delegate; + [delegate tcpConnectionDownloadActivityUpdated:self]; } - (void)requestSocksConnection { @@ -1357,15 +1473,18 @@ struct ctr_state { unsigned short port = htons(req.DestPort); [reqData appendBytes:&port length:2]; - [_socket writeData:reqData withTimeout:-1 tag:0]; + [_socket writeData:reqData]; [_socket readDataToLength:4 withTimeout:-1 tag:MTTcpSocksRequest]; } -- (void)socket:(GCDAsyncSocket *)__unused socket didReadData:(NSData *)rawData withTag:(long)tag +- (void)connectionInterface:(id)__unused connectionInterface didReadData:(NSData *)rawData withTag:(long)tag { if (_closed) return; + id delegate = _delegate; + [delegate tcpConnectionDownloadActivityUpdated:self]; + if (tag == MTTcpSocksLogin) { if (rawData.length != sizeof(struct socks5_ident_resp)) { if (MTLogEnabled()) { @@ -1410,7 +1529,7 @@ struct ctr_state { [reqData appendBytes:&passwordLength length:1]; [reqData appendData:passwordData]; - [_socket writeData:reqData withTimeout:-1 tag:0]; + [_socket writeData:reqData]; [_socket readDataToLength:2 withTimeout:-1 tag:MTTcpSocksReceiveAuthResponse]; } else { [self requestSocksConnection]; @@ -1899,7 +2018,7 @@ struct ctr_state { } } -- (void)socket:(GCDAsyncSocket *)__unused socket didConnectToHost:(NSString *)__unused host port:(uint16_t)__unused port +- (void)connectionInterface:(id)__unused connectionInterface didConnectToHost:(NSString *)__unused host port:(uint16_t)__unused port { if (_socksIp != nil) { @@ -1912,7 +2031,7 @@ struct ctr_state { } } -- (void)socketDidDisconnect:(GCDAsyncSocket *)__unused socket withError:(NSError *)error +- (void)connectionInterfaceDidDisconnect:(id)__unused connectionInterface withError:(NSError *)error { if (error != nil) { if (MTLogEnabled()) { diff --git a/submodules/MtProtoKit/Sources/MTTcpTransport.m b/submodules/MtProtoKit/Sources/MTTcpTransport.m index 7c95f93c83..5dc5154d52 100644 --- a/submodules/MtProtoKit/Sources/MTTcpTransport.m +++ b/submodules/MtProtoKit/Sources/MTTcpTransport.m @@ -551,6 +551,19 @@ static const NSTimeInterval MTTcpTransportSleepWatchdogTimeout = 60.0; }]; } +- (void)tcpConnectionDownloadActivityUpdated:(MTTcpConnection *)connection { + MTTcpTransportContext *transportContext = _transportContext; + [[MTTcpTransport tcpTransportQueue] dispatchOnQueue:^ + { + if (transportContext.connection != connection) + return; + + id delegate = self.delegate; + if ([delegate respondsToSelector:@selector(transportUpdatedDataReceiveProgress:progressToken:packetLength:progress:)]) + [delegate transportActivityUpdated:self]; + }]; +} + - (void)tcpConnectionBehaviourRequestsReconnection:(MTTcpConnectionBehaviour *)behaviour error:(bool)error { MTTcpTransportContext *transportContext = _transportContext; diff --git a/submodules/PasswordSetupUI/Sources/SetupTwoStepVerificationContentNode.swift b/submodules/PasswordSetupUI/Sources/SetupTwoStepVerificationContentNode.swift index 80a45ac163..66d8233c0c 100644 --- a/submodules/PasswordSetupUI/Sources/SetupTwoStepVerificationContentNode.swift +++ b/submodules/PasswordSetupUI/Sources/SetupTwoStepVerificationContentNode.swift @@ -67,7 +67,9 @@ final class SetupTwoStepVerificationContentNode: ASDisplayNode, UITextFieldDeleg self.inputNode.textField.autocapitalizationType = .none self.inputNode.textField.autocorrectionType = .no if #available(iOSApplicationExtension 12.0, iOS 12.0, *) { + #if DEBUG self.inputNode.textField.textContentType = .newPassword + #endif } case .text: break diff --git a/submodules/PasswordSetupUI/Sources/TwoFactorAuthDataInputScreen.swift b/submodules/PasswordSetupUI/Sources/TwoFactorAuthDataInputScreen.swift index bed5cfbedc..df15d41c55 100644 --- a/submodules/PasswordSetupUI/Sources/TwoFactorAuthDataInputScreen.swift +++ b/submodules/PasswordSetupUI/Sources/TwoFactorAuthDataInputScreen.swift @@ -1081,6 +1081,7 @@ private final class TwoFactorDataInputTextNode: ASDisplayNode, UITextFieldDelega self.inputNode.textField.returnKeyType = .next } if #available(iOS 12.0, *) { + #if DEBUG if !confirmation, let phoneNumber { let shadowInputNode = TextFieldNode() shadowInputNode.textField.font = Font.regular(17.0) @@ -1092,9 +1093,12 @@ private final class TwoFactorDataInputTextNode: ASDisplayNode, UITextFieldDelega shadowInputNode.textField.textContentType = .username shadowInputNode.textField.text = phoneNumber } + #endif + #if DEBUG self.inputNode.textField.textContentType = .newPassword self.inputNode.textField.passwordRules = UITextInputPasswordRules(descriptor: "minlength: 8;") + #endif } self.hideButtonNode.isHidden = confirmation case .email: diff --git a/submodules/TelegramCore/Sources/Account/Account.swift b/submodules/TelegramCore/Sources/Account/Account.swift index 8e294a3ac0..1b48a4be4c 100644 --- a/submodules/TelegramCore/Sources/Account/Account.swift +++ b/submodules/TelegramCore/Sources/Account/Account.swift @@ -150,7 +150,7 @@ public class UnauthorizedAccount { } } |> mapToSignal { (localizationSettings, proxySettings, networkSettings) -> Signal in - return initializedNetwork(accountId: self.id, arguments: self.networkArguments, supplementary: false, datacenterId: Int(masterDatacenterId), keychain: keychain, basePath: self.basePath, testingEnvironment: self.testingEnvironment, languageCode: localizationSettings?.primaryComponent.languageCode, proxySettings: proxySettings, networkSettings: networkSettings, phoneNumber: nil) + return initializedNetwork(accountId: self.id, arguments: self.networkArguments, supplementary: false, datacenterId: Int(masterDatacenterId), keychain: keychain, basePath: self.basePath, testingEnvironment: self.testingEnvironment, languageCode: localizationSettings?.primaryComponent.languageCode, proxySettings: proxySettings, networkSettings: networkSettings, phoneNumber: nil, useRequestTimeoutTimers: false) |> map { network in let updated = UnauthorizedAccount(networkArguments: self.networkArguments, id: self.id, rootPath: self.rootPath, basePath: self.basePath, testingEnvironment: self.testingEnvironment, postbox: self.postbox, network: network) updated.shouldBeServiceTaskMaster.set(self.shouldBeServiceTaskMaster.get()) @@ -206,7 +206,7 @@ public func accountWithId(accountManager: AccountManager mapToSignal { localizationSettings, proxySettings -> Signal in - return postbox.transaction { transaction -> (PostboxCoding?, LocalizationSettings?, ProxySettings?, NetworkSettings?) in + return postbox.transaction { transaction -> (PostboxCoding?, LocalizationSettings?, ProxySettings?, NetworkSettings?, AppConfiguration) in var state = transaction.getState() if state == nil, let backupData = backupData { let backupState = AuthorizedAccountState(isTestingEnvironment: beginWithTestingEnvironment, masterDatacenterId: backupData.masterDatacenterId, peerId: PeerId(backupData.peerId), state: nil, invalidatedChannels: []) @@ -229,15 +229,24 @@ public func accountWithId(accountManager: AccountManager mapToSignal { (accountState, localizationSettings, proxySettings, networkSettings) -> Signal in + |> mapToSignal { (accountState, localizationSettings, proxySettings, networkSettings, appConfig) -> Signal in let keychain = makeExclusiveKeychain(id: id, postbox: postbox) + var useRequestTimeoutTimers: Bool = true + if let data = appConfig.data { + if let _ = data["ios_killswitch_disable_request_timeout"] { + useRequestTimeoutTimers = false + } + } + if let accountState = accountState { switch accountState { case let unauthorizedState as UnauthorizedAccountState: - return initializedNetwork(accountId: id, arguments: networkArguments, supplementary: supplementary, datacenterId: Int(unauthorizedState.masterDatacenterId), keychain: keychain, basePath: path, testingEnvironment: unauthorizedState.isTestingEnvironment, languageCode: localizationSettings?.primaryComponent.languageCode, proxySettings: proxySettings, networkSettings: networkSettings, phoneNumber: nil) + return initializedNetwork(accountId: id, arguments: networkArguments, supplementary: supplementary, datacenterId: Int(unauthorizedState.masterDatacenterId), keychain: keychain, basePath: path, testingEnvironment: unauthorizedState.isTestingEnvironment, languageCode: localizationSettings?.primaryComponent.languageCode, proxySettings: proxySettings, networkSettings: networkSettings, phoneNumber: nil, useRequestTimeoutTimers: useRequestTimeoutTimers) |> map { network -> AccountResult in return .unauthorized(UnauthorizedAccount(networkArguments: networkArguments, id: id, rootPath: rootPath, basePath: path, testingEnvironment: unauthorizedState.isTestingEnvironment, postbox: postbox, network: network, shouldKeepAutoConnection: shouldKeepAutoConnection)) } @@ -246,7 +255,7 @@ public func accountWithId(accountManager: AccountManager mapToSignal { phoneNumber in - return initializedNetwork(accountId: id, arguments: networkArguments, supplementary: supplementary, datacenterId: Int(authorizedState.masterDatacenterId), keychain: keychain, basePath: path, testingEnvironment: authorizedState.isTestingEnvironment, languageCode: localizationSettings?.primaryComponent.languageCode, proxySettings: proxySettings, networkSettings: networkSettings, phoneNumber: phoneNumber) + return initializedNetwork(accountId: id, arguments: networkArguments, supplementary: supplementary, datacenterId: Int(authorizedState.masterDatacenterId), keychain: keychain, basePath: path, testingEnvironment: authorizedState.isTestingEnvironment, languageCode: localizationSettings?.primaryComponent.languageCode, proxySettings: proxySettings, networkSettings: networkSettings, phoneNumber: phoneNumber, useRequestTimeoutTimers: useRequestTimeoutTimers) |> map { network -> AccountResult in return .authorized(Account(accountManager: accountManager, id: id, basePath: path, testingEnvironment: authorizedState.isTestingEnvironment, postbox: postbox, network: network, networkArguments: networkArguments, peerId: authorizedState.peerId, auxiliaryMethods: auxiliaryMethods, supplementary: supplementary)) } @@ -256,7 +265,7 @@ public func accountWithId(accountManager: AccountManager map { network -> AccountResult in return .unauthorized(UnauthorizedAccount(networkArguments: networkArguments, id: id, rootPath: rootPath, basePath: path, testingEnvironment: beginWithTestingEnvironment, postbox: postbox, network: network, shouldKeepAutoConnection: shouldKeepAutoConnection)) } @@ -1441,7 +1450,8 @@ public func standaloneStateManager( languageCode: localizationSettings?.primaryComponent.languageCode, proxySettings: proxySettings, networkSettings: networkSettings, - phoneNumber: phoneNumber + phoneNumber: phoneNumber, + useRequestTimeoutTimers: false ) |> map { network -> AccountStateManager? in Logger.shared.log("StandaloneStateManager", "received network") diff --git a/submodules/TelegramCore/Sources/Network/Download.swift b/submodules/TelegramCore/Sources/Network/Download.swift index b8ebf0c990..477be727de 100644 --- a/submodules/TelegramCore/Sources/Network/Download.swift +++ b/submodules/TelegramCore/Sources/Network/Download.swift @@ -43,14 +43,16 @@ class Download: NSObject, MTRequestMessageServiceDelegate { let context: MTContext let mtProto: MTProto let requestService: MTRequestMessageService + let useRequestTimeoutTimers: Bool private let logPrefix = Atomic(value: nil) private var shouldKeepConnectionDisposable: Disposable? - init(queue: Queue, datacenterId: Int, isMedia: Bool, isCdn: Bool, context: MTContext, masterDatacenterId: Int, usageInfo: MTNetworkUsageCalculationInfo?, shouldKeepConnection: Signal) { + init(queue: Queue, datacenterId: Int, isMedia: Bool, isCdn: Bool, context: MTContext, masterDatacenterId: Int, usageInfo: MTNetworkUsageCalculationInfo?, shouldKeepConnection: Signal, useRequestTimeoutTimers: Bool) { self.datacenterId = datacenterId self.isCdn = isCdn self.context = context + self.useRequestTimeoutTimers = useRequestTimeoutTimers var requiredAuthToken: Any? var authTokenMasterDatacenterId: Int = 0 @@ -203,6 +205,7 @@ class Download: NSObject, MTRequestMessageServiceDelegate { }) request.dependsOnPasswordEntry = false + request.needsTimeoutTimer = self.useRequestTimeoutTimers request.shouldContinueExecutionWithErrorContext = { errorContext in return true @@ -254,6 +257,7 @@ class Download: NSObject, MTRequestMessageServiceDelegate { }) request.dependsOnPasswordEntry = false + request.needsTimeoutTimer = self.useRequestTimeoutTimers request.shouldContinueExecutionWithErrorContext = { errorContext in return true @@ -301,6 +305,7 @@ class Download: NSObject, MTRequestMessageServiceDelegate { }) request.dependsOnPasswordEntry = false + request.needsTimeoutTimer = self.useRequestTimeoutTimers request.shouldContinueExecutionWithErrorContext = { errorContext in return true @@ -342,6 +347,7 @@ class Download: NSObject, MTRequestMessageServiceDelegate { }) request.dependsOnPasswordEntry = false + request.needsTimeoutTimer = self.useRequestTimeoutTimers request.shouldContinueExecutionWithErrorContext = { errorContext in guard let errorContext = errorContext else { @@ -393,6 +399,7 @@ class Download: NSObject, MTRequestMessageServiceDelegate { }) request.dependsOnPasswordEntry = false + request.needsTimeoutTimer = self.useRequestTimeoutTimers request.shouldContinueExecutionWithErrorContext = { errorContext in guard let errorContext = errorContext else { diff --git a/submodules/TelegramCore/Sources/Network/Network.swift b/submodules/TelegramCore/Sources/Network/Network.swift index 97af603714..8e7a4b2264 100644 --- a/submodules/TelegramCore/Sources/Network/Network.swift +++ b/submodules/TelegramCore/Sources/Network/Network.swift @@ -450,7 +450,7 @@ public struct NetworkInitializationArguments { private let cloudDataContext = Atomic(value: nil) #endif -func initializedNetwork(accountId: AccountRecordId, arguments: NetworkInitializationArguments, supplementary: Bool, datacenterId: Int, keychain: Keychain, basePath: String, testingEnvironment: Bool, languageCode: String?, proxySettings: ProxySettings?, networkSettings: NetworkSettings?, phoneNumber: String?) -> Signal { +func initializedNetwork(accountId: AccountRecordId, arguments: NetworkInitializationArguments, supplementary: Bool, datacenterId: Int, keychain: Keychain, basePath: String, testingEnvironment: Bool, languageCode: String?, proxySettings: ProxySettings?, networkSettings: NetworkSettings?, phoneNumber: String?, useRequestTimeoutTimers: Bool) -> Signal { return Signal { subscriber in let queue = Queue() queue.async { @@ -581,7 +581,7 @@ func initializedNetwork(accountId: AccountRecordId, arguments: NetworkInitializa mtProto.delegate = connectionStatusDelegate mtProto.add(requestService) - let network = Network(queue: queue, datacenterId: datacenterId, context: context, mtProto: mtProto, requestService: requestService, connectionStatusDelegate: connectionStatusDelegate, _connectionStatus: connectionStatus, basePath: basePath, appDataDisposable: appDataDisposable, encryptionProvider: arguments.encryptionProvider) + let network = Network(queue: queue, datacenterId: datacenterId, context: context, mtProto: mtProto, requestService: requestService, connectionStatusDelegate: connectionStatusDelegate, _connectionStatus: connectionStatus, basePath: basePath, appDataDisposable: appDataDisposable, encryptionProvider: arguments.encryptionProvider, useRequestTimeoutTimers: useRequestTimeoutTimers) appDataUpdatedImpl = { [weak network] data in guard let data = data else { return @@ -711,6 +711,7 @@ public final class Network: NSObject, MTRequestMessageServiceDelegate { let requestService: MTRequestMessageService let basePath: String private let connectionStatusDelegate: MTProtoConnectionStatusDelegate + private let useRequestTimeoutTimers: Bool private let appDataDisposable: Disposable @@ -754,7 +755,7 @@ public final class Network: NSObject, MTRequestMessageServiceDelegate { return "Network context: \(self.context)" } - fileprivate init(queue: Queue, datacenterId: Int, context: MTContext, mtProto: MTProto, requestService: MTRequestMessageService, connectionStatusDelegate: MTProtoConnectionStatusDelegate, _connectionStatus: Promise, basePath: String, appDataDisposable: Disposable, encryptionProvider: EncryptionProvider) { + fileprivate init(queue: Queue, datacenterId: Int, context: MTContext, mtProto: MTProto, requestService: MTRequestMessageService, connectionStatusDelegate: MTProtoConnectionStatusDelegate, _connectionStatus: Promise, basePath: String, appDataDisposable: Disposable, encryptionProvider: EncryptionProvider, useRequestTimeoutTimers: Bool) { self.encryptionProvider = encryptionProvider self.queue = queue @@ -767,6 +768,7 @@ public final class Network: NSObject, MTRequestMessageServiceDelegate { self._connectionStatus = _connectionStatus self.appDataDisposable = appDataDisposable self.basePath = basePath + self.useRequestTimeoutTimers = useRequestTimeoutTimers super.init() @@ -899,7 +901,7 @@ public final class Network: NSObject, MTRequestMessageServiceDelegate { return shouldKeepConnection || shouldExplicitelyKeepWorkerConnections || (continueInBackground && shouldKeepBackgroundDownloadConnections) } |> distinctUntilChanged - return Download(queue: self.queue, datacenterId: datacenterId, isMedia: isMedia, isCdn: isCdn, context: self.context, masterDatacenterId: self.datacenterId, usageInfo: usageCalculationInfo(basePath: self.basePath, category: (tag as? TelegramMediaResourceFetchTag)?.statsCategory), shouldKeepConnection: shouldKeepWorkerConnection) + return Download(queue: self.queue, datacenterId: datacenterId, isMedia: isMedia, isCdn: isCdn, context: self.context, masterDatacenterId: self.datacenterId, usageInfo: usageCalculationInfo(basePath: self.basePath, category: (tag as? TelegramMediaResourceFetchTag)?.statsCategory), shouldKeepConnection: shouldKeepWorkerConnection, useRequestTimeoutTimers: self.useRequestTimeoutTimers) } private func worker(datacenterId: Int, isCdn: Bool, isMedia: Bool, tag: MediaResourceFetchTag?) -> Signal {