resolve merge conflicts of 56ad8b4 to master

Test: Build successfully

Change-Id: Ie317dca9dccf4d9cb77c821f7c97643fd8f34a19
diff --git a/include/telephony/ril.h b/include/telephony/ril.h
index 0cadea5..3bc8986 100644
--- a/include/telephony/ril.h
+++ b/include/telephony/ril.h
@@ -69,8 +69,8 @@
  * RIL_VERSION = 14 : New data structures are added, namely RIL_CarrierMatchType,
  *                    RIL_Carrier, RIL_CarrierRestrictions and RIL_PCO_Data.
  *                    New commands added: RIL_REQUEST_SET_CARRIER_RESTRICTIONS,
- *                    RIL_REQUEST_SET_CARRIER_RESTRICTIONS and
- *                    RIL_UNSOL_PCO_DATA
+ *                    RIL_REQUEST_SET_CARRIER_RESTRICTIONS and RIL_UNSOL_PCO_DATA.
+ * RIL_VERSION = 15 : New commands added: RIL_UNSOL_MODEM_RESTART
  */
 #define RIL_VERSION 12
 #define LAST_IMPRECISE_RIL_VERSION 12 // Better self-documented name
@@ -333,7 +333,17 @@
     PREF_NET_TYPE_LTE_GSM_WCDMA            = 9, /* LTE, GSM/WCDMA */
     PREF_NET_TYPE_LTE_CMDA_EVDO_GSM_WCDMA  = 10, /* LTE, CDMA, EvDo, GSM/WCDMA */
     PREF_NET_TYPE_LTE_ONLY                 = 11, /* LTE only */
-    PREF_NET_TYPE_LTE_WCDMA                = 12  /* LTE/WCDMA */
+    PREF_NET_TYPE_LTE_WCDMA                = 12,  /* LTE/WCDMA */
+    PREF_NET_TYPE_TD_SCDMA_ONLY            = 13, /* TD-SCDMA only */
+    PREF_NET_TYPE_TD_SCDMA_WCDMA           = 14, /* TD-SCDMA and WCDMA */
+    PREF_NET_TYPE_TD_SCDMA_LTE             = 15, /* TD-SCDMA and LTE */
+    PREF_NET_TYPE_TD_SCDMA_GSM             = 16, /* TD-SCDMA and GSM */
+    PREF_NET_TYPE_TD_SCDMA_GSM_LTE         = 17, /* TD-SCDMA,GSM and LTE */
+    PREF_NET_TYPE_TD_SCDMA_GSM_WCDMA       = 18, /* TD-SCDMA, GSM/WCDMA */
+    PREF_NET_TYPE_TD_SCDMA_WCDMA_LTE       = 19, /* TD-SCDMA, WCDMA and LTE */
+    PREF_NET_TYPE_TD_SCDMA_GSM_WCDMA_LTE   = 20, /* TD-SCDMA, GSM/WCDMA and LTE */
+    PREF_NET_TYPE_TD_SCDMA_GSM_WCDMA_CDMA_EVDO_AUTO  = 21, /* TD-SCDMA, GSM/WCDMA, CDMA and EvDo */
+    PREF_NET_TYPE_TD_SCDMA_LTE_CDMA_EVDO_GSM_WCDMA   = 22  /* TD-SCDMA, LTE, CDMA, EvDo GSM/WCDMA */
 } RIL_PreferredNetworkType;
 
 /* Source for cdma subscription */
@@ -2297,7 +2307,7 @@
  *                                95 - Semantically incorrect message
  *                                96 - Invalid mandatory information
  *                                97 - Message type non-existent or not implemented
- *                                98 - Message not compatible with protocol state
+ *                                98 - Message type not compatible with protocol state
  *                                99 - Information element non-existent or not implemented
  *                               100 - Conditional IE error
  *                               101 - Message not compatible with protocol state
@@ -4603,7 +4613,7 @@
  * RIL_REQUEST_VOICE_RADIO_TECH
  *
  * Query the radio technology type (3GPP/3GPP2) used for voice. Query is valid only
- * when radio state is RADIO_STATE_ON
+ * when radio state is not RADIO_STATE_UNAVAILABLE
  *
  * "data" is NULL
  * "response" is int *
@@ -5797,6 +5807,29 @@
   */
 #define RIL_UNSOL_PCO_DATA 1046
 
