@@ -149,11 +149,10 @@ public void uncaughtException(Thread t, Throwable e) {
149
149
this .throttle = throttle ;
150
150
}
151
151
152
- @ SuppressWarnings ("GuardedBy" )
152
+ @ SuppressWarnings ("GuardedBy" ) // TODO(b/145386688) this.lock==ScheduledCancellor.lock so ok
153
153
@ Nullable // null if already committed
154
154
@ CheckReturnValue
155
155
private Runnable commit (final Substream winningSubstream ) {
156
-
157
156
synchronized (lock ) {
158
157
if (state .winningSubstream != null ) {
159
158
return null ;
@@ -165,10 +164,9 @@ private Runnable commit(final Substream winningSubstream) {
165
164
// subtract the share of this RPC from channelBufferUsed.
166
165
channelBufferUsed .addAndGet (-perRpcBufferUsed );
167
166
167
+ final boolean wasCancelled = (scheduledRetry != null ) ? scheduledRetry .isCancelled () : false ;
168
168
final Future <?> retryFuture ;
169
169
if (scheduledRetry != null ) {
170
- // TODO(b/145386688): This access should be guarded by 'this.scheduledRetry.lock'; instead
171
- // found: 'this.lock'
172
170
retryFuture = scheduledRetry .markCancelled ();
173
171
scheduledRetry = null ;
174
172
} else {
@@ -177,8 +175,6 @@ private Runnable commit(final Substream winningSubstream) {
177
175
// cancel the scheduled hedging if it is scheduled prior to the commitment
178
176
final Future <?> hedgingFuture ;
179
177
if (scheduledHedging != null ) {
180
- // TODO(b/145386688): This access should be guarded by 'this.scheduledHedging.lock'; instead
181
- // found: 'this.lock'
182
178
hedgingFuture = scheduledHedging .markCancelled ();
183
179
scheduledHedging = null ;
184
180
} else {
@@ -196,7 +192,21 @@ public void run() {
196
192
}
197
193
if (retryFuture != null ) {
198
194
retryFuture .cancel (false );
195
+ if (!wasCancelled && inFlightSubStreams .decrementAndGet () == Integer .MIN_VALUE ) {
196
+ assert savedCloseMasterListenerReason != null ;
197
+ listenerSerializeExecutor .execute (
198
+ new Runnable () {
199
+ @ Override
200
+ public void run () {
201
+ isClosed = true ;
202
+ masterListener .closed (savedCloseMasterListenerReason .status ,
203
+ savedCloseMasterListenerReason .progress ,
204
+ savedCloseMasterListenerReason .metadata );
205
+ }
206
+ });
207
+ }
199
208
}
209
+
200
210
if (hedgingFuture != null ) {
201
211
hedgingFuture .cancel (false );
202
212
}
@@ -415,7 +425,7 @@ public final void start(ClientStreamListener listener) {
415
425
drain (substream );
416
426
}
417
427
418
- @ SuppressWarnings ("GuardedBy" )
428
+ @ SuppressWarnings ("GuardedBy" ) // TODO(b/145386688) this.lock==ScheduledCancellor.lock so ok
419
429
private void pushbackHedging (@ Nullable Integer delayMillis ) {
420
430
if (delayMillis == null ) {
421
431
return ;
@@ -434,8 +444,6 @@ private void pushbackHedging(@Nullable Integer delayMillis) {
434
444
return ;
435
445
}
436
446
437
- // TODO(b/145386688): This access should be guarded by 'this.scheduledHedging.lock'; instead
438
- // found: 'this.lock'
439
447
futureToBeCancelled = scheduledHedging .markCancelled ();
440
448
scheduledHedging = future = new FutureCanceller (lock );
441
449
}
@@ -469,16 +477,13 @@ public void run() {
469
477
}
470
478
callExecutor .execute (
471
479
new Runnable () {
472
- @ SuppressWarnings ("GuardedBy" )
480
+ @ SuppressWarnings ("GuardedBy" ) //TODO(b/145386688) lock==ScheduledCancellor.lock so ok
473
481
@ Override
474
482
public void run () {
475
483
boolean cancelled = false ;
476
484
FutureCanceller future = null ;
477
485
478
486
synchronized (lock ) {
479
- // TODO(b/145386688): This access should be guarded by
480
- // 'HedgingRunnable.this.scheduledHedgingRef.lock'; instead found:
481
- // 'RetriableStream.this.lock'
482
487
if (scheduledHedgingRef .isCancelled ()) {
483
488
cancelled = true ;
484
489
} else {
@@ -810,13 +815,11 @@ private boolean hasPotentialHedging(State state) {
810
815
&& !state .hedgingFrozen ;
811
816
}
812
817
813
- @ SuppressWarnings ("GuardedBy" )
818
+ @ SuppressWarnings ("GuardedBy" ) // TODO(b/145386688) this.lock==ScheduledCancellor.lock so ok
814
819
private void freezeHedging () {
815
820
Future <?> futureToBeCancelled = null ;
816
821
synchronized (lock ) {
817
822
if (scheduledHedging != null ) {
818
- // TODO(b/145386688): This access should be guarded by 'this.scheduledHedging.lock'; instead
819
- // found: 'this.lock'
820
823
futureToBeCancelled = scheduledHedging .markCancelled ();
821
824
scheduledHedging = null ;
822
825
}
@@ -999,9 +1002,19 @@ public void run() {
999
1002
synchronized (lock ) {
1000
1003
scheduledRetry = scheduledRetryCopy = new FutureCanceller (lock );
1001
1004
}
1005
+
1002
1006
class RetryBackoffRunnable implements Runnable {
1003
1007
@ Override
1008
+ @ SuppressWarnings ("FutureReturnValueIgnored" )
1004
1009
public void run () {
1010
+ synchronized (scheduledRetryCopy .lock ) {
1011
+ if (scheduledRetryCopy .isCancelled ()) {
1012
+ return ;
1013
+ } else {
1014
+ scheduledRetryCopy .markCancelled ();
1015
+ }
1016
+ }
1017
+
1005
1018
callExecutor .execute (
1006
1019
new Runnable () {
1007
1020
@ Override
@@ -1563,11 +1576,16 @@ private static final class FutureCanceller {
1563
1576
}
1564
1577
1565
1578
void setFuture (Future <?> future ) {
1579
+ boolean wasCancelled ;
1566
1580
synchronized (lock ) {
1567
- if (!cancelled ) {
1581
+ wasCancelled = cancelled ;
1582
+ if (!wasCancelled ) {
1568
1583
this .future = future ;
1569
1584
}
1570
1585
}
1586
+ if (wasCancelled ) {
1587
+ future .cancel (false );
1588
+ }
1571
1589
}
1572
1590
1573
1591
@ GuardedBy ("lock" )
0 commit comments