OLD | NEW |
---|---|
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 package org.chromium.net; | 5 package org.chromium.net; |
6 | 6 |
7 import android.content.Context; | 7 import android.content.Context; |
8 import android.os.Build; | 8 import android.os.Build; |
9 import android.os.ConditionVariable; | 9 import android.os.ConditionVariable; |
10 import android.os.Handler; | 10 import android.os.Handler; |
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
78 @UsedByReflection("CronetEngine.java") | 78 @UsedByReflection("CronetEngine.java") |
79 public CronetUrlRequestContext(final CronetEngine.Builder builder) { | 79 public CronetUrlRequestContext(final CronetEngine.Builder builder) { |
80 CronetLibraryLoader.ensureInitialized(builder.getContext(), builder); | 80 CronetLibraryLoader.ensureInitialized(builder.getContext(), builder); |
81 nativeSetMinLogLevel(getLoggingLevel()); | 81 nativeSetMinLogLevel(getLoggingLevel()); |
82 synchronized (mLock) { | 82 synchronized (mLock) { |
83 mUrlRequestContextAdapter = nativeCreateRequestContextAdapter( | 83 mUrlRequestContextAdapter = nativeCreateRequestContextAdapter( |
84 createNativeUrlRequestContextConfig(builder.getContext(), bu ilder)); | 84 createNativeUrlRequestContextConfig(builder.getContext(), bu ilder)); |
85 if (mUrlRequestContextAdapter == 0) { | 85 if (mUrlRequestContextAdapter == 0) { |
86 throw new NullPointerException("Context Adapter creation failed. "); | 86 throw new NullPointerException("Context Adapter creation failed. "); |
87 } | 87 } |
88 mNetworkQualityEstimatorEnabled = builder.networkQualityEstimatorEna bled(); | |
88 } | 89 } |
89 | 90 |
90 // Init native Chromium URLRequestContext on main UI thread. | 91 // Init native Chromium URLRequestContext on main UI thread. |
91 Runnable task = new Runnable() { | 92 Runnable task = new Runnable() { |
92 @Override | 93 @Override |
93 public void run() { | 94 public void run() { |
94 CronetLibraryLoader.ensureInitializedOnMainThread(builder.getCon text()); | 95 CronetLibraryLoader.ensureInitializedOnMainThread(builder.getCon text()); |
95 synchronized (mLock) { | 96 synchronized (mLock) { |
96 // mUrlRequestContextAdapter is guaranteed to exist until | 97 // mUrlRequestContextAdapter is guaranteed to exist until |
97 // initialization on main and network threads completes and | 98 // initialization on main and network threads completes and |
(...skipping 12 matching lines...) Expand all Loading... | |
110 | 111 |
111 static long createNativeUrlRequestContextConfig( | 112 static long createNativeUrlRequestContextConfig( |
112 final Context context, CronetEngine.Builder builder) { | 113 final Context context, CronetEngine.Builder builder) { |
113 final long urlRequestContextConfig = nativeCreateRequestContextConfig( | 114 final long urlRequestContextConfig = nativeCreateRequestContextConfig( |
114 builder.getUserAgent(), builder.storagePath(), builder.quicEnabl ed(), | 115 builder.getUserAgent(), builder.storagePath(), builder.quicEnabl ed(), |
115 builder.getDefaultQuicUserAgentId(context), builder.http2Enabled (), | 116 builder.getDefaultQuicUserAgentId(context), builder.http2Enabled (), |
116 builder.sdchEnabled(), builder.dataReductionProxyKey(), | 117 builder.sdchEnabled(), builder.dataReductionProxyKey(), |
117 builder.dataReductionProxyPrimaryProxy(), builder.dataReductionP roxyFallbackProxy(), | 118 builder.dataReductionProxyPrimaryProxy(), builder.dataReductionP roxyFallbackProxy(), |
118 builder.dataReductionProxySecureProxyCheckUrl(), builder.cacheDi sabled(), | 119 builder.dataReductionProxySecureProxyCheckUrl(), builder.cacheDi sabled(), |
119 builder.httpCacheMode(), builder.httpCacheMaxSize(), builder.exp erimentalOptions(), | 120 builder.httpCacheMode(), builder.httpCacheMaxSize(), builder.exp erimentalOptions(), |
120 builder.mockCertVerifier()); | 121 builder.mockCertVerifier(), builder.networkQualityEstimatorEnabl ed()); |
121 for (Builder.QuicHint quicHint : builder.quicHints()) { | 122 for (Builder.QuicHint quicHint : builder.quicHints()) { |
122 nativeAddQuicHint(urlRequestContextConfig, quicHint.mHost, quicHint. mPort, | 123 nativeAddQuicHint(urlRequestContextConfig, quicHint.mHost, quicHint. mPort, |
123 quicHint.mAlternatePort); | 124 quicHint.mAlternatePort); |
124 } | 125 } |
125 for (Builder.Pkp pkp : builder.publicKeyPins()) { | 126 for (Builder.Pkp pkp : builder.publicKeyPins()) { |
126 nativeAddPkp(urlRequestContextConfig, pkp.mHost, pkp.mHashes, pkp.mI ncludeSubdomains, | 127 nativeAddPkp(urlRequestContextConfig, pkp.mHost, pkp.mHashes, pkp.mI ncludeSubdomains, |
127 pkp.mExpirationDate.getTime()); | 128 pkp.mExpirationDate.getTime()); |
128 } | 129 } |
129 return urlRequestContextConfig; | 130 return urlRequestContextConfig; |
130 } | 131 } |
(...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
215 } | 216 } |
216 } | 217 } |
217 | 218 |
218 // This method is intentionally non-static to ensure Cronet native library | 219 // This method is intentionally non-static to ensure Cronet native library |
219 // is loaded by class constructor. | 220 // is loaded by class constructor. |
220 @Override | 221 @Override |
221 public byte[] getGlobalMetricsDeltas() { | 222 public byte[] getGlobalMetricsDeltas() { |
222 return nativeGetHistogramDeltas(); | 223 return nativeGetHistogramDeltas(); |
223 } | 224 } |
224 | 225 |
226 /** | |
227 * TODO(tbansal): http://crbug.com/618034 Remove this API once all | |
228 * embedders have switched to using a request finished listener that | |
229 * provides its own executor. | |
230 */ | |
231 @Override | |
232 public void setRequestFinishedListenerExecutor(Executor executor) { | |
233 if (!mNetworkQualityEstimatorEnabled) { | |
234 throw new IllegalStateException("Network quality estimator not enabl ed"); | |
235 } | |
236 if (executor == null) { | |
237 throw new NullPointerException("Request finished listener requires a n executor"); | |
238 } | |
239 if (mNetworkQualityExecutor != null) { | |
240 throw new NullPointerException("Request finished listener executor a lready set"); | |
241 } | |
242 mNetworkQualityExecutor = executor; | |
243 } | |
244 | |
245 /** | |
246 * TODO(tbansal): http://crbug.com/618034 Remove this API once all | |
247 * embedders have switched to using CronetEngine builder for enabling | |
248 * network quality estimator. | |
249 */ | |
225 @Override | 250 @Override |
226 public void enableNetworkQualityEstimator(Executor executor) { | 251 public void enableNetworkQualityEstimator(Executor executor) { |
227 enableNetworkQualityEstimatorForTesting(false, false, executor); | |
228 } | |
229 | |
230 @VisibleForTesting | |
231 @Override | |
232 void enableNetworkQualityEstimatorForTesting( | |
233 boolean useLocalHostRequests, boolean useSmallerResponses, Executor executor) { | |
234 if (mNetworkQualityEstimatorEnabled) { | 252 if (mNetworkQualityEstimatorEnabled) { |
235 throw new IllegalStateException("Network quality estimator already e nabled"); | 253 throw new IllegalStateException("Network quality estimator already e nabled"); |
236 } | 254 } |
237 mNetworkQualityEstimatorEnabled = true; | 255 mNetworkQualityEstimatorEnabled = true; |
238 if (executor == null) { | 256 if (executor == null) { |
239 throw new NullPointerException("Network quality estimator requires a n executor"); | 257 throw new NullPointerException("Network quality estimator requires a n executor"); |
240 } | 258 } |
241 mNetworkQualityExecutor = executor; | 259 mNetworkQualityExecutor = executor; |
242 synchronized (mLock) { | 260 synchronized (mLock) { |
243 checkHaveAdapter(); | 261 checkHaveAdapter(); |
244 nativeEnableNetworkQualityEstimator( | 262 nativeEnableNetworkQualityEstimator(mUrlRequestContextAdapter); |
263 } | |
264 } | |
265 | |
266 @VisibleForTesting | |
267 @Override | |
268 void configureNetworkQualityEstimatorForTesting( | |
269 boolean useLocalHostRequests, boolean useSmallerResponses) { | |
270 if (!mNetworkQualityEstimatorEnabled) { | |
271 throw new IllegalStateException("Network quality estimator must be e nabled"); | |
272 } | |
273 synchronized (mLock) { | |
274 checkHaveAdapter(); | |
275 nativeConfigureNetworkQualityEstimatorForTesting( | |
245 mUrlRequestContextAdapter, useLocalHostRequests, useSmallerR esponses); | 276 mUrlRequestContextAdapter, useLocalHostRequests, useSmallerR esponses); |
246 } | 277 } |
247 } | 278 } |
248 | 279 |
249 @Override | 280 @Override |
250 public void addRttListener(NetworkQualityRttListener listener) { | 281 public void addRttListener(NetworkQualityRttListener listener) { |
251 if (!mNetworkQualityEstimatorEnabled) { | 282 if (!mNetworkQualityEstimatorEnabled) { |
252 throw new IllegalStateException("Network quality estimator must be e nabled"); | 283 throw new IllegalStateException("Network quality estimator must be e nabled"); |
253 } | 284 } |
285 if (mNetworkQualityExecutor == null && listener.getExecutor() == null) { | |
286 throw new IllegalStateException("Executor must not be null"); | |
287 } | |
254 synchronized (mNetworkQualityLock) { | 288 synchronized (mNetworkQualityLock) { |
255 if (mRttListenerList.isEmpty()) { | 289 if (mRttListenerList.isEmpty()) { |
256 synchronized (mLock) { | 290 synchronized (mLock) { |
257 checkHaveAdapter(); | 291 checkHaveAdapter(); |
258 nativeProvideRTTObservations(mUrlRequestContextAdapter, true ); | 292 nativeProvideRTTObservations(mUrlRequestContextAdapter, true ); |
259 } | 293 } |
260 } | 294 } |
261 mRttListenerList.addObserver(listener); | 295 mRttListenerList.addObserver(listener); |
262 } | 296 } |
263 } | 297 } |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
303 mThroughputListenerList.removeObserver(listener); | 337 mThroughputListenerList.removeObserver(listener); |
304 if (mThroughputListenerList.isEmpty()) { | 338 if (mThroughputListenerList.isEmpty()) { |
305 synchronized (mLock) { | 339 synchronized (mLock) { |
306 checkHaveAdapter(); | 340 checkHaveAdapter(); |
307 nativeProvideThroughputObservations(mUrlRequestContextAdapte r, false); | 341 nativeProvideThroughputObservations(mUrlRequestContextAdapte r, false); |
308 } | 342 } |
309 } | 343 } |
310 } | 344 } |
311 } | 345 } |
312 | 346 |
347 /** | |
348 * TODO(tbansal): http://crbug.com/618034 Remove this API once all | |
349 * embedders have switched to using a request finished listener that | |
350 * provides its own executor. | |
351 */ | |
313 @Override | 352 @Override |
314 public void addRequestFinishedListener(RequestFinishedListener listener) { | 353 public void addRequestFinishedListener(RequestFinishedListener listener) { |
315 if (!mNetworkQualityEstimatorEnabled) { | 354 if (!mNetworkQualityEstimatorEnabled) { |
316 throw new IllegalStateException("Network quality estimator must be e nabled"); | 355 throw new IllegalStateException("Network quality estimator must be e nabled"); |
317 } | 356 } |
357 // RequestFinishedListener does not provide its own executor. | |
358 if (mNetworkQualityExecutor == null) { | |
359 throw new IllegalStateException("Executor must not be null"); | |
360 } | |
318 synchronized (mNetworkQualityLock) { | 361 synchronized (mNetworkQualityLock) { |
319 mFinishedListenerList.addObserver(listener); | 362 mFinishedListenerList.addObserver(listener); |
320 } | 363 } |
321 } | 364 } |
322 | 365 |
366 /** | |
367 * TODO(tbansal): http://crbug.com/618034 Remove this API. | |
368 */ | |
323 @Override | 369 @Override |
324 public void removeRequestFinishedListener(RequestFinishedListener listener) { | 370 public void removeRequestFinishedListener(RequestFinishedListener listener) { |
325 if (!mNetworkQualityEstimatorEnabled) { | 371 if (!mNetworkQualityEstimatorEnabled) { |
326 throw new IllegalStateException("Network quality estimator must be e nabled"); | 372 throw new IllegalStateException("Network quality estimator must be e nabled"); |
327 } | 373 } |
328 synchronized (mNetworkQualityLock) { | 374 synchronized (mNetworkQualityLock) { |
329 mFinishedListenerList.removeObserver(listener); | 375 mFinishedListenerList.removeObserver(listener); |
330 } | 376 } |
331 } | 377 } |
332 | 378 |
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
409 mNetworkThread = Thread.currentThread(); | 455 mNetworkThread = Thread.currentThread(); |
410 mInitCompleted.open(); | 456 mInitCompleted.open(); |
411 } | 457 } |
412 Thread.currentThread().setName("ChromiumNet"); | 458 Thread.currentThread().setName("ChromiumNet"); |
413 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); | 459 Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); |
414 } | 460 } |
415 | 461 |
416 @SuppressWarnings("unused") | 462 @SuppressWarnings("unused") |
417 @CalledByNative | 463 @CalledByNative |
418 private void onRttObservation(final int rttMs, final long whenMs, final int source) { | 464 private void onRttObservation(final int rttMs, final long whenMs, final int source) { |
419 Runnable task = new Runnable() { | 465 synchronized (mNetworkQualityLock) { |
420 @Override | 466 for (final NetworkQualityRttListener listener : mRttListenerList) { |
421 public void run() { | 467 Runnable task = new Runnable() { |
422 synchronized (mNetworkQualityLock) { | 468 @Override |
423 for (NetworkQualityRttListener listener : mRttListenerList) { | 469 public void run() { |
424 listener.onRttObservation(rttMs, whenMs, source); | 470 listener.onRttObservation(rttMs, whenMs, source); |
425 } | 471 } |
426 } | 472 }; |
473 // Use the executor provided by the listener. If not available, | |
474 // use the network quality executor. | |
475 // TODO(tbansal): Change this to always use the executor | |
476 // provided by the listener, once all embedders start providing | |
477 // a non-null executor. | |
478 Executor executor = listener.getExecutor() != null ? listener.ge tExecutor() | |
mef
2016/06/20 16:50:27
Why do we have this fallback in onRttObservation b
tbansal1
2016/06/20 20:06:57
Same reason as I commented elsewhere: "Because, th
| |
479 : mNetworkQua lityExecutor; | |
480 postObservationTaskToExecutor(executor, task); | |
427 } | 481 } |
428 }; | 482 } |
429 postObservationTaskToNetworkQualityExecutor(task); | |
430 } | 483 } |
431 | 484 |
432 @SuppressWarnings("unused") | 485 @SuppressWarnings("unused") |
433 @CalledByNative | 486 @CalledByNative |
434 private void onThroughputObservation( | 487 private void onThroughputObservation( |
435 final int throughputKbps, final long whenMs, final int source) { | 488 final int throughputKbps, final long whenMs, final int source) { |
489 synchronized (mNetworkQualityLock) { | |
490 for (final NetworkQualityThroughputListener listener : mThroughputLi stenerList) { | |
491 Runnable task = new Runnable() { | |
492 @Override | |
493 public void run() { | |
494 listener.onThroughputObservation(throughputKbps, whenMs, source); | |
495 } | |
496 }; | |
497 postObservationTaskToExecutor(listener.getExecutor(), task); | |
498 } | |
499 } | |
500 } | |
501 | |
502 void reportFinished(final CronetUrlRequest request) { | |
503 if (!mNetworkQualityEstimatorEnabled) { | |
504 return; | |
505 } | |
506 // If no request finished listener has been added, then mNetworkQualityE xecutor may be | |
507 // null. Exit early to avoid posting to a null executor. | |
508 synchronized (mNetworkQualityLock) { | |
509 if (mFinishedListenerList.isEmpty()) { | |
510 return; | |
511 } | |
512 } | |
436 Runnable task = new Runnable() { | 513 Runnable task = new Runnable() { |
437 @Override | 514 @Override |
438 public void run() { | 515 public void run() { |
439 synchronized (mNetworkQualityLock) { | 516 synchronized (mNetworkQualityLock) { |
440 for (NetworkQualityThroughputListener listener : mThroughput ListenerList) { | 517 UrlRequestInfo requestInfo = request.getRequestInfo(); |
441 listener.onThroughputObservation(throughputKbps, whenMs, source); | 518 for (RequestFinishedListener listener : mFinishedListenerLis t) { |
519 listener.onRequestFinished(requestInfo); | |
442 } | 520 } |
443 } | 521 } |
444 } | 522 } |
445 }; | 523 }; |
446 postObservationTaskToNetworkQualityExecutor(task); | 524 // Use {@link mNetworkQualityExecutor} since |
525 // RequestFInishedListeners do not provide an executor. | |
526 postObservationTaskToExecutor(mNetworkQualityExecutor, task); | |
447 } | 527 } |
448 | 528 |
449 void reportFinished(final CronetUrlRequest request) { | 529 private static void postObservationTaskToExecutor(Executor executor, Runnabl e task) { |
450 if (mNetworkQualityEstimatorEnabled) { | |
451 Runnable task = new Runnable() { | |
452 @Override | |
453 public void run() { | |
454 synchronized (mNetworkQualityLock) { | |
455 UrlRequestInfo requestInfo = request.getRequestInfo(); | |
456 for (RequestFinishedListener listener : mFinishedListene rList) { | |
457 listener.onRequestFinished(requestInfo); | |
458 } | |
459 } | |
460 } | |
461 }; | |
462 postObservationTaskToNetworkQualityExecutor(task); | |
463 } | |
464 } | |
465 | |
466 void postObservationTaskToNetworkQualityExecutor(Runnable task) { | |
467 try { | 530 try { |
468 mNetworkQualityExecutor.execute(task); | 531 executor.execute(task); |
469 } catch (RejectedExecutionException failException) { | 532 } catch (RejectedExecutionException failException) { |
470 Log.e(CronetUrlRequestContext.LOG_TAG, "Exception posting task to ex ecutor", | 533 Log.e(CronetUrlRequestContext.LOG_TAG, "Exception posting task to ex ecutor", |
471 failException); | 534 failException); |
472 } | 535 } |
473 } | 536 } |
474 | 537 |
475 // Native methods are implemented in cronet_url_request_context_adapter.cc. | 538 // Native methods are implemented in cronet_url_request_context_adapter.cc. |
476 private static native long nativeCreateRequestContextConfig(String userAgent , | 539 private static native long nativeCreateRequestContextConfig(String userAgent , |
477 String storagePath, boolean quicEnabled, String quicUserAgentId, boo lean http2Enabled, | 540 String storagePath, boolean quicEnabled, String quicUserAgentId, boo lean http2Enabled, |
478 boolean sdchEnabled, String dataReductionProxyKey, | 541 boolean sdchEnabled, String dataReductionProxyKey, |
479 String dataReductionProxyPrimaryProxy, String dataReductionProxyFall backProxy, | 542 String dataReductionProxyPrimaryProxy, String dataReductionProxyFall backProxy, |
480 String dataReductionProxySecureProxyCheckUrl, boolean disableCache, int httpCacheMode, | 543 String dataReductionProxySecureProxyCheckUrl, boolean disableCache, int httpCacheMode, |
481 long httpCacheMaxSize, String experimentalOptions, long mockCertVeri fier); | 544 long httpCacheMaxSize, String experimentalOptions, long mockCertVeri fier, |
545 boolean enableNetworkQualityEstimator); | |
482 | 546 |
483 private static native void nativeAddQuicHint( | 547 private static native void nativeAddQuicHint( |
484 long urlRequestContextConfig, String host, int port, int alternatePo rt); | 548 long urlRequestContextConfig, String host, int port, int alternatePo rt); |
485 | 549 |
486 private static native void nativeAddPkp(long urlRequestContextConfig, String host, | 550 private static native void nativeAddPkp(long urlRequestContextConfig, String host, |
487 byte[][] hashes, boolean includeSubdomains, long expirationTime); | 551 byte[][] hashes, boolean includeSubdomains, long expirationTime); |
488 | 552 |
489 private static native long nativeCreateRequestContextAdapter(long urlRequest ContextConfig); | 553 private static native long nativeCreateRequestContextAdapter(long urlRequest ContextConfig); |
490 | 554 |
491 private static native int nativeSetMinLogLevel(int loggingLevel); | 555 private static native int nativeSetMinLogLevel(int loggingLevel); |
492 | 556 |
493 private static native byte[] nativeGetHistogramDeltas(); | 557 private static native byte[] nativeGetHistogramDeltas(); |
494 | 558 |
495 @NativeClassQualifiedName("CronetURLRequestContextAdapter") | 559 @NativeClassQualifiedName("CronetURLRequestContextAdapter") |
496 private native void nativeDestroy(long nativePtr); | 560 private native void nativeDestroy(long nativePtr); |
497 | 561 |
498 @NativeClassQualifiedName("CronetURLRequestContextAdapter") | 562 @NativeClassQualifiedName("CronetURLRequestContextAdapter") |
499 private native void nativeStartNetLogToFile(long nativePtr, | 563 private native void nativeStartNetLogToFile(long nativePtr, |
500 String fileName, boolean logAll); | 564 String fileName, boolean logAll); |
501 | 565 |
502 @NativeClassQualifiedName("CronetURLRequestContextAdapter") | 566 @NativeClassQualifiedName("CronetURLRequestContextAdapter") |
503 private native void nativeStopNetLog(long nativePtr); | 567 private native void nativeStopNetLog(long nativePtr); |
504 | 568 |
505 @NativeClassQualifiedName("CronetURLRequestContextAdapter") | 569 @NativeClassQualifiedName("CronetURLRequestContextAdapter") |
506 private native void nativeInitRequestContextOnMainThread(long nativePtr); | 570 private native void nativeInitRequestContextOnMainThread(long nativePtr); |
507 | 571 |
508 @NativeClassQualifiedName("CronetURLRequestContextAdapter") | 572 @NativeClassQualifiedName("CronetURLRequestContextAdapter") |
509 private native void nativeEnableNetworkQualityEstimator( | 573 private native void nativeConfigureNetworkQualityEstimatorForTesting( |
510 long nativePtr, boolean useLocalHostRequests, boolean useSmallerResp onses); | 574 long nativePtr, boolean useLocalHostRequests, boolean useSmallerResp onses); |
511 | 575 |
512 @NativeClassQualifiedName("CronetURLRequestContextAdapter") | 576 @NativeClassQualifiedName("CronetURLRequestContextAdapter") |
577 private native void nativeEnableNetworkQualityEstimator(long nativePtr); | |
578 | |
579 @NativeClassQualifiedName("CronetURLRequestContextAdapter") | |
513 private native void nativeProvideRTTObservations(long nativePtr, boolean sho uld); | 580 private native void nativeProvideRTTObservations(long nativePtr, boolean sho uld); |
514 | 581 |
515 @NativeClassQualifiedName("CronetURLRequestContextAdapter") | 582 @NativeClassQualifiedName("CronetURLRequestContextAdapter") |
516 private native void nativeProvideThroughputObservations(long nativePtr, bool ean should); | 583 private native void nativeProvideThroughputObservations(long nativePtr, bool ean should); |
517 } | 584 } |
OLD | NEW |