@@ -70,6 +70,8 @@ @interface FView ()
7070@property (nonatomic , strong , readwrite ) FQuerySpec *query;
7171@property (nonatomic , strong ) FViewProcessor *processor;
7272@property (nonatomic , strong ) FViewCache *viewCache;
73+
74+ // All accesses must be guarded by @synchronized(self.eventRegistrations)
7375@property (nonatomic , strong ) NSMutableArray *eventRegistrations;
7476@property (nonatomic , strong ) FEventGenerator *eventGenerator;
7577
@@ -165,11 +167,15 @@ - (id)initWithQuery:(FQuerySpec *)query
165167}
166168
167169- (BOOL )isEmpty {
168- return self.eventRegistrations .count == 0 ;
170+ @synchronized (self.eventRegistrations ) {
171+ return self.eventRegistrations .count == 0 ;
172+ }
169173}
170174
171175- (void )addEventRegistration : (id <FEventRegistration>)eventRegistration {
172- [self .eventRegistrations addObject: eventRegistration];
176+ @synchronized (self.eventRegistrations ) {
177+ [self .eventRegistrations addObject: eventRegistration];
178+ }
173179}
174180
175181/* *
@@ -181,31 +187,33 @@ - (void)addEventRegistration:(id<FEventRegistration>)eventRegistration {
181187- (NSArray *)removeEventRegistration : (id <FEventRegistration>)eventRegistration
182188 cancelError : (NSError *)cancelError {
183189 NSMutableArray *cancelEvents = [[NSMutableArray alloc ] init ];
184- if (cancelError != nil ) {
185- NSAssert (eventRegistration == nil ,
186- @" A cancel should cancel all event registrations." );
187- FPath *path = self.query .path ;
188- for (id <FEventRegistration> registration in self.eventRegistrations ) {
189- FCancelEvent *maybeEvent =
190- [registration createCancelEventFromError: cancelError path: path];
191- if (maybeEvent) {
192- [cancelEvents addObject: maybeEvent];
190+ @synchronized (self.eventRegistrations ) {
191+ if (cancelError != nil ) {
192+ NSAssert (eventRegistration == nil ,
193+ @" A cancel should cancel all event registrations." );
194+ FPath *path = self.query .path ;
195+ for (id <FEventRegistration> registration in self
196+ .eventRegistrations ) {
197+ FCancelEvent *maybeEvent =
198+ [registration createCancelEventFromError: cancelError
199+ path: path];
200+ if (maybeEvent) {
201+ [cancelEvents addObject: maybeEvent];
202+ }
193203 }
194204 }
195- }
196205
197- if (eventRegistration) {
198- NSUInteger i = 0 ;
199- while (i < self.eventRegistrations .count ) {
200- id <FEventRegistration> existing = self.eventRegistrations [i];
201- if ([existing matches: eventRegistration]) {
202- [self .eventRegistrations removeObjectAtIndex: i];
203- } else {
204- i++;
205- }
206+ if (eventRegistration) {
207+ NSIndexSet *indexesToRemove =
208+ [self .eventRegistrations indexesOfObjectsPassingTest: ^BOOL (
209+ id <FEventRegistration> existing,
210+ NSUInteger idx, BOOL *stop) {
211+ return [existing matches: eventRegistration];
212+ }];
213+ [self .eventRegistrations removeObjectsAtIndexes: indexesToRemove];
214+ } else {
215+ [self .eventRegistrations removeAllObjects ];
206216 }
207- } else {
208- [self .eventRegistrations removeAllObjects ];
209217 }
210218 return cancelEvents;
211219}
@@ -270,7 +278,10 @@ - (NSArray *)generateEventsForChanges:(NSArray *)changes
270278 registration : (id <FEventRegistration>)registration {
271279 NSArray *registrations;
272280 if (registration == nil ) {
273- registrations = [[NSArray alloc ] initWithArray: self .eventRegistrations];
281+ @synchronized (self.eventRegistrations ) {
282+ registrations =
283+ [[NSArray alloc ] initWithArray: self .eventRegistrations];
284+ }
274285 } else {
275286 registrations = [[NSArray alloc ] initWithObjects: registration, nil ];
276287 }
0 commit comments