13918e13b24d4e7ad410089eb615721ca026bec01Wink Saville/** 23918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Copyright (C) 2009 The Android Open Source Project 33918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 43918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Licensed under the Apache License, Version 2.0 (the "License"); 53918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * you may not use this file except in compliance with the License. 63918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * You may obtain a copy of the License at 73918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 83918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * http://www.apache.org/licenses/LICENSE-2.0 93918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 103918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Unless required by applicable law or agreed to in writing, software 113918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * distributed under the License is distributed on an "AS IS" BASIS, 123918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 133918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * See the License for the specific language governing permissions and 143918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * limitations under the License. 153918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 163918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 173918e13b24d4e7ad410089eb615721ca026bec01Wink Savillepackage com.android.internal.telephony; 183918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 193918e13b24d4e7ad410089eb615721ca026bec01Wink Savilleimport android.util.Log; 203918e13b24d4e7ad410089eb615721ca026bec01Wink Savilleimport android.util.Pair; 213918e13b24d4e7ad410089eb615721ca026bec01Wink Savilleimport android.text.TextUtils; 223918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 233918e13b24d4e7ad410089eb615721ca026bec01Wink Savilleimport java.util.Random; 243918e13b24d4e7ad410089eb615721ca026bec01Wink Savilleimport java.util.ArrayList; 253918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 263918e13b24d4e7ad410089eb615721ca026bec01Wink Saville/** 273918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Retry manager allows a simple way to declare a series of 28390de220248d05ccb9dc10a197700ad3c1595937Jake Hamby * retry timeouts. After creating a RetryManager the configure 293918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * method is used to define the sequence. A simple linear series 303918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * may be initialized using configure with three integer parameters 313918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * The other configure method allows a series to be declared using 323918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * a string. 333918e13b24d4e7ad410089eb615721ca026bec01Wink Saville *<p> 343918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * The format of the configuration string is a series of parameters 353918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * separated by a comma. There are two name value pair parameters plus a series 363918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * of delay times. The units of of these delay times is unspecified. 373918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * The name value pairs which may be specified are: 383918e13b24d4e7ad410089eb615721ca026bec01Wink Saville *<ul> 393918e13b24d4e7ad410089eb615721ca026bec01Wink Saville *<li>max_retries=<value> 403918e13b24d4e7ad410089eb615721ca026bec01Wink Saville *<li>default_randomizationTime=<value> 413918e13b24d4e7ad410089eb615721ca026bec01Wink Saville *</ul> 423918e13b24d4e7ad410089eb615721ca026bec01Wink Saville *<p> 433918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * max_retries is the number of times that incrementRetryCount 44a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville * maybe called before isRetryNeeded will return false. if value 45a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville * is infinite then isRetryNeeded will always return true. 463918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 473918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * default_randomizationTime will be used as the randomizationTime 483918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * for delay times which have no supplied randomizationTime. If 493918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * default_randomizationTime is not defined it defaults to 0. 503918e13b24d4e7ad410089eb615721ca026bec01Wink Saville *<p> 513918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * The other parameters define The series of delay times and each 523918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * may have an optional randomization value separated from the 533918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * delay time by a colon. 543918e13b24d4e7ad410089eb615721ca026bec01Wink Saville *<p> 553918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Examples: 563918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * <ul> 57390de220248d05ccb9dc10a197700ad3c1595937Jake Hamby * <li>3 retries with no randomization value which means its 0: 583918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * <ul><li><code>"1000, 2000, 3000"</code></ul> 593918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 60390de220248d05ccb9dc10a197700ad3c1595937Jake Hamby * <li>10 retries with a 500 default randomization value for each and 613918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * the 4..10 retries all using 3000 as the delay: 623918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * <ul><li><code>"max_retries=10, default_randomization=500, 1000, 2000, 3000"</code></ul> 633918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 64390de220248d05ccb9dc10a197700ad3c1595937Jake Hamby * <li>4 retries with a 100 as the default randomization value for the first 2 values and 65a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville * the other two having specified values of 500: 663918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * <ul><li><code>"default_randomization=100, 1000, 2000, 4000:500, 5000:500"</code></ul> 67a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville * 68390de220248d05ccb9dc10a197700ad3c1595937Jake Hamby * <li>Infinite number of retries with the first one at 1000, the second at 2000 all 69a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville * others will be at 3000. 70a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville * <ul><li><code>"max_retries=infinite,1000,2000,3000</code></ul> 713918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * </ul> 723918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 733918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * {@hide} 743918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 753918e13b24d4e7ad410089eb615721ca026bec01Wink Savillepublic class RetryManager { 763918e13b24d4e7ad410089eb615721ca026bec01Wink Saville static public final String LOG_TAG = "RetryManager"; 773918e13b24d4e7ad410089eb615721ca026bec01Wink Saville static public final boolean DBG = false; 783918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 793918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 803918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Retry record with times in milli-seconds 813918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 823918e13b24d4e7ad410089eb615721ca026bec01Wink Saville private static class RetryRec { 833918e13b24d4e7ad410089eb615721ca026bec01Wink Saville RetryRec(int delayTime, int randomizationTime) { 843918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mDelayTime = delayTime; 853918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRandomizationTime = randomizationTime; 863918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 873918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 883918e13b24d4e7ad410089eb615721ca026bec01Wink Saville int mDelayTime; 893918e13b24d4e7ad410089eb615721ca026bec01Wink Saville int mRandomizationTime; 903918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 913918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 923918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** The array of retry records */ 933918e13b24d4e7ad410089eb615721ca026bec01Wink Saville private ArrayList<RetryRec> mRetryArray = new ArrayList<RetryRec>(); 943918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 953918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** When true isRetryNeeded() will always return true */ 963918e13b24d4e7ad410089eb615721ca026bec01Wink Saville private boolean mRetryForever; 973918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 983918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 993918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * The maximum number of retries to attempt before 1003918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * isRetryNeeded returns false 1013918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 1023918e13b24d4e7ad410089eb615721ca026bec01Wink Saville private int mMaxRetryCount; 1033918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 104390de220248d05ccb9dc10a197700ad3c1595937Jake Hamby /** The current number of retries */ 1053918e13b24d4e7ad410089eb615721ca026bec01Wink Saville private int mRetryCount; 1063918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1073918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** Random number generator */ 1083918e13b24d4e7ad410089eb615721ca026bec01Wink Saville private Random rng = new Random(); 1093918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1103918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** Constructor */ 1113918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public RetryManager() { 1123918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("constructor"); 1133918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 1143918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1153918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 1163918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Configure for a simple linear sequence of times plus 1173918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * a random value. 1183918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 1193918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @param maxRetryCount is the maximum number of retries 1203918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * before isRetryNeeded returns false. 1213918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @param retryTime is a time that will be returned by getRetryTime. 1223918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @param randomizationTime a random value between 0 and 1233918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * randomizationTime will be added to retryTime. this 1243918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * parameter may be 0. 125390de220248d05ccb9dc10a197700ad3c1595937Jake Hamby * @return true if successful 1263918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 1273918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public boolean configure(int maxRetryCount, int retryTime, int randomizationTime) { 1283918e13b24d4e7ad410089eb615721ca026bec01Wink Saville Pair<Boolean, Integer> value; 1293918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1303918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("configure: " + maxRetryCount + ", " + retryTime + "," + randomizationTime); 1313918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1323918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (!validateNonNegativeInt("maxRetryCount", maxRetryCount)) { 1333918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return false; 1343918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 1353918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1363918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (!validateNonNegativeInt("retryTime", retryTime)) { 1373918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return false; 1383918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 1393918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1403918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (!validateNonNegativeInt("randomizationTime", randomizationTime)) { 1413918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return false; 1423918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 1433918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1443918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mMaxRetryCount = maxRetryCount; 1453918e13b24d4e7ad410089eb615721ca026bec01Wink Saville resetRetryCount(); 1463918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryArray.clear(); 1473918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryArray.add(new RetryRec(retryTime, randomizationTime)); 1483918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1493918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return true; 1503918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 1513918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1523918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 15301b6d244174b4fe5434593fc89189ba94bc76e7dWink Saville * Configure for using string which allow arbitrary 1543918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * sequences of times. See class comments for the 1553918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * string format. 1563918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 15701b6d244174b4fe5434593fc89189ba94bc76e7dWink Saville * @return true if successful 1583918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 1593918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public boolean configure(String configStr) { 16001b6d244174b4fe5434593fc89189ba94bc76e7dWink Saville // Strip quotes if present. 16101b6d244174b4fe5434593fc89189ba94bc76e7dWink Saville if ((configStr.startsWith("\"") && configStr.endsWith("\""))) { 16201b6d244174b4fe5434593fc89189ba94bc76e7dWink Saville configStr = configStr.substring(1, configStr.length()-1); 16301b6d244174b4fe5434593fc89189ba94bc76e7dWink Saville } 1643918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("configure: '" + configStr + "'"); 1653918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1663918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (!TextUtils.isEmpty(configStr)) { 1673918e13b24d4e7ad410089eb615721ca026bec01Wink Saville int defaultRandomization = 0; 1683918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1693918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("configure: not empty"); 1703918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1713918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mMaxRetryCount = 0; 1723918e13b24d4e7ad410089eb615721ca026bec01Wink Saville resetRetryCount(); 1733918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryArray.clear(); 1743918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 1753918e13b24d4e7ad410089eb615721ca026bec01Wink Saville String strArray[] = configStr.split(","); 1763918e13b24d4e7ad410089eb615721ca026bec01Wink Saville for (int i = 0; i < strArray.length; i++) { 1773918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("configure: strArray[" + i + "]='" + strArray[i] + "'"); 1783918e13b24d4e7ad410089eb615721ca026bec01Wink Saville Pair<Boolean, Integer> value; 1793918e13b24d4e7ad410089eb615721ca026bec01Wink Saville String splitStr[] = strArray[i].split("=", 2); 1803918e13b24d4e7ad410089eb615721ca026bec01Wink Saville splitStr[0] = splitStr[0].trim(); 1813918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("configure: splitStr[0]='" + splitStr[0] + "'"); 1823918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (splitStr.length > 1) { 1833918e13b24d4e7ad410089eb615721ca026bec01Wink Saville splitStr[1] = splitStr[1].trim(); 1843918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("configure: splitStr[1]='" + splitStr[1] + "'"); 1853918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (TextUtils.equals(splitStr[0], "default_randomization")) { 1863918e13b24d4e7ad410089eb615721ca026bec01Wink Saville value = parseNonNegativeInt(splitStr[0], splitStr[1]); 1873918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (!value.first) return false; 1883918e13b24d4e7ad410089eb615721ca026bec01Wink Saville defaultRandomization = value.second; 1893918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } else if (TextUtils.equals(splitStr[0], "max_retries")) { 190a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville if (TextUtils.equals("infinite",splitStr[1])) { 191a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville mRetryForever = true; 192a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville } else { 193a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville value = parseNonNegativeInt(splitStr[0], splitStr[1]); 194a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville if (!value.first) return false; 195a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville mMaxRetryCount = value.second; 196a03ab1a6a07614f3d588232e12d9c45d840bae82Wink Saville } 1973918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } else { 1983918e13b24d4e7ad410089eb615721ca026bec01Wink Saville Log.e(LOG_TAG, "Unrecognized configuration name value pair: " 1993918e13b24d4e7ad410089eb615721ca026bec01Wink Saville + strArray[i]); 2003918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return false; 2013918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2023918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } else { 2033918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 2043918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Assume a retry time with an optional randomization value 2053918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * following a ":" 2063918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 2073918e13b24d4e7ad410089eb615721ca026bec01Wink Saville splitStr = strArray[i].split(":", 2); 2083918e13b24d4e7ad410089eb615721ca026bec01Wink Saville splitStr[0] = splitStr[0].trim(); 2093918e13b24d4e7ad410089eb615721ca026bec01Wink Saville RetryRec rr = new RetryRec(0, 0); 2103918e13b24d4e7ad410089eb615721ca026bec01Wink Saville value = parseNonNegativeInt("delayTime", splitStr[0]); 2113918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (!value.first) return false; 2123918e13b24d4e7ad410089eb615721ca026bec01Wink Saville rr.mDelayTime = value.second; 2133918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 2143918e13b24d4e7ad410089eb615721ca026bec01Wink Saville // Check if optional randomization value present 2153918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (splitStr.length > 1) { 2163918e13b24d4e7ad410089eb615721ca026bec01Wink Saville splitStr[1] = splitStr[1].trim(); 2173918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("configure: splitStr[1]='" + splitStr[1] + "'"); 2183918e13b24d4e7ad410089eb615721ca026bec01Wink Saville value = parseNonNegativeInt("randomizationTime", splitStr[1]); 2193918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (!value.first) return false; 2203918e13b24d4e7ad410089eb615721ca026bec01Wink Saville rr.mRandomizationTime = value.second; 2213918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } else { 2223918e13b24d4e7ad410089eb615721ca026bec01Wink Saville rr.mRandomizationTime = defaultRandomization; 2233918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2243918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryArray.add(rr); 2253918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2263918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2273918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (mRetryArray.size() > mMaxRetryCount) { 2283918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mMaxRetryCount = mRetryArray.size(); 2293918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("configure: setting mMaxRetryCount=" + mMaxRetryCount); 2303918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2313918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("configure: true"); 2323918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return true; 2333918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } else { 2343918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("configure: false it's empty"); 2353918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return false; 2363918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2373918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2383918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 2393918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 2403918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Report whether data reconnection should be retried 2413918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 242390de220248d05ccb9dc10a197700ad3c1595937Jake Hamby * @return {@code true} if the max retries has not been reached. {@code 2433918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * false} otherwise. 2443918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 2453918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public boolean isRetryNeeded() { 2463918e13b24d4e7ad410089eb615721ca026bec01Wink Saville boolean retVal = mRetryForever || (mRetryCount < mMaxRetryCount); 2473918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("isRetryNeeded: " + retVal); 2483918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return retVal; 2493918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2503918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 2513918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 2523918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Return the timer that should be used to trigger the data reconnection 2533918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 2543918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public int getRetryTimer() { 2553918e13b24d4e7ad410089eb615721ca026bec01Wink Saville int index; 2563918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (mRetryCount < mRetryArray.size()) { 2573918e13b24d4e7ad410089eb615721ca026bec01Wink Saville index = mRetryCount; 2583918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } else { 2593918e13b24d4e7ad410089eb615721ca026bec01Wink Saville index = mRetryArray.size() - 1; 2603918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2613918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 2623918e13b24d4e7ad410089eb615721ca026bec01Wink Saville int retVal; 2633918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if ((index >= 0) && (index < mRetryArray.size())) { 2643918e13b24d4e7ad410089eb615721ca026bec01Wink Saville retVal = mRetryArray.get(index).mDelayTime + nextRandomizationTime(index); 2653918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } else { 2663918e13b24d4e7ad410089eb615721ca026bec01Wink Saville retVal = 0; 2673918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2683918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 2693918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("getRetryTimer: " + retVal); 2703918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return retVal; 2713918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2723918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 2733918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 2743918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @return retry count 2753918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 2763918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public int getRetryCount() { 2773918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("getRetryCount: " + mRetryCount); 2783918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return mRetryCount; 2793918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2803918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 2813918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 2823918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Increase the retry counter, does not change retry forever. 2833918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 2843918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public void increaseRetryCount() { 2853918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryCount++; 2863918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (mRetryCount > mMaxRetryCount) { 2873918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryCount = mMaxRetryCount; 2883918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 289390de220248d05ccb9dc10a197700ad3c1595937Jake Hamby if (DBG) log("increaseRetryCount: " + mRetryCount); 2903918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 2913918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 2923918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 2933918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Set retry count to the specified value 2943918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * and turns off retrying forever. 2953918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 2963918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public void setRetryCount(int count) { 2973918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryCount = count; 2983918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (mRetryCount > mMaxRetryCount) { 2993918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryCount = mMaxRetryCount; 3003918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3013918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 3023918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (mRetryCount < 0) { 3033918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryCount = 0; 3043918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3053918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 3063918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryForever = false; 3073918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("setRetryCount: " + mRetryCount); 3083918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3093918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 3103918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 3113918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Reset network re-registration indicator and clear the data-retry counter 3123918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * and turns off retrying forever. 3133918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 3143918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public void resetRetryCount() { 3153918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryCount = 0; 3163918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryForever = false; 3173918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("resetRetryCount: " + mRetryCount); 3183918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3193918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 3203918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 3213918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Retry forever using last timeout time. 3223918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 3233918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public void retryForeverUsingLastTimeout() { 3243918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryCount = mMaxRetryCount; 3253918e13b24d4e7ad410089eb615721ca026bec01Wink Saville mRetryForever = true; 3263918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("retryForeverUsingLastTimeout: " + mRetryForever + ", " + mRetryCount); 3273918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3283918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 3293918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 3303918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @return true if retrying forever 3313918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 3323918e13b24d4e7ad410089eb615721ca026bec01Wink Saville public boolean isRetryForever() { 3333918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("isRetryForever: " + mRetryForever); 3343918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return mRetryForever; 3353918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3363918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 3373918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 3383918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Parse an integer validating the value is not negative. 3393918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 3403918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @param name 3413918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @param stringValue 3423918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @return Pair.first == true if stringValue an integer >= 0 3433918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 3443918e13b24d4e7ad410089eb615721ca026bec01Wink Saville private Pair<Boolean, Integer> parseNonNegativeInt(String name, String stringValue) { 3453918e13b24d4e7ad410089eb615721ca026bec01Wink Saville int value; 3463918e13b24d4e7ad410089eb615721ca026bec01Wink Saville Pair<Boolean, Integer> retVal; 3473918e13b24d4e7ad410089eb615721ca026bec01Wink Saville try { 3483918e13b24d4e7ad410089eb615721ca026bec01Wink Saville value = Integer.parseInt(stringValue); 3493918e13b24d4e7ad410089eb615721ca026bec01Wink Saville retVal = new Pair<Boolean, Integer>(validateNonNegativeInt(name, value), value); 3503918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } catch (NumberFormatException e) { 3513918e13b24d4e7ad410089eb615721ca026bec01Wink Saville Log.e(LOG_TAG, name + " bad value: " + stringValue, e); 3523918e13b24d4e7ad410089eb615721ca026bec01Wink Saville retVal = new Pair<Boolean, Integer>(false, 0); 3533918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3543918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("parseNonNetativeInt: " + name + ", " + stringValue + ", " 3553918e13b24d4e7ad410089eb615721ca026bec01Wink Saville + retVal.first + ", " + retVal.second); 3563918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return retVal; 3573918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3583918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 3593918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 3603918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Validate an integer is >= 0 and logs an error if not 3613918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * 3623918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @param name 3633918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @param value 3643918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * @return Pair.first 3653918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 3663918e13b24d4e7ad410089eb615721ca026bec01Wink Saville private boolean validateNonNegativeInt(String name, int value) { 3673918e13b24d4e7ad410089eb615721ca026bec01Wink Saville boolean retVal; 3683918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (value < 0) { 3693918e13b24d4e7ad410089eb615721ca026bec01Wink Saville Log.e(LOG_TAG, name + " bad value: is < 0"); 3703918e13b24d4e7ad410089eb615721ca026bec01Wink Saville retVal = false; 3713918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } else { 3723918e13b24d4e7ad410089eb615721ca026bec01Wink Saville retVal = true; 3733918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3743918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (DBG) log("validateNonNegative: " + name + ", " + value + ", " + retVal); 3753918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return retVal; 3763918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3773918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 3783918e13b24d4e7ad410089eb615721ca026bec01Wink Saville /** 3793918e13b24d4e7ad410089eb615721ca026bec01Wink Saville * Return next random number for the index 3803918e13b24d4e7ad410089eb615721ca026bec01Wink Saville */ 3813918e13b24d4e7ad410089eb615721ca026bec01Wink Saville private int nextRandomizationTime(int index) { 3823918e13b24d4e7ad410089eb615721ca026bec01Wink Saville int randomTime = mRetryArray.get(index).mRandomizationTime; 3833918e13b24d4e7ad410089eb615721ca026bec01Wink Saville if (randomTime == 0) { 3843918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return 0; 3853918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } else { 3863918e13b24d4e7ad410089eb615721ca026bec01Wink Saville return rng.nextInt(randomTime); 3873918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3883918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3893918e13b24d4e7ad410089eb615721ca026bec01Wink Saville 3903918e13b24d4e7ad410089eb615721ca026bec01Wink Saville private void log(String s) { 3913918e13b24d4e7ad410089eb615721ca026bec01Wink Saville Log.d(LOG_TAG, s); 3923918e13b24d4e7ad410089eb615721ca026bec01Wink Saville } 3933918e13b24d4e7ad410089eb615721ca026bec01Wink Saville} 394