Skip to content

Commit 1338e87

Browse files
committed
Moved onError, onCompleted and cancel.unsubscribed outside the lock
1 parent d5d0159 commit 1338e87

File tree

1 file changed

+33
-18
lines changed

1 file changed

+33
-18
lines changed

rxjava-core/src/main/java/rx/operators/OperationCombineLatest.java

Lines changed: 33 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -182,38 +182,49 @@ public Collector(Observer<? super R> observer, Subscription cancel, int count) {
182182
this.lock = new ReentrantLock();
183183
}
184184
public void next(int index, T value) {
185+
Throwable err = null;
185186
lock.lock();
186187
try {
187-
values[index] = value;
188-
if (!hasValue.get(index)) {
189-
hasValue.set(index);
190-
hasCount++;
191-
}
192-
if (hasCount == values.length) {
193-
// clone: defensive copy due to varargs
194-
try {
195-
observer.onNext(combiner.call(values.clone()));
196-
} catch (Throwable t) {
197-
terminate();
198-
observer.onError(t);
199-
cancel.unsubscribe();
188+
if (!isTerminated()) {
189+
values[index] = value;
190+
if (!hasValue.get(index)) {
191+
hasValue.set(index);
192+
hasCount++;
193+
}
194+
if (hasCount == values.length) {
195+
// clone: defensive copy due to varargs
196+
try {
197+
observer.onNext(combiner.call(values.clone()));
198+
} catch (Throwable t) {
199+
terminate();
200+
err = t;
201+
}
200202
}
201203
}
202204
} finally {
203205
lock.unlock();
204206
}
207+
if (err != null) {
208+
// no need to lock here
209+
observer.onError(err);
210+
cancel.unsubscribe();
211+
}
205212
}
206213
public void error(int index, Throwable e) {
214+
boolean unsub = false;
207215
lock.lock();
208216
try {
209217
if (!isTerminated()) {
210218
terminate();
211-
observer.onError(e);
212-
cancel.unsubscribe();
219+
unsub = true;
213220
}
214221
} finally {
215222
lock.unlock();
216223
}
224+
if (unsub) {
225+
observer.onError(e);
226+
cancel.unsubscribe();
227+
}
217228
}
218229
boolean isTerminated() {
219230
return completedCount == values.length + 1;
@@ -223,6 +234,7 @@ void terminate() {
223234
Arrays.fill(values, null);
224235
}
225236
public void completed(int index) {
237+
boolean unsub = false;
226238
lock.lock();
227239
try {
228240
if (!completed.get(index)) {
@@ -232,13 +244,16 @@ public void completed(int index) {
232244
if ((!hasValue.get(index) || completedCount == values.length)
233245
&& !isTerminated()) {
234246
terminate();
235-
observer.onCompleted();
236-
cancel.unsubscribe();
247+
unsub = true;
237248
}
238249
} finally {
239250
lock.unlock();
240251
}
241-
252+
if (unsub) {
253+
// no need to hold a lock at this point
254+
observer.onCompleted();
255+
cancel.unsubscribe();
256+
}
242257
}
243258
}
244259
/**

0 commit comments

Comments
 (0)