// // PSPDFThreadSafeMutableDictionary.m // // Copyright (c) 2013 Peter Steinberger, PSPDFKit GmbH. All rights reserved. // // Permission is hereby granted, free of charge, to any person obtaining a copy // of this software and associated documentation files (the "Software"), to deal // in the Software without restriction, including without limitation the rights // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell // copies of the Software, and to permit persons to whom the Software is // furnished to do so, subject to the following conditions: // // The above copyright notice and this permission notice shall be included in // all copies or substantial portions of the Software. // // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN // THE SOFTWARE. #import // Dictionary-Subclasss whose primitive operations are thread safe. @interface PSPDFThreadSafeMutableDictionary : NSMutableDictionary @end // ---------------------------------------------------------------- #import "PSPDFThreadSafeMutableDictionary.h" #import @implementation PSPDFThreadSafeMutableDictionary { OSSpinLock _lock; NSMutableDictionary *_dictionary; // Class Cluster } /////////////////////////////////////////////////////////////////////////////////////////// #pragma mark - NSObject - (id)init { return [self initWithCapacity:0]; } - (id)initWithObjects:(NSArray *)objects forKeys:(NSArray *)keys { if ((self = [self initWithCapacity:objects.count])) { [objects enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) { _dictionary[keys[idx]] = obj; }]; } return self; } - (id)initWithCapacity:(NSUInteger)capacity { if ((self = [super init])) { _dictionary = [[NSMutableDictionary alloc] initWithCapacity:capacity]; _lock = OS_SPINLOCK_INIT; } return self; } /////////////////////////////////////////////////////////////////////////////////////////// #pragma mark - NSMutableDictionary - (void)setObject:(id)anObject forKey:(id)aKey { OSSpinLockLock(&_lock); _dictionary[aKey] = anObject; OSSpinLockUnlock(&_lock); } - (void)removeObjectForKey:(id)aKey { OSSpinLockLock(&_lock); [_dictionary removeObjectForKey:aKey]; OSSpinLockUnlock(&_lock); } - (NSUInteger)count { OSSpinLockLock(&_lock); NSUInteger count = _dictionary.count; OSSpinLockUnlock(&_lock); return count; } - (id)objectForKey:(id)aKey { OSSpinLockLock(&_lock); id obj = _dictionary[aKey]; OSSpinLockUnlock(&_lock); return obj; } - (NSEnumerator *)keyEnumerator { OSSpinLockLock(&_lock); NSEnumerator *keyEnumerator = [_dictionary keyEnumerator]; OSSpinLockUnlock(&_lock); return keyEnumerator; } @end