Merge "Startup WAP PUSH service before handling SMS messages" am: e4b4df1e28 am: 13797df914 am: fcdef52da4

Original change: https://android-review.googlesource.com/c/platform/frameworks/base/+/1336116

Change-Id: I4f83c804058d98a2f0be36de74a8590600955a00
This commit is contained in:
Amit Mahajan 2021-04-06 02:16:32 +00:00 committed by Automerger Merge Worker
commit a44fbe08cf
3 changed files with 148 additions and 43 deletions

View File

@ -27,7 +27,8 @@
<original-package android:name="com.android.smspush" />
<application
android:allowClearUserData="false">
android:allowClearUserData="false"
android:directBootAware="true">
<service android:name=".WapPushManager"
android:permission="com.android.smspush.WAPPUSH_MANAGER_BIND"
android:exported="true">

View File

@ -26,17 +26,21 @@ import android.content.pm.ApplicationInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageManager.NameNotFoundException;
import android.database.Cursor;
import android.database.sqlite.SQLiteOpenHelper;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.os.Build;
import android.os.IBinder;
import android.os.PowerManager;
import android.os.RemoteException;
import android.os.UserManager;
import android.util.Log;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.telephony.IWapPushManager;
import com.android.internal.telephony.WapPushManagerParams;
import java.io.File;
/**
* The WapPushManager service is implemented to process incoming
* WAP Push messages and to maintain the Receiver Application/Application
@ -67,8 +71,13 @@ public class WapPushManager extends Service {
/**
* Inner class that deals with application ID table
*/
private class WapPushManDBHelper extends SQLiteOpenHelper {
WapPushManDBHelper(Context context) {
@VisibleForTesting
public static class WapPushManDBHelper extends SQLiteOpenHelper {
/**
* Constructor
*/
@VisibleForTesting
public WapPushManDBHelper(Context context) {
super(context, DATABASE_NAME, null, WAP_PUSH_MANAGER_VERSION);
if (LOCAL_LOGV) Log.v(LOG_TAG, "helper instance created.");
}
@ -269,10 +278,6 @@ public class WapPushManager extends Service {
int app_type, boolean need_signature, boolean further_processing) {
WapPushManDBHelper dbh = getDatabase(mContext);
SQLiteDatabase db = dbh.getWritableDatabase();
WapPushManDBHelper.queryData lastapp = dbh.queryLastApp(db, x_app_id, content_type);
boolean ret = false;
boolean insert = false;
int sq = 0;
if (!appTypeCheck(app_type)) {
Log.w(LOG_TAG, "invalid app_type " + app_type + ". app_type must be "
@ -280,34 +285,8 @@ public class WapPushManager extends Service {
+ WapPushManagerParams.APP_TYPE_SERVICE);
return false;
}
if (lastapp == null) {
insert = true;
sq = 0;
} else if (!lastapp.packageName.equals(package_name) ||
!lastapp.className.equals(class_name)) {
insert = true;
sq = lastapp.installOrder + 1;
}
if (insert) {
ContentValues values = new ContentValues();
values.put("x_wap_application", x_app_id);
values.put("content_type", content_type);
values.put("package_name", package_name);
values.put("class_name", class_name);
values.put("app_type", app_type);
values.put("need_signature", need_signature ? 1 : 0);
values.put("further_processing", further_processing ? 1 : 0);
values.put("install_order", sq);
db.insert(APPID_TABLE_NAME, null, values);
if (LOCAL_LOGV) Log.v(LOG_TAG, "add:" + x_app_id + ":" + content_type
+ " " + package_name + "." + class_name
+ ", newsq:" + sq);
ret = true;
}
boolean ret = insertPackage(dbh, db, x_app_id, content_type, package_name, class_name,
app_type, need_signature, further_processing);
db.close();
return ret;
@ -404,11 +383,91 @@ public class WapPushManager extends Service {
protected WapPushManDBHelper getDatabase(Context context) {
if (mDbHelper == null) {
if (LOCAL_LOGV) Log.v(LOG_TAG, "create new db inst.");
mDbHelper = new WapPushManDBHelper(context);
mDbHelper = new WapPushManDBHelper(context.createDeviceProtectedStorageContext());
}
// Migrate existing legacy database into the device encrypted storage.
migrateWapPushManDBIfNeeded(context);
return mDbHelper;
}
/**
* Inserts a package information into a database
*/
@VisibleForTesting
public boolean insertPackage(WapPushManDBHelper dbh, SQLiteDatabase db, String appId,
String contentType, String packageName, String className, int appType,
boolean needSignature, boolean furtherProcessing) {
WapPushManDBHelper.queryData lastapp = dbh.queryLastApp(db, appId, contentType);
boolean insert = false;
int sq = 0;
if (lastapp == null) {
insert = true;
sq = 0;
} else if (!lastapp.packageName.equals(packageName)
|| !lastapp.className.equals(className)) {
insert = true;
sq = lastapp.installOrder + 1;
}
if (insert) {
ContentValues values = new ContentValues();
values.put("x_wap_application", appId);
values.put("content_type", contentType);
values.put("package_name", packageName);
values.put("class_name", className);
values.put("app_type", appType);
values.put("need_signature", needSignature ? 1 : 0);
values.put("further_processing", furtherProcessing ? 1 : 0);
values.put("install_order", sq);
db.insert(APPID_TABLE_NAME, null, values);
if (LOCAL_LOGV) {
Log.v(LOG_TAG, "add:" + appId + ":" + contentType + " " + packageName
+ "." + className + ", newsq:" + sq);
}
return true;
}
return false;
}
/**
* Migrates a legacy database into the device encrypted storage
*/
private void migrateWapPushManDBIfNeeded(Context context) {
UserManager userManager = (UserManager) context.getSystemService(Context.USER_SERVICE);
File file = context.getDatabasePath(DATABASE_NAME);
if (!userManager.isUserUnlocked() || !file.exists()) {
// Check if the device is unlocked because a legacy database can't access during
// DirectBoot.
return;
}
// Migration steps below:
// 1. Merge the package info to legacy database if there is any package info which is
// registered during DirectBoot.
// 2. Move the data base to the device encryped storage.
WapPushManDBHelper legacyDbHelper = new WapPushManDBHelper(context);
SQLiteDatabase legacyDb = legacyDbHelper.getWritableDatabase();
SQLiteDatabase db = mDbHelper.getWritableDatabase();
Cursor cur = db.query(APPID_TABLE_NAME, null, null, null, null, null, null);
while (cur.moveToNext()) {
insertPackage(legacyDbHelper, legacyDb,
cur.getString(cur.getColumnIndex("x_wap_application")),
cur.getString(cur.getColumnIndex("content_type")),
cur.getString(cur.getColumnIndex("package_name")),
cur.getString(cur.getColumnIndex("class_name")),
cur.getInt(cur.getColumnIndex("app_type")),
cur.getInt(cur.getColumnIndex("need_signature")) == 1,
cur.getInt(cur.getColumnIndex("further_processing")) == 1);
}
cur.close();
legacyDb.close();
db.close();
context.createDeviceProtectedStorageContext().moveDatabaseFrom(context, DATABASE_NAME);
Log.i(LOG_TAG, "Migrated the legacy database.");
}
/**
* This method is used for testing

View File

@ -21,6 +21,7 @@ import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.database.sqlite.SQLiteDatabase;
import android.os.IBinder;
import android.os.RemoteException;
import android.provider.Telephony.Sms.Intents;
@ -33,7 +34,9 @@ import com.android.internal.telephony.WspTypeDecoder;
import com.android.internal.telephony.uicc.IccUtils;
import com.android.internal.util.HexDump;
import com.android.smspush.WapPushManager;
import com.android.smspush.WapPushManager.WapPushManDBHelper;
import java.io.File;
import java.util.Random;
/**
@ -467,8 +470,9 @@ public class WapPushTest extends ServiceTestCase<WapPushManager> {
try {
super.setUp();
// get verifier
getContext().bindService(new Intent(IDataVerify.class.getName()),
mConn, Context.BIND_AUTO_CREATE);
Intent intent = new Intent(IDataVerify.class.getName());
intent.setPackage("com.android.smspush.unitTests");
getContext().bindService(intent, mConn, Context.BIND_AUTO_CREATE);
} catch (Exception e) {
Log.w(LOG_TAG, "super exception");
}
@ -552,15 +556,15 @@ public class WapPushTest extends ServiceTestCase<WapPushManager> {
}
/**
* Add sqlite injection test
* Sqlite injection test
*/
public void testAddPackage0() {
public void testSqliteInjection() {
String inject = "' union select 0,'com.android.settings','com.android.settings.Settings',0,0,0--";
// insert new data
// update data
IWapPushManager iwapman = getInterface();
try {
assertFalse(iwapman.addPackage(
assertFalse(iwapman.updatePackage(
inject,
Integer.toString(mContentTypeValue),
mPackageName, mClassName,
@ -2528,4 +2532,45 @@ public class WapPushTest extends ServiceTestCase<WapPushManager> {
mMessageBody = originalMessageBody;
}
/**
* DataBase migration test.
*/
public void testDataBaseMigration() {
IWapPushManager iwapman = getInterface();
WapPushManager wpman = getService();
Context context = getContext();
addPackageToLegacyDB(mAppIdValue, mContentTypeValue, mPackageName, mClassName,
WapPushManagerParams.APP_TYPE_SERVICE, true, true);
addPackageToLegacyDB(mAppIdValue + 10, mContentTypeValue, mPackageName, mClassName,
WapPushManagerParams.APP_TYPE_SERVICE, true, true);
File oldDbFile = context.getDatabasePath("wappush.db");
assertTrue(oldDbFile.exists());
assertTrue(wpman.verifyData(Integer.toString(mAppIdValue),
Integer.toString(mContentTypeValue),
mPackageName, mClassName,
WapPushManagerParams.APP_TYPE_SERVICE, true, true));
assertFalse(oldDbFile.exists());
// Clean up DB
try {
iwapman.deletePackage(Integer.toString(mAppIdValue),
Integer.toString(mContentTypeValue), mPackageName, mClassName);
iwapman.deletePackage(Integer.toString(mAppIdValue + 10),
Integer.toString(mContentTypeValue), mPackageName, mClassName);
} catch (RemoteException e) {
assertTrue(false);
}
}
private void addPackageToLegacyDB(int appId, int contextType, String packagename,
String classnName, int appType, boolean signature, boolean furtherProcessing) {
WapPushManager wpman = getService();
WapPushManDBHelper dbh = new WapPushManDBHelper(getContext());
SQLiteDatabase db = dbh.getWritableDatabase();
wpman.insertPackage(dbh, db, Integer.toString(appId), Integer.toString(contextType),
packagename, classnName, appType, signature, furtherProcessing);
}
}