+ /**
+  * RIL_UNSOL_MODEM_RESTART
+  *
+  * Called when there is a modem reset.
+  *
+  * "reason" is "const char *" containing the reason for the reset. It
+  * could be a crash signature if the restart was due to a crash or some
+  * string such as "user-initiated restart" or "AT command initiated
+  * restart" that explains the cause of the modem restart.
+  *
+  * When modem restarts, one of the following radio state transitions will happen
+  * 1) RADIO_STATE_ON->RADIO_STATE_UNAVAILABLE->RADIO_STATE_ON or
+  * 2) RADIO_STATE_OFF->RADIO_STATE_UNAVAILABLE->RADIO_STATE_OFF
+  * This message can be sent either just before the RADIO_STATE changes to RADIO_STATE_UNAVAILABLE
+  * or just after but should never be sent after the RADIO_STATE changes from UNAVAILABLE to
+  * AVAILABLE(RADIO_STATE_ON/RADIO_STATE_OFF) again.
+  *
+  * It should NOT be sent after the RADIO_STATE changes to AVAILABLE after the
+  * modem restart as that could be interpreted as a second modem reset by the
+  * framework.
+  */
+#define RIL_UNSOL_MODEM_RESTART 1047
+
 /***********************************************************************/
 
 
diff --git a/libril/RilSapSocket.cpp b/libril/RilSapSocket.cpp
index e282598..b562844 100644
--- a/libril/RilSapSocket.cpp
+++ b/libril/RilSapSocket.cpp
@@ -86,7 +86,9 @@
        const void *data,
        size_t datalen) {
     RilSapSocket *sap_socket = getSocketById(RIL_SOCKET_1);
-    sap_socket->onUnsolicitedResponse(unsolResponse, (void *)data, datalen);
+    if(sap_socket){
+        sap_socket->onUnsolicitedResponse(unsolResponse, (void *)data, datalen);
+    }
 }
 #endif
 
@@ -249,7 +251,7 @@
     int per_line = 0;
 
     do {
-        dest += sprintf(out, "%8.8s [%8.8x] ", who, source);
+        dest += snprintf(out, sizeof(out), "%8.8s [%8.8x] ", who, source);
         for(; source < length && dest_len - dest > 3 && per_line < BYTES_PER_LINE; source++,
         per_line ++) {
             out[dest++] = HEX_HIGH(buffer[source]);
diff --git a/libril/ril.cpp b/libril/ril.cpp
index 923df90..ce5876c 100644
--- a/libril/ril.cpp
+++ b/libril/ril.cpp
@@ -832,6 +832,10 @@
                 len = 0;
             } else {
                 uusInfo.uusData = (char*) p.readInplace(len);
+                // check if the length is invalid
+                if (uusInfo.uusData == NULL) {
+                    goto invalid;
+                }
             }
 
             uusInfo.uusLength = len;
@@ -5611,6 +5615,7 @@
         case RIL_UNSOL_RADIO_CAPABILITY: return "RIL_UNSOL_RADIO_CAPABILITY";
         case RIL_RESPONSE_ACKNOWLEDGEMENT: return "RIL_RESPONSE_ACKNOWLEDGEMENT";
         case RIL_UNSOL_PCO_DATA: return "RIL_UNSOL_PCO_DATA";
+        case RIL_UNSOL_MODEM_RESTART: return "RIL_UNSOL_MODEM_RESTART";
         default: return "<unknown request>";
     }
 }
diff --git a/libril/ril_unsol_commands.h b/libril/ril_unsol_commands.h
index 11ae050..7e675ac 100755
--- a/libril/ril_unsol_commands.h
+++ b/libril/ril_unsol_commands.h
@@ -61,3 +61,4 @@
     {RIL_UNSOL_STK_CC_ALPHA_NOTIFY, responseString, WAKE_PARTIAL},
     {RIL_UNSOL_LCEDATA_RECV, responseLceData, WAKE_PARTIAL},
     {RIL_UNSOL_PCO_DATA, responsePcoData, WAKE_PARTIAL},
+    {RIL_UNSOL_MODEM_RESTART, responseString, WAKE_PARTIAL},
diff --git a/reference-ril/reference-ril.c b/reference-ril/reference-ril.c
index 16a279c..8a9f48a 100644
--- a/reference-ril/reference-ril.c
+++ b/reference-ril/reference-ril.c
@@ -543,23 +543,27 @@
         err = at_tok_nextstr(&line, &out);
         if (err < 0)
             goto error;
-        responses[i].type = alloca(strlen(out) + 1);
-        strcpy(responses[i].type, out);
+
+        int type_size = strlen(out) + 1;
+        responses[i].type = alloca(type_size);
+        strlcpy(responses[i].type, out, type_size);
 
         // APN ignored for v5
         err = at_tok_nextstr(&line, &out);
         if (err < 0)
             goto error;
 
