An amazing project that generates micro reports from tournament results
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
pa-tournament-stats/Carthage/Checkouts/realm-cocoa/Realm/RLMThreadSafeReference.mm

79 lines
2.6 KiB

////////////////////////////////////////////////////////////////////////////
//
// Copyright 2016 Realm Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
////////////////////////////////////////////////////////////////////////////
#import "RLMThreadSafeReference_Private.hpp"
#import "RLMUtil.hpp"
template<typename Function>
static auto translateErrors(Function&& f) {
try {
return f();
}
catch (std::exception const& e) {
@throw RLMException(e);
}
}
@implementation RLMThreadSafeReference {
std::unique_ptr<realm::ThreadSafeReferenceBase> _reference;
id _metadata;
Class _type;
}
- (instancetype)initWithThreadConfined:(id<RLMThreadConfined>)threadConfined {
if (!(self = [super init])) {
return nil;
}
REALM_ASSERT_DEBUG([threadConfined conformsToProtocol:@protocol(RLMThreadConfined)]);
if (![threadConfined conformsToProtocol:@protocol(RLMThreadConfined_Private)]) {
@throw RLMException(@"Illegal custom conformance to `RLMThreadConfined` by `%@`", threadConfined.class);
} else if (threadConfined.invalidated) {
@throw RLMException(@"Cannot construct reference to invalidated object");
} else if (!threadConfined.realm) {
@throw RLMException(@"Cannot construct reference to unmanaged object, "
"which can be passed across threads directly");
}
translateErrors([&] {
_reference = [(id<RLMThreadConfined_Private>)threadConfined makeThreadSafeReference];
_metadata = ((id<RLMThreadConfined_Private>)threadConfined).objectiveCMetadata;
});
_type = threadConfined.class;
return self;
}
+ (instancetype)referenceWithThreadConfined:(id<RLMThreadConfined>)threadConfined {
return [[self alloc] initWithThreadConfined:threadConfined];
}
- (id<RLMThreadConfined>)resolveReferenceInRealm:(RLMRealm *)realm {
if (!_reference) {
@throw RLMException(@"Can only resolve a thread safe reference once.");
}
return translateErrors([&] {
return [_type objectWithThreadSafeReference:std::move(_reference) metadata:_metadata realm:realm];
});
}
- (BOOL)isInvalidated {
return !_reference;
}
@end