Merge "Do not add FDN if number is not entered."
diff --git a/Android.mk b/Android.mk
index cbebc44..24fb423 100644
--- a/Android.mk
+++ b/Android.mk
@@ -9,9 +9,17 @@
src_dirs := src $(phone_common_dir)/src sip/src
res_dirs := res $(phone_common_dir)/res sip/res
-LOCAL_JAVA_LIBRARIES := telephony-common voip-common ims-common
+LOCAL_JAVA_LIBRARIES := \
+ telephony-common \
+ voip-common \
+ ims-common \
+ org.apache.http.legacy
+
LOCAL_STATIC_JAVA_LIBRARIES := \
- org.apache.http.legacy \
+ android-support-v7-appcompat \
+ android-support-v7-preference \
+ android-support-v7-recyclerview \
+ android-support-v14-preference \
guava \
volley
diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index f1d293f..fb92d3f 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -58,9 +58,9 @@
<protected-broadcast android:name= "android.intent.action.stk.session_end" />
<protected-broadcast android:name= "android.intent.action.stk.icc_status_change" />
<protected-broadcast android:name= "android.intent.action.stk.alpha_notify" />
- <protected-broadcast android:name= "android.intent.action.CARRIER_SIGNAL_REDIRECTED" />
- <protected-broadcast android:name= "android.intent.action.CARRIER_SIGNAL_REQUEST_NETWORK_FAILED" />
- <protected-broadcast android:name= "android.intent.action.CARRIER_SIGNAL_PCO_VALUE" />
+ <protected-broadcast android:name= "com.android.internal.telephony.CARRIER_SIGNAL_REDIRECTED" />
+ <protected-broadcast android:name= "com.android.internal.telephony.CARRIER_SIGNAL_REQUEST_NETWORK_FAILED" />
+ <protected-broadcast android:name= "com.android.internal.telephony.CARRIER_SIGNAL_PCO_VALUE" />
<protected-broadcast android:name= "android.intent.action.VOICEMAIL_SMS_RECEIVED" />
<protected-broadcast android:name= "com.android.intent.isim_refresh" />
<protected-broadcast android:name= "com.android.ims.IMS_SERVICE_UP" />
@@ -157,6 +157,7 @@
start requests, even if they happen immediately after the user
presses home. -->
<uses-permission android:name="android.permission.STOP_APP_SWITCHES" />
+ <uses-permission android:name="android.permission.UPDATE_DEVICE_STATS" />
<application android:name="PhoneApp"
android:persistent="true"
@@ -315,18 +316,6 @@
</intent-filter>
</receiver>
- <!-- Trampoline activity that handles the PERFORM_CDMA_PROVISIONING intent. -->
- <activity android:name="InCallScreenShowActivation"
- android:permission="android.permission.PERFORM_CDMA_PROVISIONING"
- android:label="@string/phoneIconLabel"
- android:theme="@android:style/Theme.NoDisplay"
- android:excludeFromRecents="true">
- <intent-filter>
- <action android:name="com.android.phone.PERFORM_CDMA_PROVISIONING" />
- <category android:name="android.intent.category.DEFAULT" />
- </intent-filter>
- </activity>
-
<!-- "Mobile network settings" screen, used on both
non-voice-capable tablets and regular phone devices. -->
<activity android:name="MobileNetworkSettings"
@@ -449,15 +438,6 @@
</intent-filter>
</activity>
- <!-- Broadcast Receiver that will process BOOT Complete and launch OTA -->
- <!-- TODO http://b/23526250 Handle OTASP under system user -->
- <receiver android:name="OtaStartupReceiver" android:exported="false"
- androidprv:systemUserOnly="true">
- <intent-filter android:priority="100">
- <action android:name="android.intent.action.BOOT_COMPLETED"/>
- </intent-filter>
- </receiver>
-
<!-- Activation service that trigger OTASP sim provisioning -->
<service android:name=".otasp.OtaspActivationService" android:launchMode="singleInstance"
androidprv:systemUserOnly="true">
@@ -466,7 +446,8 @@
</intent-filter>
</service>
- <receiver android:name=".otasp.OtaspSimStateReceiver" android:exported ="false">
+ <receiver android:name=".otasp.OtaspSimStateReceiver" androidprv:systemUserOnly="true"
+ android:exported ="false">
<intent-filter>
<action android:name="android.telephony.action.CARRIER_CONFIG_CHANGED" />
</intent-filter>
@@ -570,13 +551,6 @@
android:theme="@style/Empty">
</activity>
- <activity android:name="HfaActivity"
- android:configChanges="orientation|screenSize|keyboardHidden"
- android:launchMode="singleInstance"
- android:theme="@style/Empty"
- android:exported="false">
- </activity>
-
<activity android:name="com.android.phone.settings.PhoneAccountSettingsActivity"
android:label="@string/phone_accounts"
android:theme="@style/DialerSettingsLight">
@@ -601,9 +575,6 @@
</intent-filter>
</activity>
- <!-- service to dump telephony information -->
- <service android:name="HfaService" android:exported="false"/>
-
<!-- Telecom integration -->
<service
android:singleUser="true"
diff --git a/res/values/strings.xml b/res/values/strings.xml
index c42e0cd..6701fec 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -95,6 +95,8 @@
<string name="no_vm_number_msg">No voicemail number is stored on the SIM card.</string>
<!-- Button label on the "Missing voicemail number" dialog -->
<string name="add_vm_number_str">Add number</string>
+ <!--Toast in Call settings when asked to launch voicemail for a guest user -->
+ <string name="voice_number_setting_primary_user_only">Voice mail for Call settings can only be changed by the primary user.</string>
<!-- Status message displayed on SIM PIN unlock panel -->
<string name="puk_unlocked">Your SIM card has been unblocked. Your phone is unlocking\u2026</string>
@@ -1366,6 +1368,12 @@
Unable to connect, please insert a valid SIM card.
</string>
+ <!-- Call failure reason displayed when an in-progress WIFI call fails due to a loss of WIFI
+ connectivity, or the WIFI signal has degraded to the point the call cannot continue. -->
+ <string name="callFailed_wifi_lost">
+ Wi-Fi connection lost. Call ended.
+ </string>
+
<!-- The title for the change voicemail PIN activity -->
<string name="change_pin_title">Change Voicemail PIN</string>
<!-- The label for the continue button in change voicemail PIN activity -->
diff --git a/res/xml/cdma_options.xml b/res/xml/cdma_options.xml
index 78e3630..c86787b 100644
--- a/res/xml/cdma_options.xml
+++ b/res/xml/cdma_options.xml
@@ -43,14 +43,6 @@
</PreferenceScreen>
<PreferenceScreen
- android:key="cdma_activate_device_key"
- android:title="@string/cdma_activate_device">
- <intent android:action="com.android.phone.PERFORM_VOICELESS_CDMA_PROVISIONING">
- <extra android:name="autoStart" android:value="true" />
- </intent>
- </PreferenceScreen>
-
- <PreferenceScreen
android:key="carrier_settings_key"
android:title="@string/carrier_settings_title">
<intent android:action="android.intent.action.MAIN"
diff --git a/sip/src/com/android/services/telephony/sip/SipEditor.java b/sip/src/com/android/services/telephony/sip/SipEditor.java
index 27941c3..dd475e6 100644
--- a/sip/src/com/android/services/telephony/sip/SipEditor.java
+++ b/sip/src/com/android/services/telephony/sip/SipEditor.java
@@ -360,7 +360,13 @@
}
}
} else if (key == PreferenceKey.Port) {
- int port = Integer.parseInt(PreferenceKey.Port.getValue());
+ int port;
+ try {
+ port = Integer.parseInt(PreferenceKey.Port.getValue());
+ } catch (NumberFormatException e) {
+ showAlert(getString(R.string.not_a_valid_port));
+ return;
+ }
if ((port < 1000) || (port > 65534)) {
showAlert(getString(R.string.not_a_valid_port));
return;
diff --git a/src/com/android/phone/CallController.java b/src/com/android/phone/CallController.java
index 5b08662..a5d340c 100644
--- a/src/com/android/phone/CallController.java
+++ b/src/com/android/phone/CallController.java
@@ -19,7 +19,6 @@
import com.android.internal.telephony.CallManager;
import com.android.internal.telephony.Phone;
import com.android.internal.telephony.PhoneConstants;
-import com.android.internal.telephony.TelephonyCapabilities;
import com.android.phone.CallGatewayManager.RawGatewayInfo;
import com.android.phone.Constants.CallStatusCode;
@@ -226,14 +225,6 @@
throw new IllegalArgumentException("Unexpected action: " + action);
}
- // Check to see if this is an OTASP call (the "activation" call
- // used to provision CDMA devices), and if so, do some
- // OTASP-specific setup.
- Phone phone = mApp.mCM.getDefaultPhone();
- if (TelephonyCapabilities.supportsOtasp(phone)) {
- checkForOtaspCall(intent);
- }
-
CallStatusCode status = placeCallInternal(intent);
switch (status) {
@@ -670,28 +661,6 @@
mApp.startActivity(intent);
}
- /**
- * Checks the current outgoing call to see if it's an OTASP call (the
- * "activation" call used to provision CDMA devices). If so, do any
- * necessary OTASP-specific setup before actually placing the call.
- */
- private void checkForOtaspCall(Intent intent) {
- if (OtaUtils.isOtaspCallIntent(intent)) {
- Log.i(TAG, "checkForOtaspCall: handling OTASP intent! " + intent);
-
- // ("OTASP-specific setup" basically means creating and initializing
- // the OtaUtils instance. Note that this setup needs to be here in
- // the CallController.placeCall() sequence, *not* in
- // OtaUtils.startInteractiveOtasp(), since it's also possible to
- // start an OTASP call by manually dialing "*228" (in which case
- // OtaUtils.startInteractiveOtasp() never gets run at all.)
- OtaUtils.setupOtaspCall(intent);
- } else {
- if (DBG) log("checkForOtaspCall: not an OTASP call.");
- }
- }
-
-
//
// Debugging
//
diff --git a/src/com/android/phone/CallFeaturesSetting.java b/src/com/android/phone/CallFeaturesSetting.java
index 111e263..47833ea 100644
--- a/src/com/android/phone/CallFeaturesSetting.java
+++ b/src/com/android/phone/CallFeaturesSetting.java
@@ -249,6 +249,8 @@
Preference cdmaOptions = prefSet.findPreference(BUTTON_CDMA_OPTIONS);
Preference gsmOptions = prefSet.findPreference(BUTTON_GSM_UMTS_OPTIONS);
+ Preference fdnButton = prefSet.findPreference(BUTTON_FDN_KEY);
+ fdnButton.setIntent(mSubscriptionInfoHelper.getIntent(FdnSetting.class));
if (carrierConfig.getBoolean(CarrierConfigManager.KEY_WORLD_PHONE_BOOL)) {
cdmaOptions.setIntent(mSubscriptionInfoHelper.getIntent(CdmaCallOptions.class));
gsmOptions.setIntent(mSubscriptionInfoHelper.getIntent(GsmUmtsCallOptions.class));
@@ -257,7 +259,6 @@
prefSet.removePreference(gsmOptions);
int phoneType = mPhone.getPhoneType();
- Preference fdnButton = prefSet.findPreference(BUTTON_FDN_KEY);
if (carrierConfig.getBoolean(CarrierConfigManager.KEY_HIDE_CARRIER_NETWORK_SETTINGS_BOOL)) {
prefSet.removePreference(fdnButton);
} else {
@@ -269,7 +270,6 @@
addPreferencesFromResource(R.xml.cdma_call_privacy);
}
} else if (phoneType == PhoneConstants.PHONE_TYPE_GSM) {
- fdnButton.setIntent(mSubscriptionInfoHelper.getIntent(FdnSetting.class));
if (carrierConfig.getBoolean(
CarrierConfigManager.KEY_ADDITIONAL_CALL_SETTING_BOOL)) {
diff --git a/src/com/android/phone/CallNotifier.java b/src/com/android/phone/CallNotifier.java
index 7836248..b3d8ade 100644
--- a/src/com/android/phone/CallNotifier.java
+++ b/src/com/android/phone/CallNotifier.java
@@ -16,12 +16,10 @@
package com.android.phone;
-import com.android.internal.telephony.Call;
import com.android.internal.telephony.CallManager;
-import com.android.internal.telephony.Connection;
+
import com.android.internal.telephony.Phone;
import com.android.internal.telephony.PhoneConstants;
-import com.android.internal.telephony.TelephonyCapabilities;
import com.android.internal.telephony.cdma.CdmaInformationRecords.CdmaDisplayInfoRec;
import com.android.internal.telephony.cdma.CdmaInformationRecords.CdmaSignalInfoRec;
import com.android.internal.telephony.cdma.SignalToneUtil;
@@ -30,17 +28,14 @@
import android.bluetooth.BluetoothHeadset;
import android.bluetooth.BluetoothProfile;
import android.content.Context;
-import android.media.AudioAttributes;
import android.media.AudioManager;
import android.media.ToneGenerator;
import android.os.AsyncResult;
import android.os.Handler;
import android.os.Message;
import android.os.SystemProperties;
-import android.provider.Settings;
import android.telecom.TelecomManager;
-import android.telephony.DisconnectCause;
-import android.telephony.PhoneNumberUtils;
+
import android.telephony.PhoneStateListener;
import android.telephony.SubscriptionInfo;
import android.telephony.SubscriptionManager;
@@ -103,8 +98,6 @@
// We should store all the possible event type values in one place to make sure that
// they don't step on each others' toes.
public static final int INTERNAL_SHOW_MESSAGE_NOTIFICATION_DONE = 22;
- // Other events from call manager
- public static final int EVENT_OTA_PROVISION_CHANGE = 20;
/**
* Initialize the singleton CallNotifier instance.
@@ -177,7 +170,6 @@
*/
private void registerForNotifications() {
mCM.registerForDisconnect(this, PHONE_DISCONNECT, null);
- mCM.registerForCdmaOtaStatusChange(this, EVENT_OTA_PROVISION_CHANGE, null);
mCM.registerForDisplayInfo(this, PHONE_STATE_DISPLAYINFO, null);
mCM.registerForSignalInfo(this, PHONE_STATE_SIGNALINFO, null);
mCM.registerForInCallVoicePrivacyOn(this, PHONE_ENHANCED_VP_ON, null);
@@ -214,11 +206,6 @@
PhoneDisplayMessage.dismissMessage();
break;
- case EVENT_OTA_PROVISION_CHANGE:
- if (DBG) log("EVENT_OTA_PROVISION_CHANGE...");
- mApplication.handleOtaspEvent(msg);
- break;
-
case PHONE_ENHANCED_VP_ON:
if (DBG) log("PHONE_ENHANCED_VP_ON...");
if (!mVoicePrivacyState) {
@@ -375,18 +362,6 @@
toneVolume = TONE_RELATIVE_VOLUME_HIPRI;
toneLengthMillis = 200;
break;
- case TONE_OTA_CALL_END:
- if (mApplication.cdmaOtaConfigData.otaPlaySuccessFailureTone ==
- OtaUtils.OTA_PLAY_SUCCESS_FAILURE_TONE_ON) {
- toneType = ToneGenerator.TONE_CDMA_ALERT_CALL_GUARD;
- toneVolume = TONE_RELATIVE_VOLUME_HIPRI;
- toneLengthMillis = 750;
- } else {
- toneType = ToneGenerator.TONE_PROP_PROMPT;
- toneVolume = TONE_RELATIVE_VOLUME_HIPRI;
- toneLengthMillis = 200;
- }
- break;
case TONE_VOICE_PRIVACY:
toneType = ToneGenerator.TONE_CDMA_ALERT_NETWORK_LITE;
toneVolume = TONE_RELATIVE_VOLUME_HIPRI;
diff --git a/src/com/android/phone/CdmaOptions.java b/src/com/android/phone/CdmaOptions.java
index eabbdd2..a02d3df 100644
--- a/src/com/android/phone/CdmaOptions.java
+++ b/src/com/android/phone/CdmaOptions.java
@@ -31,7 +31,6 @@
import android.text.TextUtils;
import com.android.internal.telephony.Phone;
-import com.android.internal.telephony.PhoneConstants;
import com.android.internal.telephony.TelephonyProperties;
/**
@@ -46,7 +45,6 @@
private static final String BUTTON_CDMA_SYSTEM_SELECT_KEY = "cdma_system_select_key";
private static final String BUTTON_CDMA_SUBSCRIPTION_KEY = "cdma_subscription_key";
- private static final String BUTTON_CDMA_ACTIVATE_DEVICE_KEY = "cdma_activate_device_key";
private static final String BUTTON_CARRIER_SETTINGS_KEY = "carrier_settings_key";
private static final String BUTTON_APN_EXPAND_KEY = "button_apn_key_cdma";
@@ -108,16 +106,6 @@
.findPreference(BUTTON_CDMA_SUBSCRIPTION_KEY));
}
- final boolean voiceCapable = mPrefActivity.getResources().getBoolean(
- com.android.internal.R.bool.config_voice_capable);
- final boolean isLTE = mPhone.getLteOnCdmaMode() == PhoneConstants.LTE_ON_CDMA_TRUE;
- if (voiceCapable || isLTE) {
- // This option should not be available on voice-capable devices (i.e. regular phones)
- // and is replaced by the LTE data service item on LTE devices
- mPrefScreen.removePreference(
- mPrefScreen.findPreference(BUTTON_CDMA_ACTIVATE_DEVICE_KEY));
- }
-
// Read platform settings for carrier settings
final boolean isCarrierSettingsEnabled = carrierConfig.getBoolean(
CarrierConfigManager.KEY_CARRIER_SETTINGS_ENABLE_BOOL);
diff --git a/src/com/android/phone/HfaActivity.java b/src/com/android/phone/HfaActivity.java
deleted file mode 100644
index b526d46..0000000
--- a/src/com/android/phone/HfaActivity.java
+++ /dev/null
@@ -1,143 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.phone;
-
-import android.app.Activity;
-import android.app.AlertDialog;
-import android.app.PendingIntent;
-import android.content.DialogInterface;
-import android.os.Bundle;
-import android.util.Log;
-
-/**
- * Starts and displays status for Hands Free Activation (HFA).
- *
- * This class operates with Hands Free Activation apps. It comes up during activation
- * requests that occur outside of setup wizard and so provides its own UI.
- * It uses {@link HfaLogic} to perform the actual activation and during the process
- * displays a "performing activation..." dialog. This will remain up until the user
- * chooses to skip the activation (still happens in the background) or the activation
- * is successful. Upon failure, the dialog also goes away but a subsequent dialog will
- * ask the user if they would like to try again or cancel.
- */
-public class HfaActivity extends Activity {
- private static final String TAG = HfaActivity.class.getSimpleName();
-
- private AlertDialog mDialog;
- private HfaLogic mHfaLogic;
-
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- Log.i(TAG, "onCreate");
-
- final PendingIntent otaResponseIntent = getIntent().getParcelableExtra(
- OtaUtils.EXTRA_OTASP_RESULT_CODE_PENDING_INTENT);
-
- mHfaLogic = new HfaLogic(this.getApplicationContext(), new HfaLogic.HfaLogicCallback() {
- @Override
- public void onSuccess() {
- onHfaSuccess();
- }
-
- @Override
- public void onError(String error) {
- onHfaError(error);
- }
- }, otaResponseIntent);
-
- startProvisioning();
- }
-
- @Override
- protected void onDestroy() {
- super.onDestroy();
-
- Log.i(TAG, "onDestroy");
-
- if (mDialog != null && mDialog.isShowing()) {
- mDialog.dismiss();
- mDialog = null;
- }
- }
-
- private void startProvisioning() {
- buildAndShowDialog();
- mHfaLogic.start();
- }
-
- private void buildAndShowDialog() {
- mDialog = new AlertDialog.Builder(this, AlertDialog.THEME_DEVICE_DEFAULT_LIGHT)
- .setTitle(R.string.ota_hfa_activation_title)
- .setMessage(R.string.ota_hfa_activation_dialog_message)
- .setPositiveButton(R.string.ota_skip_activation_dialog_skip_label,
- new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface di, int which) {
- onUserSkip();
- }})
- /*.setOnCancelListener(new DialogInterface.OnCancelListener() {
- @Override
- public void onCancel(DialogInterface di) {
- sendFinalResponse(OTASP_USER_SKIPPED);
- }})*/
- .create();
-
- // Do not allow user to dismiss dialog unless they are clicking "skip"
- mDialog.setCanceledOnTouchOutside(false);
- mDialog.setCancelable(false);
-
- Log.i(TAG, "showing dialog");
- mDialog.show();
- }
-
- private void onHfaError(String errorMsg) {
- mDialog.dismiss();
-
- AlertDialog errorDialog = new AlertDialog.Builder(this,
- AlertDialog.THEME_DEVICE_DEFAULT_LIGHT)
- .setMessage(errorMsg)
- .setPositiveButton(R.string.ota_skip_activation_dialog_skip_label,
- new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface di, int which) {
- di.dismiss();
- onUserSkip();
- }
- })
- .setNegativeButton(R.string.ota_try_again,
- new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface di, int which) {
- di.dismiss();
- startProvisioning();
- }
- })
- .create();
-
- errorDialog.show();
- }
-
- private void onHfaSuccess() {
- finish();
- }
-
- private void onUserSkip() {
- finish();
- }
-
-}
diff --git a/src/com/android/phone/HfaLogic.java b/src/com/android/phone/HfaLogic.java
deleted file mode 100644
index b064b18..0000000
--- a/src/com/android/phone/HfaLogic.java
+++ /dev/null
@@ -1,225 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.phone;
-
-import android.app.PendingIntent;
-import android.app.PendingIntent.CanceledException;
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.os.AsyncResult;
-import android.os.Handler;
-import android.os.Message;
-import android.telephony.ServiceState;
-import android.util.Log;
-
-import com.android.internal.telephony.Phone;
-import com.google.common.base.Preconditions;
-
-/**
- * Starts and displays status for Hands Free Activation (HFA).
- *
- * This class operates with Hands Free Activation apps.
- * It starts by broadcasting the intent com.android.action.START_HFA.
- * An HFA app will pick that up and start the HFA process.
- * If it fails it return ERROR_HFA Intent and upon success returns COMPLETE_HFA.
- *
- * If successful, we bounce the radio so that the service picks up the new number.
- * Once the radio is back on we callback the requestor.
- *
- * If there is an error, we do not bounce the radio but still callback with a failure.
- *
- * TODO(klp): We need system-only permissions for the HFA intents.
- */
-public class HfaLogic {
- private static final String TAG = HfaLogic.class.getSimpleName();
-
- private static final String ACTION_START = "com.android.action.START_HFA";
- private static final String ACTION_ERROR = "com.android.action.ERROR_HFA";
- private static final String ACTION_CANCEL = "com.android.action.CANCEL_HFA";
- private static final String ACTION_COMPLETE = "com.android.action.COMPLETE_HFA";
-
- private static final int SERVICE_STATE_CHANGED = 1;
-
- public static final int NOT_WAITING = 0;
- public static final int WAITING_FOR_RADIO_OFF = 1;
- public static final int WAITING_FOR_RADIO_ON = 2;
-
- public static final int OTASP_UNKNOWN = 0;
- public static final int OTASP_USER_SKIPPED = 1;
- public static final int OTASP_SUCCESS = 2;
- public static final int OTASP_FAILURE = 3;
-
- private int mPhoneMonitorState = NOT_WAITING;
- private BroadcastReceiver mReceiver;
- private HfaLogicCallback mCallback;
- private PendingIntent mResponseIntent;
- private Context mContext;
-
- // No retry at the moment. Increase later if necessary.
- private static final int DEFAULT_RETRY_COUNT = 0;
- private int mRetryCount;
-
- public interface HfaLogicCallback {
- public void onSuccess();
- public void onError(String errorMsg);
- }
-
- public HfaLogic(Context context, HfaLogicCallback callback, PendingIntent intent) {
- mCallback = Preconditions.checkNotNull(callback);
- mContext = Preconditions.checkNotNull(context);
- mResponseIntent = intent;
- }
-
- public void start() {
- Log.i(TAG, "start:");
- mRetryCount = DEFAULT_RETRY_COUNT;
- startHfaIntentReceiver();
- startProvisioning();
- }
-
- private void startProvisioning() {
- Log.i(TAG, "startProvisioning:");
- sendHfaCommand(ACTION_START);
- }
-
- private void sendHfaCommand(String action) {
- Log.i(TAG, "sendHfaCommand: command=" + action);
- mContext.sendBroadcast(new Intent(action));
- }
-
- private void onHfaError(String errorMsg) {
- Log.i(TAG, "onHfaError: call mCallBack.onError errorMsg=" + errorMsg
- + " mRetryCount=" + mRetryCount);
- mRetryCount -= 1;
- if (mRetryCount >= 0) {
- Log.i(TAG, "onHfaError: retry");
- startProvisioning();
- } else {
- Log.i(TAG, "onHfaError: Declare OTASP_FAILURE");
- mRetryCount = 0;
- stopHfaIntentReceiver();
- sendFinalResponse(OTASP_FAILURE, errorMsg);
- mCallback.onError(errorMsg);
- }
- }
-
- private void onHfaSuccess() {
- Log.i(TAG, "onHfaSuccess: NOT bouncing radio call onTotalSuccess");
- stopHfaIntentReceiver();
- // bounceRadio();
- onTotalSuccess();
- }
-
- private void onTotalSuccess() {
- Log.i(TAG, "onTotalSuccess: call mCallBack.onSuccess");
- sendFinalResponse(OTASP_SUCCESS, null);
- mCallback.onSuccess();
- }
-
- private void bounceRadio() {
- final Phone phone = PhoneGlobals.getInstance().getPhone();
- phone.registerForServiceStateChanged(mHandler, SERVICE_STATE_CHANGED, null);
-
- mPhoneMonitorState = WAITING_FOR_RADIO_OFF;
- phone.setRadioPower(false);
- onServiceStateChange(phone.getServiceState());
- }
-
- private void onServiceStateChange(ServiceState state) {
- final boolean radioIsOff = state.getVoiceRegState() == ServiceState.STATE_POWER_OFF;
- final Phone phone = PhoneGlobals.getInstance().getPhone();
-
- Log.i(TAG, "Radio is on: " + !radioIsOff);
-
- if (mPhoneMonitorState == WAITING_FOR_RADIO_OFF) {
- if (radioIsOff) {
- mPhoneMonitorState = WAITING_FOR_RADIO_ON;
- phone.setRadioPower(true);
- }
- } else if (mPhoneMonitorState == WAITING_FOR_RADIO_ON) {
- if (!radioIsOff) {
- mPhoneMonitorState = NOT_WAITING;
- phone.unregisterForServiceStateChanged(mHandler);
-
- onTotalSuccess();
- }
- }
- }
-
- private void startHfaIntentReceiver() {
- final IntentFilter filter = new IntentFilter(ACTION_COMPLETE);
- filter.addAction(ACTION_ERROR);
-
- mReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive(Context context, Intent intent) {
- final String action = intent.getAction();
- if (action.equals(ACTION_ERROR)) {
- onHfaError(intent.getStringExtra("errorCode"));
- } else if (action.equals(ACTION_COMPLETE)) {
- Log.i(TAG, "Hfa Successful");
- onHfaSuccess();
- }
- }
- };
-
- mContext.registerReceiver(mReceiver, filter);
- }
-
- private void stopHfaIntentReceiver() {
- if (mReceiver != null) {
- mContext.unregisterReceiver(mReceiver);
- mReceiver = null;
- }
- }
-
- private void sendFinalResponse(int responseCode, String errorCode) {
- if (mResponseIntent != null) {
- final Intent extraStuff = new Intent();
- extraStuff.putExtra(OtaUtils.EXTRA_OTASP_RESULT_CODE, responseCode);
-
- if (responseCode == OTASP_FAILURE && errorCode != null) {
- extraStuff.putExtra(OtaUtils.EXTRA_OTASP_ERROR_CODE, errorCode);
- }
-
- try {
- Log.i(TAG, "Sending OTASP confirmation with result code: "
- + responseCode);
- mResponseIntent.send(mContext, 0 /* resultCode (not used) */, extraStuff);
- } catch (CanceledException e) {
- Log.e(TAG, "Pending Intent canceled");
- }
- }
- }
-
- private Handler mHandler = new Handler() {
- @Override
- public void handleMessage(Message msg) {
- switch (msg.what) {
- case SERVICE_STATE_CHANGED:
- ServiceState state = (ServiceState) ((AsyncResult) msg.obj).result;
- onServiceStateChange(state);
- break;
- default:
- break;
- }
- }
- };
-
-}
diff --git a/src/com/android/phone/HfaService.java b/src/com/android/phone/HfaService.java
deleted file mode 100644
index bc07453..0000000
--- a/src/com/android/phone/HfaService.java
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.phone;
-
-import android.app.PendingIntent;
-import android.app.Service;
-import android.content.Intent;
-import android.os.IBinder;
-import android.util.Log;
-
-/**
- * Service for performing HfaActivation without any UI.
- */
-public class HfaService extends Service {
- private static final String TAG = HfaService.class.getSimpleName();
-
- private HfaLogic mHfaLogic;
-
- @Override
- public void onCreate() {
- Log.i(TAG, "service started");
- }
-
- @Override
- public int onStartCommand(Intent intent, int flags, int startId) {
- final PendingIntent otaResponseIntent = intent.getParcelableExtra(
- OtaUtils.EXTRA_OTASP_RESULT_CODE_PENDING_INTENT);
-
- mHfaLogic = new HfaLogic(this, new HfaLogic.HfaLogicCallback() {
- @Override
- public void onSuccess() {
- Log.i(TAG, "onSuccess");
- onComplete();
- }
-
- @Override
- public void onError(String msg) {
- Log.i(TAG, "onError: " + msg);
- // We do not respond from this service. On success or failure
- // we do the same thing...finish.
- onComplete();
- }
- }, otaResponseIntent);
- mHfaLogic.start();
-
- return START_REDELIVER_INTENT;
- }
-
- @Override
- public IBinder onBind(Intent intent) {
- return null;
- }
-
- private void onComplete() {
- stopSelf();
- }
-}
diff --git a/src/com/android/phone/InCallScreenShowActivation.java b/src/com/android/phone/InCallScreenShowActivation.java
deleted file mode 100644
index 9d35442..0000000
--- a/src/com/android/phone/InCallScreenShowActivation.java
+++ /dev/null
@@ -1,243 +0,0 @@
-/*
- * Copyright (C) 2009 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.phone;
-
-import android.app.Activity;
-import android.app.PendingIntent;
-import android.content.Context;
-import android.content.Intent;
-import android.content.pm.PackageManager;
-import android.content.pm.ResolveInfo;
-import android.os.Bundle;
-import android.os.PersistableBundle;
-import android.os.SystemProperties;
-import android.provider.Settings;
-import android.telephony.CarrierConfigManager;
-import android.util.Log;
-
-import com.android.internal.telephony.Phone;
-import com.android.internal.telephony.TelephonyCapabilities;
-
-/**
- * Invisible activity that handles the com.android.phone.PERFORM_CDMA_PROVISIONING intent.
- * This activity is protected by the android.permission.PERFORM_CDMA_PROVISIONING permission.
- *
- * We handle the PERFORM_CDMA_PROVISIONING action by launching an OTASP
- * call via one of the OtaUtils helper methods: startInteractiveOtasp() on
- * regular phones, or startNonInteractiveOtasp() on data-only devices.
- *
- * TODO: The class name InCallScreenShowActivation is misleading, since
- * this activity is totally unrelated to the InCallScreen (which
- * implements the in-call UI.) Let's eventually rename this to something
- * like CdmaProvisioningLauncher or CdmaProvisioningHandler...
- */
-public class InCallScreenShowActivation extends Activity {
- private static final String LOG_TAG = "InCallScreenShowActivation";
- private static final boolean DBG =
- (PhoneGlobals.DBG_LEVEL >= 1) && (SystemProperties.getInt("ro.debuggable", 0) == 1);
-
- @Override
- protected void onCreate(Bundle icicle) {
- super.onCreate(icicle);
-
- Intent intent = getIntent();
- if (DBG) Log.d(LOG_TAG, "onCreate: intent = " + intent);
- Bundle extras = intent.getExtras();
- if (DBG && (extras != null)) {
- Log.d(LOG_TAG, " - has extras: size = " + extras.size()); // forces an unparcel()
- Log.d(LOG_TAG, " - extras = " + extras);
- }
-
- PhoneGlobals app = PhoneGlobals.getInstanceIfPrimary();
- if (app == null) {
- // TODO: All CDMA provisioning code should move into a BroadcastReceiver that runs
- // exclusively in the primary user's context. This is because the majority of the
- // telephony logic -- and all of the important bits -- runs only as primary so we don't
- // have access to the things we need. We still need to maintain an Activity to support
- // legacy code which starts this using startActivity() but that Activity should be a
- // simple intent-trampoline for the new BroadcastReceiver.
- //
- // Though this conditional protects this code from NPEs on a secondary user due to an
- // uninitialized PhoneGlobals, there's not a good reason at the time of this writing as
- // to why a secondary user context shouldn't trigger a CDMA provisioning, or at least
- // nobody has expressed concern.
- Log.i(LOG_TAG, "Being asked to provision CDMA SIM from secondary user, skipping.");
- setResult(RESULT_CANCELED);
- finish();
- return;
- }
-
- Phone phone = app.getPhone();
- if (!TelephonyCapabilities.supportsOtasp(phone)) {
- Log.w(LOG_TAG, "CDMA Provisioning not supported on this device");
- setResult(RESULT_CANCELED);
- finish();
- return;
- }
-
- if (intent.getAction().equals(OtaUtils.ACTION_PERFORM_CDMA_PROVISIONING)) {
-
- PersistableBundle carrierConfig = app.getCarrierConfig();
- boolean usesHfa = carrierConfig.getBoolean(
- CarrierConfigManager.KEY_USE_HFA_FOR_PROVISIONING_BOOL);
- if (usesHfa) {
- Log.i(LOG_TAG, "Starting Hfa from ACTION_PERFORM_CDMA_PROVISIONING");
- startHfa();
- finish();
- return;
- }
-
- boolean usesOtasp = carrierConfig.getBoolean(
- CarrierConfigManager.KEY_USE_OTASP_FOR_PROVISIONING_BOOL);
- if (usesOtasp) {
- // On voice-capable devices, we perform CDMA provisioning in
- // "interactive" mode by directly launching the InCallScreen.
- // boolean interactiveMode = PhoneGlobals.sVoiceCapable;
- // TODO: Renable interactive mode for device provisioning.
- boolean interactiveMode = false;
- Log.i(LOG_TAG, "ACTION_PERFORM_CDMA_PROVISIONING (interactiveMode = "
- + interactiveMode + ")...");
-
- // Testing: this intent extra allows test apps manually
- // enable/disable "interactive mode", regardless of whether
- // the current device is voice-capable. This is allowed only
- // in userdebug or eng builds.
- if (intent.hasExtra(OtaUtils.EXTRA_OVERRIDE_INTERACTIVE_MODE)
- && (SystemProperties.getInt("ro.debuggable", 0) == 1)) {
- interactiveMode =
- intent.getBooleanExtra(OtaUtils.EXTRA_OVERRIDE_INTERACTIVE_MODE, false);
- Log.d(LOG_TAG, "==> MANUALLY OVERRIDING interactiveMode to " + interactiveMode);
- }
-
- // We allow the caller to pass a PendingIntent (as the
- // EXTRA_NONINTERACTIVE_OTASP_RESULT_PENDING_INTENT extra)
- // which we'll later use to notify them when the OTASP call
- // fails or succeeds.
- //
- // Stash that away here, and we'll fire it off later in
- // OtaUtils.sendOtaspResult().
- app.cdmaOtaScreenState.otaspResultCodePendingIntent =
- (PendingIntent) intent.getParcelableExtra(
- OtaUtils.EXTRA_OTASP_RESULT_CODE_PENDING_INTENT);
-
- if (interactiveMode) {
- // On voice-capable devices, launch an OTASP call and arrange
- // for the in-call UI to come up. (The InCallScreen will
- // notice that an OTASP call is active, and display the
- // special OTASP UI instead of the usual in-call controls.)
-
- if (DBG) Log.d(LOG_TAG, "==> Starting interactive CDMA provisioning...");
- OtaUtils.startInteractiveOtasp(this);
-
- // The result we set here is actually irrelevant, since the
- // InCallScreen's "interactive" OTASP sequence never actually
- // finish()es; it ends by directly launching the Home
- // activity. So our caller won't actually ever get an
- // onActivityResult() call in this case.
- setResult(OtaUtils.RESULT_INTERACTIVE_OTASP_STARTED);
- } else {
- // On data-only devices, manually launch the OTASP call
- // *without* displaying any UI. (Our caller, presumably
- // SetupWizardActivity, is responsible for displaying some
- // sort of progress UI.)
-
- if (DBG) Log.d(LOG_TAG, "==> Starting non-interactive CDMA provisioning...");
- int callStatus = OtaUtils.startNonInteractiveOtasp(this);
-
- if (callStatus == PhoneUtils.CALL_STATUS_DIALED) {
- if (DBG) Log.d(LOG_TAG,
- " ==> successful result from startNonInteractiveOtasp(): " +
- callStatus);
- setResult(OtaUtils.RESULT_NONINTERACTIVE_OTASP_STARTED);
- } else {
- Log.w(LOG_TAG, "Failure code from startNonInteractiveOtasp(): " +
- callStatus);
- setResult(OtaUtils.RESULT_NONINTERACTIVE_OTASP_FAILED);
- }
- }
- } else {
- Log.i(LOG_TAG, "Skipping activation.");
- }
- } else {
- Log.e(LOG_TAG, "Unexpected intent action: " + intent);
- setResult(RESULT_CANCELED);
- }
-
- finish();
- }
-
- /**
- * On devices that provide a phone initialization wizard (such as Google Setup Wizard),
- * the wizard displays it's own activation UI. The Hfa activation started by this class
- * will show a UI or not depending on the status of the setup wizard. If the setup wizard
- * is running, do not show a UI, otherwise show our own UI since setup wizard will not.
- *
- * The method checks two properties:
- * 1. Does the device require a setup wizard (ro.setupwizard.mode == (REQUIRED|OPTIONAL))
- * 2. Is device_provisioned set to non-zero--a property that setup wizard sets at completion.
- * @return true if wizard is running, false otherwise.
- */
- private boolean isWizardRunning(Context context) {
- Intent intent = new Intent("android.intent.action.DEVICE_INITIALIZATION_WIZARD");
- ResolveInfo resolveInfo = context.getPackageManager().resolveActivity(intent,
- PackageManager.MATCH_DEFAULT_ONLY);
- boolean provisioned = Settings.Global.getInt(context.getContentResolver(),
- Settings.Global.DEVICE_PROVISIONED, 0) != 0;
- String mode = SystemProperties.get("ro.setupwizard.mode", "REQUIRED");
- boolean runningSetupWizard = "REQUIRED".equals(mode) || "OPTIONAL".equals(mode);
- if (DBG) {
- Log.v(LOG_TAG, "resolvInfo = " + resolveInfo + ", provisioned = " + provisioned
- + ", runningSetupWizard = " + runningSetupWizard);
- }
- return resolveInfo != null && !provisioned && runningSetupWizard;
- }
-
- /**
- * Starts the HFA provisioning process by bringing up the HFA Activity.
- */
- private void startHfa() {
- boolean isWizardRunning = isWizardRunning(this);
- // We always run our HFA logic if we're in setup wizard, but if we're outside of setup
- // wizard then we have to check a config to see if we should still run HFA.
- if (isWizardRunning ||
- getResources().getBoolean(R.bool.config_allow_hfa_outside_of_setup_wizard)) {
-
- final Intent intent = new Intent();
-
- final PendingIntent otaResponseIntent = getIntent().getParcelableExtra(
- OtaUtils.EXTRA_OTASP_RESULT_CODE_PENDING_INTENT);
-
- final boolean showUi = !isWizardRunning;
- intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
-
- if (otaResponseIntent != null) {
- intent.putExtra(OtaUtils.EXTRA_OTASP_RESULT_CODE_PENDING_INTENT, otaResponseIntent);
- }
-
- Log.v(LOG_TAG, "Starting hfa activation activity");
- if (showUi) {
- intent.setClassName(this, HfaActivity.class.getName());
- startActivity(intent);
- } else {
- intent.setClassName(this, HfaService.class.getName());
- startService(intent);
- }
-
- }
- setResult(RESULT_OK);
- }
-}
diff --git a/src/com/android/phone/OtaStartupReceiver.java b/src/com/android/phone/OtaStartupReceiver.java
deleted file mode 100644
index 09cb185..0000000
--- a/src/com/android/phone/OtaStartupReceiver.java
+++ /dev/null
@@ -1,183 +0,0 @@
-/*
- * Copyright (C) 2009 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.phone;
-
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.pm.PackageManager;
-import android.content.pm.ResolveInfo;
-import android.os.AsyncResult;
-import android.os.Handler;
-import android.os.Message;
-import android.os.SystemProperties;
-import android.provider.Settings;
-import android.telephony.PhoneStateListener;
-import android.telephony.ServiceState;
-import android.telephony.TelephonyManager;
-
-import com.android.internal.telephony.Phone;
-import com.android.internal.telephony.ServiceStateTracker;
-import com.android.internal.telephony.TelephonyCapabilities;
-
-import android.util.Log;
-
-/*
- * Handles OTA Start procedure at phone power up. At phone power up, if phone is not OTA
- * provisioned (check MIN value of the Phone) and 'device_provisioned' is not set,
- * OTA Activation screen is shown that helps user activate the phone
- */
-public class OtaStartupReceiver extends BroadcastReceiver {
- private static final String TAG = "OtaStartupReceiver";
- private static final boolean DBG = false;
- private static final int MIN_READY = 10;
- private static final int SERVICE_STATE_CHANGED = 11;
- private Context mContext;
-
- private int mOtaspMode = -1;
- private boolean mPhoneStateListenerRegistered = false;
- private PhoneStateListener mPhoneStateListener = new PhoneStateListener() {
- @Override
- public void onOtaspChanged(int otaspMode) {
- if (mOtaspMode == otaspMode) {
- return;
- }
- mOtaspMode = otaspMode;
- Log.v(TAG, "onOtaspChanged: mOtaspMode=" + mOtaspMode);
-
- if (otaspMode == ServiceStateTracker.OTASP_NEEDED) {
- Log.i(TAG, "OTASP is needed - performing CDMA provisioning");
- final Intent intent = new Intent(OtaUtils.ACTION_PERFORM_CDMA_PROVISIONING);
- intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- mContext.startActivity(intent);
- }
- }
- };
-
-
- private Handler mHandler = new Handler() {
- @Override
- public void handleMessage(Message msg) {
- switch (msg.what) {
- case MIN_READY:
- Log.v(TAG, "Attempting OtaActivation from handler, mOtaspMode=" + mOtaspMode);
- OtaUtils.maybeDoOtaCall(mContext, mHandler, MIN_READY);
- break;
- case SERVICE_STATE_CHANGED: {
- ServiceState state = (ServiceState) ((AsyncResult) msg.obj).result;
- if (DBG) Log.d(TAG, "onServiceStateChanged()... new state = " + state);
-
- // Possible service states:
- // - STATE_IN_SERVICE // Normal operation
- // - STATE_OUT_OF_SERVICE // Still searching for an operator to register to,
- // // or no radio signal
- // - STATE_EMERGENCY_ONLY // Phone is locked; only emergency numbers are allowed
- // - STATE_POWER_OFF // Radio is explicitly powered off (airplane mode)
-
- // Once we reach STATE_IN_SERVICE
- // it's finally OK to start OTA provisioning
- if (state.getState() == ServiceState.STATE_IN_SERVICE) {
- if (DBG) Log.d(TAG, "call OtaUtils.maybeDoOtaCall after network is available");
- Phone phone = PhoneGlobals.getPhone();
- phone.unregisterForServiceStateChanged(this);
- OtaUtils.maybeDoOtaCall(mContext, mHandler, MIN_READY);
- }
- break;
- }
- }
-
- }
- };
-
- @Override
- public void onReceive(Context context, Intent intent) {
- mContext = context;
- if (DBG) {
- Log.v(TAG, "onReceive: intent action=" + intent.getAction() +
- " mOtaspMode=" + mOtaspMode);
- }
-
- PhoneGlobals globals = PhoneGlobals.getInstanceIfPrimary();
- if (globals == null) {
- if (DBG) Log.d(TAG, "Not primary user, nothing to do.");
- return;
- }
-
- if (mPhoneStateListenerRegistered == false) {
- if (DBG) Log.d(TAG, "Register our PhoneStateListener");
- TelephonyManager telephonyManager = (TelephonyManager)context.getSystemService(
- Context.TELEPHONY_SERVICE);
- telephonyManager.listen(mPhoneStateListener, PhoneStateListener.LISTEN_OTASP_CHANGED);
- mPhoneStateListenerRegistered = true;
- } else {
- if (DBG) Log.d(TAG, "PhoneStateListener already registered");
- }
-
- if (!TelephonyCapabilities.supportsOtasp(PhoneGlobals.getPhone())) {
- if (DBG) Log.d(TAG, "OTASP not supported, nothing to do.");
- return;
- }
-
- if (shouldPostpone(context)) {
- if (DBG) Log.d(TAG, "Postponing OTASP until wizard runs");
- return;
- }
-
- // Delay OTA provisioning if network is not available yet
- PhoneGlobals app = PhoneGlobals.getInstance();
- Phone phone = PhoneGlobals.getPhone();
- if (app.mCM.getServiceState() != ServiceState.STATE_IN_SERVICE) {
- if (DBG) Log.w(TAG, "Network is not ready. Registering to receive notification.");
- phone.registerForServiceStateChanged(mHandler, SERVICE_STATE_CHANGED, null);
- return;
- }
-
- // The following depends on the phone process being persistent. Normally we can't
- // expect a BroadcastReceiver to persist after returning from this function but it does
- // because the phone activity is persistent.
- if (DBG) Log.d(TAG, "call OtaUtils.maybeDoOtaCall");
- OtaUtils.maybeDoOtaCall(mContext, mHandler, MIN_READY);
- }
-
- /**
- * On devices that provide a phone initialization wizard (such as Google Setup Wizard), we
- * allow delaying CDMA OTA setup so it can be done in a single wizard. The wizard is responsible
- * for (1) disabling itself once it has been run and/or (2) setting the 'device_provisioned'
- * flag to something non-zero and (3) calling the OTA Setup with the action below.
- *
- * NB: Typical phone initialization wizards will install themselves as the homescreen
- * (category "android.intent.category.HOME") with a priority higher than the default.
- * The wizard should set 'device_provisioned' when it completes, disable itself with the
- * PackageManager.setComponentEnabledSetting() and then start home screen.
- *
- * @return true if setup will be handled by wizard, false if it should be done now.
- */
- private boolean shouldPostpone(Context context) {
- Intent intent = new Intent("android.intent.action.DEVICE_INITIALIZATION_WIZARD");
- ResolveInfo resolveInfo = context.getPackageManager().resolveActivity(intent,
- PackageManager.MATCH_DEFAULT_ONLY);
- boolean provisioned = Settings.Global.getInt(context.getContentResolver(),
- Settings.Global.DEVICE_PROVISIONED, 0) != 0;
- String mode = SystemProperties.get("ro.setupwizard.mode", "REQUIRED");
- boolean runningSetupWizard = "REQUIRED".equals(mode) || "OPTIONAL".equals(mode);
- if (DBG) {
- Log.v(TAG, "resolvInfo = " + resolveInfo + ", provisioned = " + provisioned
- + ", runningSetupWizard = " + runningSetupWizard);
- }
- return resolveInfo != null && !provisioned && runningSetupWizard;
- }
-}
diff --git a/src/com/android/phone/OtaUtils.java b/src/com/android/phone/OtaUtils.java
deleted file mode 100644
index a37ce80..0000000
--- a/src/com/android/phone/OtaUtils.java
+++ /dev/null
@@ -1,1581 +0,0 @@
-/*
- * Copyright (C) 2009 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.phone;
-
-import com.android.internal.telephony.Phone;
-import com.android.internal.telephony.PhoneConstants;
-import com.android.internal.telephony.TelephonyCapabilities;
-import com.android.internal.telephony.TelephonyProperties;
-import com.android.phone.OtaUtils.CdmaOtaInCallScreenUiState.State;
-
-import android.app.Activity;
-import android.app.ActivityManager;
-import android.app.AlertDialog;
-import android.app.PendingIntent;
-import android.app.PendingIntent.CanceledException;
-import android.content.ActivityNotFoundException;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.content.Intent;
-import android.net.Uri;
-import android.os.AsyncResult;
-import android.os.Handler;
-import android.os.SystemClock;
-import android.os.SystemProperties;
-import android.os.UserHandle;
-import android.telecom.PhoneAccount;
-import android.telephony.TelephonyManager;
-import android.util.Log;
-import android.view.KeyEvent;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.WindowManager;
-import android.widget.Button;
-import android.widget.ProgressBar;
-import android.widget.TextView;
-import android.widget.ToggleButton;
-
-/**
- * Handles all OTASP Call related logic and UI functionality.
- * The InCallScreen interacts with this class to perform an OTASP Call.
- *
- * OTASP is a CDMA-specific feature:
- * OTA or OTASP == Over The Air service provisioning
- * SPC == Service Programming Code
- * TODO: Include pointer to more detailed documentation.
- *
- * TODO: This is Over The Air Service Provisioning (OTASP)
- * A better name would be OtaspUtils.java.
- */
-public class OtaUtils {
- private static final String LOG_TAG = "OtaUtils";
- private static final boolean DBG = false;
-
- public static final int OTA_SHOW_ACTIVATION_SCREEN_OFF = 0;
- public static final int OTA_SHOW_ACTIVATION_SCREEN_ON = 1;
- public static final int OTA_SHOW_LISTENING_SCREEN_OFF =0;
- public static final int OTA_SHOW_LISTENING_SCREEN_ON =1;
- public static final int OTA_SHOW_ACTIVATE_FAIL_COUNT_OFF = 0;
- public static final int OTA_SHOW_ACTIVATE_FAIL_COUNT_THREE = 3;
- public static final int OTA_PLAY_SUCCESS_FAILURE_TONE_OFF = 0;
- public static final int OTA_PLAY_SUCCESS_FAILURE_TONE_ON = 1;
-
- // SPC Timeout is 60 seconds
- public final int OTA_SPC_TIMEOUT = 60;
- public final int OTA_FAILURE_DIALOG_TIMEOUT = 2;
-
- // Constants for OTASP-related Intents and intent extras.
- // Watch out: these must agree with the corresponding constants in
- // apps/SetupWizard!
-
- // Intent action to launch an OTASP call.
- public static final String ACTION_PERFORM_CDMA_PROVISIONING =
- "com.android.phone.PERFORM_CDMA_PROVISIONING";
-
- // Intent action to launch activation on a non-voice capable device
- public static final String ACTION_PERFORM_VOICELESS_CDMA_PROVISIONING =
- "com.android.phone.PERFORM_VOICELESS_CDMA_PROVISIONING";
-
- // Intent action to display the InCallScreen in the OTASP "activation" state.
- public static final String ACTION_DISPLAY_ACTIVATION_SCREEN =
- "com.android.phone.DISPLAY_ACTIVATION_SCREEN";
-
- // boolean voiceless provisioning extra that enables a "don't show this again" checkbox
- // the user can check to never see the activity upon bootup again
- public static final String EXTRA_VOICELESS_PROVISIONING_OFFER_DONTSHOW =
- "com.android.phone.VOICELESS_PROVISIONING_OFFER_DONTSHOW";
-
- // Activity result codes for the ACTION_PERFORM_CDMA_PROVISIONING intent
- // (see the InCallScreenShowActivation activity.)
- //
- // Note: currently, our caller won't ever actually receive the
- // RESULT_INTERACTIVE_OTASP_STARTED result code; see comments in
- // InCallScreenShowActivation.onCreate() for details.
-
- public static final int RESULT_INTERACTIVE_OTASP_STARTED = Activity.RESULT_FIRST_USER;
- public static final int RESULT_NONINTERACTIVE_OTASP_STARTED = Activity.RESULT_FIRST_USER + 1;
- public static final int RESULT_NONINTERACTIVE_OTASP_FAILED = Activity.RESULT_FIRST_USER + 2;
-
- // Testing: Extra for the ACTION_PERFORM_CDMA_PROVISIONING intent that
- // allows the caller to manually enable/disable "interactive mode" for
- // the OTASP call. Only available in userdebug or eng builds.
- public static final String EXTRA_OVERRIDE_INTERACTIVE_MODE =
- "ota_override_interactive_mode";
-
- // Extra for the ACTION_PERFORM_CDMA_PROVISIONING intent, holding a
- // PendingIntent which the phone app can use to send a result code
- // back to the caller.
- public static final String EXTRA_OTASP_RESULT_CODE_PENDING_INTENT =
- "otasp_result_code_pending_intent";
-
- // Extra attached to the above PendingIntent that indicates
- // success or failure.
- public static final String EXTRA_OTASP_RESULT_CODE = "otasp_result_code";
-
- // Extra attached to the above PendingIntent that contains an error code.
- public static final String EXTRA_OTASP_ERROR_CODE = "otasp_error_code";
-
- public static final int OTASP_UNKNOWN = 0;
- public static final int OTASP_USER_SKIPPED = 1; // Only meaningful with interactive OTASP
- public static final int OTASP_SUCCESS = 2;
- public static final int OTASP_FAILURE = 3;
- // failed due to CDMA_OTA_PROVISION_STATUS_SPC_RETRIES_EXCEEDED
- public static final int OTASP_FAILURE_SPC_RETRIES = 4;
- // TODO: Distinguish between interactive and non-interactive success
- // and failure. Then, have the PendingIntent be sent after
- // interactive OTASP as well (so the caller can find out definitively
- // when interactive OTASP completes.)
-
- private static final String OTASP_NUMBER = "*228";
- private static final String OTASP_NUMBER_NON_INTERACTIVE = "*22899";
-
- private Context mContext;
- private PhoneGlobals mApplication;
- private OtaWidgetData mOtaWidgetData;
-
- private static boolean sIsWizardMode = true;
-
- // How many times do we retry maybeDoOtaCall() if the LTE state is not known yet,
- // and how long do we wait between retries
- private static final int OTA_CALL_LTE_RETRIES_MAX = 5;
- private static final int OTA_CALL_LTE_RETRY_PERIOD = 3000;
- private static int sOtaCallLteRetries = 0;
-
- // In "interactive mode", the OtaUtils object is tied to an
- // InCallScreen instance, where we display a bunch of UI specific to
- // the OTASP call. But on devices that are not "voice capable", the
- // OTASP call runs in a non-interactive mode, and we don't have
- // an InCallScreen or CallCard or any OTASP UI elements at all.
- private boolean mInteractive = true;
-
- /**
- * OtaWidgetData class represent all OTA UI elements
- *
- * TODO(OTASP): It's really ugly for the OtaUtils object to reach into the
- * InCallScreen like this and directly manipulate its widgets.
- *
- * Instead, the model/view separation should be more clear: OtaUtils
- * should only know about a higher-level abstraction of the
- * OTASP-specific UI state (just like how the CallController uses the
- * InCallUiState object), and the InCallScreen itself should translate
- * that higher-level abstraction into actual onscreen views and widgets.
- */
- private class OtaWidgetData {
- public Button otaEndButton;
- public Button otaActivateButton;
- public Button otaSkipButton;
- public Button otaNextButton;
- public ToggleButton otaSpeakerButton;
- public ViewGroup otaUpperWidgets;
- public View callCardOtaButtonsFailSuccess;
- public ProgressBar otaTextProgressBar;
- public TextView otaTextSuccessFail;
- public View callCardOtaButtonsActivate;
- public View callCardOtaButtonsListenProgress;
- public TextView otaTextActivate;
- public TextView otaTextListenProgress;
- public AlertDialog spcErrorDialog;
- public AlertDialog otaFailureDialog;
- public AlertDialog otaSkipConfirmationDialog;
- public TextView otaTitle;
- public Button otaTryAgainButton;
- }
-
- /**
- * OtaUtils constructor.
- *
- * @param context the Context of the calling Activity or Application
- * @param interactive if true, use the InCallScreen to display the progress
- * and result of the OTASP call. In practice this is
- * true IFF the current device is a voice-capable phone.
- *
- * Note if interactive is true, you must also call updateUiWidgets() as soon
- * as the InCallScreen instance is ready.
- */
- public OtaUtils(Context context, boolean interactive) {
- if (DBG) log("OtaUtils constructor...");
- mApplication = PhoneGlobals.getInstance();
- mContext = context;
- mInteractive = interactive;
- }
-
- /**
- * Starts the OTA provisioning call. If the MIN isn't available yet, it returns false and adds
- * an event to return the request to the calling app when it becomes available.
- *
- * @param context
- * @param handler
- * @param request
- * @return true if we were able to launch Ota activity or it's not required; false otherwise
- */
- public static boolean maybeDoOtaCall(Context context, Handler handler, int request) {
- PhoneGlobals app = PhoneGlobals.getInstance();
- Phone phone = PhoneGlobals.getPhone();
-
- if (ActivityManager.isRunningInTestHarness()) {
- Log.i(LOG_TAG, "Don't run provisioning when in test harness");
- return true;
- }
-
- if (!TelephonyCapabilities.supportsOtasp(phone)) {
- // Presumably not a CDMA phone.
- if (DBG) log("maybeDoOtaCall: OTASP not supported on this device");
- return true; // Nothing to do here.
- }
-
- if (!phone.isMinInfoReady()) {
- if (DBG) log("MIN is not ready. Registering to receive notification.");
- phone.registerForSubscriptionInfoReady(handler, request, null);
- return false;
- }
- phone.unregisterForSubscriptionInfoReady(handler);
-
- if (getLteOnCdmaMode(context) == PhoneConstants.LTE_ON_CDMA_UNKNOWN) {
- if (sOtaCallLteRetries < OTA_CALL_LTE_RETRIES_MAX) {
- if (DBG) log("maybeDoOtaCall: LTE state still unknown: retrying");
- handler.sendEmptyMessageDelayed(request, OTA_CALL_LTE_RETRY_PERIOD);
- sOtaCallLteRetries++;
- return false;
- } else {
- Log.w(LOG_TAG, "maybeDoOtaCall: LTE state still unknown: giving up");
- return true;
- }
- }
-
- boolean phoneNeedsActivation = phone.needsOtaServiceProvisioning();
- if (DBG) log("phoneNeedsActivation is set to " + phoneNeedsActivation);
-
- int otaShowActivationScreen = context.getResources().getInteger(
- R.integer.OtaShowActivationScreen);
- if (DBG) log("otaShowActivationScreen: " + otaShowActivationScreen);
-
- // Run the OTASP call in "interactive" mode only if
- // this is a non-LTE "voice capable" device.
- if (PhoneGlobals.sVoiceCapable && getLteOnCdmaMode(context) == PhoneConstants.LTE_ON_CDMA_FALSE) {
- if (phoneNeedsActivation
- && (otaShowActivationScreen == OTA_SHOW_ACTIVATION_SCREEN_ON)) {
- app.cdmaOtaProvisionData.isOtaCallIntentProcessed = false;
- sIsWizardMode = false;
-
- if (DBG) Log.d(LOG_TAG, "==> Starting interactive CDMA provisioning...");
- OtaUtils.startInteractiveOtasp(context);
-
- if (DBG) log("maybeDoOtaCall: voice capable; activation started.");
- } else {
- if (DBG) log("maybeDoOtaCall: voice capable; activation NOT started.");
- }
- } else {
- if (phoneNeedsActivation) {
- app.cdmaOtaProvisionData.isOtaCallIntentProcessed = false;
- Intent newIntent = new Intent(ACTION_PERFORM_VOICELESS_CDMA_PROVISIONING);
- newIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- newIntent.putExtra(EXTRA_VOICELESS_PROVISIONING_OFFER_DONTSHOW, true);
- try {
- context.startActivity(newIntent);
- } catch (ActivityNotFoundException e) {
- loge("No activity Handling PERFORM_VOICELESS_CDMA_PROVISIONING!");
- return false;
- }
- if (DBG) log("maybeDoOtaCall: non-interactive; activation intent sent.");
- } else {
- if (DBG) log("maybeDoOtaCall: non-interactive, no need for OTASP.");
- }
- }
- return true;
- }
-
- /**
- * Starts a normal "interactive" OTASP call (i.e. CDMA activation
- * for regular voice-capable phone devices.)
- *
- * This method is called from the InCallScreenShowActivation activity when
- * handling the ACTION_PERFORM_CDMA_PROVISIONING intent.
- */
- public static void startInteractiveOtasp(Context context) {
- if (DBG) log("startInteractiveOtasp()...");
- PhoneGlobals app = PhoneGlobals.getInstance();
-
- // There are two ways to start OTASP on voice-capable devices:
- //
- // (1) via the PERFORM_CDMA_PROVISIONING intent
- // - this is triggered by the "Activate device" button in settings,
- // or can be launched automatically upon boot if the device
- // thinks it needs to be provisioned.
- // - the intent is handled by InCallScreenShowActivation.onCreate(),
- // which calls this method
- // - we prepare for OTASP by initializing the OtaUtils object
- // - we bring up the InCallScreen in the ready-to-activate state
- // - when the user presses the "Activate" button we launch the
- // call by calling CallController.placeCall() via the
- // otaPerformActivation() method.
- //
- // (2) by manually making an outgoing call to a special OTASP number
- // like "*228" or "*22899".
- // - That sequence does NOT involve this method (OtaUtils.startInteractiveOtasp()).
- // Instead, the outgoing call request goes straight to CallController.placeCall().
- // - CallController.placeCall() notices that it's an OTASP
- // call, and initializes the OtaUtils object.
- // - The InCallScreen is launched (as the last step of
- // CallController.placeCall()). The InCallScreen notices that
- // OTASP is active and shows the correct UI.
-
- // Here, we start sequence (1):
- // Do NOT immediately start the call. Instead, bring up the InCallScreen
- // in the special "activate" state (see OtaUtils.otaShowActivateScreen()).
- // We won't actually make the call until the user presses the "Activate"
- // button.
-
- Intent activationScreenIntent = new Intent().setClass(context, InCallScreen.class)
- .setAction(ACTION_DISPLAY_ACTIVATION_SCREEN);
-
- // Watch out: in the scenario where OTASP gets triggered from the
- // BOOT_COMPLETED broadcast (see OtaStartupReceiver.java), we might be
- // running in the PhoneApp's context right now.
- // So the FLAG_ACTIVITY_NEW_TASK flag is required here.
- activationScreenIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
-
- // We're about to start the OTASP sequence, so create and initialize the
- // OtaUtils instance. (This needs to happen before bringing up the
- // InCallScreen.)
- OtaUtils.setupOtaspCall(activationScreenIntent);
-
- // And bring up the InCallScreen...
- Log.i(LOG_TAG, "startInteractiveOtasp: launching InCallScreen in 'activate' state: "
- + activationScreenIntent);
- context.startActivity(activationScreenIntent);
- }
-
- /**
- * Starts the OTASP call *without* involving the InCallScreen or
- * displaying any UI.
- *
- * This is used on data-only devices, which don't support any kind of
- * in-call phone UI.
- *
- * @return PhoneUtils.CALL_STATUS_DIALED if we successfully
- * dialed the OTASP number, or one of the other
- * CALL_STATUS_* constants if there was a failure.
- */
- public static int startNonInteractiveOtasp(Context context) {
- if (DBG) log("startNonInteractiveOtasp()...");
- PhoneGlobals app = PhoneGlobals.getInstance();
-
- if (app.otaUtils != null) {
- // An OtaUtils instance already exists, presumably from a previous OTASP call.
- Log.i(LOG_TAG, "startNonInteractiveOtasp: "
- + "OtaUtils already exists; nuking the old one and starting again...");
- }
-
- // Create the OtaUtils instance.
- app.otaUtils = new OtaUtils(context, false /* non-interactive mode */);
- if (DBG) log("- created OtaUtils: " + app.otaUtils);
-
- // ... and kick off the OTASP call.
- // TODO(InCallScreen redesign): This should probably go through
- // the CallController, rather than directly calling
- // PhoneUtils.placeCall().
- Phone phone = PhoneGlobals.getPhone();
- String number = OTASP_NUMBER_NON_INTERACTIVE;
- Log.i(LOG_TAG, "startNonInteractiveOtasp: placing call to '" + number + "'...");
- int callStatus = PhoneUtils.placeCall(context,
- phone,
- number,
- null, // contactRef
- false); //isEmergencyCall
-
- if (callStatus == PhoneUtils.CALL_STATUS_DIALED) {
- if (DBG) log(" ==> successful return from placeCall(): callStatus = " + callStatus);
- } else {
- Log.w(LOG_TAG, "Failure from placeCall() for OTA number '"
- + number + "': code " + callStatus);
- return callStatus;
- }
-
- // TODO: Any other special work to do here?
- // Such as:
- //
- // - manually kick off progress updates, either using TelephonyRegistry
- // or else by sending PendingIntents directly to our caller?
- //
- // - manually silence the in-call audio? (Probably unnecessary
- // if Stingray truly has no audio path from phone baseband
- // to the device's speakers.)
- //
-
- return callStatus;
- }
-
- /**
- * @return true if the specified Intent is a CALL action that's an attempt
- * to initate an OTASP call.
- *
- * OTASP is a CDMA-specific concept, so this method will always return false
- * on GSM phones.
- *
- * This code was originally part of the InCallScreen.checkIsOtaCall() method.
- */
- public static boolean isOtaspCallIntent(Intent intent) {
- if (DBG) log("isOtaspCallIntent(" + intent + ")...");
- PhoneGlobals app = PhoneGlobals.getInstance();
- Phone phone = app.mCM.getDefaultPhone();
-
- if (intent == null) {
- return false;
- }
- if (!TelephonyCapabilities.supportsOtasp(phone)) {
- return false;
- }
-
- String action = intent.getAction();
- if (action == null) {
- return false;
- }
- if (!action.equals(Intent.ACTION_CALL)) {
- if (DBG) log("isOtaspCallIntent: not a CALL action: '" + action + "' ==> not OTASP");
- return false;
- }
-
- if ((app.cdmaOtaScreenState == null) || (app.cdmaOtaProvisionData == null)) {
- // Uh oh -- something wrong with our internal OTASP state.
- // (Since this is an OTASP-capable device, these objects
- // *should* have already been created by PhoneApp.onCreate().)
- throw new IllegalStateException("isOtaspCallIntent: "
- + "app.cdmaOta* objects(s) not initialized");
- }
-
- // This is an OTASP call iff the number we're trying to dial is one of
- // the magic OTASP numbers.
- String number;
- try {
- number = PhoneUtils.getInitialNumber(intent);
- } catch (PhoneUtils.VoiceMailNumberMissingException ex) {
- // This was presumably a "voicemail:" intent, so it's
- // obviously not an OTASP number.
- if (DBG) log("isOtaspCallIntent: VoiceMailNumberMissingException => not OTASP");
- return false;
- }
- if (phone.isOtaSpNumber(number)) {
- if (DBG) log("isOtaSpNumber: ACTION_CALL to '" + number + "' ==> OTASP call!");
- return true;
- }
- return false;
- }
-
- /**
- * Set up for an OTASP call.
- *
- * This method is called as part of the CallController placeCall() sequence
- * before initiating an outgoing OTASP call.
- *
- * The purpose of this method is mainly to create and initialize the
- * OtaUtils instance, along with some other misc pre-OTASP cleanup.
- */
- public static void setupOtaspCall(Intent intent) {
- if (DBG) log("setupOtaspCall(): preparing for OTASP call to " + intent);
- PhoneGlobals app = PhoneGlobals.getInstance();
-
- if (app.otaUtils != null) {
- // An OtaUtils instance already exists, presumably from a prior OTASP call.
- // Nuke the old one and start this call with a fresh instance.
- Log.i(LOG_TAG, "setupOtaspCall: "
- + "OtaUtils already exists; replacing with new instance...");
- }
-
- // Create the OtaUtils instance.
- app.otaUtils = new OtaUtils(app.getApplicationContext(), true /* interactive */);
- if (DBG) log("- created OtaUtils: " + app.otaUtils);
-
- // NOTE we still need to call OtaUtils.updateUiWidgets() once the
- // InCallScreen instance is ready; see InCallScreen.checkOtaspStateOnResume()
-
- // Make sure the InCallScreen knows that it needs to switch into OTASP mode.
- //
- // NOTE in gingerbread and earlier, we used to do
- // setInCallScreenMode(InCallScreenMode.OTA_NORMAL);
- // directly in the InCallScreen, back when this check happened inside the InCallScreen.
- //
- // But now, set the global CdmaOtaInCallScreenUiState object into
- // NORMAL mode, which will then cause the InCallScreen (when it
- // comes up) to realize that an OTA call is active.
-
- app.otaUtils.setCdmaOtaInCallScreenUiState(
- OtaUtils.CdmaOtaInCallScreenUiState.State.NORMAL);
-
- // TODO(OTASP): note app.inCallUiState.inCallScreenMode and
- // app.cdmaOtaInCallScreenUiState.state are mostly redundant. Combine them.
- // app.inCallUiState.inCallScreenMode = InCallUiState.InCallScreenMode.OTA_NORMAL;
-
- // TODO(OTASP / bug 5092031): we ideally should call
- // otaShowListeningScreen() here to make sure that the DTMF dialpad
- // becomes visible at the start of the "*228" call:
- //
- // // ...and get the OTASP-specific UI into the right state.
- // app.otaUtils.otaShowListeningScreen();
- // if (app.otaUtils.mInCallScreen != null) {
- // app.otaUtils.mInCallScreen.requestUpdateScreen();
- // }
- //
- // But this doesn't actually work; the call to otaShowListeningScreen()
- // *doesn't* actually bring up the listening screen, since the
- // cdmaOtaConfigData.otaShowListeningScreen config parameter hasn't been
- // initialized (we haven't run readXmlSettings() yet at this point!)
-
- // Also, since the OTA call is now just starting, clear out
- // the "committed" flag in app.cdmaOtaProvisionData.
- if (app.cdmaOtaProvisionData != null) {
- app.cdmaOtaProvisionData.isOtaCallCommitted = false;
- }
- }
-
- private void setSpeaker(boolean state) {
- if (DBG) log("setSpeaker : " + state );
-
- if (!mInteractive) {
- if (DBG) log("non-interactive mode, ignoring setSpeaker.");
- return;
- }
-
- if (state == PhoneUtils.isSpeakerOn(mContext)) {
- if (DBG) log("no change. returning");
- return;
- }
-
- PhoneUtils.turnOnSpeaker(mContext, state, true);
- }
-
- /**
- * Handles OTA Provision events from the telephony layer.
- * These events come in to this method whether or not
- * the InCallScreen is visible.
- *
- * Possible events are:
- * OTA Commit Event - OTA provisioning was successful
- * SPC retries exceeded - SPC failure retries has exceeded, and Phone needs to
- * power down.
- */
- public void onOtaProvisionStatusChanged(AsyncResult r) {
- int OtaStatus[] = (int[]) r.result;
- if (DBG) log("Provision status event!");
- if (DBG) log("onOtaProvisionStatusChanged(): status = "
- + OtaStatus[0] + " ==> " + otaProvisionStatusToString(OtaStatus[0]));
-
- // In practice, in a normal successful OTASP call, events come in as follows:
- // - SPL_UNLOCKED within a couple of seconds after the call starts
- // - then a delay of around 45 seconds
- // - then PRL_DOWNLOADED and MDN_DOWNLOADED and COMMITTED within a span of 2 seconds
-
- switch(OtaStatus[0]) {
- case Phone.CDMA_OTA_PROVISION_STATUS_SPC_RETRIES_EXCEEDED:
- if (DBG) log("onOtaProvisionStatusChanged(): RETRIES EXCEEDED");
- updateOtaspProgress();
- mApplication.cdmaOtaProvisionData.otaSpcUptime = SystemClock.elapsedRealtime();
- if (mInteractive) {
- otaShowSpcErrorNotice(OTA_SPC_TIMEOUT);
- } else {
- sendOtaspResult(OTASP_FAILURE_SPC_RETRIES);
- }
- // Power.shutdown();
- break;
-
- case Phone.CDMA_OTA_PROVISION_STATUS_COMMITTED:
- if (DBG) {
- log("onOtaProvisionStatusChanged(): DONE, isOtaCallCommitted set to true");
- }
- mApplication.cdmaOtaProvisionData.isOtaCallCommitted = true;
- if (mApplication.cdmaOtaScreenState.otaScreenState !=
- CdmaOtaScreenState.OtaScreenState.OTA_STATUS_UNDEFINED) {
- updateOtaspProgress();
- }
-
- break;
-
- case Phone.CDMA_OTA_PROVISION_STATUS_SPL_UNLOCKED:
- case Phone.CDMA_OTA_PROVISION_STATUS_A_KEY_EXCHANGED:
- case Phone.CDMA_OTA_PROVISION_STATUS_SSD_UPDATED:
- case Phone.CDMA_OTA_PROVISION_STATUS_NAM_DOWNLOADED:
- case Phone.CDMA_OTA_PROVISION_STATUS_MDN_DOWNLOADED:
- case Phone.CDMA_OTA_PROVISION_STATUS_IMSI_DOWNLOADED:
- case Phone.CDMA_OTA_PROVISION_STATUS_PRL_DOWNLOADED:
- case Phone.CDMA_OTA_PROVISION_STATUS_OTAPA_STARTED:
- case Phone.CDMA_OTA_PROVISION_STATUS_OTAPA_STOPPED:
- case Phone.CDMA_OTA_PROVISION_STATUS_OTAPA_ABORTED:
- // Only update progress when OTA call is in normal state
- if (getCdmaOtaInCallScreenUiState() == CdmaOtaInCallScreenUiState.State.NORMAL) {
- if (DBG) log("onOtaProvisionStatusChanged(): change to ProgressScreen");
- updateOtaspProgress();
- }
- break;
-
- default:
- if (DBG) log("onOtaProvisionStatusChanged(): Ignoring OtaStatus " + OtaStatus[0]);
- break;
- }
- }
-
- /**
- * Handle a disconnect event from the OTASP call.
- */
- public void onOtaspDisconnect() {
- if (DBG) log("onOtaspDisconnect()...");
- // We only handle this event explicitly in non-interactive mode.
- // (In interactive mode, the InCallScreen does any post-disconnect
- // cleanup.)
- if (!mInteractive) {
- // Send a success or failure indication back to our caller.
- updateNonInteractiveOtaSuccessFailure();
- }
- cleanOtaScreen(true);
- }
-
- private void otaShowHome() {
- if (DBG) log("otaShowHome()...");
- mApplication.cdmaOtaScreenState.otaScreenState =
- CdmaOtaScreenState.OtaScreenState.OTA_STATUS_UNDEFINED;
- // mInCallScreen.endInCallScreenSession();
- Intent intent = new Intent(Intent.ACTION_MAIN);
- intent.addCategory (Intent.CATEGORY_HOME);
- intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- mContext.startActivityAsUser(intent, UserHandle.CURRENT);
- return;
- }
-
- private void otaSkipActivation() {
- if (DBG) log("otaSkipActivation()...");
-
- sendOtaspResult(OTASP_USER_SKIPPED);
-
- // if (mInteractive) mInCallScreen.finish();
- return;
- }
-
- /**
- * Actually initiate the OTASP call. This method is triggered by the
- * onscreen "Activate" button, and is only used in interactive mode.
- */
- private void otaPerformActivation() {
- if (DBG) log("otaPerformActivation()...");
- if (!mInteractive) {
- // We shouldn't ever get here in non-interactive mode!
- Log.w(LOG_TAG, "otaPerformActivation: not interactive!");
- return;
- }
-
- if (!mApplication.cdmaOtaProvisionData.inOtaSpcState) {
- // Place an outgoing call to the special OTASP number:
- Intent newIntent = new Intent(Intent.ACTION_CALL);
- newIntent.setData(Uri.fromParts(PhoneAccount.SCHEME_TEL, OTASP_NUMBER, null));
-
- // Initiate the outgoing call:
- mApplication.callController.placeCall(newIntent);
-
- // ...and get the OTASP-specific UI into the right state.
- otaShowListeningScreen();
- // mInCallScreen.requestUpdateScreen();
- }
- return;
- }
-
- /**
- * Show Activation Screen when phone powers up and OTA provision is
- * required. Also shown when activation fails and user needs
- * to re-attempt it. Contains ACTIVATE and SKIP buttons
- * which allow user to start OTA activation or skip the activation process.
- */
- public void otaShowActivateScreen() {
- if (DBG) log("otaShowActivateScreen()...");
- if (mApplication.cdmaOtaConfigData.otaShowActivationScreen
- == OTA_SHOW_ACTIVATION_SCREEN_ON) {
- if (DBG) log("otaShowActivateScreen(): show activation screen");
- if (!isDialerOpened()) {
- otaScreenInitialize();
- mOtaWidgetData.otaSkipButton.setVisibility(sIsWizardMode ?
- View.VISIBLE : View.INVISIBLE);
- mOtaWidgetData.otaTextActivate.setVisibility(View.VISIBLE);
- mOtaWidgetData.callCardOtaButtonsActivate.setVisibility(View.VISIBLE);
- }
- mApplication.cdmaOtaScreenState.otaScreenState =
- CdmaOtaScreenState.OtaScreenState.OTA_STATUS_ACTIVATION;
- } else {
- if (DBG) log("otaShowActivateScreen(): show home screen");
- otaShowHome();
- }
- }
-
- /**
- * Show "Listen for Instruction" screen during OTA call. Shown when OTA Call
- * is initiated and user needs to listen for network instructions and press
- * appropriate DTMF digits to proceed to the "Programming in Progress" phase.
- */
- private void otaShowListeningScreen() {
- if (DBG) log("otaShowListeningScreen()...");
- if (!mInteractive) {
- // We shouldn't ever get here in non-interactive mode!
- Log.w(LOG_TAG, "otaShowListeningScreen: not interactive!");
- return;
- }
-
- if (mApplication.cdmaOtaConfigData.otaShowListeningScreen
- == OTA_SHOW_LISTENING_SCREEN_ON) {
- if (DBG) log("otaShowListeningScreen(): show listening screen");
- if (!isDialerOpened()) {
- otaScreenInitialize();
- mOtaWidgetData.otaTextListenProgress.setVisibility(View.VISIBLE);
- mOtaWidgetData.otaTextListenProgress.setText(R.string.ota_listen);
- // mOtaWidgetData.otaDtmfDialerView.setVisibility(View.VISIBLE);
- mOtaWidgetData.callCardOtaButtonsListenProgress.setVisibility(View.VISIBLE);
- mOtaWidgetData.otaSpeakerButton.setVisibility(View.VISIBLE);
- boolean speakerOn = PhoneUtils.isSpeakerOn(mContext);
- mOtaWidgetData.otaSpeakerButton.setChecked(speakerOn);
- }
- mApplication.cdmaOtaScreenState.otaScreenState =
- CdmaOtaScreenState.OtaScreenState.OTA_STATUS_LISTENING;
- } else {
- if (DBG) log("otaShowListeningScreen(): show progress screen");
- otaShowInProgressScreen();
- }
- }
-
- /**
- * Do any necessary updates (of onscreen UI, for example)
- * based on the latest status of the OTASP call.
- */
- private void updateOtaspProgress() {
- if (DBG) log("updateOtaspProgress()... mInteractive = " + mInteractive);
- if (mInteractive) {
- // On regular phones we just call through to
- // otaShowInProgressScreen(), which updates the
- // InCallScreen's onscreen UI.
- otaShowInProgressScreen();
- } else {
- // We're not using the InCallScreen to show OTA progress.
-
- // For now, at least, there's nothing to do here.
- // The overall "success" or "failure" indication we send back
- // (to our caller) is triggered by the DISCONNECT event;
- // see updateNonInteractiveOtaSuccessFailure().
-
- // But if we ever need to send *intermediate* progress updates back
- // to our caller, we'd do that here, possbily using the same
- // PendingIntent that we already use to indicate success or failure.
- }
- }
-
- /**
- * When a non-interactive OTASP call completes, send a success or
- * failure indication back to our caller.
- *
- * This is basically the non-interactive equivalent of
- * otaShowSuccessFailure().
- */
- private void updateNonInteractiveOtaSuccessFailure() {
- // This is basically the same logic as otaShowSuccessFailure(): we
- // check the isOtaCallCommitted bit, and if that's true it means
- // that activation was successful.
-
- if (DBG) log("updateNonInteractiveOtaSuccessFailure(): isOtaCallCommitted = "
- + mApplication.cdmaOtaProvisionData.isOtaCallCommitted);
- int resultCode =
- mApplication.cdmaOtaProvisionData.isOtaCallCommitted
- ? OTASP_SUCCESS : OTASP_FAILURE;
- sendOtaspResult(resultCode);
- }
-
- /**
- * Sends the specified OTASP result code back to our caller (presumably
- * SetupWizard) via the PendingIntent that they originally sent along with
- * the ACTION_PERFORM_CDMA_PROVISIONING intent.
- */
- private void sendOtaspResult(int resultCode) {
- if (DBG) log("sendOtaspResult: resultCode = " + resultCode);
-
- // Pass the success or failure indication back to our caller by
- // adding an additional extra to the PendingIntent we already
- // have.
- // (NB: there's a PendingIntent send() method that takes a resultCode
- // directly, but we can't use that here since that call is only
- // meaningful for pending intents that are actually used as activity
- // results.)
-
- Intent extraStuff = new Intent();
- extraStuff.putExtra(EXTRA_OTASP_RESULT_CODE, resultCode);
- // When we call PendingIntent.send() below, the extras from this
- // intent will get merged with any extras already present in
- // cdmaOtaScreenState.otaspResultCodePendingIntent.
-
- if (mApplication.cdmaOtaScreenState == null) {
- Log.e(LOG_TAG, "updateNonInteractiveOtaSuccessFailure: no cdmaOtaScreenState object!");
- return;
- }
- if (mApplication.cdmaOtaScreenState.otaspResultCodePendingIntent == null) {
- Log.w(LOG_TAG, "updateNonInteractiveOtaSuccessFailure: "
- + "null otaspResultCodePendingIntent!");
- return;
- }
-
- try {
- if (DBG) log("- sendOtaspResult: SENDING PENDING INTENT: " +
- mApplication.cdmaOtaScreenState.otaspResultCodePendingIntent);
- mApplication.cdmaOtaScreenState.otaspResultCodePendingIntent.send(
- mContext,
- 0, /* resultCode (unused) */
- extraStuff);
- } catch (CanceledException e) {
- // should never happen because no code cancels the pending intent right now,
- Log.e(LOG_TAG, "PendingIntent send() failed: " + e);
- }
- }
-
- /**
- * Show "Programming In Progress" screen during OTA call. Shown when OTA
- * provisioning is in progress after user has selected an option.
- */
- private void otaShowInProgressScreen() {
- if (DBG) log("otaShowInProgressScreen()...");
- if (!mInteractive) {
- // We shouldn't ever get here in non-interactive mode!
- Log.w(LOG_TAG, "otaShowInProgressScreen: not interactive!");
- return;
- }
-
- mApplication.cdmaOtaScreenState.otaScreenState =
- CdmaOtaScreenState.OtaScreenState.OTA_STATUS_PROGRESS;
-
- if ((mOtaWidgetData == null) /* || (mInCallScreen == null) */) {
- Log.w(LOG_TAG, "otaShowInProgressScreen: UI widgets not set up yet!");
-
- // TODO(OTASP): our CdmaOtaScreenState is now correct; we just set
- // it to OTA_STATUS_PROGRESS. But we still need to make sure that
- // when the InCallScreen eventually comes to the foreground, it
- // notices that state and does all the same UI updating we do below.
- return;
- }
-
- if (!isDialerOpened()) {
- otaScreenInitialize();
- mOtaWidgetData.otaTextListenProgress.setVisibility(View.VISIBLE);
- mOtaWidgetData.otaTextListenProgress.setText(R.string.ota_progress);
- mOtaWidgetData.otaTextProgressBar.setVisibility(View.VISIBLE);
- mOtaWidgetData.callCardOtaButtonsListenProgress.setVisibility(View.VISIBLE);
- mOtaWidgetData.otaSpeakerButton.setVisibility(View.VISIBLE);
- boolean speakerOn = PhoneUtils.isSpeakerOn(mContext);
- mOtaWidgetData.otaSpeakerButton.setChecked(speakerOn);
- }
- }
-
- /**
- * Show programming failure dialog when OTA provisioning fails.
- * If OTA provisioning attempts fail more than 3 times, then unsuccessful
- * dialog is shown. Otherwise a two-second notice is shown with unsuccessful
- * information. When notice expires, phone returns to activation screen.
- */
- private void otaShowProgramFailure(int length) {
- if (DBG) log("otaShowProgramFailure()...");
- mApplication.cdmaOtaProvisionData.activationCount++;
- if ((mApplication.cdmaOtaProvisionData.activationCount <
- mApplication.cdmaOtaConfigData.otaShowActivateFailTimes)
- && (mApplication.cdmaOtaConfigData.otaShowActivationScreen ==
- OTA_SHOW_ACTIVATION_SCREEN_ON)) {
- if (DBG) log("otaShowProgramFailure(): activationCount"
- + mApplication.cdmaOtaProvisionData.activationCount);
- if (DBG) log("otaShowProgramFailure(): show failure notice");
- otaShowProgramFailureNotice(length);
- } else {
- if (DBG) log("otaShowProgramFailure(): show failure dialog");
- otaShowProgramFailureDialog();
- }
- }
-
- /**
- * Show either programming success dialog when OTA provisioning succeeds, or
- * programming failure dialog when it fails. See {@link #otaShowProgramFailure}
- * for more details.
- */
- public void otaShowSuccessFailure() {
- if (DBG) log("otaShowSuccessFailure()...");
- if (!mInteractive) {
- // We shouldn't ever get here in non-interactive mode!
- Log.w(LOG_TAG, "otaShowSuccessFailure: not interactive!");
- return;
- }
-
- otaScreenInitialize();
- if (DBG) log("otaShowSuccessFailure(): isOtaCallCommitted"
- + mApplication.cdmaOtaProvisionData.isOtaCallCommitted);
- if (mApplication.cdmaOtaProvisionData.isOtaCallCommitted) {
- if (DBG) log("otaShowSuccessFailure(), show success dialog");
- otaShowProgramSuccessDialog();
- } else {
- if (DBG) log("otaShowSuccessFailure(), show failure dialog");
- otaShowProgramFailure(OTA_FAILURE_DIALOG_TIMEOUT);
- }
- return;
- }
-
- /**
- * Show programming failure dialog when OTA provisioning fails more than 3
- * times.
- */
- private void otaShowProgramFailureDialog() {
- if (DBG) log("otaShowProgramFailureDialog()...");
- mApplication.cdmaOtaScreenState.otaScreenState =
- CdmaOtaScreenState.OtaScreenState.OTA_STATUS_SUCCESS_FAILURE_DLG;
- mOtaWidgetData.otaTitle.setText(R.string.ota_title_problem_with_activation);
- mOtaWidgetData.otaTextSuccessFail.setVisibility(View.VISIBLE);
- mOtaWidgetData.otaTextSuccessFail.setText(R.string.ota_unsuccessful);
- mOtaWidgetData.callCardOtaButtonsFailSuccess.setVisibility(View.VISIBLE);
- mOtaWidgetData.otaTryAgainButton.setVisibility(View.VISIBLE);
- //close the dialer if open
- // if (isDialerOpened()) {
- // mOtaCallCardDtmfDialer.closeDialer(false);
- // }
- }
-
- /**
- * Show programming success dialog when OTA provisioning succeeds.
- */
- private void otaShowProgramSuccessDialog() {
- if (DBG) log("otaShowProgramSuccessDialog()...");
- mApplication.cdmaOtaScreenState.otaScreenState =
- CdmaOtaScreenState.OtaScreenState.OTA_STATUS_SUCCESS_FAILURE_DLG;
- mOtaWidgetData.otaTitle.setText(R.string.ota_title_activate_success);
- mOtaWidgetData.otaTextSuccessFail.setVisibility(View.VISIBLE);
- mOtaWidgetData.otaTextSuccessFail.setText(R.string.ota_successful);
- mOtaWidgetData.callCardOtaButtonsFailSuccess.setVisibility(View.VISIBLE);
- mOtaWidgetData.otaNextButton.setVisibility(View.VISIBLE);
- //close the dialer if open
- // if (isDialerOpened()) {
- // mOtaCallCardDtmfDialer.closeDialer(false);
- // }
- }
-
- /**
- * Show SPC failure notice when SPC attempts exceed 15 times.
- * During OTA provisioning, if SPC code is incorrect OTA provisioning will
- * fail. When SPC attempts are over 15, it shows SPC failure notice for one minute and
- * then phone will power down.
- */
- private void otaShowSpcErrorNotice(int length) {
- if (DBG) log("otaShowSpcErrorNotice()...");
- if (mOtaWidgetData.spcErrorDialog == null) {
- mApplication.cdmaOtaProvisionData.inOtaSpcState = true;
- DialogInterface.OnKeyListener keyListener;
- keyListener = new DialogInterface.OnKeyListener() {
- public boolean onKey(DialogInterface dialog, int keyCode, KeyEvent event) {
- log("Ignoring key events...");
- return true;
- }};
- mOtaWidgetData.spcErrorDialog = new AlertDialog.Builder(null /* mInCallScreen */)
- .setMessage(R.string.ota_spc_failure)
- .setOnKeyListener(keyListener)
- .create();
- mOtaWidgetData.spcErrorDialog.getWindow().addFlags(
- WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE
- | WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
- mOtaWidgetData.spcErrorDialog.show();
- //close the dialer if open
- // if (isDialerOpened()) {
- // mOtaCallCardDtmfDialer.closeDialer(false);
- // }
- long noticeTime = length*1000;
- if (DBG) log("otaShowSpcErrorNotice(), remaining SPC noticeTime" + noticeTime);
- // mInCallScreen.requestCloseSpcErrorNotice(noticeTime);
- }
- }
-
- /**
- * When SPC notice times out, force phone to power down.
- */
- public void onOtaCloseSpcNotice() {
- if (DBG) log("onOtaCloseSpcNotice(), send shutdown intent");
- Intent shutdown = new Intent(Intent.ACTION_REQUEST_SHUTDOWN);
- shutdown.putExtra(Intent.EXTRA_KEY_CONFIRM, false);
- shutdown.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- mContext.startActivity(shutdown);
- }
-
- /**
- * Show two-second notice when OTA provisioning fails and number of failed attempts
- * is less then 3.
- */
- private void otaShowProgramFailureNotice(int length) {
- if (DBG) log("otaShowProgramFailureNotice()...");
- if (mOtaWidgetData.otaFailureDialog == null) {
- mOtaWidgetData.otaFailureDialog = new AlertDialog.Builder(null /* mInCallScreen */)
- .setMessage(R.string.ota_failure)
- .create();
- mOtaWidgetData.otaFailureDialog.getWindow().addFlags(
- WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE
- | WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
- mOtaWidgetData.otaFailureDialog.show();
-
- long noticeTime = length*1000;
- // mInCallScreen.requestCloseOtaFailureNotice(noticeTime);
- }
- }
-
- /**
- * Handle OTA unsuccessful notice expiry. Dismisses the
- * two-second notice and shows the activation screen.
- */
- public void onOtaCloseFailureNotice() {
- if (DBG) log("onOtaCloseFailureNotice()...");
- if (mOtaWidgetData.otaFailureDialog != null) {
- mOtaWidgetData.otaFailureDialog.dismiss();
- mOtaWidgetData.otaFailureDialog = null;
- }
- otaShowActivateScreen();
- }
-
- /**
- * Initialize all OTA UI elements to be gone. Also set inCallPanel,
- * callCard and the dialpad handle to be gone. This is called before any OTA screen
- * gets drawn.
- */
- private void otaScreenInitialize() {
- if (DBG) log("otaScreenInitialize()...");
-
- if (!mInteractive) {
- // We should never be doing anything with UI elements in
- // non-interactive mode.
- Log.w(LOG_TAG, "otaScreenInitialize: not interactive!");
- return;
- }
-
- // if (mInCallTouchUi != null) mInCallTouchUi.setVisibility(View.GONE);
- // if (mCallCard != null) {
- // mCallCard.setVisibility(View.GONE);
- // // TODO: try removing this.
- // mCallCard.hideCallCardElements();
- // }
-
- mOtaWidgetData.otaTitle.setText(R.string.ota_title_activate);
- mOtaWidgetData.otaTextActivate.setVisibility(View.GONE);
- mOtaWidgetData.otaTextListenProgress.setVisibility(View.GONE);
- mOtaWidgetData.otaTextProgressBar.setVisibility(View.GONE);
- mOtaWidgetData.otaTextSuccessFail.setVisibility(View.GONE);
- mOtaWidgetData.callCardOtaButtonsActivate.setVisibility(View.GONE);
- mOtaWidgetData.callCardOtaButtonsListenProgress.setVisibility(View.GONE);
- mOtaWidgetData.callCardOtaButtonsFailSuccess.setVisibility(View.GONE);
- // mOtaWidgetData.otaDtmfDialerView.setVisibility(View.GONE);
- mOtaWidgetData.otaSpeakerButton.setVisibility(View.GONE);
- mOtaWidgetData.otaTryAgainButton.setVisibility(View.GONE);
- mOtaWidgetData.otaNextButton.setVisibility(View.GONE);
- mOtaWidgetData.otaUpperWidgets.setVisibility(View.VISIBLE);
- mOtaWidgetData.otaSkipButton.setVisibility(View.VISIBLE);
- }
-
- public void hideOtaScreen() {
- if (DBG) log("hideOtaScreen()...");
-
- mOtaWidgetData.callCardOtaButtonsActivate.setVisibility(View.GONE);
- mOtaWidgetData.callCardOtaButtonsListenProgress.setVisibility(View.GONE);
- mOtaWidgetData.callCardOtaButtonsFailSuccess.setVisibility(View.GONE);
- mOtaWidgetData.otaUpperWidgets.setVisibility(View.GONE);
- }
-
- public boolean isDialerOpened() {
- // boolean retval = (mOtaCallCardDtmfDialer != null && mOtaCallCardDtmfDialer.isOpened());
- boolean retval = false;
- if (DBG) log("- isDialerOpened() ==> " + retval);
- return retval;
- }
-
- /**
- * Show the appropriate OTA screen based on the current state of OTA call.
- *
- * This is called from the InCallScreen when the screen needs to be
- * refreshed (and thus is only ever used in interactive mode.)
- *
- * Since this is called as part of the InCallScreen.updateScreen() sequence,
- * this method does *not* post an mInCallScreen.requestUpdateScreen()
- * request.
- */
- public void otaShowProperScreen() {
- if (DBG) log("otaShowProperScreen()...");
- if (!mInteractive) {
- // We shouldn't ever get here in non-interactive mode!
- Log.w(LOG_TAG, "otaShowProperScreen: not interactive!");
- return;
- }
-
- // if ((mInCallScreen != null) && mInCallScreen.isForegroundActivity()) {
- // if (DBG) log("otaShowProperScreen(): InCallScreen in foreground, currentstate = "
- // + mApplication.cdmaOtaScreenState.otaScreenState);
- // if (mInCallTouchUi != null) {
- // mInCallTouchUi.setVisibility(View.GONE);
- // }
- // if (mCallCard != null) {
- // mCallCard.setVisibility(View.GONE);
- // }
- // if (mApplication.cdmaOtaScreenState.otaScreenState
- // == CdmaOtaScreenState.OtaScreenState.OTA_STATUS_ACTIVATION) {
- // otaShowActivateScreen();
- // } else if (mApplication.cdmaOtaScreenState.otaScreenState
- // == CdmaOtaScreenState.OtaScreenState.OTA_STATUS_LISTENING) {
- // otaShowListeningScreen();
- // } else if (mApplication.cdmaOtaScreenState.otaScreenState
- // == CdmaOtaScreenState.OtaScreenState.OTA_STATUS_PROGRESS) {
- // otaShowInProgressScreen();
- // }
-
- // if (mApplication.cdmaOtaProvisionData.inOtaSpcState) {
- // otaShowSpcErrorNotice(getOtaSpcDisplayTime());
- // }
- // }
- }
-
- /**
- * Read configuration values for each OTA screen from config.xml.
- * These configuration values control visibility of each screen.
- */
- private void readXmlSettings() {
- if (DBG) log("readXmlSettings()...");
- if (mApplication.cdmaOtaConfigData.configComplete) {
- return;
- }
-
- mApplication.cdmaOtaConfigData.configComplete = true;
- int tmpOtaShowActivationScreen =
- mContext.getResources().getInteger(R.integer.OtaShowActivationScreen);
- mApplication.cdmaOtaConfigData.otaShowActivationScreen = tmpOtaShowActivationScreen;
- if (DBG) log("readXmlSettings(), otaShowActivationScreen = "
- + mApplication.cdmaOtaConfigData.otaShowActivationScreen);
-
- int tmpOtaShowListeningScreen =
- mContext.getResources().getInteger(R.integer.OtaShowListeningScreen);
- mApplication.cdmaOtaConfigData.otaShowListeningScreen = tmpOtaShowListeningScreen;
- if (DBG) log("readXmlSettings(), otaShowListeningScreen = "
- + mApplication.cdmaOtaConfigData.otaShowListeningScreen);
-
- int tmpOtaShowActivateFailTimes =
- mContext.getResources().getInteger(R.integer.OtaShowActivateFailTimes);
- mApplication.cdmaOtaConfigData.otaShowActivateFailTimes = tmpOtaShowActivateFailTimes;
- if (DBG) log("readXmlSettings(), otaShowActivateFailTimes = "
- + mApplication.cdmaOtaConfigData.otaShowActivateFailTimes);
-
- int tmpOtaPlaySuccessFailureTone =
- mContext.getResources().getInteger(R.integer.OtaPlaySuccessFailureTone);
- mApplication.cdmaOtaConfigData.otaPlaySuccessFailureTone = tmpOtaPlaySuccessFailureTone;
- if (DBG) log("readXmlSettings(), otaPlaySuccessFailureTone = "
- + mApplication.cdmaOtaConfigData.otaPlaySuccessFailureTone);
- }
-
- /**
- * Handle the click events for OTA buttons.
- */
- public void onClickHandler(int id) {
- switch (id) {
- case R.id.otaEndButton:
- onClickOtaEndButton();
- break;
-
- case R.id.otaSpeakerButton:
- onClickOtaSpeakerButton();
- break;
-
- case R.id.otaActivateButton:
- onClickOtaActivateButton();
- break;
-
- case R.id.otaSkipButton:
- onClickOtaActivateSkipButton();
- break;
-
- case R.id.otaNextButton:
- onClickOtaActivateNextButton();
- break;
-
- case R.id.otaTryAgainButton:
- onClickOtaTryAgainButton();
- break;
-
- default:
- if (DBG) log ("onClickHandler: received a click event for unrecognized id");
- break;
- }
- }
-
- private void onClickOtaTryAgainButton() {
- if (DBG) log("Activation Try Again Clicked!");
- if (!mApplication.cdmaOtaProvisionData.inOtaSpcState) {
- otaShowActivateScreen();
- }
- }
-
- private void onClickOtaEndButton() {
- if (DBG) log("Activation End Call Button Clicked!");
- if (!mApplication.cdmaOtaProvisionData.inOtaSpcState) {
- if (PhoneUtils.hangup(mApplication.mCM) == false) {
- // If something went wrong when placing the OTA call,
- // the screen is not updated by the call disconnect
- // handler and we have to do it here
- setSpeaker(false);
- // mInCallScreen.handleOtaCallEnd();
- }
- }
- }
-
- private void onClickOtaSpeakerButton() {
- if (DBG) log("OTA Speaker button Clicked!");
- if (!mApplication.cdmaOtaProvisionData.inOtaSpcState) {
- boolean isChecked = !PhoneUtils.isSpeakerOn(mContext);
- setSpeaker(isChecked);
- }
- }
-
- private void onClickOtaActivateButton() {
- if (DBG) log("Call Activation Clicked!");
- otaPerformActivation();
- }
-
- private void onClickOtaActivateSkipButton() {
- if (DBG) log("Activation Skip Clicked!");
- DialogInterface.OnKeyListener keyListener;
- keyListener = new DialogInterface.OnKeyListener() {
- public boolean onKey(DialogInterface dialog, int keyCode,
- KeyEvent event) {
- if (DBG) log("Ignoring key events...");
- return true;
- }
- };
- mOtaWidgetData.otaSkipConfirmationDialog = new AlertDialog.Builder(null /* mInCallScreen */)
- .setTitle(R.string.ota_skip_activation_dialog_title)
- .setMessage(R.string.ota_skip_activation_dialog_message)
- .setPositiveButton(
- android.R.string.ok,
- // "OK" means "skip activation".
- new AlertDialog.OnClickListener() {
- public void onClick(DialogInterface dialog, int which) {
- otaSkipActivation();
- }
- })
- .setNegativeButton(
- android.R.string.cancel,
- // "Cancel" means just dismiss the dialog.
- // Don't actually start an activation call.
- null)
- .setOnKeyListener(keyListener)
- .create();
- mOtaWidgetData.otaSkipConfirmationDialog.show();
- }
-
- private void onClickOtaActivateNextButton() {
- if (DBG) log("Dialog Next Clicked!");
- if (!mApplication.cdmaOtaProvisionData.inOtaSpcState) {
- mApplication.cdmaOtaScreenState.otaScreenState =
- CdmaOtaScreenState.OtaScreenState.OTA_STATUS_UNDEFINED;
- otaShowHome();
- }
- }
-
- public void dismissAllOtaDialogs() {
- if (mOtaWidgetData != null) {
- if (mOtaWidgetData.spcErrorDialog != null) {
- if (DBG) log("- DISMISSING mSpcErrorDialog.");
- mOtaWidgetData.spcErrorDialog.dismiss();
- mOtaWidgetData.spcErrorDialog = null;
- }
- if (mOtaWidgetData.otaFailureDialog != null) {
- if (DBG) log("- DISMISSING mOtaFailureDialog.");
- mOtaWidgetData.otaFailureDialog.dismiss();
- mOtaWidgetData.otaFailureDialog = null;
- }
- }
- }
-
- private int getOtaSpcDisplayTime() {
- if (DBG) log("getOtaSpcDisplayTime()...");
- int tmpSpcTime = 1;
- if (mApplication.cdmaOtaProvisionData.inOtaSpcState) {
- long tmpOtaSpcRunningTime = 0;
- long tmpOtaSpcLeftTime = 0;
- tmpOtaSpcRunningTime = SystemClock.elapsedRealtime();
- tmpOtaSpcLeftTime =
- tmpOtaSpcRunningTime - mApplication.cdmaOtaProvisionData.otaSpcUptime;
- if (tmpOtaSpcLeftTime >= OTA_SPC_TIMEOUT*1000) {
- tmpSpcTime = 1;
- } else {
- tmpSpcTime = OTA_SPC_TIMEOUT - (int)tmpOtaSpcLeftTime/1000;
- }
- }
- if (DBG) log("getOtaSpcDisplayTime(), time for SPC error notice: " + tmpSpcTime);
- return tmpSpcTime;
- }
-
- /**
- * Initialize the OTA widgets for all OTA screens.
- */
- private void initOtaInCallScreen() {
- if (DBG) log("initOtaInCallScreen()...");
- // mOtaWidgetData.otaTitle = (TextView) mInCallScreen.findViewById(R.id.otaTitle);
- // mOtaWidgetData.otaTextActivate = (TextView) mInCallScreen.findViewById(R.id.otaActivate);
- mOtaWidgetData.otaTextActivate.setVisibility(View.GONE);
- // mOtaWidgetData.otaTextListenProgress =
- // (TextView) mInCallScreen.findViewById(R.id.otaListenProgress);
- // mOtaWidgetData.otaTextProgressBar =
- // (ProgressBar) mInCallScreen.findViewById(R.id.progress_large);
- mOtaWidgetData.otaTextProgressBar.setIndeterminate(true);
- // mOtaWidgetData.otaTextSuccessFail =
- // (TextView) mInCallScreen.findViewById(R.id.otaSuccessFailStatus);
-
- // mOtaWidgetData.otaUpperWidgets =
- // (ViewGroup) mInCallScreen.findViewById(R.id.otaUpperWidgets);
- // mOtaWidgetData.callCardOtaButtonsListenProgress =
- // (View) mInCallScreen.findViewById(R.id.callCardOtaListenProgress);
- // mOtaWidgetData.callCardOtaButtonsActivate =
- // (View) mInCallScreen.findViewById(R.id.callCardOtaActivate);
- // mOtaWidgetData.callCardOtaButtonsFailSuccess =
- // (View) mInCallScreen.findViewById(R.id.callCardOtaFailOrSuccessful);
-
- // mOtaWidgetData.otaEndButton = (Button) mInCallScreen.findViewById(R.id.otaEndButton);
- // mOtaWidgetData.otaEndButton.setOnClickListener(mInCallScreen);
- // mOtaWidgetData.otaSpeakerButton =
- // (ToggleButton) mInCallScreen.findViewById(R.id.otaSpeakerButton);
- // mOtaWidgetData.otaSpeakerButton.setOnClickListener(mInCallScreen);
- // mOtaWidgetData.otaActivateButton =
- // (Button) mInCallScreen.findViewById(R.id.otaActivateButton);
- // mOtaWidgetData.otaActivateButton.setOnClickListener(mInCallScreen);
- // mOtaWidgetData.otaSkipButton = (Button) mInCallScreen.findViewById(R.id.otaSkipButton);
- // mOtaWidgetData.otaSkipButton.setOnClickListener(mInCallScreen);
- // mOtaWidgetData.otaNextButton = (Button) mInCallScreen.findViewById(R.id.otaNextButton);
- // mOtaWidgetData.otaNextButton.setOnClickListener(mInCallScreen);
- // mOtaWidgetData.otaTryAgainButton =
- // (Button) mInCallScreen.findViewById(R.id.otaTryAgainButton);
- // mOtaWidgetData.otaTryAgainButton.setOnClickListener(mInCallScreen);
-
- // mOtaWidgetData.otaDtmfDialerView =
- // (DTMFTwelveKeyDialerView) mInCallScreen.findViewById(R.id.otaDtmfDialerView);
- // Sanity-check: the otaDtmfDialerView widget should *always* be present.
- // if (mOtaWidgetData.otaDtmfDialerView == null) {
- // throw new IllegalStateException("initOtaInCallScreen: couldn't find otaDtmfDialerView");
- // }
-
- // Create a new DTMFTwelveKeyDialer instance purely for use by the
- // DTMFTwelveKeyDialerView ("otaDtmfDialerView") that comes from
- // otacall_card.xml.
- // mOtaCallCardDtmfDialer = new DTMFTwelveKeyDialer(mInCallScreen,
- // mOtaWidgetData.otaDtmfDialerView);
-
- // Initialize the new DTMFTwelveKeyDialer instance. This is
- // needed to play local DTMF tones.
- // mOtaCallCardDtmfDialer.startDialerSession();
-
- // mOtaWidgetData.otaDtmfDialerView.setDialer(mOtaCallCardDtmfDialer);
- }
-
- /**
- * Clear out all OTA UI widget elements. Needs to get called
- * when OTA call ends or InCallScreen is destroyed.
- * @param disableSpeaker parameter control whether Speaker should be turned off.
- */
- public void cleanOtaScreen(boolean disableSpeaker) {
- if (DBG) log("OTA ends, cleanOtaScreen!");
-
- mApplication.cdmaOtaScreenState.otaScreenState =
- CdmaOtaScreenState.OtaScreenState.OTA_STATUS_UNDEFINED;
- mApplication.cdmaOtaProvisionData.isOtaCallCommitted = false;
- mApplication.cdmaOtaProvisionData.isOtaCallIntentProcessed = false;
- mApplication.cdmaOtaProvisionData.inOtaSpcState = false;
- mApplication.cdmaOtaProvisionData.activationCount = 0;
- mApplication.cdmaOtaProvisionData.otaSpcUptime = 0;
- mApplication.cdmaOtaInCallScreenUiState.state = State.UNDEFINED;
-
- if (mInteractive && (mOtaWidgetData != null)) {
- // if (mInCallTouchUi != null) mInCallTouchUi.setVisibility(View.VISIBLE);
- // if (mCallCard != null) {
- // mCallCard.setVisibility(View.VISIBLE);
- // mCallCard.hideCallCardElements();
- // }
-
- // Free resources from the DTMFTwelveKeyDialer instance we created
- // in initOtaInCallScreen().
- // if (mOtaCallCardDtmfDialer != null) {
- // mOtaCallCardDtmfDialer.stopDialerSession();
- // }
-
- mOtaWidgetData.otaTextActivate.setVisibility(View.GONE);
- mOtaWidgetData.otaTextListenProgress.setVisibility(View.GONE);
- mOtaWidgetData.otaTextProgressBar.setVisibility(View.GONE);
- mOtaWidgetData.otaTextSuccessFail.setVisibility(View.GONE);
- mOtaWidgetData.callCardOtaButtonsActivate.setVisibility(View.GONE);
- mOtaWidgetData.callCardOtaButtonsListenProgress.setVisibility(View.GONE);
- mOtaWidgetData.callCardOtaButtonsFailSuccess.setVisibility(View.GONE);
- mOtaWidgetData.otaUpperWidgets.setVisibility(View.GONE);
- // mOtaWidgetData.otaDtmfDialerView.setVisibility(View.GONE);
- mOtaWidgetData.otaNextButton.setVisibility(View.GONE);
- mOtaWidgetData.otaTryAgainButton.setVisibility(View.GONE);
- }
-
- // turn off the speaker in case it was turned on
- // but the OTA call could not be completed
- if (disableSpeaker) {
- setSpeaker(false);
- }
- }
-
- /**
- * Defines OTA information that needs to be maintained during
- * an OTA call when display orientation changes.
- */
- public static class CdmaOtaProvisionData {
- public boolean isOtaCallCommitted;
- public boolean isOtaCallIntentProcessed;
- public boolean inOtaSpcState;
- public int activationCount;
- public long otaSpcUptime;
- }
-
- /**
- * Defines OTA screen configuration items read from config.xml
- * and used to control OTA display.
- */
- public static class CdmaOtaConfigData {
- public int otaShowActivationScreen;
- public int otaShowListeningScreen;
- public int otaShowActivateFailTimes;
- public int otaPlaySuccessFailureTone;
- public boolean configComplete;
- public CdmaOtaConfigData() {
- if (DBG) log("CdmaOtaConfigData constructor!");
- otaShowActivationScreen = OTA_SHOW_ACTIVATION_SCREEN_OFF;
- otaShowListeningScreen = OTA_SHOW_LISTENING_SCREEN_OFF;
- otaShowActivateFailTimes = OTA_SHOW_ACTIVATE_FAIL_COUNT_OFF;
- otaPlaySuccessFailureTone = OTA_PLAY_SUCCESS_FAILURE_TONE_OFF;
- }
- }
-
- /**
- * The state of the OTA InCallScreen UI.
- */
- public static class CdmaOtaInCallScreenUiState {
- public enum State {
- UNDEFINED,
- NORMAL,
- ENDED
- }
-
- public State state;
-
- public CdmaOtaInCallScreenUiState() {
- if (DBG) log("CdmaOtaInCallScreenState: constructor init to UNDEFINED");
- state = CdmaOtaInCallScreenUiState.State.UNDEFINED;
- }
- }
-
- /**
- * Save the Ota InCallScreen UI state
- */
- public void setCdmaOtaInCallScreenUiState(CdmaOtaInCallScreenUiState.State state) {
- if (DBG) log("setCdmaOtaInCallScreenState: " + state);
- mApplication.cdmaOtaInCallScreenUiState.state = state;
- }
-
- /**
- * Get the Ota InCallScreen UI state
- */
- public CdmaOtaInCallScreenUiState.State getCdmaOtaInCallScreenUiState() {
- if (DBG) log("getCdmaOtaInCallScreenState: "
- + mApplication.cdmaOtaInCallScreenUiState.state);
- return mApplication.cdmaOtaInCallScreenUiState.state;
- }
-
- /**
- * The OTA screen state machine.
- */
- public static class CdmaOtaScreenState {
- public enum OtaScreenState {
- OTA_STATUS_UNDEFINED,
- OTA_STATUS_ACTIVATION,
- OTA_STATUS_LISTENING,
- OTA_STATUS_PROGRESS,
- OTA_STATUS_SUCCESS_FAILURE_DLG
- }
-
- public OtaScreenState otaScreenState;
-
- public CdmaOtaScreenState() {
- otaScreenState = OtaScreenState.OTA_STATUS_UNDEFINED;
- }
-
- /**
- * {@link PendingIntent} used to report an OTASP result status code
- * back to our caller. Can be null.
- *
- * Our caller (presumably SetupWizard) may create this PendingIntent,
- * pointing back at itself, and passes it along as an extra with the
- * ACTION_PERFORM_CDMA_PROVISIONING intent. Then, when there's an
- * OTASP result to report, we send that PendingIntent back, adding an
- * extra called EXTRA_OTASP_RESULT_CODE to indicate the result.
- *
- * Possible result values are the OTASP_RESULT_* constants.
- */
- public PendingIntent otaspResultCodePendingIntent;
- }
-
- /** @see com.android.internal.telephony.Phone */
- private static String otaProvisionStatusToString(int status) {
- switch (status) {
- case Phone.CDMA_OTA_PROVISION_STATUS_SPL_UNLOCKED:
- return "SPL_UNLOCKED";
- case Phone.CDMA_OTA_PROVISION_STATUS_SPC_RETRIES_EXCEEDED:
- return "SPC_RETRIES_EXCEEDED";
- case Phone.CDMA_OTA_PROVISION_STATUS_A_KEY_EXCHANGED:
- return "A_KEY_EXCHANGED";
- case Phone.CDMA_OTA_PROVISION_STATUS_SSD_UPDATED:
- return "SSD_UPDATED";
- case Phone.CDMA_OTA_PROVISION_STATUS_NAM_DOWNLOADED:
- return "NAM_DOWNLOADED";
- case Phone.CDMA_OTA_PROVISION_STATUS_MDN_DOWNLOADED:
- return "MDN_DOWNLOADED";
- case Phone.CDMA_OTA_PROVISION_STATUS_IMSI_DOWNLOADED:
- return "IMSI_DOWNLOADED";
- case Phone.CDMA_OTA_PROVISION_STATUS_PRL_DOWNLOADED:
- return "PRL_DOWNLOADED";
- case Phone.CDMA_OTA_PROVISION_STATUS_COMMITTED:
- return "COMMITTED";
- case Phone.CDMA_OTA_PROVISION_STATUS_OTAPA_STARTED:
- return "OTAPA_STARTED";
- case Phone.CDMA_OTA_PROVISION_STATUS_OTAPA_STOPPED:
- return "OTAPA_STOPPED";
- case Phone.CDMA_OTA_PROVISION_STATUS_OTAPA_ABORTED:
- return "OTAPA_ABORTED";
- default:
- return "<unknown status" + status + ">";
- }
- }
-
- private static int getLteOnCdmaMode(Context context) {
- final TelephonyManager telephonyManager = (TelephonyManager) context.getSystemService(
- Context.TELEPHONY_SERVICE);
- // If the telephony manager is not available yet, or if it doesn't know the answer yet,
- // try falling back on the system property that may or may not be there
- if (telephonyManager == null
- || telephonyManager.getLteOnCdmaMode() == PhoneConstants.LTE_ON_CDMA_UNKNOWN) {
- return SystemProperties.getInt(TelephonyProperties.PROPERTY_LTE_ON_CDMA_DEVICE,
- PhoneConstants.LTE_ON_CDMA_UNKNOWN);
- }
- return telephonyManager.getLteOnCdmaMode();
- }
-
- private static void log(String msg) {
- Log.d(LOG_TAG, msg);
- }
-
- private static void loge(String msg) {
- Log.e(LOG_TAG, msg);
- }
-}
diff --git a/src/com/android/phone/OutgoingCallBroadcaster.java b/src/com/android/phone/OutgoingCallBroadcaster.java
index cfe6f32..dab2077 100644
--- a/src/com/android/phone/OutgoingCallBroadcaster.java
+++ b/src/com/android/phone/OutgoingCallBroadcaster.java
@@ -190,47 +190,6 @@
final PhoneGlobals app = PhoneGlobals.getInstance();
final Phone phone = PhoneGlobals.getPhone();
- // OTASP-specific checks.
- // TODO: This should probably all happen in
- // OutgoingCallBroadcaster.onCreate(), since there's no reason to
- // even bother with the NEW_OUTGOING_CALL broadcast if we're going
- // to disallow the outgoing call anyway...
- if (TelephonyCapabilities.supportsOtasp(phone)) {
- boolean activateState = (app.cdmaOtaScreenState.otaScreenState
- == OtaUtils.CdmaOtaScreenState.OtaScreenState.OTA_STATUS_ACTIVATION);
- boolean dialogState = (app.cdmaOtaScreenState.otaScreenState
- == OtaUtils.CdmaOtaScreenState.OtaScreenState
- .OTA_STATUS_SUCCESS_FAILURE_DLG);
- boolean isOtaCallActive = false;
-
- // TODO: Need cleaner way to check if OTA is active.
- // Also, this check seems to be broken in one obscure case: if
- // you interrupt an OTASP call by pressing Back then Skip,
- // otaScreenState somehow gets left in either PROGRESS or
- // LISTENING.
- if ((app.cdmaOtaScreenState.otaScreenState
- == OtaUtils.CdmaOtaScreenState.OtaScreenState.OTA_STATUS_PROGRESS)
- || (app.cdmaOtaScreenState.otaScreenState
- == OtaUtils.CdmaOtaScreenState.OtaScreenState.OTA_STATUS_LISTENING)) {
- isOtaCallActive = true;
- }
-
- if (activateState || dialogState) {
- // The OTASP sequence is active, but either (1) the call
- // hasn't started yet, or (2) the call has ended and we're
- // showing the success/failure screen. In either of these
- // cases it's OK to make a new outgoing call, but we need
- // to take down any OTASP-related UI first.
- if (dialogState) app.dismissOtaDialogs();
- app.clearOtaState();
- } else if (isOtaCallActive) {
- // The actual OTASP call is active. Don't allow new
- // outgoing calls at all from this state.
- Log.w(TAG, "OTASP call is active: disallowing a new outgoing call.");
- return false;
- }
- }
-
if (number == null) {
if (DBG) Log.v(TAG, "CALL cancelled (null number), returning...");
return false;
diff --git a/src/com/android/phone/PhoneGlobals.java b/src/com/android/phone/PhoneGlobals.java
index cec5a76..5008604 100644
--- a/src/com/android/phone/PhoneGlobals.java
+++ b/src/com/android/phone/PhoneGlobals.java
@@ -159,26 +159,6 @@
// Broadcast receiver for various intent broadcasts (see onCreate())
private final BroadcastReceiver mReceiver = new PhoneAppBroadcastReceiver();
- /**
- * The singleton OtaUtils instance used for OTASP calls.
- *
- * The OtaUtils instance is created lazily the first time we need to
- * make an OTASP call, regardless of whether it's an interactive or
- * non-interactive OTASP call.
- */
- public OtaUtils otaUtils;
-
- // Following are the CDMA OTA information Objects used during OTA Call.
- // cdmaOtaProvisionData object store static OTA information that needs
- // to be maintained even during Slider open/close scenarios.
- // cdmaOtaConfigData object stores configuration info to control visiblity
- // of each OTA Screens.
- // cdmaOtaScreenState object store OTA Screen State information.
- public OtaUtils.CdmaOtaProvisionData cdmaOtaProvisionData;
- public OtaUtils.CdmaOtaConfigData cdmaOtaConfigData;
- public OtaUtils.CdmaOtaScreenState cdmaOtaScreenState;
- public OtaUtils.CdmaOtaInCallScreenUiState cdmaOtaInCallScreenUiState;
-
Handler mHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
@@ -366,11 +346,6 @@
PhoneUtils.setAudioMode(mCM);
}
- cdmaOtaProvisionData = new OtaUtils.CdmaOtaProvisionData();
- cdmaOtaConfigData = new OtaUtils.CdmaOtaConfigData();
- cdmaOtaScreenState = new OtaUtils.CdmaOtaScreenState();
- cdmaOtaInCallScreenUiState = new OtaUtils.CdmaOtaInCallScreenUiState();
-
// XXX pre-load the SimProvider so that it's ready
resolver.getType(Uri.parse("content://icc/adn"));
@@ -434,43 +409,6 @@
}
/**
- * Handles OTASP-related events from the telephony layer.
- *
- * While an OTASP call is active, the CallNotifier forwards
- * OTASP-related telephony events to this method.
- */
- void handleOtaspEvent(Message msg) {
- if (DBG) Log.d(LOG_TAG, "handleOtaspEvent(message " + msg + ")...");
-
- if (otaUtils == null) {
- // We shouldn't be getting OTASP events without ever
- // having started the OTASP call in the first place!
- Log.w(LOG_TAG, "handleOtaEvents: got an event but otaUtils is null! "
- + "message = " + msg);
- return;
- }
-
- otaUtils.onOtaProvisionStatusChanged((AsyncResult) msg.obj);
- }
-
- /**
- * Similarly, handle the disconnect event of an OTASP call
- * by forwarding it to the OtaUtils instance.
- */
- /* package */ void handleOtaspDisconnect() {
- if (DBG) Log.d(LOG_TAG, "handleOtaspDisconnect()...");
-
- if (otaUtils == null) {
- // We shouldn't be getting OTASP events without ever
- // having started the OTASP call in the first place!
- Log.w(LOG_TAG, "handleOtaspDisconnect: otaUtils is null!");
- return;
- }
-
- otaUtils.onOtaspDisconnect();
- }
-
- /**
* Sets the activity responsible for un-PUK-blocking the device
* so that we may close it when we receive a positive result.
* mPUKEntryActivity is also used to indicate to the device that
@@ -618,15 +556,8 @@
PhoneUtils.displayMMIComplete(mmiCode.getPhone(), getInstance(), mmiCode, null, null);
}
- private void initForNewRadioTechnology(int phoneId) {
+ private void initForNewRadioTechnology() {
if (DBG) Log.d(LOG_TAG, "initForNewRadioTechnology...");
-
- final Phone phone = PhoneFactory.getPhone(phoneId);
- if (phone == null || !TelephonyCapabilities.supportsOtasp(phone)) {
- // Clean up OTA for non-CDMA since it is only valid for CDMA.
- clearOtaState();
- }
-
notifier.updateCallNotifierRegistrationsAfterRadioTechnologyChange();
}
@@ -758,16 +689,13 @@
intent.getStringExtra(IccCardConstants.INTENT_KEY_ICC_STATE)));
} else if (action.equals(TelephonyIntents.ACTION_RADIO_TECHNOLOGY_CHANGED)) {
String newPhone = intent.getStringExtra(PhoneConstants.PHONE_NAME_KEY);
- int phoneId = intent.getIntExtra(PhoneConstants.PHONE_KEY,
- SubscriptionManager.INVALID_PHONE_INDEX);
- Log.d(LOG_TAG, "Radio technology switched. Now " + newPhone + " (" + phoneId
- + ") is active.");
- initForNewRadioTechnology(phoneId);
+ Log.d(LOG_TAG, "Radio technology switched. Now " + newPhone + " is active.");
+ initForNewRadioTechnology();
} else if (action.equals(TelephonyIntents.ACTION_SERVICE_STATE_CHANGED)) {
handleServiceStateChanged(intent);
} else if (action.equals(TelephonyIntents.ACTION_EMERGENCY_CALLBACK_MODE_CHANGED)) {
int phoneId = intent.getIntExtra(PhoneConstants.PHONE_KEY, 0);
- phoneInEcm = getPhone(phoneId);
+ phoneInEcm = PhoneFactory.getPhone(phoneId);
Log.d(LOG_TAG, "Emergency Callback Mode. phoneId:" + phoneId);
if (phoneInEcm != null) {
if (TelephonyCapabilities.supportsEcm(phoneInEcm)) {
@@ -812,24 +740,6 @@
}
}
- // it is safe to call clearOtaState() even if the InCallScreen isn't active
- public void clearOtaState() {
- if (DBG) Log.d(LOG_TAG, "- clearOtaState ...");
- if (otaUtils != null) {
- otaUtils.cleanOtaScreen(true);
- if (DBG) Log.d(LOG_TAG, " - clearOtaState clears OTA screen");
- }
- }
-
- // it is safe to call dismissOtaDialogs() even if the InCallScreen isn't active
- public void dismissOtaDialogs() {
- if (DBG) Log.d(LOG_TAG, "- dismissOtaDialogs ...");
- if (otaUtils != null) {
- otaUtils.dismissAllOtaDialogs();
- if (DBG) Log.d(LOG_TAG, " - dismissOtaDialogs clears OTA dialogs");
- }
- }
-
public Phone getPhoneInEcm() {
return phoneInEcm;
}
diff --git a/src/com/android/phone/PhoneInterfaceManager.java b/src/com/android/phone/PhoneInterfaceManager.java
index b1ad364..da58d2b 100644
--- a/src/com/android/phone/PhoneInterfaceManager.java
+++ b/src/com/android/phone/PhoneInterfaceManager.java
@@ -38,6 +38,7 @@
import android.os.ServiceManager;
import android.os.UserHandle;
import android.os.UserManager;
+import android.os.WorkSource;
import android.preference.PreferenceManager;
import android.provider.Settings;
import android.service.carrier.CarrierIdentifier;
@@ -46,6 +47,7 @@
import android.telecom.TelecomManager;
import android.telephony.CarrierConfigManager;
import android.telephony.CellInfo;
+import android.telephony.ClientRequestStats;
import android.telephony.IccOpenLogicalChannelResponse;
import android.telephony.ModemActivityInfo;
import android.telephony.NeighboringCellInfo;
@@ -81,7 +83,9 @@
import com.android.internal.telephony.SubscriptionController;
import com.android.internal.telephony.uicc.IccIoResult;
import com.android.internal.telephony.uicc.IccUtils;
+import com.android.internal.telephony.uicc.SIMRecords;
import com.android.internal.telephony.uicc.UiccCard;
+import com.android.internal.telephony.uicc.UiccCardApplication;
import com.android.internal.telephony.uicc.UiccController;
import com.android.internal.util.HexDump;
import com.android.phone.settings.VisualVoicemailSettingsUtil;
@@ -149,6 +153,8 @@
private static final int EVENT_SET_ALLOWED_CARRIERS_DONE = 44;
private static final int CMD_GET_ALLOWED_CARRIERS = 45;
private static final int EVENT_GET_ALLOWED_CARRIERS_DONE = 46;
+ private static final int CMD_GET_FORBIDDEN_PLMNS = 48;
+ private static final int EVENT_GET_FORBIDDEN_PLMNS_DONE = 49;
/** The singleton instance. */
private static PhoneInterfaceManager sInstance;
@@ -275,7 +281,7 @@
request = (MainThreadRequest) msg.obj;
onCompleted = obtainMessage(EVENT_NEIGHBORING_CELL_DONE,
request);
- mPhone.getNeighboringCids(onCompleted);
+ mPhone.getNeighboringCids(onCompleted, (WorkSource)request.argument);
break;
case EVENT_NEIGHBORING_CELL_DONE:
@@ -833,6 +839,56 @@
}
break;
+ case EVENT_GET_FORBIDDEN_PLMNS_DONE:
+ ar = (AsyncResult) msg.obj;
+ request = (MainThreadRequest) ar.userObj;
+ if (ar.exception == null && ar.result != null) {
+ request.result = ar.result;
+ } else {
+ request.result = new IllegalArgumentException(
+ "Failed to retrieve Forbidden Plmns");
+ if (ar.result == null) {
+ loge("getForbiddenPlmns: Empty response");
+ } else {
+ loge("getForbiddenPlmns: Unknown exception");
+ }
+ }
+ synchronized (request) {
+ request.notifyAll();
+ }
+ break;
+
+ case CMD_GET_FORBIDDEN_PLMNS:
+ request = (MainThreadRequest) msg.obj;
+ uiccCard = getUiccCardFromRequest(request);
+ if (uiccCard == null) {
+ loge("getForbiddenPlmns() UiccCard is null");
+ request.result = new IllegalArgumentException(
+ "getForbiddenPlmns() UiccCard is null");
+ synchronized (request) {
+ request.notifyAll();
+ }
+ break;
+ }
+ Integer appType = (Integer) request.argument;
+ UiccCardApplication uiccApp = uiccCard.getApplicationByType(appType);
+ if (uiccApp == null) {
+ loge("getForbiddenPlmns() no app with specified type -- "
+ + appType);
+ request.result = new IllegalArgumentException("Failed to get UICC App");
+ synchronized (request) {
+ request.notifyAll();
+ }
+ break;
+ } else {
+ if (DBG) logv("getForbiddenPlmns() found app " + uiccApp.getAid()
+ + " specified type -- " + appType);
+ }
+ onCompleted = obtainMessage(EVENT_GET_FORBIDDEN_PLMNS_DONE, request);
+ ((SIMRecords) uiccApp.getIccRecords()).getForbiddenPlmns(
+ onCompleted);
+ break;
+
default:
Log.w(LOG_TAG, "MainThreadHandler: unexpected message code: " + msg.what);
break;
@@ -1526,7 +1582,9 @@
if (phone == null) {
return null;
}
- phone.getCellLocation().fillInNotifierBundle(data);
+
+ WorkSource workSource = getWorkSource(null, Binder.getCallingUid());
+ phone.getCellLocation(workSource).fillInNotifierBundle(data);
return data;
} else {
log("getCellLocation: suppress non-active user");
@@ -1600,9 +1658,10 @@
ArrayList<NeighboringCellInfo> cells = null;
+ WorkSource workSource = getWorkSource(null, Binder.getCallingUid());
try {
cells = (ArrayList<NeighboringCellInfo>) sendRequest(
- CMD_HANDLE_NEIGHBORING_CELL, null,
+ CMD_HANDLE_NEIGHBORING_CELL, workSource,
SubscriptionManager.INVALID_SUBSCRIPTION_ID);
} catch (RuntimeException e) {
Log.e(LOG_TAG, "getNeighboringCellInfo " + e);
@@ -1628,10 +1687,11 @@
if (checkIfCallerIsSelfOrForegroundUser() ||
checkCallerInteractAcrossUsersFull()) {
if (DBG_LOC) log("getAllCellInfo: is active user");
+ WorkSource workSource = getWorkSource(null, Binder.getCallingUid());
List<CellInfo> cellInfos = new ArrayList<CellInfo>();
for (Phone phone : PhoneFactory.getPhones()) {
- final List<CellInfo> info = phone.getAllCellInfo();
- if (info != null) cellInfos.addAll(phone.getAllCellInfo());
+ final List<CellInfo> info = phone.getAllCellInfo(workSource);
+ if (info != null) cellInfos.addAll(info);
}
return cellInfos;
} else {
@@ -1642,7 +1702,8 @@
@Override
public void setCellInfoListRate(int rateInMillis) {
- mPhone.setCellInfoListRate(rateInMillis);
+ WorkSource workSource = getWorkSource(null, Binder.getCallingUid());
+ mPhone.setCellInfoListRate(rateInMillis, workSource);
}
@Override
@@ -1960,6 +2021,66 @@
.getVisualVoicemailSmsFilterSettings(mPhone.getContext(), packageName, subId);
}
/**
+ * Sets the voice activation state of a given subId.
+ */
+ @Override
+ public void setVoiceActivationState(int subId, int activationState) {
+ enforceModifyPermissionOrCarrierPrivilege(subId);
+ final Phone phone = getPhone(subId);
+ if (phone != null) {
+ phone.setVoiceActivationState(activationState);
+ } else {
+ loge("setVoiceActivationState fails with invalid subId: " + subId);
+ }
+ }
+
+ /**
+ * Sets the data activation state of a given subId.
+ */
+ @Override
+ public void setDataActivationState(int subId, int activationState) {
+ enforceModifyPermissionOrCarrierPrivilege(subId);
+ final Phone phone = getPhone(subId);
+ if (phone != null) {
+ phone.setDataActivationState(activationState);
+ } else {
+ loge("setVoiceActivationState fails with invalid subId: " + subId);
+ }
+ }
+
+ /**
+ * Returns the voice activation state of a given subId.
+ */
+ @Override
+ public int getVoiceActivationState(int subId, String callingPackage) {
+ if (!canReadPhoneState(callingPackage, "getVoiceActivationStateForSubscriber")) {
+ return TelephonyManager.SIM_ACTIVATION_STATE_UNKNOWN;
+ }
+ final Phone phone = getPhone(subId);
+ if (phone != null) {
+ return phone.getVoiceActivationState();
+ } else {
+ return TelephonyManager.SIM_ACTIVATION_STATE_UNKNOWN;
+ }
+ }
+
+ /**
+ * Returns the data activation state of a given subId.
+ */
+ @Override
+ public int getDataActivationState(int subId, String callingPackage) {
+ if (!canReadPhoneState(callingPackage, "getDataActivationStateForSubscriber")) {
+ return TelephonyManager.SIM_ACTIVATION_STATE_UNKNOWN;
+ }
+ final Phone phone = getPhone(subId);
+ if (phone != null) {
+ return phone.getDataActivationState();
+ } else {
+ return TelephonyManager.SIM_ACTIVATION_STATE_UNKNOWN;
+ }
+ }
+
+ /**
* Returns the unread count of voicemails
*/
public int getVoiceMessageCount() {
@@ -2255,6 +2376,26 @@
return result;
}
+ /**
+ * Get the forbidden PLMN List from the given app type (ex APPTYPE_USIM)
+ * on a particular subscription
+ */
+ public String[] getForbiddenPlmns(int subId, int appType) {
+ mApp.enforceCallingOrSelfPermission(android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE,
+ "Requires READ_PRIVILEGED_PHONE_STATE");
+ if (appType != TelephonyManager.APPTYPE_USIM && appType != TelephonyManager.APPTYPE_SIM) {
+ loge("getForbiddenPlmnList(): App Type must be USIM or SIM");
+ return null;
+ }
+ Object response = sendRequest(
+ CMD_GET_FORBIDDEN_PLMNS, new Integer(appType), subId);
+ if (response instanceof String[]) {
+ return (String[]) response;
+ }
+ // Response is an Exception of some kind, which is signalled to the user as a NULL retval
+ return null;
+ }
+
@Override
public String sendEnvelopeWithStatus(int subId, String content) {
enforceModifyPermissionOrCarrierPrivilege(subId);
@@ -2816,6 +2957,7 @@
}
@Override
+ @Deprecated
public int invokeOemRilRequestRaw(byte[] oemReq, byte[] oemResp) {
enforceModifyPermission();
@@ -3408,4 +3550,54 @@
phone.setPolicyDataEnabled(enabled);
}
}
+
+ /**
+ * Get Client request stats
+ * @return List of Client Request Stats
+ * @hide
+ */
+ @Override
+ public List<ClientRequestStats> getClientRequestStats(String callingPackage, int subId) {
+ if (!canReadPhoneState(callingPackage, "getClientRequestStats")) {
+ return null;
+ }
+
+ Phone phone = getPhone(subId);
+ if (phone != null) {
+ return phone.getClientRequestStats();
+ }
+
+ return null;
+ }
+
+ private WorkSource getWorkSource(WorkSource workSource, int uid) {
+ if (workSource != null) {
+ return workSource;
+ }
+
+ String packageName = mPhone.getContext().getPackageManager().getNameForUid(uid);
+ workSource = new WorkSource(uid, packageName);
+ return workSource;
+ }
+
+ /**
+ * Set SIM card power state. Request is equivalent to inserting or removing the card.
+ *
+ * @param slotId SIM slot id.
+ * @param powerUp True if powering up the SIM, otherwise powering down
+ *
+ **/
+ @Override
+ public void setSimPowerStateForSlot(int slotId, boolean powerUp) {
+ enforceModifyPermission();
+ int subId[] = mSubscriptionController.getSubIdUsingSlotId(slotId);
+ if (subId == null || subId.length == 0) {
+ return;
+ }
+
+ final Phone phone = getPhone(subId[0]);
+ if (phone != null) {
+ phone.setSimPowerState(powerUp);
+ }
+ }
}
diff --git a/src/com/android/phone/otasp/OtaspActivationService.java b/src/com/android/phone/otasp/OtaspActivationService.java
index 504315f..158925a 100644
--- a/src/com/android/phone/otasp/OtaspActivationService.java
+++ b/src/com/android/phone/otasp/OtaspActivationService.java
@@ -16,12 +16,15 @@
package com.android.phone.otasp;
import android.app.Service;
+import android.content.Context;
import android.content.Intent;
import android.os.AsyncResult;
import android.os.Handler;
import android.os.IBinder;
import android.os.Message;
import android.telephony.ServiceState;
+import android.telephony.SubscriptionManager;
+import android.telephony.TelephonyManager;
import com.android.internal.telephony.Phone;
import com.android.internal.telephony.PhoneConstants;
@@ -80,7 +83,7 @@
logd("OTASP call tried " + sOtaspCallRetries + " times");
if (sOtaspCallRetries > OTASP_CALL_RETRIES_MAX) {
logd("OTASP call exceeds max retries => activation failed");
- //TODO updateActivationState(DEACTIVATED)
+ updateActivationState(this, false);
onComplete();
return;
}
@@ -180,10 +183,10 @@
if (mPhone.getState().equals(PhoneConstants.State.IDLE)) {
if (mIsOtaspCallCommitted) {
logd("Otasp activation succeed");
- //TODO updateActivationState(ACTIVATED)
+ updateActivationState(this, true);
} else {
logd("Otasp activation failed");
- //TODO updateActivationState(DEACTIVATED)
+ updateActivationState(this, false);
}
onComplete();
}
@@ -203,6 +206,15 @@
mHandler.removeCallbacksAndMessages(null);
}
+ public static void updateActivationState(Context context, boolean success) {
+ final TelephonyManager mTelephonyMgr = TelephonyManager.from(context);
+ int state = (success) ? TelephonyManager.SIM_ACTIVATION_STATE_ACTIVATED :
+ TelephonyManager.SIM_ACTIVATION_STATE_DEACTIVATED;
+ int subId = SubscriptionManager.getDefaultSubscriptionId();
+ mTelephonyMgr.setVoiceActivationState(subId, state);
+ mTelephonyMgr.setDataActivationState(subId, state);
+ }
+
private static void logd(String s) {
android.util.Log.d(TAG, s);
}
diff --git a/src/com/android/phone/otasp/OtaspSimStateReceiver.java b/src/com/android/phone/otasp/OtaspSimStateReceiver.java
index ef34e20..c0409ba 100644
--- a/src/com/android/phone/otasp/OtaspSimStateReceiver.java
+++ b/src/com/android/phone/otasp/OtaspSimStateReceiver.java
@@ -36,10 +36,11 @@
@Override
public void onOtaspChanged(int otaspMode) {
logd("onOtaspChanged: otaspMode=" + otaspMode);
- if (otaspMode == ServiceStateTracker.OTASP_NEEDED && isCarrierSupported()
- && PhoneGlobals.getPhone().getIccRecordsLoaded()) {
+ if (otaspMode == ServiceStateTracker.OTASP_NEEDED) {
logd("otasp activation required, start otaspActivationService");
mContext.startService(new Intent(mContext, OtaspActivationService.class));
+ } else if (otaspMode == ServiceStateTracker.OTASP_NOT_NEEDED) {
+ OtaspActivationService.updateActivationState(mContext, true);
}
}
};
@@ -72,9 +73,11 @@
mContext = context;
if(CarrierConfigManager.ACTION_CARRIER_CONFIG_CHANGED.equals(intent.getAction())) {
if (DBG) logd("Received intent: " + intent.getAction());
- final TelephonyManager telephonyManager = (TelephonyManager) context
- .getSystemService(Context.TELEPHONY_SERVICE);
- telephonyManager.listen(mPhoneStateListener, PhoneStateListener.LISTEN_OTASP_CHANGED);
+ if (PhoneGlobals.getPhone().getIccRecordsLoaded() && isCarrierSupported()) {
+ final TelephonyManager telephonyManager = TelephonyManager.from(context);
+ telephonyManager.listen(mPhoneStateListener,
+ PhoneStateListener.LISTEN_OTASP_CHANGED);
+ }
}
}
diff --git a/src/com/android/phone/settings/VoicemailSettingsActivity.java b/src/com/android/phone/settings/VoicemailSettingsActivity.java
index 6bb481f..9db20e8 100644
--- a/src/com/android/phone/settings/VoicemailSettingsActivity.java
+++ b/src/com/android/phone/settings/VoicemailSettingsActivity.java
@@ -24,6 +24,7 @@
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
+import android.os.UserManager;
import android.preference.CheckBoxPreference;
import android.preference.Preference;
import android.preference.PreferenceActivity;
@@ -37,6 +38,8 @@
import android.util.Log;
import android.view.MenuItem;
import android.widget.ListAdapter;
+import android.widget.Toast;
+
import com.android.internal.telephony.CallForwardInfo;
import com.android.internal.telephony.Phone;
import com.android.internal.telephony.PhoneConstants;
@@ -199,7 +202,7 @@
private SubscriptionInfoHelper mSubscriptionInfoHelper;
private OmtpVvmCarrierConfigHelper mOmtpVvmCarrierConfigHelper;
- private EditPhoneNumberPreference mSubMenuVoicemailSettings;
+ private EditPhoneNumberPreference mSubMenuVoicemailSettings = null;
private VoicemailProviderListPreference mVoicemailProviders;
private PreferenceScreen mVoicemailSettings;
private VoicemailRingtonePreference mVoicemailNotificationRingtone;
@@ -214,7 +217,14 @@
@Override
protected void onCreate(Bundle icicle) {
super.onCreate(icicle);
-
+ // Make sure we are running as the primary user only
+ UserManager userManager = getApplicationContext().getSystemService(UserManager.class);
+ if (!userManager.isPrimaryUser()) {
+ Toast.makeText(this, R.string.voice_number_setting_primary_user_only,
+ Toast.LENGTH_SHORT).show();
+ finish();
+ return;
+ }
// Show the voicemail preference in onResume if the calling intent specifies the
// ACTION_ADD_VOICEMAIL action.
mShowVoicemailPreference = (icicle == null) &&
@@ -227,6 +237,7 @@
mPhoneAccountHandle = PhoneUtils.makePstnPhoneAccountHandle(mPhone);
mOmtpVvmCarrierConfigHelper = new OmtpVvmCarrierConfigHelper(
mPhone.getContext(), mPhone.getSubId());
+ addPreferencesFromResource(R.xml.voicemail_settings);
}
@Override
@@ -234,18 +245,17 @@
super.onResume();
mForeground = true;
- PreferenceScreen preferenceScreen = getPreferenceScreen();
- if (preferenceScreen != null) {
- preferenceScreen.removeAll();
- }
-
- addPreferencesFromResource(R.xml.voicemail_settings);
-
PreferenceScreen prefSet = getPreferenceScreen();
- mSubMenuVoicemailSettings = (EditPhoneNumberPreference) findPreference(BUTTON_VOICEMAIL_KEY);
- mSubMenuVoicemailSettings.setParentActivity(this, VOICEMAIL_PREF_ID, this);
- mSubMenuVoicemailSettings.setDialogOnClosedListener(this);
- mSubMenuVoicemailSettings.setDialogTitle(R.string.voicemail_settings_number_label);
+
+ if (mSubMenuVoicemailSettings == null) {
+ mSubMenuVoicemailSettings =
+ (EditPhoneNumberPreference) findPreference(BUTTON_VOICEMAIL_KEY);
+ }
+ if (mSubMenuVoicemailSettings != null) {
+ mSubMenuVoicemailSettings.setParentActivity(this, VOICEMAIL_PREF_ID, this);
+ mSubMenuVoicemailSettings.setDialogOnClosedListener(this);
+ mSubMenuVoicemailSettings.setDialogTitle(R.string.voicemail_settings_number_label);
+ }
mVoicemailProviders = (VoicemailProviderListPreference) findPreference(
BUTTON_VOICEMAIL_PROVIDER_KEY);
@@ -264,34 +274,36 @@
getResources().getString(R.string.voicemail_notification_vibrate_key));
mVoicemailNotificationVibrate.setOnPreferenceChangeListener(this);
- mVoicemailVisualVoicemail = (SwitchPreference) findPreference(
+ mVoicemailVisualVoicemail = (SwitchPreference) prefSet.findPreference(
getResources().getString(R.string.voicemail_visual_voicemail_key));
- mVoicemailChangePinPreference = findPreference(
+ mVoicemailChangePinPreference = prefSet.findPreference(
getResources().getString(R.string.voicemail_change_pin_key));
- Intent changePinIntent = new Intent(new Intent(this, VoicemailChangePinActivity.class));
- changePinIntent.putExtra(VoicemailChangePinActivity.EXTRA_PHONE_ACCOUNT_HANDLE,
- mPhoneAccountHandle);
+ if (mVoicemailChangePinPreference != null) {
+ Intent changePinIntent = new Intent(new Intent(this, VoicemailChangePinActivity.class));
+ changePinIntent.putExtra(VoicemailChangePinActivity.EXTRA_PHONE_ACCOUNT_HANDLE,
+ mPhoneAccountHandle);
- mVoicemailChangePinPreference.setIntent(changePinIntent);
- if (VoicemailChangePinActivity.isDefaultOldPinSet(this, mPhoneAccountHandle)) {
- mVoicemailChangePinPreference.setTitle(R.string.voicemail_set_pin_dialog_title);
- } else {
- mVoicemailChangePinPreference.setTitle(R.string.voicemail_change_pin_dialog_title);
+ mVoicemailChangePinPreference.setIntent(changePinIntent);
+ if (VoicemailChangePinActivity.isDefaultOldPinSet(this, mPhoneAccountHandle)) {
+ mVoicemailChangePinPreference.setTitle(R.string.voicemail_set_pin_dialog_title);
+ } else {
+ mVoicemailChangePinPreference.setTitle(R.string.voicemail_change_pin_dialog_title);
+ }
}
-
- if (mOmtpVvmCarrierConfigHelper.isValid()) {
- mVoicemailVisualVoicemail.setOnPreferenceChangeListener(this);
- mVoicemailVisualVoicemail.setChecked(
- VisualVoicemailSettingsUtil.isEnabled(this, mPhoneAccountHandle));
- if (!isVisualVoicemailActivated()) {
+ if (mVoicemailVisualVoicemail != null) {
+ if (mOmtpVvmCarrierConfigHelper.isValid()) {
+ mVoicemailVisualVoicemail.setOnPreferenceChangeListener(this);
+ mVoicemailVisualVoicemail.setChecked(
+ VisualVoicemailSettingsUtil.isEnabled(this, mPhoneAccountHandle));
+ if (!isVisualVoicemailActivated()) {
+ prefSet.removePreference(mVoicemailChangePinPreference);
+ }
+ } else {
+ prefSet.removePreference(mVoicemailVisualVoicemail);
prefSet.removePreference(mVoicemailChangePinPreference);
}
- } else {
- prefSet.removePreference(mVoicemailVisualVoicemail);
- prefSet.removePreference(mVoicemailChangePinPreference);
}
-
updateVMPreferenceWidgets(mVoicemailProviders.getValue());
// check the intent that started this activity and pop up the voicemail
@@ -348,6 +360,13 @@
dialog.getActionBar().setDisplayHomeAsUpEnabled(false);
}
+ mSubMenuVoicemailSettings =
+ (EditPhoneNumberPreference) findPreference(BUTTON_VOICEMAIL_KEY);
+ mSubMenuVoicemailSettings.setParentActivity(this, VOICEMAIL_PREF_ID, this);
+ mSubMenuVoicemailSettings.setDialogOnClosedListener(this);
+ mSubMenuVoicemailSettings.setDialogTitle(R.string.voicemail_settings_number_label);
+ updateVoiceNumberField();
+
if (preference.getIntent() != null) {
if (DBG) log("Invoking cfg intent " + preference.getIntent().getPackage());
diff --git a/src/com/android/services/telephony/CdmaConnection.java b/src/com/android/services/telephony/CdmaConnection.java
index 8020996..29ccc6c 100644
--- a/src/com/android/services/telephony/CdmaConnection.java
+++ b/src/com/android/services/telephony/CdmaConnection.java
@@ -184,7 +184,7 @@
}
@Override
- public void performConference(TelephonyConnection otherConnection) {
+ public void performConference(android.telecom.Connection otherConnection) {
if (isImsConnection()) {
super.performConference(otherConnection);
} else {
diff --git a/src/com/android/services/telephony/ConferenceParticipantConnection.java b/src/com/android/services/telephony/ConferenceParticipantConnection.java
index ed7ad44..19dda54 100644
--- a/src/com/android/services/telephony/ConferenceParticipantConnection.java
+++ b/src/com/android/services/telephony/ConferenceParticipantConnection.java
@@ -16,6 +16,7 @@
package com.android.services.telephony;
+import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.telephony.Phone;
import com.android.internal.telephony.PhoneConstants;
@@ -70,7 +71,7 @@
address = null;
} else {
String countryIso = getCountryIso(parentConnection.getCall().getPhone());
- address = getParticipantAddress(participant, countryIso);
+ address = getParticipantAddress(participant.getHandle(), countryIso);
}
setAddress(address, presentation);
setCallerDisplayName(participant.getDisplayName(), presentation);
@@ -212,21 +213,19 @@
* Conference event package data contains SIP URIs, so we try to extract the phone number and
* format into a typical tel: style URI.
*
- * @param participant The conference participant.
+ * @param address The conference participant's address.
* @param countryIso The country ISO of the current subscription; used when formatting the
* participant phone number to E.164 format.
* @return The participant's address URI.
*/
- private Uri getParticipantAddress(ConferenceParticipant participant, String countryIso) {
- Uri address = participant.getHandle();
+ @VisibleForTesting
+ public static Uri getParticipantAddress(Uri address, String countryIso) {
if (address == null) {
return address;
}
-
- // If the participant's address is already a TEL scheme, just return it as is.
- if (PhoneAccount.SCHEME_TEL.equals(address.getScheme())) {
- return address;
- }
+ // Even if address is already in tel: format, still parse it and rebuild.
+ // This is to recognize tel URIs such as:
+ // tel:6505551212;phone-context=ims.mnc012.mcc034.3gppnetwork.org
// Conference event package participants are identified using SIP URIs (see RFC3261).
// A valid SIP uri has the format: sip:user:password@host:port;uri-parameters?headers
diff --git a/src/com/android/services/telephony/DisconnectCauseUtil.java b/src/com/android/services/telephony/DisconnectCauseUtil.java
index 534f510..c356899 100644
--- a/src/com/android/services/telephony/DisconnectCauseUtil.java
+++ b/src/com/android/services/telephony/DisconnectCauseUtil.java
@@ -130,6 +130,7 @@
case android.telephony.DisconnectCause.DATA_LIMIT_REACHED:
case android.telephony.DisconnectCause.DIALED_ON_WRONG_SLOT:
case android.telephony.DisconnectCause.IMEI_NOT_ACCEPTED:
+ case android.telephony.DisconnectCause.WIFI_LOST:
return DisconnectCause.ERROR;
case android.telephony.DisconnectCause.DIALED_MMI:
@@ -386,6 +387,10 @@
resourceId = R.string.callFailed_imei_not_accepted;
break;
+ case android.telephony.DisconnectCause.WIFI_LOST:
+ resourceId = R.string.callFailed_wifi_lost;
+ break;
+
default:
break;
}
diff --git a/src/com/android/services/telephony/ImsConference.java b/src/com/android/services/telephony/ImsConference.java
index e33c351..6c4fadc 100644
--- a/src/com/android/services/telephony/ImsConference.java
+++ b/src/com/android/services/telephony/ImsConference.java
@@ -330,6 +330,10 @@
Connection.CAPABILITY_CANNOT_DOWNGRADE_VIDEO_TO_AUDIO,
can(capabilities, Connection.CAPABILITY_CANNOT_DOWNGRADE_VIDEO_TO_AUDIO));
+ conferenceCapabilities = changeBitmask(conferenceCapabilities,
+ Connection.CAPABILITY_CAN_PAUSE_VIDEO,
+ mConferenceHost.getVideoPauseSupported() && isVideoCapable());
+
return conferenceCapabilities;
}
@@ -439,7 +443,7 @@
@Override
public void onMerge(android.telecom.Connection connection) {
try {
- Phone phone = ((TelephonyConnection) connection).getPhone();
+ Phone phone = mConferenceHost.getPhone();
if (phone != null) {
phone.conference();
}
@@ -940,6 +944,16 @@
}
}
+ /**
+ * Determines if the host of this conference is capable of video calling.
+ * @return {@code true} if video capable, {@code false} otherwise.
+ */
+ private boolean isVideoCapable() {
+ int capabilities = mConferenceHost.getConnectionCapabilities();
+ return can(capabilities, Connection.CAPABILITY_SUPPORTS_VT_LOCAL_BIDIRECTIONAL)
+ && can(capabilities, Connection.CAPABILITY_SUPPORTS_VT_REMOTE_BIDIRECTIONAL);
+ }
+
private void updateStatusHints() {
if (mConferenceHost == null) {
setStatusHints(null);
diff --git a/src/com/android/services/telephony/ImsConferenceController.java b/src/com/android/services/telephony/ImsConferenceController.java
index 6669482..4df6444 100644
--- a/src/com/android/services/telephony/ImsConferenceController.java
+++ b/src/com/android/services/telephony/ImsConferenceController.java
@@ -187,6 +187,7 @@
Log.v(this, "recalculateConferenceable : %d", mTelephonyConnections.size());
HashSet<Conferenceable> conferenceableSet = new HashSet<>(mTelephonyConnections.size() +
mImsConferences.size());
+ HashSet<Conferenceable> conferenceParticipantsSet = new HashSet<>();
// Loop through and collect all calls which are active or holding
for (TelephonyConnection connection : mTelephonyConnections) {
@@ -240,6 +241,7 @@
case Connection.STATE_ACTIVE:
//fall through
case Connection.STATE_HOLDING:
+ conferenceParticipantsSet.addAll(conference.getConnections());
conferenceableSet.add(conference);
continue;
default:
@@ -256,6 +258,16 @@
.stream()
.filter(conferenceable -> c != conferenceable)
.collect(Collectors.toList());
+ // TODO: Remove this once RemoteConnection#setConferenceableConnections is fixed.
+ // Add all conference participant connections as conferenceable with a standalone
+ // Connection. We need to do this to ensure that RemoteConnections work properly.
+ // At the current time, a RemoteConnection will not be conferenceable with a
+ // Conference, so we need to add its children to ensure the user can merge the call
+ // into the conference.
+ // We should add support for RemoteConnection#setConferenceables, which accepts a
+ // list of remote conferences and connections in the future.
+ conferenceables.addAll(conferenceParticipantsSet);
+
((Connection) c).setConferenceables(conferenceables);
} else if (c instanceof Conference) {
// Remove all conferences from the set, since we can not conference a conference
@@ -331,6 +343,7 @@
// This is necessary since the Connection Service does not support removing a connection
// from Telecom. Instead we create a new instance and remove the old one from telecom.
TelephonyConnection conferenceHostConnection = connection.cloneConnection();
+ conferenceHostConnection.setVideoPauseSupported(connection.getVideoPauseSupported());
PhoneAccountHandle phoneAccountHandle = null;
diff --git a/src/com/android/services/telephony/TelephonyConnection.java b/src/com/android/services/telephony/TelephonyConnection.java
index ef2b414..5ae1a26 100644
--- a/src/com/android/services/telephony/TelephonyConnection.java
+++ b/src/com/android/services/telephony/TelephonyConnection.java
@@ -683,7 +683,7 @@
}
}
- public void performConference(TelephonyConnection otherConnection) {
+ public void performConference(Connection otherConnection) {
Log.d(this, "performConference - %s", this);
if (getPhone() != null) {
try {
@@ -1549,6 +1549,14 @@
}
/**
+ * @return {@code true} if this connection supports pausing the outgoing video using the
+ * {@link android.telecom.VideoProfile#STATE_PAUSED} VideoState.
+ */
+ public boolean getVideoPauseSupported() {
+ return mIsVideoPauseSupported;
+ }
+
+ /**
* Sets whether this connection supports conference calling.
* @param isConferenceSupported {@code true} if conference calling is supported by this
* connection, {@code false} otherwise.
diff --git a/src/com/android/services/telephony/TelephonyConnectionService.java b/src/com/android/services/telephony/TelephonyConnectionService.java
index 77a7cfb..6e8e61a 100644
--- a/src/com/android/services/telephony/TelephonyConnectionService.java
+++ b/src/com/android/services/telephony/TelephonyConnectionService.java
@@ -42,12 +42,12 @@
import com.android.internal.telephony.Call;
import com.android.internal.telephony.CallStateException;
+import com.android.internal.telephony.GsmCdmaPhone;
import com.android.internal.telephony.IccCard;
import com.android.internal.telephony.IccCardConstants;
import com.android.internal.telephony.Phone;
import com.android.internal.telephony.PhoneConstants;
import com.android.internal.telephony.PhoneFactory;
-import com.android.internal.telephony.SubscriptionController;
import com.android.internal.telephony.imsphone.ImsExternalCallTracker;
import com.android.internal.telephony.imsphone.ImsPhone;
import com.android.phone.MMIDialogActivity;
@@ -617,14 +617,35 @@
}
}
+ /**
+ * Conferences two connections.
+ *
+ * Note: The {@link android.telecom.RemoteConnection#setConferenceableConnections(List)} API has
+ * a limitation in that it can only specify conferenceables which are instances of
+ * {@link android.telecom.RemoteConnection}. In the case of an {@link ImsConference}, the
+ * regular {@link Connection#setConferenceables(List)} API properly handles being able to merge
+ * a {@link Conference} and a {@link Connection}. As a result when, merging a
+ * {@link android.telecom.RemoteConnection} into a {@link android.telecom.RemoteConference}
+ * require merging a {@link ConferenceParticipantConnection} which is a child of the
+ * {@link Conference} with a {@link TelephonyConnection}. The
+ * {@link ConferenceParticipantConnection} class does not have the capability to initiate a
+ * conference merge, so we need to call
+ * {@link TelephonyConnection#performConference(Connection)} on either {@code connection1} or
+ * {@code connection2}, one of which is an instance of {@link TelephonyConnection}.
+ *
+ * @param connection1 A connection to merge into a conference call.
+ * @param connection2 A connection to merge into a conference call.
+ */
@Override
public void onConference(Connection connection1, Connection connection2) {
- if (connection1 instanceof TelephonyConnection &&
- connection2 instanceof TelephonyConnection) {
- ((TelephonyConnection) connection1).performConference(
- (TelephonyConnection) connection2);
+ if (connection1 instanceof TelephonyConnection) {
+ ((TelephonyConnection) connection1).performConference(connection2);
+ } else if (connection2 instanceof TelephonyConnection) {
+ ((TelephonyConnection) connection2).performConference(connection1);
+ } else {
+ Log.w(this, "onConference - cannot merge connections " +
+ "Connection1: %s, Connection2: %2", connection1, connection2);
}
-
}
private boolean isRadioOn() {
@@ -706,6 +727,18 @@
try {
if (phone != null) {
originalConnection = phone.dial(number, null, videoState, extras);
+
+ if (phone instanceof GsmCdmaPhone) {
+ GsmCdmaPhone gsmCdmaPhone = (GsmCdmaPhone) phone;
+ if (gsmCdmaPhone.isNotificationOfWfcCallRequired(number)) {
+ // Send connection event to InCall UI to inform the user of the fact they
+ // are potentially placing an international call on WFC.
+ Log.i(this, "placeOutgoingConnection - sending international call on WFC " +
+ "confirmation event");
+ connection.sendConnectionEvent(
+ TelephonyManager.EVENT_NOTIFY_INTERNATIONAL_CALL_ON_WFC, null);
+ }
+ }
}
} catch (CallStateException e) {
Log.e(this, e, "placeOutgoingConnection, phone.dial exception: " + e);
@@ -781,7 +814,7 @@
Phone chosenPhone = null;
int subId = PhoneUtils.getSubIdForPhoneAccountHandle(accountHandle);
if (subId != SubscriptionManager.INVALID_SUBSCRIPTION_ID) {
- int phoneId = SubscriptionController.getInstance().getPhoneId(subId);
+ int phoneId = SubscriptionManager.getPhoneId(subId);
chosenPhone = PhoneFactory.getPhone(phoneId);
}
// If this is an emergency call and the phone we originally planned to make this call
diff --git a/tests/AndroidManifest.xml b/tests/AndroidManifest.xml
index 7962738..0aa5be2 100644
--- a/tests/AndroidManifest.xml
+++ b/tests/AndroidManifest.xml
@@ -38,16 +38,6 @@
</intent-filter>
</activity>
- <!-- Test activity mimicking the PERFORM_CDMA_PROVISIONING behavior of
- SetupWizard, useful for testing "non-interactive" OTASP. -->
- <activity android:name="OtaspTestActivity"
- android:label="OtaspTest">
- <intent-filter>
- <action android:name="android.intent.action.MAIN" />
- <category android:name="android.intent.category.DEFAULT" />
- </intent-filter>
- </activity>
-
<service android:name="SendInstantTextTestService"
android:permission="android.permission.SEND_RESPOND_VIA_MESSAGE" >
<intent-filter>
diff --git a/tests/src/com/android/phone/tests/OtaspTestActivity.java b/tests/src/com/android/phone/tests/OtaspTestActivity.java
deleted file mode 100644
index ead86c3..0000000
--- a/tests/src/com/android/phone/tests/OtaspTestActivity.java
+++ /dev/null
@@ -1,267 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.phone.tests;
-
-import android.app.Activity;
-import android.app.PendingIntent;
-import android.content.ActivityNotFoundException;
-import android.content.Intent;
-import android.os.Bundle;
-import android.util.Log;
-import android.view.View;
-import android.widget.Button;
-import android.widget.ProgressBar;
-import android.widget.TextView;
-
-import com.android.phone.OtaUtils;
-
-/**
- * Test activity that mimics the PERFORM_CDMA_PROVISIONING behavior of
- * SetupWizard, useful for testing "non-interactive" OTASP.
- * @see OtaUtils.startNonInteractiveOtasp
- *
- */
-public class OtaspTestActivity extends Activity implements View.OnClickListener {
- private static final String LOG_TAG = "OtaspTestActivity";
-
- // Request code used with startActivityForResult()
- private static final int PERFORM_CDMA_PROVISIONING_REQUEST_CODE = 1;
-
- // UI elements
- private TextView mLabel;
- private ProgressBar mProgressBar;
- private TextView mResult;
- private Button mButton;
-
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- Intent intent = getIntent();
- Log.i(LOG_TAG, "##### onCreate: intent = " + intent);
- Bundle extras = intent.getExtras();
- if (extras != null) {
- Log.i(LOG_TAG, " - has extras: size = " + extras.size()); // forces an unparcel()
- Log.i(LOG_TAG, " - extras = " + extras);
- }
-
- // Construct our basic UI:
- super.onCreate(savedInstanceState);
- setContentView(R.layout.otasp_test_activity);
-
- mLabel = (TextView) findViewById(R.id.label1);
- mLabel.setText("OTA Test Activity");
-
- mProgressBar = (ProgressBar) findViewById(R.id.progress_bar);
- mResult = (TextView) findViewById(R.id.result1);
-
- mButton = (Button) findViewById(R.id.button1);
- mButton.setText("Make test call");
- mButton.setOnClickListener(this);
-
-
- // We can be launched either:
- //
- // (1) Directly from the launcher, in which case the current intent
- // will simply be an ACTION_MAIN intent
- //
- // (2) Via the PendingIntent that we sent along (when we originally
- // fired off the ACTION_PERFORM_CDMA_PROVISIONING intent) that
- // allows the phone app to send us back a result code.
- // We can identify this case by the presence of the
- // EXTRA_OTASP_RESULT_CODE extra.
-
- if (intent.hasExtra(OtaUtils.EXTRA_OTASP_RESULT_CODE)) {
- // Got a result from the OTASP call!
- Log.i(LOG_TAG, "==> onCreate: got a result from the OTASP call!");
-
- int resultCode = intent.getIntExtra(OtaUtils.EXTRA_OTASP_RESULT_CODE,
- OtaUtils.OTASP_UNKNOWN);
- Log.i(LOG_TAG, " - resultCode = " + resultCode);
-
- String resultString;
- switch (resultCode) {
- case OtaUtils.OTASP_USER_SKIPPED:
- resultString = "User skipped!";
- break;
- case OtaUtils.OTASP_SUCCESS:
- resultString = "Success!";
- break;
- case OtaUtils.OTASP_FAILURE:
- resultString = "FAILURE";
- break;
- default:
- resultString = "Unexpected code: " + resultCode;
- break;
- }
- Log.i(LOG_TAG, " - result: " + resultString);
- mResult.setText(resultString);
- mResult.setVisibility(View.VISIBLE);
- mProgressBar.setVisibility(View.INVISIBLE);
-
- } else {
- // We must have gotten here directly from the launcher.
- // Leave the UI in its initial state.
- Log.i(LOG_TAG, "==> onCreate: entered from the launcher.");
- }
- }
-
- @Override
- protected void onNewIntent(Intent intent) {
- Log.i(LOG_TAG, "onNewIntent: intent=" + intent);
- Bundle extras = intent.getExtras();
- if (extras != null) Log.i(LOG_TAG, " - intent extras = " + extras);
-
- // This method isn't actually used since this test activity is not
- // launched in "singleTop" mode.
-
- // Activities that *are* launched in singleTop mode, like the SetupWizard,
- // would have to handle the various PendingIntents here just like
- // we do above in onCreate().
- }
-
- @Override
- protected void onActivityResult(int requestCode, int resultCode, Intent data) {
- Log.i(LOG_TAG, "onActivityResult: request " + requestCode
- + " result " + resultCode + " data " + data);
-
- // Note we receive this call immediately before onResume(), when
- // we get re-started after launching the PERFORM_CDMA_PROVISIONING
- // intent.
-
- if (requestCode == PERFORM_CDMA_PROVISIONING_REQUEST_CODE) {
- // The InCallScreenShowActivation activity can set the following
- // result codes:
- //
- // RESULT_INTERACTIVE_OTASP_STARTED
- // RESULT_NONINTERACTIVE_OTASP_STARTED
- // RESULT_NONINTERACTIVE_OTASP_FAILED
- //
- // but note that in practice we won't ever *get* the
- // RESULT_INTERACTIVE_OTASP_STARTED result code, since the
- // "interactive" OTASP sequence never actually finish()es;
- // it ends by directly launching the Home activity.
- //
- // However, in non-interactive OTASP, the
- // InCallScreenShowActivation activity will set one of the
- // RESULT_NONINTERACTIVE_* codes and immediately
- // finish(), so we *will* see that result here.
- //
- // Also, resultCode will be RESULT_CANCELED (= 0) if the
- // InCallScreenShowActivation activity didn't return any
- // result, or crashed.
-
- switch (resultCode) {
- case OtaUtils.RESULT_INTERACTIVE_OTASP_STARTED:
- Log.i(LOG_TAG, "==> onActivityResult: INTERACTIVE_OTASP_STARTED");
- break;
- case OtaUtils.RESULT_NONINTERACTIVE_OTASP_STARTED:
- Log.i(LOG_TAG, "==> onActivityResult: NONINTERACTIVE_OTASP_STARTED");
- break;
- case OtaUtils.RESULT_NONINTERACTIVE_OTASP_FAILED:
- Log.w(LOG_TAG, "==> onActivityResult: NONINTERACTIVE_OTASP_FAILED");
- // This means we couldn't even *initiate* an outgoing call
- // to start the OTASP process. Not sure what could cause this.
- // TODO: Update UI to indicate the error.
- break;
- case RESULT_CANCELED:
- Log.i(LOG_TAG, "==> onActivityResult: CANCELED");
- break;
- default:
- Log.i(LOG_TAG, "==> onActivityResult: unknown result: " + resultCode);
- break;
- }
- }
- }
-
- @Override
- protected void onResume() {
- Log.i(LOG_TAG, "onResume()...");
- super.onResume();
- }
-
- @Override
- protected void onPause() {
- Log.i(LOG_TAG, "onPause()...");
- super.onPause();
- }
-
- // View.OnClickListener implementation
- @Override
- public void onClick(View view) {
- int id = view.getId();
- Log.i(LOG_TAG, "onClick(View " + view + ", id " + id + ")...");
-
- switch (id) {
- case R.id.button1:
- Log.i(LOG_TAG, "onClick: button1...");
- makeTestCall();
- break;
- default:
- Log.w(LOG_TAG, "onClick: unexpected View: " + view);
- break;
- }
- }
-
- private void makeTestCall() {
- Log.i(LOG_TAG, "##### makeTestCall()...");
-
- mProgressBar.setVisibility(View.VISIBLE);
- mResult.setVisibility(View.INVISIBLE);
-
- try {
- Intent performProvisioningIntent =
- new Intent(OtaUtils.ACTION_PERFORM_CDMA_PROVISIONING);
-
- // Set the magic extra to force "non-interactive mode" for the
- // OTASP call.
- performProvisioningIntent.putExtra(OtaUtils.EXTRA_OVERRIDE_INTERACTIVE_MODE, false);
-
- // Pass a PendingIntent along with the
- // ACTION_PERFORM_CDMA_PROVISIONING intent, which allows
- // results to be sent back to us.
- Intent resultIntent = new Intent(this, this.getClass());
- PendingIntent pendingResultIntent =
- PendingIntent.getActivity(this, 0,
- resultIntent, 0);
- performProvisioningIntent.putExtra(OtaUtils.EXTRA_OTASP_RESULT_CODE_PENDING_INTENT,
- pendingResultIntent);
-
- Log.i(LOG_TAG, "- Firing off PERFORM_CDMA_PROVISIONING intent: "
- + performProvisioningIntent);
- Bundle extras = performProvisioningIntent.getExtras();
- if (extras != null) Log.i(LOG_TAG, " - intent extras = " + extras);
-
- // Originally, we would simply call
- // startActivity(performProvisioningIntent);
- // to launch the InCallScreenShowActivation activity and *not* expect
- // a result. (Note that calling the plain startActivity()
- // method *guarantees* that your onActivityResult() method
- // will NOT be called at all.)
-
- // Now, we ask for a result:
- startActivityForResult(performProvisioningIntent,
- PERFORM_CDMA_PROVISIONING_REQUEST_CODE);
-
- // On a non-voice-capable device, the InCallScreenShowActivation activity
- // will kick off the OTASP call and immediately return, passing
- // the code RESULT_STARTED_NONINTERACTIVE_OTASP to our
- // onActivityResult method.
-
- } catch (ActivityNotFoundException e) {
- Log.w(LOG_TAG, "Couldn't show activiation UI; ActivityNotFoundException: " + e);
- }
- }
-}
diff --git a/tests/src/com/android/services/telephony/ConferenceParticipantConnectionTest.java b/tests/src/com/android/services/telephony/ConferenceParticipantConnectionTest.java
new file mode 100644
index 0000000..73fe0af
--- /dev/null
+++ b/tests/src/com/android/services/telephony/ConferenceParticipantConnectionTest.java
@@ -0,0 +1,82 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.services.telephony;
+
+import android.net.Uri;
+import android.support.test.runner.AndroidJUnit4;
+import android.telecom.Conference;
+import android.telecom.ConferenceParticipant;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+import static com.android.services.telephony.ConferenceParticipantConnection.getParticipantAddress;
+import static org.junit.Assert.assertEquals;
+
+/**
+ * Tests proper parsing of conference event package participant addresses.
+ */
+@RunWith(AndroidJUnit4.class)
+public class ConferenceParticipantConnectionTest {
+
+ @Test
+ public void testParticipantParseSimpleTel() {
+ assertUrisEqual(Uri.parse("tel:+16505551212"),
+ getParticipantAddress(Uri.parse("tel:6505551212"), "US"));
+ }
+
+ @Test
+ public void testParticipantParseTelExtended() {
+ assertUrisEqual(Uri.parse("tel:+16505551212"),
+ getParticipantAddress(Uri.parse("tel:6505551212;phone-context=blah"), "US"));
+ }
+
+ @Test
+ public void testParticipantParseSip() {
+ assertUrisEqual(Uri.parse("tel:+16505551212"),
+ getParticipantAddress(Uri.parse("sip:16505551212;[email protected]"),
+ "US"));
+ }
+
+ @Test
+ public void testParticipantParseSip2() {
+ assertUrisEqual(Uri.parse("tel:+12125551212"),
+ getParticipantAddress(Uri.parse("sip:[email protected];user=phone"),
+ "US"));
+ }
+
+ @Test
+ public void testParticipantParseTelJp() {
+ assertUrisEqual(Uri.parse("tel:+819066570660"),
+ getParticipantAddress(Uri.parse(
+ "tel:09066570660;phone-context=ims.mnc020.mcc440.3gppnetwork.org"),
+ "JP"));
+ }
+
+ @Test
+ public void testParticipantParseSipJp() {
+ assertUrisEqual(Uri.parse("tel:+819066571180"),
+ getParticipantAddress(Uri.parse(
+ "sip:[email protected];user=phone"),
+ "JP"));
+ }
+
+ private void assertUrisEqual(Uri expected, Uri actual) {
+ assertEquals(expected.getScheme(), actual.getScheme());
+ assertEquals(expected.getSchemeSpecificPart(), actual.getSchemeSpecificPart());
+ }
+}