DefaultPromise.getNow() does not correctly handle DefaultPromise.setUncancellable() (#8154)

Motivation:

We do not correctly check for previous calles of setUncancellable() in getNow() which may result in ClassCastException as we incorrectly return the internally UNCANCELLABLE object and not null if setUncancellable() we as called before.

Modifications:

Correctly check for UNCANCELLABLE and add unit test.

Result:

Fixes https://github.com/netty/netty/issues/8135.
This commit is contained in:
Norman Maurer 2018-07-27 01:55:21 +08:00 committed by GitHub
parent 952eeb8e1e
commit 0dc71cee3a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 18 additions and 5 deletions

View File

@ -301,7 +301,7 @@ public class DefaultPromise<V> extends AbstractFuture<V> implements Promise<V> {
@Override
public V getNow() {
Object result = this.result;
if (result instanceof CauseHolder || result == SUCCESS) {
if (result instanceof CauseHolder || result == SUCCESS || result == UNCANCELLABLE) {
return null;
}
return (V) result;

View File

@ -37,10 +37,7 @@ import java.util.concurrent.atomic.AtomicInteger;
import static java.lang.Math.max;
import static org.hamcrest.Matchers.lessThan;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertThat;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.*;
@SuppressWarnings("unchecked")
public class DefaultPromiseTest {
@ -258,6 +255,22 @@ public class DefaultPromiseTest {
assertTrue(promise.isSuccess());
}
@Test
public void setUncancellableGetNow() {
final Promise<String> promise = new DefaultPromise<String>(ImmediateEventExecutor.INSTANCE);
assertNull(promise.getNow());
assertTrue(promise.setUncancellable());
assertNull(promise.getNow());
assertFalse(promise.isDone());
assertFalse(promise.isSuccess());
promise.setSuccess("success");
assertTrue(promise.isDone());
assertTrue(promise.isSuccess());
assertEquals("success", promise.getNow());
}
private static void testStackOverFlowChainedFuturesA(int promiseChainLength, final EventExecutor executor,
boolean runTestInExecutorThread)
throws InterruptedException {