Merge "Send shutdown command to modem"
diff --git a/src/java/com/android/internal/telephony/ServiceStateTracker.java b/src/java/com/android/internal/telephony/ServiceStateTracker.java
index bd2e4e4..b3e6958 100644
--- a/src/java/com/android/internal/telephony/ServiceStateTracker.java
+++ b/src/java/com/android/internal/telephony/ServiceStateTracker.java
@@ -212,6 +212,7 @@
     protected static final int EVENT_RADIO_POWER_FROM_CARRIER          = 51;
     protected static final int EVENT_SIM_NOT_INSERTED                  = 52;
     protected static final int EVENT_IMS_SERVICE_STATE_CHANGED         = 53;
+    protected static final int EVENT_RADIO_POWER_OFF_DONE              = 54;
 
     protected static final String TIMEZONE_PROPERTY = "persist.sys.timezone";
 
@@ -1134,6 +1135,16 @@
                 }
                 break;
 
+            case EVENT_RADIO_POWER_OFF_DONE:
+                if (DBG) log("EVENT_RADIO_POWER_OFF_DONE");
+                if (mDeviceShuttingDown && mCi.getRadioState().isAvailable()) {
+                    // during shutdown the modem may not send radio state changed event
+                    // as a result of radio power request
+                    // Hence, issuing shut down regardless of radio power response
+                    mCi.requestShutdown(null);
+                }
+                break;
+
             // GSM
             case EVENT_SIM_READY:
                 // Reset the mPreviousSubId so we treat a SIM power bounce
@@ -4460,7 +4471,7 @@
             mPhone.mCT.mForegroundCall.hangupIfAlive();
         }
 
-        mCi.setRadioPower(false, null);
+        mCi.setRadioPower(false, obtainMessage(EVENT_RADIO_POWER_OFF_DONE));
 
     }
 
diff --git a/src/java/com/android/internal/telephony/test/SimulatedCommands.java b/src/java/com/android/internal/telephony/test/SimulatedCommands.java
index 7553b61..1b43bcd 100644
--- a/src/java/com/android/internal/telephony/test/SimulatedCommands.java
+++ b/src/java/com/android/internal/telephony/test/SimulatedCommands.java
@@ -132,6 +132,7 @@
 
     private boolean mDcSuccess = true;
     private DataCallResponse mDcResponse;
+    private boolean mIsRadioPowerFailResponse = false;
 
     //***** Constructor
     public
@@ -1188,11 +1189,17 @@
 
     @Override
     public void setRadioPower(boolean on, Message result) {
+        if (mIsRadioPowerFailResponse) {
+            resultFail(result, null, new RuntimeException("setRadioPower failed!"));
+            return;
+        }
+
         if(on) {
             setRadioState(RadioState.RADIO_ON);
         } else {
             setRadioState(RadioState.RADIO_OFF);
         }
+        resultSuccess(result, null);
     }
 
 
@@ -2151,4 +2158,8 @@
         super.setOnRestrictedStateChanged(h, what, obj);
         SimulatedCommandsVerifier.getInstance().setOnRestrictedStateChanged(h, what, obj);
     }
+
+    public void setRadioPowerFailResponse(boolean fail) {
+        mIsRadioPowerFailResponse = fail;
+    }
 }
diff --git a/tests/telephonytests/src/com/android/internal/telephony/ServiceStateTrackerTest.java b/tests/telephonytests/src/com/android/internal/telephony/ServiceStateTrackerTest.java
index 018ac88..fba9ead 100644
--- a/tests/telephonytests/src/com/android/internal/telephony/ServiceStateTrackerTest.java
+++ b/tests/telephonytests/src/com/android/internal/telephony/ServiceStateTrackerTest.java
@@ -1114,6 +1114,33 @@
 
     @Test
     @SmallTest
+    public void testShuttingDownRequest() throws Exception {
+        sst.setRadioPower(true);
+        waitForMs(100);
+
+        sst.requestShutdown();
+        waitForMs(100);
+        assertFalse(mSimulatedCommands.getRadioState().isAvailable());
+    }
+
+    @Test
+    @SmallTest
+    public void testShuttingDownRequestWithRadioPowerFailResponse() throws Exception {
+        sst.setRadioPower(true);
+        waitForMs(100);
+
+        // Simulate RIL fails the radio power settings.
+        mSimulatedCommands.setRadioPowerFailResponse(true);
+        sst.setRadioPower(false);
+        waitForMs(100);
+        assertTrue(mSimulatedCommands.getRadioState().isOn());
+        sst.requestShutdown();
+        waitForMs(100);
+        assertFalse(mSimulatedCommands.getRadioState().isAvailable());
+    }
+
+    @Test
+    @SmallTest
     public void testSetTimeFromNITZStr() throws Exception {
         doReturn(mAlarmManager).when(mIBinder).queryLocalInterface(anyString());
         mServiceManagerMockedServices.put(Context.ALARM_SERVICE, mIBinder);