Merge "Improve Range Checks on CellIdentity Classes"
am: 7b2d8029ca

Change-Id: Id13a1cfa3be8b303da238eb816f843c01ee6008d
diff --git a/telephony/java/android/telephony/CellIdentity.java b/telephony/java/android/telephony/CellIdentity.java
index 3728de2..a83d8f0 100644
--- a/telephony/java/android/telephony/CellIdentity.java
+++ b/telephony/java/android/telephony/CellIdentity.java
@@ -229,4 +229,23 @@
     protected void log(String s) {
         Rlog.w(mTag, s);
     }
+
+    /** @hide */
+    protected static final int inRangeOrUnavailable(int value, int rangeMin, int rangeMax) {
+        if (value < rangeMin || value > rangeMax) return CellInfo.UNAVAILABLE;
+        return value;
+    }
+
+    /** @hide */
+    protected static final long inRangeOrUnavailable(long value, long rangeMin, long rangeMax) {
+        if (value < rangeMin || value > rangeMax) return CellInfo.UNAVAILABLE_LONG;
+        return value;
+    }
+
+    /** @hide */
+    protected static final int inRangeOrUnavailable(
+            int value, int rangeMin, int rangeMax, int special) {
+        if ((value < rangeMin || value > rangeMax) && value != special) return CellInfo.UNAVAILABLE;
+        return value;
+    }
 }
diff --git a/telephony/java/android/telephony/CellIdentityCdma.java b/telephony/java/android/telephony/CellIdentityCdma.java
index 637f49d..0897e0f 100644
--- a/telephony/java/android/telephony/CellIdentityCdma.java
+++ b/telephony/java/android/telephony/CellIdentityCdma.java
@@ -28,12 +28,25 @@
     private static final String TAG = CellIdentityCdma.class.getSimpleName();
     private static final boolean DBG = false;
 
+    private static final int NETWORK_ID_MAX = 65535;
+    private static final int SYSTEM_ID_MAX = 32767;
+    private static final int BASESTATION_ID_MAX = 65535;
+
+    private static final int LONGITUDE_MIN = -2592000;
+    private static final int LONGITUDE_MAX = 2592000;
+
+    private static final int LATITUDE_MIN = -1296000;
+    private static final int LATITUDE_MAX = 1296000;
+
     // Network Id 0..65535
     private final int mNetworkId;
+
     // CDMA System Id 0..32767
     private final int mSystemId;
+
     // Base Station Id 0..65535
     private final int mBasestationId;
+
     /**
      * Longitude is a decimal number as specified in 3GPP2 C.S0005-A v6.0.
      * It is represented in units of 0.25 seconds and ranges from -2592000
@@ -41,6 +54,7 @@
      * to +180 degrees).
      */
     private final int mLongitude;
+
     /**
      * Latitude is a decimal number as specified in 3GPP2 C.S0005-A v6.0.
      * It is represented in units of 0.25 seconds and ranges from -1296000
@@ -78,9 +92,12 @@
     public CellIdentityCdma(
             int nid, int sid, int bid, int lon, int lat, String alphal, String alphas) {
         super(TAG, CellInfo.TYPE_CDMA, null, null, alphal, alphas);
-        mNetworkId = nid;
-        mSystemId = sid;
-        mBasestationId = bid;
+        mNetworkId = inRangeOrUnavailable(nid, 0, NETWORK_ID_MAX);
+        mSystemId = inRangeOrUnavailable(sid, 0, SYSTEM_ID_MAX);
+        mBasestationId = inRangeOrUnavailable(bid, 0, BASESTATION_ID_MAX);
+        lat = inRangeOrUnavailable(lat, LATITUDE_MIN, LATITUDE_MAX);
+        lon = inRangeOrUnavailable(lon, LONGITUDE_MIN, LONGITUDE_MAX);
+
         if (!isNullIsland(lat, lon)) {
             mLongitude = lon;
             mLatitude = lat;
diff --git a/telephony/java/android/telephony/CellIdentityGsm.java b/telephony/java/android/telephony/CellIdentityGsm.java
index ae8e13a..4b7c9e4 100644
--- a/telephony/java/android/telephony/CellIdentityGsm.java
+++ b/telephony/java/android/telephony/CellIdentityGsm.java
@@ -31,6 +31,11 @@
     private static final String TAG = CellIdentityGsm.class.getSimpleName();
     private static final boolean DBG = false;
 
+    private static final int MAX_LAC = 65535;
+    private static final int MAX_CID = 65535;
+    private static final int MAX_ARFCN = 65535;
+    private static final int MAX_BSIC = 63;
+
     // 16-bit Location Area Code, 0..65535
     private final int mLac;
     // 16-bit GSM Cell Identity described in TS 27.007, 0..65535
@@ -68,10 +73,10 @@
     public CellIdentityGsm(int lac, int cid, int arfcn, int bsic, String mccStr,
                             String mncStr, String alphal, String alphas) {
         super(TAG, CellInfo.TYPE_GSM, mccStr, mncStr, alphal, alphas);
-        mLac = lac;
-        mCid = cid;
-        mArfcn = arfcn;
-        mBsic = bsic;
+        mLac = inRangeOrUnavailable(lac, 0, MAX_LAC);
+        mCid = inRangeOrUnavailable(cid, 0, MAX_CID);
+        mArfcn = inRangeOrUnavailable(arfcn, 0, MAX_ARFCN);
+        mBsic = inRangeOrUnavailable(bsic, 0, MAX_BSIC);
     }
 
     /** @hide */
