1 /* 2 * Copyright 2020 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.google.android.iwlan; 18 19 import static com.android.dx.mockito.inline.extended.ExtendedMockito.mockitoSession; 20 21 import static org.junit.Assert.assertEquals; 22 import static org.junit.Assert.assertFalse; 23 import static org.junit.Assert.assertTrue; 24 import static org.mockito.Mockito.*; 25 import static org.mockito.Mockito.mock; 26 import static org.mockito.Mockito.spy; 27 28 import android.content.ContentResolver; 29 import android.content.Context; 30 import android.content.res.AssetManager; 31 import android.net.ipsec.ike.exceptions.IkeProtocolException; 32 import android.os.PersistableBundle; 33 import android.telephony.CarrierConfigManager; 34 import android.telephony.DataFailCause; 35 import android.telephony.SubscriptionInfo; 36 import android.telephony.SubscriptionManager; 37 import android.telephony.TelephonyManager; 38 import android.telephony.data.DataService; 39 40 import androidx.test.InstrumentationRegistry; 41 42 import org.junit.After; 43 import org.junit.Before; 44 import org.junit.Test; 45 import org.mockito.Mock; 46 import org.mockito.MockitoAnnotations; 47 import org.mockito.MockitoSession; 48 import org.mockito.quality.Strictness; 49 50 import java.io.InputStream; 51 import java.util.Map; 52 53 public class ErrorPolicyManagerTest { 54 private static final String TAG = "ErrorPolicyManagerTest"; 55 56 // @Rule public final MockitoRule mockito = MockitoJUnit.rule(); 57 58 private ErrorPolicyManager mErrorPolicyManager; 59 private static final int DEFAULT_SLOT_INDEX = 0; 60 private static final int DEFAULT_SUBID = 0; 61 private static final int TEST_CARRIER_ID = 1; 62 63 @Mock private Context mMockContext; 64 @Mock CarrierConfigManager mMockCarrierConfigManager; 65 @Mock SubscriptionManager mMockSubscriptionManager; 66 @Mock TelephonyManager mMockTelephonyManager; 67 @Mock SubscriptionInfo mMockSubscriptionInfo; 68 @Mock DataService.DataServiceProvider mMockDataServiceProvider; 69 @Mock private ContentResolver mMockContentResolver; 70 MockitoSession mStaticMockSession; 71 72 @Before setUp()73 public void setUp() throws Exception { 74 MockitoAnnotations.initMocks(this); 75 mStaticMockSession = 76 mockitoSession() 77 .mockStatic(IwlanDataService.class) 78 .strictness(Strictness.LENIENT) 79 .startMocking(); 80 when(IwlanDataService.getDataServiceProvider(anyInt())) 81 .thenReturn(mMockDataServiceProvider); 82 AssetManager mockAssetManager = mock(AssetManager.class); 83 Context context = InstrumentationRegistry.getTargetContext(); 84 InputStream is = context.getResources().getAssets().open("defaultiwlanerrorconfig.json"); 85 doReturn(mockAssetManager).when(mMockContext).getAssets(); 86 doReturn(is).when(mockAssetManager).open(any()); 87 setupMockForCarrierConfig(null); 88 mErrorPolicyManager = spy(ErrorPolicyManager.getInstance(mMockContext, DEFAULT_SLOT_INDEX)); 89 } 90 91 @After cleanUp()92 public void cleanUp() throws Exception { 93 mStaticMockSession.finishMocking(); 94 mErrorPolicyManager.releaseInstance(); 95 } 96 buildIwlanIkeProtocolError(int errorCode, byte[] errorData)97 private static IwlanError buildIwlanIkeProtocolError(int errorCode, byte[] errorData) { 98 final IkeProtocolException exception = mock(IkeProtocolException.class); 99 when(exception.getErrorType()).thenReturn(errorCode); 100 when(exception.getErrorData()).thenReturn(errorData); 101 return new IwlanError(exception); 102 } 103 buildIwlanIkeProtocolError(int errorCode)104 private static IwlanError buildIwlanIkeProtocolError(int errorCode) { 105 return buildIwlanIkeProtocolError(errorCode, new byte[0]); 106 } 107 buildIwlanIkeAuthFailedError()108 private static IwlanError buildIwlanIkeAuthFailedError() { 109 return buildIwlanIkeProtocolError(IkeProtocolException.ERROR_TYPE_AUTHENTICATION_FAILED); 110 } 111 buildIwlanIkeChildSaNotFoundError()112 private static IwlanError buildIwlanIkeChildSaNotFoundError() { 113 return buildIwlanIkeProtocolError(IkeProtocolException.ERROR_TYPE_CHILD_SA_NOT_FOUND); 114 } 115 116 @Test testValidCarrierConfig()117 public void testValidCarrierConfig() throws Exception { 118 String apn = "ims"; 119 String config = 120 "[{" 121 + "\"ApnName\": \"" 122 + apn 123 + "\"," 124 + "\"ErrorTypes\": [{" 125 + getErrorTypeInJSON( 126 "IKE_PROTOCOL_ERROR_TYPE", 127 new String[] {"24", "34", "9000-9050"}, 128 new String[] {"4", "8", "16"}, 129 new String[] {"APM_ENABLE_EVENT", "WIFI_AP_CHANGED_EVENT"}) 130 + "}, {" 131 + getErrorTypeInJSON( 132 "GENERIC_ERROR_TYPE", 133 new String[] {"SERVER_SELECTION_FAILED"}, 134 new String[] {"0"}, 135 new String[] {"APM_ENABLE_EVENT"}) 136 + "}]" 137 + "}]"; 138 139 PersistableBundle bundle = new PersistableBundle(); 140 bundle.putString(ErrorPolicyManager.KEY_ERROR_POLICY_CONFIG_STRING, config); 141 setupMockForCarrierConfig(bundle); 142 mErrorPolicyManager 143 .mHandler 144 .obtainMessage(IwlanEventListener.CARRIER_CONFIG_CHANGED_EVENT) 145 .sendToTarget(); 146 147 sleep(1000); 148 149 // IKE_PROTOCOL_ERROR_TYPE(24) and retryArray = 4,8,16 150 IwlanError iwlanError = buildIwlanIkeAuthFailedError(); 151 long time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 152 assertEquals(4, time); 153 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 154 assertEquals(8, time); 155 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 156 assertEquals(16, time); 157 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 158 assertEquals(86400, time); 159 160 // Validate the range error detail. 161 iwlanError = buildIwlanIkeProtocolError(9030, new byte[] {0x00, 0x01}); 162 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 163 assertEquals(4, time); 164 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 165 assertEquals(8, time); 166 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 167 assertEquals(16, time); 168 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 169 assertEquals(86400, time); 170 171 // GENERIC_PROTOCOL_ERROR_TYPE - SERVER_SELECTION_FAILED and retryArray = 0 172 iwlanError = new IwlanError(IwlanError.EPDG_SELECTOR_SERVER_SELECTION_FAILED); 173 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 174 assertEquals(0, time); 175 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 176 assertEquals(86400, time); 177 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 178 assertEquals(86400, time); 179 180 // Fallback case GENERIC_PROTOCOL_ERROR_TYPE(44) and retryArray is 5, 10, -1 as in 181 // DEFAULT_CONFIG 182 iwlanError = buildIwlanIkeChildSaNotFoundError(); 183 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 184 assertEquals(5, time); 185 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 186 assertEquals(10, time); 187 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 188 assertEquals(10, time); 189 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 190 assertEquals(10, time); 191 } 192 193 @Test testInvalidCarrierConfig()194 public void testInvalidCarrierConfig() throws Exception { 195 String apn = "ims"; 196 String config = 197 "[{" 198 + "\"ApnName\": \"" 199 + apn 200 + "\"," 201 + "\"ErrorTypes\": [{" 202 + getErrorTypeInJSON( 203 "IKE_PROTOCOL_ERROR_TYPE", 204 new String[] {"WRONG_ERROR_DETAIL"}, 205 new String[] {"4", "8", "16"}, 206 new String[] {"APM_ENABLE_EVENT", "WIFI_AP_CHANGED_EVENT"}) 207 + "}]" 208 + "}]"; 209 210 PersistableBundle bundle = new PersistableBundle(); 211 bundle.putString(ErrorPolicyManager.KEY_ERROR_POLICY_CONFIG_STRING, config); 212 setupMockForCarrierConfig(bundle); 213 mErrorPolicyManager 214 .mHandler 215 .obtainMessage(IwlanEventListener.CARRIER_CONFIG_CHANGED_EVENT) 216 .sendToTarget(); 217 218 sleep(1000); 219 220 // IKE_PROTOCOL_ERROR_TYPE(24) and retryArray = 5, 10, 15 as it will fallback due to failed 221 // parsing 222 IwlanError iwlanError = buildIwlanIkeAuthFailedError(); 223 long time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 224 assertEquals(5, time); 225 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 226 assertEquals(10, time); 227 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 228 assertEquals(10, time); 229 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 230 assertEquals(10, time); 231 } 232 233 @Test testChoosingFallbackPolicy()234 public void testChoosingFallbackPolicy() throws Exception { 235 String apn = "ims"; 236 String config = 237 "[{" 238 + "\"ApnName\": \"" 239 + apn 240 + "\"," 241 + "\"ErrorTypes\": [{" 242 + getErrorTypeInJSON( 243 "IKE_PROTOCOL_ERROR_TYPE", 244 new String[] {"24", "34"}, 245 new String[] {"4", "8", "16"}, 246 new String[] {"APM_ENABLE_EVENT", "WIFI_AP_CHANGED_EVENT"}) 247 + "}, {" 248 + getErrorTypeInJSON( 249 "IKE_PROTOCOL_ERROR_TYPE", 250 new String[] {"*"}, 251 new String[] {"0"}, 252 new String[] {"APM_ENABLE_EVENT"}) 253 + "}]" 254 + "}]"; 255 PersistableBundle bundle = new PersistableBundle(); 256 bundle.putString(ErrorPolicyManager.KEY_ERROR_POLICY_CONFIG_STRING, config); 257 setupMockForCarrierConfig(bundle); 258 mErrorPolicyManager 259 .mHandler 260 .obtainMessage(IwlanEventListener.CARRIER_CONFIG_CHANGED_EVENT) 261 .sendToTarget(); 262 263 sleep(1000); 264 265 mErrorPolicyManager.logErrorPolicies(); 266 267 // IKE_PROTOCOL_ERROR_TYPE(24) and retryArray = 4, 8, 16 268 IwlanError iwlanError = buildIwlanIkeAuthFailedError(); 269 long time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 270 assertEquals(4, time); 271 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 272 assertEquals(8, time); 273 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 274 assertEquals(16, time); 275 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 276 assertEquals(86400, time); 277 278 // IKE_PROTOCOL_ERROR_TYPE(44) and retryArray = 0 as it will fallback to 279 // IKE_PROTOCOL_ERROR_TYPE generic fallback first. 280 iwlanError = buildIwlanIkeChildSaNotFoundError(); 281 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 282 assertEquals(0, time); 283 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 284 assertEquals(86400, time); 285 } 286 287 @Test testCanBringUpTunnel()288 public void testCanBringUpTunnel() throws Exception { 289 String apn = "ims"; 290 String config = 291 "[{" 292 + "\"ApnName\": \"" 293 + apn 294 + "\"," 295 + "\"ErrorTypes\": [{" 296 + getErrorTypeInJSON( 297 "IKE_PROTOCOL_ERROR_TYPE", 298 new String[] {"24", "34"}, 299 new String[] {"4", "8", "16"}, 300 new String[] {"APM_ENABLE_EVENT", "WIFI_AP_CHANGED_EVENT"}) 301 + "}, {" 302 + getErrorTypeInJSON( 303 "GENERIC_ERROR_TYPE", 304 new String[] {"SERVER_SELECTION_FAILED"}, 305 new String[] {"0"}, 306 new String[] {"APM_ENABLE_EVENT"}) 307 + "}]" 308 + "}]"; 309 PersistableBundle bundle = new PersistableBundle(); 310 bundle.putString(ErrorPolicyManager.KEY_ERROR_POLICY_CONFIG_STRING, config); 311 setupMockForCarrierConfig(bundle); 312 mErrorPolicyManager 313 .mHandler 314 .obtainMessage(IwlanEventListener.CARRIER_CONFIG_CHANGED_EVENT) 315 .sendToTarget(); 316 317 sleep(1000); 318 319 // IKE_PROTOCOL_ERROR_TYPE(24) and retryArray = 4,8,16 320 IwlanError iwlanError = buildIwlanIkeAuthFailedError(); 321 long time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 322 assertEquals(4, time); 323 324 boolean bringUpTunnel = mErrorPolicyManager.canBringUpTunnel(apn); 325 assertFalse(bringUpTunnel); 326 327 sleep(4000); 328 329 bringUpTunnel = mErrorPolicyManager.canBringUpTunnel(apn); 330 assertTrue(bringUpTunnel); 331 332 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 333 assertEquals(8, time); 334 335 bringUpTunnel = mErrorPolicyManager.canBringUpTunnel(apn); 336 assertFalse(bringUpTunnel); 337 } 338 339 @Test testNoErrorScenario()340 public void testNoErrorScenario() throws Exception { 341 String apn = "ims"; 342 String config = 343 "[{" 344 + "\"ApnName\": \"" 345 + apn 346 + "\"," 347 + "\"ErrorTypes\": [{" 348 + getErrorTypeInJSON( 349 "IKE_PROTOCOL_ERROR_TYPE", 350 new String[] {"24", "34"}, 351 new String[] {"4", "8", "16"}, 352 new String[] {"APM_ENABLE_EVENT", "WIFI_AP_CHANGED_EVENT"}) 353 + "}, {" 354 + getErrorTypeInJSON( 355 "GENERIC_ERROR_TYPE", 356 new String[] {"SERVER_SELECTION_FAILED"}, 357 new String[] {"0"}, 358 new String[] {"APM_ENABLE_EVENT"}) 359 + "}]" 360 + "}]"; 361 PersistableBundle bundle = new PersistableBundle(); 362 bundle.putString(ErrorPolicyManager.KEY_ERROR_POLICY_CONFIG_STRING, config); 363 setupMockForCarrierConfig(bundle); 364 mErrorPolicyManager 365 .mHandler 366 .obtainMessage(IwlanEventListener.CARRIER_CONFIG_CHANGED_EVENT) 367 .sendToTarget(); 368 369 sleep(1000); 370 371 // IKE_PROTOCOL_ERROR_TYPE(24) and retryArray = 4,8,16 372 IwlanError iwlanError = buildIwlanIkeAuthFailedError(); 373 long time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 374 assertEquals(4, time); 375 376 // report no error 377 iwlanError = new IwlanError(IwlanError.NO_ERROR); 378 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 379 assertEquals(-1, time); 380 381 // Check whether the error is cleared after NO_ERROR is reported 382 boolean bringUpTunnel = mErrorPolicyManager.canBringUpTunnel(apn); 383 assertTrue(bringUpTunnel); 384 } 385 386 @Test testWifiDisableUnthrottle()387 public void testWifiDisableUnthrottle() throws Exception { 388 String apn = "ims"; 389 String config = 390 "[{" 391 + "\"ApnName\": \"" 392 + apn 393 + "\"," 394 + "\"ErrorTypes\": [{" 395 + getErrorTypeInJSON( 396 "IKE_PROTOCOL_ERROR_TYPE", 397 new String[] {"24", "34"}, 398 new String[] {"6", "12", "24"}, 399 new String[] {"APM_ENABLE_EVENT", "WIFI_DISABLE_EVENT"}) 400 + "}, {" 401 + getErrorTypeInJSON( 402 "GENERIC_ERROR_TYPE", 403 new String[] {"SERVER_SELECTION_FAILED"}, 404 new String[] {"0"}, 405 new String[] {"APM_DISABLE_EVENT"}) 406 + "}]" 407 + "}]"; 408 PersistableBundle bundle = new PersistableBundle(); 409 bundle.putString(ErrorPolicyManager.KEY_ERROR_POLICY_CONFIG_STRING, config); 410 setupMockForCarrierConfig(bundle); 411 mErrorPolicyManager 412 .mHandler 413 .obtainMessage(IwlanEventListener.CARRIER_CONFIG_CHANGED_EVENT) 414 .sendToTarget(); 415 sleep(1000); 416 417 // IKE_PROTOCOL_ERROR_TYPE(24) and retryArray = 6, 12, 24 418 IwlanError iwlanError = buildIwlanIkeAuthFailedError(); 419 long time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 420 assertEquals(6, time); 421 422 mErrorPolicyManager 423 .mHandler 424 .obtainMessage(IwlanEventListener.WIFI_DISABLE_EVENT) 425 .sendToTarget(); 426 sleep(500); 427 verify(mMockDataServiceProvider, times(1)).notifyApnUnthrottled(eq(apn)); 428 429 boolean bringUpTunnel = mErrorPolicyManager.canBringUpTunnel(apn); 430 assertTrue(bringUpTunnel); 431 432 iwlanError = buildIwlanIkeAuthFailedError(); 433 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 434 assertEquals(6, time); 435 } 436 437 @Test testWFCDisableUnthrottle()438 public void testWFCDisableUnthrottle() throws Exception { 439 String apn = "ims"; 440 String config = 441 "[{" 442 + "\"ApnName\": \"" 443 + apn 444 + "\"," 445 + "\"ErrorTypes\": [{" 446 + getErrorTypeInJSON( 447 "IKE_PROTOCOL_ERROR_TYPE", 448 new String[] {"24", "34"}, 449 new String[] {"6", "12", "24"}, 450 new String[] {"WIFI_CALLING_DISABLE_EVENT", "WIFI_DISABLE_EVENT"}) 451 + "}, {" 452 + getErrorTypeInJSON( 453 "GENERIC_ERROR_TYPE", 454 new String[] {"SERVER_SELECTION_FAILED"}, 455 new String[] {"0"}, 456 new String[] {"APM_DISABLE_EVENT"}) 457 + "}]" 458 + "}]"; 459 PersistableBundle bundle = new PersistableBundle(); 460 bundle.putString(ErrorPolicyManager.KEY_ERROR_POLICY_CONFIG_STRING, config); 461 setupMockForCarrierConfig(bundle); 462 mErrorPolicyManager 463 .mHandler 464 .obtainMessage(IwlanEventListener.CARRIER_CONFIG_CHANGED_EVENT) 465 .sendToTarget(); 466 sleep(1000); 467 468 // IKE_PROTOCOL_ERROR_TYPE(24) and retryArray = 6, 12, 24 469 IwlanError iwlanError = buildIwlanIkeAuthFailedError(); 470 long time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 471 assertEquals(6, time); 472 473 mErrorPolicyManager 474 .mHandler 475 .obtainMessage(IwlanEventListener.WIFI_CALLING_DISABLE_EVENT) 476 .sendToTarget(); 477 sleep(500); 478 verify(mMockDataServiceProvider, times(1)).notifyApnUnthrottled(eq(apn)); 479 480 boolean bringUpTunnel = mErrorPolicyManager.canBringUpTunnel(apn); 481 assertTrue(bringUpTunnel); 482 483 iwlanError = buildIwlanIkeAuthFailedError(); 484 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 485 assertEquals(6, time); 486 } 487 488 @Test testAPMUnthrottle()489 public void testAPMUnthrottle() throws Exception { 490 String apn = "ims"; 491 String config = 492 "[{" 493 + "\"ApnName\": \"" 494 + apn 495 + "\"," 496 + "\"ErrorTypes\": [{" 497 + getErrorTypeInJSON( 498 "IKE_PROTOCOL_ERROR_TYPE", 499 new String[] {"24", "34"}, 500 new String[] {"4", "8", "16"}, 501 new String[] {"APM_ENABLE_EVENT", "WIFI_AP_CHANGED_EVENT"}) 502 + "}, {" 503 + getErrorTypeInJSON( 504 "GENERIC_ERROR_TYPE", 505 new String[] {"SERVER_SELECTION_FAILED"}, 506 new String[] {"0"}, 507 new String[] {"APM_DISABLE_EVENT"}) 508 + "}]" 509 + "}]"; 510 PersistableBundle bundle = new PersistableBundle(); 511 bundle.putString(ErrorPolicyManager.KEY_ERROR_POLICY_CONFIG_STRING, config); 512 setupMockForCarrierConfig(bundle); 513 mErrorPolicyManager 514 .mHandler 515 .obtainMessage(IwlanEventListener.CARRIER_CONFIG_CHANGED_EVENT) 516 .sendToTarget(); 517 sleep(1000); 518 519 // IKE_PROTOCOL_ERROR_TYPE(24) and retryArray = 4,8,16 520 IwlanError iwlanError = buildIwlanIkeAuthFailedError(); 521 long time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 522 assertEquals(4, time); 523 524 mErrorPolicyManager 525 .mHandler 526 .obtainMessage(IwlanEventListener.APM_ENABLE_EVENT) 527 .sendToTarget(); 528 sleep(500); 529 verify(mMockDataServiceProvider, times(1)).notifyApnUnthrottled(eq(apn)); 530 531 boolean bringUpTunnel = mErrorPolicyManager.canBringUpTunnel(apn); 532 assertTrue(bringUpTunnel); 533 534 iwlanError = buildIwlanIkeAuthFailedError(); 535 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 536 assertEquals(4, time); 537 } 538 539 @Test testGetDataFailCauseRetryTime()540 public void testGetDataFailCauseRetryTime() throws Exception { 541 String apn1 = "ims"; 542 String apn2 = "mms"; 543 String config = 544 "[{" 545 + "\"ApnName\": \"" 546 + apn1 547 + "\"," 548 + "\"ErrorTypes\": [{" 549 + getErrorTypeInJSON( 550 "IKE_PROTOCOL_ERROR_TYPE", 551 new String[] {"24", "34"}, 552 new String[] {"4", "8", "16"}, 553 new String[] {"APM_ENABLE_EVENT", "WIFI_AP_CHANGED_EVENT"}) 554 + "}, {" 555 + getErrorTypeInJSON( 556 "GENERIC_ERROR_TYPE", 557 new String[] {"SERVER_SELECTION_FAILED"}, 558 new String[] {"0"}, 559 new String[] {"APM_ENABLE_EVENT"}) 560 + "}]" 561 + "}]"; 562 PersistableBundle bundle = new PersistableBundle(); 563 bundle.putString(ErrorPolicyManager.KEY_ERROR_POLICY_CONFIG_STRING, config); 564 setupMockForCarrierConfig(bundle); 565 mErrorPolicyManager 566 .mHandler 567 .obtainMessage(IwlanEventListener.CARRIER_CONFIG_CHANGED_EVENT) 568 .sendToTarget(); 569 570 sleep(1000); 571 572 // IKE_PROTOCOL_ERROR_TYPE(24) and retryArray = 4,8,16 573 IwlanError iwlanError = buildIwlanIkeAuthFailedError(); 574 long time = mErrorPolicyManager.reportIwlanError(apn1, iwlanError); 575 assertEquals(4, time); 576 577 iwlanError = 578 buildIwlanIkeProtocolError( 579 8192 /*PDN_CONNECTION_REJECTION*/, new byte[] {0x00, 0x01}); 580 time = mErrorPolicyManager.reportIwlanError(apn2, iwlanError); 581 assertEquals(5, time); 582 583 int failCause = mErrorPolicyManager.getDataFailCause(apn1); 584 assertEquals(DataFailCause.IWLAN_IKEV2_AUTH_FAILURE, failCause); 585 586 failCause = mErrorPolicyManager.getDataFailCause(apn2); 587 assertEquals(DataFailCause.IWLAN_PDN_CONNECTION_REJECTION, failCause); 588 589 long retryTime = 590 Math.round((double) mErrorPolicyManager.getCurrentRetryTimeMs(apn1) / 1000); 591 assertEquals(4, retryTime); 592 593 retryTime = Math.round((double) mErrorPolicyManager.getCurrentRetryTimeMs(apn2) / 1000); 594 assertEquals(5, retryTime); 595 } 596 597 @Test testBackOffTime()598 public void testBackOffTime() throws Exception { 599 String apn = "ims"; 600 String config = 601 "[{" 602 + "\"ApnName\": \"" 603 + apn 604 + "\"," 605 + "\"ErrorTypes\": [{" 606 + getErrorTypeInJSON( 607 "IKE_PROTOCOL_ERROR_TYPE", 608 new String[] {"24", "34"}, 609 new String[] {"10", "15", "20"}, 610 new String[] {"APM_ENABLE_EVENT", "WIFI_AP_CHANGED_EVENT"}) 611 + "}, {" 612 + getErrorTypeInJSON( 613 "GENERIC_ERROR_TYPE", 614 new String[] {"SERVER_SELECTION_FAILED"}, 615 new String[] {"0"}, 616 new String[] {"APM_ENABLE_EVENT"}) 617 + "}]" 618 + "}]"; 619 620 PersistableBundle bundle = new PersistableBundle(); 621 bundle.putString(ErrorPolicyManager.KEY_ERROR_POLICY_CONFIG_STRING, config); 622 setupMockForCarrierConfig(bundle); 623 mErrorPolicyManager 624 .mHandler 625 .obtainMessage(IwlanEventListener.CARRIER_CONFIG_CHANGED_EVENT) 626 .sendToTarget(); 627 628 sleep(1000); 629 630 // IKE_PROTOCOL_ERROR_TYPE(24) and retryArray = 4,8,16 631 IwlanError iwlanError = buildIwlanIkeAuthFailedError(); 632 long time = mErrorPolicyManager.reportIwlanError(apn, iwlanError, 2); 633 634 time = Math.round((double) mErrorPolicyManager.getCurrentRetryTimeMs(apn) / 1000); 635 assertEquals(time, 2); 636 637 // sleep for 2 seconds and make sure that we can bring up tunnel after 2 secs 638 // as back off time - 2 secs should override the retry time in policy - 10 secs 639 sleep(2000); 640 boolean bringUpTunnel = mErrorPolicyManager.canBringUpTunnel(apn); 641 assertTrue(bringUpTunnel); 642 643 // test whether the same error reported later uses the right policy 644 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 645 assertEquals(10, time); 646 647 bringUpTunnel = mErrorPolicyManager.canBringUpTunnel(apn); 648 assertFalse(bringUpTunnel); 649 650 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError, 5); 651 time = Math.round((double) mErrorPolicyManager.getCurrentRetryTimeMs(apn) / 1000); 652 assertEquals(time, 5); 653 654 // test whether the same error reported later starts from the beginning of retry array 655 time = mErrorPolicyManager.reportIwlanError(apn, iwlanError); 656 assertEquals(10, time); 657 } 658 659 @Test testErrorStats()660 public void testErrorStats() throws Exception { 661 String apn1 = "ims"; 662 String apn2 = "mms"; 663 664 setupMockForCarrierConfig(null); 665 666 IwlanError iwlanError1 = buildIwlanIkeAuthFailedError(); 667 long ikeAuthCountApn1 = 4L; 668 long ikeAuthCountApn2 = 5L; 669 for (int i = 0; i < ikeAuthCountApn1; i++) { 670 mErrorPolicyManager.reportIwlanError(apn1, iwlanError1); 671 } 672 for (int i = 0; i < ikeAuthCountApn2; i++) { 673 mErrorPolicyManager.reportIwlanError(apn2, iwlanError1); 674 } 675 676 long serverSelectionCountApn1 = 3L; 677 long serverSelectionCountApn2 = 6L; 678 IwlanError iwlanError2 = new IwlanError(IwlanError.EPDG_SELECTOR_SERVER_SELECTION_FAILED); 679 for (int i = 0; i < serverSelectionCountApn1; i++) { 680 mErrorPolicyManager.reportIwlanError(apn1, iwlanError2); 681 } 682 // calling backoff timer api 683 for (int i = 0; i < serverSelectionCountApn2; i++) { 684 mErrorPolicyManager.reportIwlanError(apn2, iwlanError2, 3); 685 } 686 687 Map<String, Long> apn1Stats = mErrorPolicyManager.getErrorStats().mStats.get(apn1); 688 Map<String, Long> apn2Stats = mErrorPolicyManager.getErrorStats().mStats.get(apn2); 689 690 long resultAuthApn1 = apn1Stats.get(iwlanError1.toString()); 691 long resultAuthApn2 = apn2Stats.get(iwlanError1.toString()); 692 long resultServerApn1 = apn1Stats.get(iwlanError2.toString()); 693 long resultServerApn2 = apn2Stats.get(iwlanError2.toString()); 694 assertEquals(resultAuthApn1, ikeAuthCountApn1); 695 assertEquals(resultAuthApn2, ikeAuthCountApn2); 696 assertEquals(resultServerApn1, serverSelectionCountApn1); 697 assertEquals(resultServerApn2, serverSelectionCountApn2); 698 } 699 getErrorTypeInJSON( String ErrorType, String[] errorDetails, String[] retryArray, String[] unthrottlingEvents)700 private String getErrorTypeInJSON( 701 String ErrorType, 702 String[] errorDetails, 703 String[] retryArray, 704 String[] unthrottlingEvents) { 705 return "\"ErrorType\": \"" 706 + ErrorType 707 + "\"," 708 + "\"ErrorDetails\": [\"" 709 + String.join("\", \"", errorDetails) 710 + "\"]," 711 + "\"RetryArray\": [\"" 712 + String.join("\", \"", retryArray) 713 + "\"]," 714 + "\"UnthrottlingEvents\": [\"" 715 + String.join("\", \"", unthrottlingEvents) 716 + "\"]"; 717 } 718 sleep(long time)719 private void sleep(long time) { 720 try { 721 Thread.sleep(time); 722 } catch (Exception e) { 723 e.printStackTrace(); 724 } 725 } 726 setupMockForCarrierConfig(PersistableBundle bundle)727 private void setupMockForCarrierConfig(PersistableBundle bundle) { 728 doReturn(mMockCarrierConfigManager) 729 .when(mMockContext) 730 .getSystemService(eq(CarrierConfigManager.class)); 731 doReturn(mMockSubscriptionManager) 732 .when(mMockContext) 733 .getSystemService(eq(SubscriptionManager.class)); 734 doReturn(mMockTelephonyManager).when(mMockContext).getSystemService(TelephonyManager.class); 735 doReturn(mMockTelephonyManager) 736 .when(mMockTelephonyManager) 737 .createForSubscriptionId(anyInt()); 738 doReturn(TEST_CARRIER_ID).when(mMockTelephonyManager).getSimCarrierId(); 739 SubscriptionInfo mockSubInfo = mock(SubscriptionInfo.class); 740 doReturn(mockSubInfo) 741 .when(mMockSubscriptionManager) 742 .getActiveSubscriptionInfoForSimSlotIndex(DEFAULT_SLOT_INDEX); 743 doReturn(DEFAULT_SUBID).when(mockSubInfo).getSubscriptionId(); 744 doReturn(bundle).when(mMockCarrierConfigManager).getConfigForSubId(DEFAULT_SLOT_INDEX); 745 when(mMockContext.getContentResolver()).thenReturn(mMockContentResolver); 746 } 747 } 748