Merge "Handle LANGUAGE NOTIFICATION command"
diff --git a/src/java/com/android/internal/telephony/cat/AppInterface.java b/src/java/com/android/internal/telephony/cat/AppInterface.java
old mode 100644
new mode 100755
index c78b7f8..1f2d3a0
--- a/src/java/com/android/internal/telephony/cat/AppInterface.java
+++ b/src/java/com/android/internal/telephony/cat/AppInterface.java
@@ -84,6 +84,7 @@
SET_UP_MENU(0x25),
SET_UP_CALL(0x10),
PROVIDE_LOCAL_INFORMATION(0x26),
+ LANGUAGE_NOTIFICATION(0x35),
OPEN_CHANNEL(0x40),
CLOSE_CHANNEL(0x41),
RECEIVE_DATA(0x42),
diff --git a/src/java/com/android/internal/telephony/cat/CatService.java b/src/java/com/android/internal/telephony/cat/CatService.java
old mode 100644
new mode 100755
index 7e70212..cd7a756
--- a/src/java/com/android/internal/telephony/cat/CatService.java
+++ b/src/java/com/android/internal/telephony/cat/CatService.java
@@ -16,15 +16,21 @@
package com.android.internal.telephony.cat;
+import android.app.ActivityManagerNative;
+import android.app.IActivityManager;
+import android.app.backup.BackupManager;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
+import android.content.res.Configuration;
import android.content.res.Resources.NotFoundException;
import android.os.AsyncResult;
import android.os.Handler;
import android.os.HandlerThread;
+import android.os.LocaleList;
import android.os.Message;
+import android.os.RemoteException;
import android.os.SystemProperties;
import android.telephony.SubscriptionManager;
import android.telephony.TelephonyManager;
@@ -450,6 +456,18 @@
((CallSetupParams) cmdParams).mConfirmMsg.text = message.toString();
}
break;
+ case LANGUAGE_NOTIFICATION:
+ String language = ((LanguageParams) cmdParams).mLanguage;
+ ResultCode result = ResultCode.OK;
+ if (language != null && language.length() > 0) {
+ try {
+ changeLanguage(language);
+ } catch (RemoteException e) {
+ result = ResultCode.TERMINAL_CRNTLY_UNABLE_TO_PROCESS;
+ }
+ }
+ sendTerminalResponse(cmdParams.mCmdDet, result, false, 0, null);
+ return;
case OPEN_CHANNEL:
case CLOSE_CHANNEL:
case RECEIVE_DATA:
@@ -1129,4 +1147,13 @@
mCmdIf.reportStkServiceIsRunning(null);
}
}
+
+ private void changeLanguage(String language) throws RemoteException {
+ IActivityManager am = ActivityManagerNative.getDefault();
+ Configuration config = am.getConfiguration();
+ config.setLocales(new LocaleList(new Locale(language), LocaleList.getDefault()));
+ config.userSetLocale = true;
+ am.updatePersistentConfiguration(config);
+ BackupManager.dataChanged("com.android.providers.settings");
+ }
}
diff --git a/src/java/com/android/internal/telephony/cat/CommandParams.java b/src/java/com/android/internal/telephony/cat/CommandParams.java
old mode 100644
new mode 100755
index 7dfedab..59cd414
--- a/src/java/com/android/internal/telephony/cat/CommandParams.java
+++ b/src/java/com/android/internal/telephony/cat/CommandParams.java
@@ -150,6 +150,15 @@
}
}
+class LanguageParams extends CommandParams {
+ String mLanguage;
+
+ LanguageParams(CommandDetails cmdDet, String lang) {
+ super(cmdDet);
+ mLanguage = lang;
+ }
+}
+
class SelectItemParams extends CommandParams {
Menu mMenu = null;
boolean mLoadTitleIcon = false;
diff --git a/src/java/com/android/internal/telephony/cat/CommandParamsFactory.java b/src/java/com/android/internal/telephony/cat/CommandParamsFactory.java
index 3dd5337..eb92888 100644
--- a/src/java/com/android/internal/telephony/cat/CommandParamsFactory.java
+++ b/src/java/com/android/internal/telephony/cat/CommandParamsFactory.java
@@ -19,12 +19,15 @@
import android.graphics.Bitmap;
import android.os.Handler;
import android.os.Message;
+import android.text.TextUtils;
import com.android.internal.telephony.GsmAlphabet;
import com.android.internal.telephony.uicc.IccFileHandler;
import java.util.Iterator;
import java.util.List;
+import java.util.Locale;
+
import static com.android.internal.telephony.cat.CatCmdMessage.
SetupEventListConstants.USER_ACTIVITY_EVENT;
import static com.android.internal.telephony.cat.CatCmdMessage.
@@ -47,6 +50,8 @@
private int mIconLoadState = LOAD_NO_ICON;
private RilMessageDecoder mCaller = null;
private boolean mloadIcon = false;
+ private String mSavedLanguage;
+ private String mRequestedLanguage;
// constants
static final int MSG_ID_LOAD_ICON_DONE = 1;
@@ -66,6 +71,10 @@
static final int DTTZ_SETTING = 0x03;
static final int LANGUAGE_SETTING = 0x04;
+ // Command Qualifier value for language notification command
+ static final int NON_SPECIFIC_LANGUAGE = 0x00;
+ static final int SPECIFIC_LANGUAGE = 0x01;
+
// As per TS 102.223 Annex C, Structure of CAT communications,
// the APDU length can be max 255 bytes. This leaves only 239 bytes for user
// input string. CMD details TLV + Device IDs TLV + Result TLV + Other
@@ -203,6 +212,9 @@
case PROVIDE_LOCAL_INFORMATION:
cmdPending = processProvideLocalInfo(cmdDet, ctlvs);
break;
+ case LANGUAGE_NOTIFICATION:
+ cmdPending = processLanguageNotification(cmdDet, ctlvs);
+ break;
case OPEN_CHANNEL:
case CLOSE_CHANNEL:
case RECEIVE_DATA:
@@ -1014,6 +1026,67 @@
return false;
}
+ /**
+ * Processes LANGUAGE_NOTIFICATION proactive command from the SIM card.
+ *
+ * The SPECIFIC_LANGUAGE notification sets the specified language.
+ * The NON_SPECIFIC_LANGUAGE notification restores the last specifically set language.
+ *
+ * @param cmdDet Command Details object retrieved from the proactive command object
+ * @param ctlvs List of ComprehensionTlv objects following Command Details
+ * object and Device Identities object within the proactive command
+ * @return false. This function always returns false meaning that the command
+ * processing is not pending and additional asynchronous processing
+ * is not required.
+ */
+ private boolean processLanguageNotification(CommandDetails cmdDet, List<ComprehensionTlv> ctlvs)
+ throws ResultException {
+ CatLog.d(this, "process Language Notification");
+
+ String desiredLanguage = null;
+ String currentLanguage = Locale.getDefault().getLanguage();
+ switch (cmdDet.commandQualifier) {
+ case NON_SPECIFIC_LANGUAGE:
+ if (!TextUtils.isEmpty(mSavedLanguage) && (!TextUtils.isEmpty(mRequestedLanguage)
+ && mRequestedLanguage.equals(currentLanguage))) {
+ CatLog.d(this, "Non-specific language notification changes the language "
+ + "setting back to " + mSavedLanguage);
+ desiredLanguage = mSavedLanguage;
+ }
+
+ mSavedLanguage = null;
+ mRequestedLanguage = null;
+ break;
+ case SPECIFIC_LANGUAGE:
+ ComprehensionTlv ctlv = searchForTag(ComprehensionTlvTag.LANGUAGE, ctlvs);
+ if (ctlv != null) {
+ int valueLen = ctlv.getLength();
+ if (valueLen != 2) {
+ throw new ResultException(ResultCode.CMD_DATA_NOT_UNDERSTOOD);
+ }
+
+ byte[] rawValue = ctlv.getRawValue();
+ int valueIndex = ctlv.getValueIndex();
+ desiredLanguage = GsmAlphabet.gsm8BitUnpackedToString(rawValue, valueIndex, 2);
+
+ if (TextUtils.isEmpty(mSavedLanguage) || (!TextUtils.isEmpty(mRequestedLanguage)
+ && !mRequestedLanguage.equals(currentLanguage))) {
+ mSavedLanguage = currentLanguage;
+ }
+ mRequestedLanguage = desiredLanguage;
+ CatLog.d(this, "Specific language notification changes the language setting to "
+ + mRequestedLanguage);
+ }
+ break;
+ default:
+ CatLog.d(this, "LN[" + cmdDet.commandQualifier + "] Command Not Supported");
+ break;
+ }
+
+ mCmdParams = new LanguageParams(cmdDet, desiredLanguage);
+ return false;
+ }
+
private boolean processBIPClient(CommandDetails cmdDet,
List<ComprehensionTlv> ctlvs) throws ResultException {
AppInterface.CommandType commandType =