diff --git a/telephony/java/android/telephony/CellIdentityLte.java b/telephony/java/android/telephony/CellIdentityLte.java
index ecd7da7..d81f98f 100644
--- a/telephony/java/android/telephony/CellIdentityLte.java
+++ b/telephony/java/android/telephony/CellIdentityLte.java
@@ -32,6 +32,12 @@
     private static final String TAG = CellIdentityLte.class.getSimpleName();
     private static final boolean DBG = false;
 
+    private static final int MAX_CI = 268435455;
+    private static final int MAX_PCI = 503;
+    private static final int MAX_TAC = 65535;
+    private static final int MAX_EARFCN = 262143;
+    private static final int MAX_BANDWIDTH = 20000;
+
     // 28-bit cell identity
     private final int mCi;
     // physical cell id 0..503
@@ -89,11 +95,11 @@
     public CellIdentityLte(int ci, int pci, int tac, int earfcn, int bandwidth, String mccStr,
             String mncStr, String alphal, String alphas) {
         super(TAG, CellInfo.TYPE_LTE, mccStr, mncStr, alphal, alphas);
-        mCi = ci;
-        mPci = pci;
-        mTac = tac;
-        mEarfcn = earfcn;
-        mBandwidth = bandwidth;
+        mCi = inRangeOrUnavailable(ci, 0, MAX_CI);
+        mPci = inRangeOrUnavailable(pci, 0, MAX_PCI);
+        mTac = inRangeOrUnavailable(tac, 0, MAX_TAC);
+        mEarfcn = inRangeOrUnavailable(earfcn, 0, MAX_EARFCN);
+        mBandwidth = inRangeOrUnavailable(bandwidth, 0, MAX_BANDWIDTH);
     }
 
     /** @hide */
