From cd4134c9dac11b810a37f7526413086f07122a69 Mon Sep 17 00:00:00 2001 From: Matthew Chen Date: Fri, 31 Mar 2017 18:36:08 -0400 Subject: [PATCH] Apply assert to ensure singletons are only created once. // FREEBIE --- .../Attachments/TSAttachmentPointer.h | 4 ++- src/Messages/TSBlockingManager.m | 2 ++ src/Messages/TSMessagesManager.m | 4 ++- src/Network/WebSockets/TSSocketManager.h | 8 ++--- src/Network/WebSockets/TSSocketManager.m | 2 ++ src/Storage/TSStorageManager.h | 2 ++ src/Storage/TSStorageManager.m | 2 ++ src/Util/Asserts.h | 34 +++++++++++++++++++ 8 files changed, 51 insertions(+), 7 deletions(-) diff --git a/src/Messages/Attachments/TSAttachmentPointer.h b/src/Messages/Attachments/TSAttachmentPointer.h index cb8143fdb..becece41d 100644 --- a/src/Messages/Attachments/TSAttachmentPointer.h +++ b/src/Messages/Attachments/TSAttachmentPointer.h @@ -17,11 +17,13 @@ typedef NS_ENUM(NSUInteger, TSAttachmentPointerState) { */ @interface TSAttachmentPointer : TSAttachment +- (instancetype)init NS_UNAVAILABLE; + - (instancetype)initWithServerId:(UInt64)serverId key:(NSData *)key digest:(nullable NSData *)digest contentType:(NSString *)contentType - relay:(NSString *)relay NS_DESIGNATED_INITIALIZER; + relay:(NSString *)relay; @property (nonatomic, readonly) NSString *relay; @property (atomic) TSAttachmentPointerState state; diff --git a/src/Messages/TSBlockingManager.m b/src/Messages/TSBlockingManager.m index 032c3dc96..c10357402 100644 --- a/src/Messages/TSBlockingManager.m +++ b/src/Messages/TSBlockingManager.m @@ -66,6 +66,8 @@ NSString *const kTSStorageManager_SyncedBlockedPhoneNumbersKey = @"kTSStorageMan _storageManager = storageManager; _messageSender = messageSender; + OWSSingletonAssert(); + return self; } diff --git a/src/Messages/TSMessagesManager.m b/src/Messages/TSMessagesManager.m index 2f660901e..4ea23fc6d 100644 --- a/src/Messages/TSMessagesManager.m +++ b/src/Messages/TSMessagesManager.m @@ -105,7 +105,9 @@ NS_ASSUME_NONNULL_BEGIN _disappearingMessagesJob = [[OWSDisappearingMessagesJob alloc] initWithStorageManager:storageManager]; _incomingMessageFinder = [[OWSIncomingMessageFinder alloc] initWithDatabase:storageManager.database]; _blockingManager = [TSBlockingManager sharedManager]; - + + OWSSingletonAssert(); + return self; } diff --git a/src/Network/WebSockets/TSSocketManager.h b/src/Network/WebSockets/TSSocketManager.h index 9a6e81457..079eea6a2 100644 --- a/src/Network/WebSockets/TSSocketManager.h +++ b/src/Network/WebSockets/TSSocketManager.h @@ -1,9 +1,5 @@ // -// TSSocketManager.h -// TextSecureiOS -// -// Created by Frederic Jacobs on 17/05/14. -// Copyright (c) 2014 Open Whisper Systems. All rights reserved. +// Copyright (c) 2017 Open Whisper Systems. All rights reserved. // #import @@ -23,6 +19,8 @@ extern NSString *const SocketConnectingNotification; @interface TSSocketManager : NSObject +- (instancetype)init NS_UNAVAILABLE; + + (void)becomeActiveFromForeground; + (void)becomeActiveFromBackgroundExpectMessage:(BOOL)expected; diff --git a/src/Network/WebSockets/TSSocketManager.m b/src/Network/WebSockets/TSSocketManager.m index 68404d339..83a2ad4a0 100644 --- a/src/Network/WebSockets/TSSocketManager.m +++ b/src/Network/WebSockets/TSSocketManager.m @@ -61,6 +61,8 @@ NSString *const SocketConnectingNotification = @"SocketConnectingNotification"; [self addObserver:self forKeyPath:@"status" options:0 context:kSocketStatusObservationContext]; + OWSSingletonAssert(); + return self; } diff --git a/src/Storage/TSStorageManager.h b/src/Storage/TSStorageManager.h index 08f41e367..a0c9be407 100644 --- a/src/Storage/TSStorageManager.h +++ b/src/Storage/TSStorageManager.h @@ -16,6 +16,8 @@ extern NSString *const TSUIDatabaseConnectionDidUpdateNotification; @interface TSStorageManager : NSObject +- (instancetype)init NS_UNAVAILABLE; + + (instancetype)sharedManager; /** diff --git a/src/Storage/TSStorageManager.m b/src/Storage/TSStorageManager.m index eaca489b8..ace86f0a2 100644 --- a/src/Storage/TSStorageManager.m +++ b/src/Storage/TSStorageManager.m @@ -129,6 +129,8 @@ static NSString *keychainDBPassAccount = @"TSDatabasePass"; [NSException raise:TSStorageManagerExceptionNameNoDatabase format:@"Failed to initialize database."]; } + + OWSSingletonAssert(); } return self; diff --git a/src/Util/Asserts.h b/src/Util/Asserts.h index d0cfbc728..6ec08413e 100755 --- a/src/Util/Asserts.h +++ b/src/Util/Asserts.h @@ -35,3 +35,37 @@ NSCAssert(0, @"Assertion failed: %s", CONVERT_EXPR_TO_STRING(X)); \ #endif #endif + +#pragma mark - Singleton Asserts + +// The "singleton asserts" can be used to ensure +// that we only create a singleton once. +// +// The simplest way to use them is the OWSSingletonAssert() macro. +// It is intended to be used inside the singleton's initializer. +// +// If, however, a singleton has multiple possible initializers, +// you need to: +// +// 1. Use OWSSingletonAssertFlag() outside the class definition. +// 2. Use OWSSingletonAssertInit() in each initializer. +#ifdef DEBUG + +#define OWSSingletonAssertFlag() static BOOL _isSingletonCreated = NO; + +#define OWSSingletonAssertInit() \ + @synchronized([self class]) \ + { \ + OWSAssert(!_isSingletonCreated); \ + _isSingletonCreated = YES; \ + } + +#define OWSSingletonAssert() OWSSingletonAssertFlag() OWSSingletonAssertInit() + +#else + +#define OWSSingletonAssertFlag() +#define OWSSingletonAssertInit() +#define OWSSingletonAssert() + +#endif