-        responses[i].ifname = alloca(strlen(PPP_TTY_PATH) + 1);
-        strcpy(responses[i].ifname, PPP_TTY_PATH);
+        int ifname_size = strlen(PPP_TTY_PATH) + 1;
+        responses[i].ifname = alloca(ifname_size);
+        strlcpy(responses[i].ifname, PPP_TTY_PATH, ifname_size);
 
         err = at_tok_nextstr(&line, &out);
         if (err < 0)
             goto error;
 
-        responses[i].addresses = alloca(strlen(out) + 1);
-        strcpy(responses[i].addresses, out);
+        int addresses_size = strlen(out) + 1;
+        responses[i].addresses = alloca(addresses_size);
+        strlcpy(responses[i].addresses, out, addresses_size);
 
         if (isInEmulator()) {
             /* We are in the emulator - the dns servers are listed
diff --git a/rild/Android.mk b/rild/Android.mk
index b8de0bd..37f1153 100644
--- a/rild/Android.mk
+++ b/rild/Android.mk
@@ -6,14 +6,14 @@
 LOCAL_SRC_FILES:= \
 	rild.c
 
-
 LOCAL_SHARED_LIBRARIES := \
-	liblog \
 	libcutils \
-	libril \
-	libdl
+	libdl \
+	liblog \
+	libminijail \
+	libril
 
-# temporary hack for broken vendor rils
+# Temporary hack for broken vendor RILs.
 LOCAL_WHOLE_STATIC_LIBRARIES := \
 	librilutils_static
 
diff --git a/rild/rild.c b/rild/rild.c
index 56c5653..dec950e 100644
--- a/rild/rild.c
+++ b/rild/rild.c
@@ -33,6 +33,7 @@
 #include <sys/prctl.h>
 #include <sys/stat.h>
 #include <sys/types.h>
+#include <libminijail.h>
 #include <libril/ril_ex.h>
 
 #include <private/android_filesystem_config.h>
@@ -102,34 +103,14 @@
  */
 void switchUser() {
     char debuggable[PROP_VALUE_MAX];
+    struct minijail *j = minijail_new();
+    minijail_change_uid(j, AID_RADIO);
+    minijail_use_caps(j, CAP_MASK_LONG(CAP_BLOCK_SUSPEND) |
+                         CAP_MASK_LONG(CAP_NET_ADMIN) |
+                         CAP_MASK_LONG(CAP_NET_RAW));
 
-    prctl(PR_SET_KEEPCAPS, 1, 0, 0, 0);
-    if (setresuid(AID_RADIO, AID_RADIO, AID_RADIO) == -1) {
-        RLOGE("setresuid failed: %s", strerror(errno));
-        exit(EXIT_FAILURE);
-    }
-
-    struct __user_cap_header_struct header;
-    memset(&header, 0, sizeof(header));
-    header.version = _LINUX_CAPABILITY_VERSION_3;
-    header.pid = 0;
-
-    struct __user_cap_data_struct data[MAX_CAP_NUM];
-    memset(&data, 0, sizeof(data));
-
-    data[CAP_TO_INDEX(CAP_NET_ADMIN)].effective |= CAP_TO_MASK(CAP_NET_ADMIN);
-    data[CAP_TO_INDEX(CAP_NET_ADMIN)].permitted |= CAP_TO_MASK(CAP_NET_ADMIN);
-
-    data[CAP_TO_INDEX(CAP_NET_RAW)].effective |= CAP_TO_MASK(CAP_NET_RAW);
-    data[CAP_TO_INDEX(CAP_NET_RAW)].permitted |= CAP_TO_MASK(CAP_NET_RAW);
-
-    data[CAP_TO_INDEX(CAP_BLOCK_SUSPEND)].effective |= CAP_TO_MASK(CAP_BLOCK_SUSPEND);
-    data[CAP_TO_INDEX(CAP_BLOCK_SUSPEND)].permitted |= CAP_TO_MASK(CAP_BLOCK_SUSPEND);
-
-    if (capset(&header, &data[0]) == -1) {
-        RLOGE("capset failed: %s", strerror(errno));
-        exit(EXIT_FAILURE);
-    }
+    minijail_enter(j);
+    minijail_destroy(j);
 
     /*
      * Debuggable build only:
@@ -142,7 +123,7 @@
 }
 
 int main(int argc, char **argv) {
-    const char * rilLibPath = NULL;
+    const char *rilLibPath = NULL;
     char **rilArgv;
     void *dlHandle;
     const RIL_RadioFunctions *(*rilInit)(const struct RIL_Env *, int, char **);
@@ -239,7 +220,7 @@
     }
 
     rilArgv[argc++] = "-c";
-    rilArgv[argc++] = clientId;
+    rilArgv[argc++] = (char*)clientId;
     RLOGD("RIL_Init argc = %d clientId = %s", argc, rilArgv[argc-1]);
 
     // Make sure there's a reasonable argv[0]