diff --git a/telephony/java/android/telephony/CellIdentityNr.java b/telephony/java/android/telephony/CellIdentityNr.java
index 44896e2..05e5c75 100644
--- a/telephony/java/android/telephony/CellIdentityNr.java
+++ b/telephony/java/android/telephony/CellIdentityNr.java
@@ -29,6 +29,11 @@
 public final class CellIdentityNr extends CellIdentity {
     private static final String TAG = "CellIdentityNr";
 
+    private static final int MAX_PCI = 1007;
+    private static final int MAX_TAC = 65535;
+    private static final int MAX_NRARFCN = 3279165;
+    private static final long MAX_NCI = 68719476735L;
+
     private final int mNrArfcn;
     private final int mPci;
     private final int mTac;
@@ -41,6 +46,7 @@
      * @param nrArfcn NR Absolute Radio Frequency Channel Number, in range [0, 3279165].
      * @param mccStr 3-digit Mobile Country Code in string format.
      * @param mncStr 2 or 3-digit Mobile Network Code in string format.
+     * @param nci The 36-bit NR Cell Identity in range [0, 68719476735].
      * @param alphal long alpha Operator Name String or Enhanced Operator Name String.
      * @param alphas short alpha Operator Name String or Enhanced Operator Name String.
      *
@@ -49,10 +55,10 @@
     public CellIdentityNr(int pci, int tac, int nrArfcn, String mccStr, String mncStr,
             long nci, String alphal, String alphas) {
         super(TAG, CellInfo.TYPE_NR, mccStr, mncStr, alphal, alphas);
-        mPci = pci;
-        mTac = tac;
-        mNrArfcn = nrArfcn;
-        mNci = nci;
+        mPci = inRangeOrUnavailable(pci, 0, MAX_PCI);
+        mTac = inRangeOrUnavailable(tac, 0, MAX_TAC);
+        mNrArfcn = inRangeOrUnavailable(nrArfcn, 0, MAX_NRARFCN);
+        mNci = inRangeOrUnavailable(nci, 0, MAX_NCI);
     }
 
     /** @hide */
diff --git a/telephony/java/android/telephony/CellIdentityTdscdma.java b/telephony/java/android/telephony/CellIdentityTdscdma.java
index 937de70..558e346 100644
--- a/telephony/java/android/telephony/CellIdentityTdscdma.java
+++ b/telephony/java/android/telephony/CellIdentityTdscdma.java
@@ -30,12 +30,18 @@
     private static final String TAG = CellIdentityTdscdma.class.getSimpleName();
     private static final boolean DBG = false;
 
+    private static final int MAX_LAC = 65535;
+    private static final int MAX_CID = 268435455;
+    private static final int MAX_CPID = 127;
+    private static final int MAX_UARFCN = 65535;
+
     // 16-bit Location Area Code, 0..65535, CellInfo.UNAVAILABLE if unknown.
     private final int mLac;
     // 28-bit UMTS Cell Identity described in TS 25.331, 0..268435455, CellInfo.UNAVAILABLE
     // if unknown.
     private final int mCid;
-    // 8-bit Cell Parameters ID described in TS 25.331, 0..127, CellInfo.UNAVAILABLE if unknown.
+    // 8-bit Cell Parameters ID described in TS 25.331 sec 10.3.6.9,
+    // 0..127, CellInfo.UNAVAILABLE if unknown.
     private final int mCpid;
     // 16-bit UMTS Absolute RF Channel Number described in TS 25.101 sec. 5.4.3
     private final int mUarfcn;
@@ -68,10 +74,10 @@
     public CellIdentityTdscdma(String mcc, String mnc, int lac, int cid, int cpid, int uarfcn,
             String alphal, String alphas) {
         super(TAG, CellInfo.TYPE_TDSCDMA, mcc, mnc, alphal, alphas);
-        mLac = lac;
-        mCid = cid;
-        mCpid = cpid;
-        mUarfcn = uarfcn;
+        mLac = inRangeOrUnavailable(lac, 0, MAX_LAC);
+        mCid = inRangeOrUnavailable(cid, 0, MAX_CID);
+        mCpid = inRangeOrUnavailable(cpid, 0, MAX_CPID);
+        mUarfcn = inRangeOrUnavailable(uarfcn, 0, MAX_UARFCN);
     }
 
     private CellIdentityTdscdma(CellIdentityTdscdma cid) {
diff --git a/telephony/java/android/telephony/CellIdentityWcdma.java b/telephony/java/android/telephony/CellIdentityWcdma.java
index aa2085a..e500c92 100644
--- a/telephony/java/android/telephony/CellIdentityWcdma.java
+++ b/telephony/java/android/telephony/CellIdentityWcdma.java
@@ -31,6 +31,11 @@
     private static final String TAG = CellIdentityWcdma.class.getSimpleName();
     private static final boolean DBG = false;
 
+    private static final int MAX_LAC = 65535;
+    private static final int MAX_CID = 268435455;
+    private static final int MAX_PSC = 511;
+    private static final int MAX_UARFCN = 16383; // a 14 bit number; TS 25.331 ex sec 10.3.8.15
+
     // 16-bit Location Area Code, 0..65535
     private final int mLac;
     // 28-bit UMTS Cell Identity described in TS 25.331, 0..268435455
@@ -68,10 +73,10 @@
     public CellIdentityWcdma (int lac, int cid, int psc, int uarfcn,
                               String mccStr, String mncStr, String alphal, String alphas) {
         super(TAG, CellInfo.TYPE_WCDMA, mccStr, mncStr, alphal, alphas);
-        mLac = lac;
-        mCid = cid;
-        mPsc = psc;
-        mUarfcn = uarfcn;
+        mLac = inRangeOrUnavailable(lac, 0, MAX_LAC);
+        mCid = inRangeOrUnavailable(cid, 0, MAX_CID);
+        mPsc = inRangeOrUnavailable(psc, 0, MAX_PSC);
+        mUarfcn = inRangeOrUnavailable(uarfcn, 0, MAX_UARFCN);
     }
 
     /** @hide */