diff options
Diffstat (limited to 'packages')
20 files changed, 4010 insertions, 0 deletions
diff --git a/packages/WAPPushManager/Android.mk b/packages/WAPPushManager/Android.mk new file mode 100644 index 0000000..c1d8f4b --- /dev/null +++ b/packages/WAPPushManager/Android.mk @@ -0,0 +1,20 @@ +# Copyright 2007-2008 The Android Open Source Project + + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +LOCAL_MODULE_TAGS := optional + +LOCAL_SRC_FILES := $(call all-java-files-under, src) + +LOCAL_PACKAGE_NAME := WAPPushManager + +LOCAL_STATIC_JAVA_LIBRARIES += android-common + +LOCAL_PROGUARD_FLAGS := -include $(LOCAL_PATH)/proguard.flags + +include $(BUILD_PACKAGE) + +# This finds and builds the test apk as well, so a single make does both. +include $(call all-makefiles-under,$(LOCAL_PATH)) diff --git a/packages/WAPPushManager/AndroidManifest.xml b/packages/WAPPushManager/AndroidManifest.xml new file mode 100644 index 0000000..89e9d6a --- /dev/null +++ b/packages/WAPPushManager/AndroidManifest.xml @@ -0,0 +1,38 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +/* + * Copyright (C) 2007-2008 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. + */ +--> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.smspush"> + + <permission android:name="com.android.smspush.WAPPUSH_MANAGER_BIND" + android:protectionLevel="signatureOrSystem" /> + + <original-package android:name="com.android.smspush" /> + <application> + <service android:name=".WapPushManager" + android:permission="com.android.smspush.WAPPUSH_MANAGER_BIND" + android:exported="true"> + <intent-filter> + <action android:name="com.android.internal.telephony.IWapPushManager"></action> + </intent-filter> + </service> + </application> + + +</manifest> diff --git a/packages/WAPPushManager/CleanSpec.mk b/packages/WAPPushManager/CleanSpec.mk new file mode 100644 index 0000000..b84e1b6 --- /dev/null +++ b/packages/WAPPushManager/CleanSpec.mk @@ -0,0 +1,49 @@ +# Copyright (C) 2007 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. +# + +# If you don't need to do a full clean build but would like to touch +# a file or delete some intermediate files, add a clean step to the end +# of the list. These steps will only be run once, if they haven't been +# run before. +# +# E.g.: +# $(call add-clean-step, touch -c external/sqlite/sqlite3.h) +# $(call add-clean-step, rm -rf $(PRODUCT_OUT)/obj/STATIC_LIBRARIES/libz_intermediates) +# +# Always use "touch -c" and "rm -f" or "rm -rf" to gracefully deal with +# files that are missing or have been moved. +# +# Use $(PRODUCT_OUT) to get to the "out/target/product/blah/" directory. +# Use $(OUT_DIR) to refer to the "out" directory. +# +# If you need to re-do something that's already mentioned, just copy +# the command and add it to the bottom of the list. E.g., if a change +# that you made last week required touching a file and a change you +# made today requires touching the same file, just copy the old +# touch step and add it to the end of the list. +# +# ************************************************ +# NEWER CLEAN STEPS MUST BE AT THE END OF THE LIST +# ************************************************ + +# For example: +#$(call add-clean-step, rm -rf $(OUT_DIR)/target/common/obj/APPS/AndroidTests_intermediates) +#$(call add-clean-step, rm -rf $(OUT_DIR)/target/common/obj/JAVA_LIBRARIES/core_intermediates) +#$(call add-clean-step, find $(OUT_DIR) -type f -name "IGTalkSession*" -print0 | xargs -0 rm -f) +#$(call add-clean-step, rm -rf $(PRODUCT_OUT)/data/*) + +# ************************************************ +# NEWER CLEAN STEPS MUST BE AT THE END OF THE LIST +# ************************************************ diff --git a/packages/WAPPushManager/MODULE_LICENSE_APACHE2 b/packages/WAPPushManager/MODULE_LICENSE_APACHE2 new file mode 100644 index 0000000..e69de29 --- /dev/null +++ b/packages/WAPPushManager/MODULE_LICENSE_APACHE2 diff --git a/packages/WAPPushManager/NOTICE b/packages/WAPPushManager/NOTICE new file mode 100644 index 0000000..c5b1efa --- /dev/null +++ b/packages/WAPPushManager/NOTICE @@ -0,0 +1,190 @@ + + Copyright (c) 2005-2008, 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. + + 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. + + + Apache License + Version 2.0, January 2004 + http://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS + diff --git a/packages/WAPPushManager/proguard.flags b/packages/WAPPushManager/proguard.flags new file mode 100644 index 0000000..d09887b --- /dev/null +++ b/packages/WAPPushManager/proguard.flags @@ -0,0 +1,18 @@ + +#apply method is dynamically referenced by the reflection class. +-keep class android.app.ContextImpl$SharedPreferencesImpl$EditorImpl { + void apply(); +} +-keep class android.content.SharedPreferences$Editor { + void apply(); +} + +#WapPushManager is referenced only by AndroidManifest.xml +-keep class com.android.smspush.WapPushManager { +#CTS module method + public boolean isDataExist(java.lang.String, java.lang.String, + java.lang.String, java.lang.String); + public boolean verifyData(java.lang.String, java.lang.String, + java.lang.String, java.lang.String, int, boolean, boolean); +} + diff --git a/packages/WAPPushManager/src/com/android/smspush/WapPushManager.java b/packages/WAPPushManager/src/com/android/smspush/WapPushManager.java new file mode 100644 index 0000000..96e0377 --- /dev/null +++ b/packages/WAPPushManager/src/com/android/smspush/WapPushManager.java @@ -0,0 +1,424 @@ +/* + * 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.smspush; + +import android.app.Service; +import android.content.ActivityNotFoundException; +import android.content.ComponentName; +import android.content.ContentValues; +import android.content.Context; +import android.content.Intent; +import android.content.pm.PackageManager; +import android.database.Cursor; +import android.database.sqlite.SQLiteOpenHelper; +import android.database.sqlite.SQLiteDatabase; +import android.os.IBinder; +import android.os.RemoteException; +import android.util.Log; + +import com.android.internal.telephony.IWapPushManager; +import com.android.internal.telephony.WapPushManagerParams; + +/** + * The WapPushManager service is implemented to process incoming + * WAP Push messages and to maintain the Receiver Application/Application + * ID mapping. The WapPushManager runs as a system service, and only the + * WapPushManager can update the WAP Push message and Receiver Application + * mapping (Application ID Table). When the device receives an SMS WAP Push + * message, the WapPushManager looks up the Receiver Application name in + * Application ID Table. If an application is found, the application is + * launched using its full component name instead of broadcasting an implicit + * Intent. If a Receiver Application is not found in the Application ID + * Table or the WapPushManager returns a process-further value, the + * telephony stack will process the message using existing message processing + * flow, and broadcast an implicit Intent. + */ +public class WapPushManager extends Service { + + private static final String LOG_TAG = "WAP PUSH"; + private static final String DATABASE_NAME = "wappush.db"; + private static final String APPID_TABLE_NAME = "appid_tbl"; + + /** + * Version number must be incremented when table structure is changed. + */ + private static final int WAP_PUSH_MANAGER_VERSION = 1; + private static final boolean DEBUG_SQL = false; + private static final boolean LOCAL_LOGV = false; + + /** + * Inner class that deals with application ID table + */ + private class WapPushManDBHelper extends SQLiteOpenHelper { + WapPushManDBHelper(Context context) { + super(context, DATABASE_NAME, null, WAP_PUSH_MANAGER_VERSION); + if (LOCAL_LOGV) Log.v(LOG_TAG, "helper instance created."); + } + + @Override + public void onCreate(SQLiteDatabase db) { + if (LOCAL_LOGV) Log.v(LOG_TAG, "db onCreate."); + String sql = "CREATE TABLE " + APPID_TABLE_NAME + " (" + + "id INTEGER PRIMARY KEY, " + + "x_wap_application TEXT, " + + "content_type TEXT, " + + "package_name TEXT, " + + "class_name TEXT, " + + "app_type INTEGER, " + + "need_signature INTEGER, " + + "further_processing INTEGER, " + + "install_order INTEGER " + + ")"; + + if (DEBUG_SQL) Log.v(LOG_TAG, "sql: " + sql); + db.execSQL(sql); + } + + @Override + public void onUpgrade(SQLiteDatabase db, + int oldVersion, int newVersion) { + // TODO: when table structure is changed, need to dump and restore data. + /* + db.execSQL( + "drop table if exists "+APPID_TABLE_NAME); + onCreate(db); + */ + Log.w(LOG_TAG, "onUpgrade is not implemented yet. do nothing."); + } + + protected class queryData { + public String packageName; + public String className; + int appType; + int needSignature; + int furtherProcessing; + int installOrder; + } + + /** + * Query the latest receiver application info with supplied application ID and + * content type. + * @param app_id application ID to look up + * @param content_type content type to look up + */ + protected queryData queryLastApp(SQLiteDatabase db, + String app_id, String content_type) { + String sql = "select install_order, package_name, class_name, " + + " app_type, need_signature, further_processing" + + " from " + APPID_TABLE_NAME + + " where x_wap_application=\'" + app_id + "\'" + + " and content_type=\'" + content_type + "\'" + + " order by install_order desc"; + if (DEBUG_SQL) Log.v(LOG_TAG, "sql: " + sql); + Cursor cur = db.rawQuery(sql, null); + queryData ret = null; + + if (cur.moveToNext()) { + ret = new queryData(); + ret.installOrder = cur.getInt(cur.getColumnIndex("install_order")); + ret.packageName = cur.getString(cur.getColumnIndex("package_name")); + ret.className = cur.getString(cur.getColumnIndex("class_name")); + ret.appType = cur.getInt(cur.getColumnIndex("app_type")); + ret.needSignature = cur.getInt(cur.getColumnIndex("need_signature")); + ret.furtherProcessing = cur.getInt(cur.getColumnIndex("further_processing")); + } + cur.close(); + return ret; + } + + } + + /** + * The exported API implementations class + */ + private class IWapPushManagerStub extends IWapPushManager.Stub { + public Context mContext; + + public IWapPushManagerStub() { + + } + + /** + * Compare the package signature with WapPushManager package + */ + protected boolean signatureCheck(String package_name) { + PackageManager pm = mContext.getPackageManager(); + int match = pm.checkSignatures(mContext.getPackageName(), package_name); + + if (LOCAL_LOGV) Log.v(LOG_TAG, "compare signature " + mContext.getPackageName() + + " and " + package_name + ", match=" + match); + + return match == PackageManager.SIGNATURE_MATCH; + } + + /** + * Returns the status value of the message processing. + * The message will be processed as follows: + * 1.Look up Application ID Table with x-wap-application-id + content type + * 2.Check the signature of package name that is found in the + * Application ID Table by using PackageManager.checkSignature + * 3.Trigger the Application + * 4.Returns the process status value. + */ + public int processMessage(String app_id, String content_type, Intent intent) + throws RemoteException { + Log.d(LOG_TAG, "wpman processMsg " + app_id + ":" + content_type); + + WapPushManDBHelper dbh = getDatabase(mContext); + SQLiteDatabase db = dbh.getReadableDatabase(); + WapPushManDBHelper.queryData lastapp = dbh.queryLastApp(db, app_id, content_type); + db.close(); + + if (lastapp == null) { + Log.w(LOG_TAG, "no receiver app found for " + app_id + ":" + content_type); + return WapPushManagerParams.APP_QUERY_FAILED; + } + if (LOCAL_LOGV) Log.v(LOG_TAG, "starting " + lastapp.packageName + + "/" + lastapp.className); + + if (lastapp.needSignature != 0) { + if (!signatureCheck(lastapp.packageName)) { + return WapPushManagerParams.SIGNATURE_NO_MATCH; + } + } + + if (lastapp.appType == WapPushManagerParams.APP_TYPE_ACTIVITY) { + //Intent intent = new Intent(Intent.ACTION_MAIN); + intent.setClassName(lastapp.packageName, lastapp.className); + intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); + + try { + mContext.startActivity(intent); + } catch (ActivityNotFoundException e) { + Log.w(LOG_TAG, "invalid name " + + lastapp.packageName + "/" + lastapp.className); + return WapPushManagerParams.INVALID_RECEIVER_NAME; + } + } else { + intent.setClassName(mContext, lastapp.className); + intent.setComponent(new ComponentName(lastapp.packageName, + lastapp.className)); + if (mContext.startService(intent) == null) { + Log.w(LOG_TAG, "invalid name " + + lastapp.packageName + "/" + lastapp.className); + return WapPushManagerParams.INVALID_RECEIVER_NAME; + } + } + + return WapPushManagerParams.MESSAGE_HANDLED + | (lastapp.furtherProcessing == 1 ? + WapPushManagerParams.FURTHER_PROCESSING : 0); + } + + protected boolean appTypeCheck(int app_type) { + if (app_type == WapPushManagerParams.APP_TYPE_ACTIVITY || + app_type == WapPushManagerParams.APP_TYPE_SERVICE) { + return true; + } else { + return false; + } + } + + /** + * Returns true if adding the package succeeded. + */ + public boolean addPackage(String x_app_id, String content_type, + String package_name, String class_name, + 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 " + + WapPushManagerParams.APP_TYPE_ACTIVITY + " or " + + 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; + } + + db.close(); + + return ret; + } + + /** + * Returns true if updating the package succeeded. + */ + public boolean updatePackage(String x_app_id, String content_type, + String package_name, String class_name, + int app_type, boolean need_signature, boolean further_processing) { + + if (!appTypeCheck(app_type)) { + Log.w(LOG_TAG, "invalid app_type " + app_type + ". app_type must be " + + WapPushManagerParams.APP_TYPE_ACTIVITY + " or " + + WapPushManagerParams.APP_TYPE_SERVICE); + return false; + } + + WapPushManDBHelper dbh = getDatabase(mContext); + SQLiteDatabase db = dbh.getWritableDatabase(); + WapPushManDBHelper.queryData lastapp = dbh.queryLastApp(db, x_app_id, content_type); + + if (lastapp == null) { + db.close(); + return false; + } + + ContentValues values = new ContentValues(); + String where = "x_wap_application=\'" + x_app_id + "\'" + + " and content_type=\'" + content_type + "\'" + + " and install_order=" + lastapp.installOrder; + + 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); + + int num = db.update(APPID_TABLE_NAME, values, where, null); + if (LOCAL_LOGV) Log.v(LOG_TAG, "update:" + x_app_id + ":" + content_type + " " + + package_name + "." + class_name + + ", sq:" + lastapp.installOrder); + + db.close(); + + return num > 0; + } + + /** + * Returns true if deleting the package succeeded. + */ + public boolean deletePackage(String x_app_id, String content_type, + String package_name, String class_name) { + WapPushManDBHelper dbh = getDatabase(mContext); + SQLiteDatabase db = dbh.getWritableDatabase(); + String where = "x_wap_application=\'" + x_app_id + "\'" + + " and content_type=\'" + content_type + "\'" + + " and package_name=\'" + package_name + "\'" + + " and class_name=\'" + class_name + "\'"; + int num_removed = db.delete(APPID_TABLE_NAME, where, null); + + db.close(); + if (LOCAL_LOGV) Log.v(LOG_TAG, "deleted " + num_removed + " rows:" + + x_app_id + ":" + content_type + " " + + package_name + "." + class_name); + return num_removed > 0; + } + }; + + + /** + * Linux IPC Binder + */ + private final IWapPushManagerStub mBinder = new IWapPushManagerStub(); + + /** + * Default constructor + */ + public WapPushManager() { + super(); + mBinder.mContext = this; + } + + @Override + public IBinder onBind(Intent arg0) { + return mBinder; + } + + /** + * Application ID database instance + */ + private WapPushManDBHelper mDbHelper = null; + protected WapPushManDBHelper getDatabase(Context context) { + if (mDbHelper == null) { + if (LOCAL_LOGV) Log.v(LOG_TAG, "create new db inst."); + mDbHelper = new WapPushManDBHelper(context); + } + return mDbHelper; + } + + + /** + * This method is used for testing + */ + public boolean verifyData(String x_app_id, String content_type, + String package_name, String class_name, + int app_type, boolean need_signature, boolean further_processing) { + WapPushManDBHelper dbh = getDatabase(this); + SQLiteDatabase db = dbh.getReadableDatabase(); + WapPushManDBHelper.queryData lastapp = dbh.queryLastApp(db, x_app_id, content_type); + + db.close(); + + if (lastapp == null) return false; + + if (lastapp.packageName.equals(package_name) + && lastapp.className.equals(class_name) + && lastapp.appType == app_type + && lastapp.needSignature == (need_signature ? 1 : 0) + && lastapp.furtherProcessing == (further_processing ? 1 : 0)) { + return true; + } else { + return false; + } + } + + /** + * This method is used for testing + */ + public boolean isDataExist(String x_app_id, String content_type, + String package_name, String class_name) { + WapPushManDBHelper dbh = getDatabase(this); + SQLiteDatabase db = dbh.getReadableDatabase(); + boolean ret = dbh.queryLastApp(db, x_app_id, content_type) != null; + + db.close(); + return ret; + } + +} + diff --git a/packages/WAPPushManager/tests/Android.mk b/packages/WAPPushManager/tests/Android.mk new file mode 100644 index 0000000..0a95b52 --- /dev/null +++ b/packages/WAPPushManager/tests/Android.mk @@ -0,0 +1,38 @@ +# Copyright 2008, 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. + +LOCAL_PATH:= $(call my-dir) +include $(CLEAR_VARS) + +# We only want this apk build for tests. +LOCAL_MODULE_TAGS := tests + +LOCAL_JAVA_LIBRARIES := android.test.runner + +# Include all test java files. +LOCAL_SRC_FILES := $(call all-java-files-under, src) +LOCAL_SRC_FILES += \ + src/com/android/smspush/unitTests/IDataVerify.aidl + + +# Notice that we don't have to include the src files of Email because, by +# running the tests using an instrumentation targeting Eamil, we +# automatically get all of its classes loaded into our environment. + +LOCAL_PACKAGE_NAME := WAPPushManagerTests + +LOCAL_INSTRUMENTATION_FOR := WAPPushManager + +include $(BUILD_PACKAGE) + diff --git a/packages/WAPPushManager/tests/AndroidManifest.xml b/packages/WAPPushManager/tests/AndroidManifest.xml new file mode 100644 index 0000000..da7634f --- /dev/null +++ b/packages/WAPPushManager/tests/AndroidManifest.xml @@ -0,0 +1,71 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- Copyright (C) 2008 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 name must be unique so suffix with "tests" so package loader doesn't ignore us --> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" + package="com.android.smspush.unitTests"> + + + <uses-permission android:name="com.android.smspush.WAPPUSH_MANAGER_BIND" /> + <uses-permission android:name="android.permission.RECEIVE_WAP_PUSH" /> + <!--testing.../--> + <application android:icon="@drawable/icon" android:label="wappush test"> + <uses-library android:name="android.test.runner" /> + <activity android:name=".ClientTest" + android:label="wappush test"> + <intent-filter> + <action android:name="android.intent.action.MAIN" /> + <category android:name="android.intent.category.LAUNCHER" /> + </intent-filter> + </activity> + + <receiver android:name=".DrmReceiver" android:enabled="true"> + <intent-filter> + <action android:name="android.provider.Telephony.WAP_PUSH_RECEIVED" /> + <data android:mimeType="application/vnd.oma.drm.rights+xml" /> + <data android:value="application/vnd.oma.drm.rights+wbxml" /> + </intent-filter> + </receiver> + + <service android:enabled="true" android:name=".ReceiverService" + android:exported="true"/> + + <activity android:name=".ReceiverActivity" + android:exported="true" android:label="test receiver" /> + + <service android:name=".DataVerify" + android:exported="true"> + <intent-filter> + <action android:name="com.android.smspush.unitTests.IDataVerify" /> + </intent-filter> + </service> + + </application> + + <!-- + This declares that this application uses the instrumentation test runner targeting + the package of com.android.smspush. To run the tests use the command: + "adb shell am instrument -w + com.android.smspush.unitTests/android.test.InstrumentationTestRunner" + --> + <instrumentation android:name="android.test.InstrumentationTestRunner" + android:targetPackage="com.android.smspush" + android:label="Tests for WAPPushManager"/> + +</manifest> + diff --git a/packages/WAPPushManager/tests/res/drawable-hdpi/icon.png b/packages/WAPPushManager/tests/res/drawable-hdpi/icon.png Binary files differnew file mode 100644 index 0000000..8074c4c --- /dev/null +++ b/packages/WAPPushManager/tests/res/drawable-hdpi/icon.png diff --git a/packages/WAPPushManager/tests/res/drawable-ldpi/icon.png b/packages/WAPPushManager/tests/res/drawable-ldpi/icon.png Binary files differnew file mode 100644 index 0000000..1095584 --- /dev/null +++ b/packages/WAPPushManager/tests/res/drawable-ldpi/icon.png diff --git a/packages/WAPPushManager/tests/res/drawable-mdpi/icon.png b/packages/WAPPushManager/tests/res/drawable-mdpi/icon.png Binary files differnew file mode 100644 index 0000000..a07c69f --- /dev/null +++ b/packages/WAPPushManager/tests/res/drawable-mdpi/icon.png diff --git a/packages/WAPPushManager/tests/res/layout/main.xml b/packages/WAPPushManager/tests/res/layout/main.xml new file mode 100644 index 0000000..c7bdbb2 --- /dev/null +++ b/packages/WAPPushManager/tests/res/layout/main.xml @@ -0,0 +1,152 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- 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. +--> +<AbsoluteLayout +android:id="@+id/widget133" +android:layout_width="fill_parent" +android:layout_height="fill_parent" +xmlns:android="http://schemas.android.com/apk/res/android" +> +<EditText +android:id="@+id/app_id" +android:layout_width="wrap_content" +android:layout_height="wrap_content" +android:text="10" +android:textSize="18sp" +android:layout_x="0px" +android:layout_y="26px" +> +</EditText> +<EditText +android:id="@+id/cont" +android:layout_width="wrap_content" +android:layout_height="wrap_content" +android:text="20" +android:textSize="18sp" +android:layout_x="47px" +android:layout_y="26px" +> +</EditText> +<EditText +android:id="@+id/pkg" +android:layout_width="125px" +android:layout_height="wrap_content" +android:text="pkg" +android:textSize="18sp" +android:layout_x="0px" +android:layout_y="81px" +> +</EditText> +<EditText +android:id="@+id/cls" +android:layout_width="173px" +android:layout_height="wrap_content" +android:text="cls" +android:textSize="18sp" +android:layout_x="147px" +android:layout_y="81px" +> +</EditText> +<Button +android:id="@+id/addpkg" +android:layout_width="182px" +android:layout_height="wrap_content" +android:text="add/update package" +android:layout_x="15px" +android:layout_y="225px" +> +</Button> +<TextView +android:id="@+id/widget52" +android:layout_width="wrap_content" +android:layout_height="wrap_content" +android:text="input app_id, cont_type, pkg, cls" +android:textSize="18sp" +android:layout_x="0px" +android:layout_y="0px" +> +</TextView> +<Button +android:id="@+id/procmsg" +android:layout_width="109px" +android:layout_height="wrap_content" +android:text="process msg" +android:layout_x="197px" +android:layout_y="361px" +> +</Button> +<RadioGroup +android:id="@+id/widget137" +android:layout_width="83px" +android:layout_height="80px" +android:orientation="vertical" +android:layout_x="19px" +android:layout_y="137px" +> +<RadioButton +android:id="@+id/act" +android:layout_width="182px" +android:layout_height="wrap_content" +android:text="act" +android:checked="true" +> +</RadioButton> +<RadioButton +android:id="@+id/svc" +android:layout_width="wrap_content" +android:layout_height="wrap_content" +android:text="svc" +> +</RadioButton> +</RadioGroup> +<Button +android:id="@+id/delpkg" +android:layout_width="174px" +android:layout_height="wrap_content" +android:text="delete pkg" +android:layout_x="14px" +android:layout_y="283px" +> +</Button> +<EditText +android:id="@+id/pdu" +android:layout_width="186px" +android:layout_height="83px" +android:text="0006080302030aaf02905c030d6a0085070373616d706c6540646f636f6d6f2e6e652e6a700005c3072009102012345601" +android:textSize="18sp" +android:layout_x="10px" +android:layout_y="341px" +> +</EditText> +<CheckBox +android:id="@+id/ftr" +android:layout_width="wrap_content" +android:layout_height="wrap_content" +android:text="ftr_proc" +android:layout_x="143px" +android:layout_y="181px" +> +</CheckBox> +<CheckBox +android:id="@+id/sig" +android:layout_width="wrap_content" +android:layout_height="wrap_content" +android:text="nd_sig" +android:checked="true" +android:layout_x="142px" +android:layout_y="140px" +> +</CheckBox> +</AbsoluteLayout> diff --git a/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/ClientTest.java b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/ClientTest.java new file mode 100644 index 0000000..78fd174 --- /dev/null +++ b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/ClientTest.java @@ -0,0 +1,174 @@ +/* + * 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.smspush.unitTests; + +import android.app.Activity; +import android.content.ComponentName; +import android.content.Context; +import android.content.Intent; +import android.content.ServiceConnection; +import android.os.Bundle; +import android.os.IBinder; +import android.os.RemoteException; +import android.util.Log; +import android.view.View; +import android.widget.Button; +import android.widget.CheckBox; +import android.widget.EditText; +import android.widget.RadioButton; + +import com.android.internal.telephony.IWapPushManager; +import com.android.internal.telephony.WapPushManagerParams; +import com.android.internal.telephony.WapPushOverSms; +import com.android.internal.util.HexDump; +import com.android.smspush.WapPushManager; + +/** + * WapPushManager test application + */ +public class ClientTest extends Activity { + private static final String LOG_TAG = "WAP PUSH"; + + /** Called when the activity is first created. */ + @Override + public void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.main); + + Button addpbtn = (Button) findViewById(R.id.addpkg); + Button procbtn = (Button) findViewById(R.id.procmsg); + Button delbtn = (Button) findViewById(R.id.delpkg); + + Log.v(LOG_TAG, "activity created!!"); + + addpbtn.setOnClickListener(new View.OnClickListener() { + public void onClick(View v) { + EditText app_id = (EditText) findViewById(R.id.app_id); + EditText cont = (EditText) findViewById(R.id.cont); + EditText pkg = (EditText) findViewById(R.id.pkg); + EditText cls = (EditText) findViewById(R.id.cls); + RadioButton act = (RadioButton) findViewById(R.id.act); + CheckBox sig = (CheckBox) findViewById(R.id.sig); + CheckBox ftr = (CheckBox) findViewById(R.id.ftr); + + try { + if (!mWapPushMan.addPackage( + app_id.getText().toString(), + cont.getText().toString(), + pkg.getText().toString(), + cls.getText().toString(), + act.isChecked() ? WapPushManagerParams.APP_TYPE_ACTIVITY : + WapPushManagerParams.APP_TYPE_SERVICE, + sig.isChecked(), ftr.isChecked())) { + + Log.w(LOG_TAG, "remote add pkg failed..."); + mWapPushMan.updatePackage( + app_id.getText().toString(), + cont.getText().toString(), + pkg.getText().toString(), + cls.getText().toString(), + act.isChecked() ? WapPushManagerParams.APP_TYPE_ACTIVITY : + WapPushManagerParams.APP_TYPE_SERVICE, + sig.isChecked(), ftr.isChecked()); + } + } catch (RemoteException e) { + Log.w(LOG_TAG, "remote func failed..."); + } + } + }); + + delbtn.setOnClickListener(new View.OnClickListener() { + public void onClick(View v) { + EditText app_id = (EditText) findViewById(R.id.app_id); + EditText cont = (EditText) findViewById(R.id.cont); + EditText pkg = (EditText) findViewById(R.id.pkg); + EditText cls = (EditText) findViewById(R.id.cls); + // CheckBox delall = (CheckBox) findViewById(R.id.delall); + // Log.d(LOG_TAG, "button clicked"); + + try { + mWapPushMan.deletePackage( + app_id.getText().toString(), + cont.getText().toString(), + pkg.getText().toString(), + cls.getText().toString()); + // delall.isChecked()); + } catch (RemoteException e) { + Log.w(LOG_TAG, "remote func failed..."); + } + } + }); + + procbtn.setOnClickListener(new View.OnClickListener() { + public void onClick(View v) { + EditText pdu = (EditText) findViewById(R.id.pdu); + EditText app_id = (EditText) findViewById(R.id.app_id); + EditText cont = (EditText) findViewById(R.id.cont); + + // WapPushOverSms wap = new WapPushOverSms(); + // wap.dispatchWapPdu(strToHex(pdu.getText().toString())); + try { + Intent intent = new Intent(); + intent.putExtra("transactionId", 0); + intent.putExtra("pduType", 6); + intent.putExtra("header", + HexDump.hexStringToByteArray(pdu.getText().toString())); + intent.putExtra("data", + HexDump.hexStringToByteArray(pdu.getText().toString())); + + mWapPushMan.processMessage( + app_id.getText().toString(), + cont.getText().toString(), + intent); + //HexDump.hexStringToByteArray(pdu.getText().toString()), 0, 6, 5, 5); + } catch (RemoteException e) { + Log.w(LOG_TAG, "remote func failed..."); + } + } + }); + } + + private IWapPushManager mWapPushMan; + private ServiceConnection conn = new ServiceConnection() { + public void onServiceDisconnected(ComponentName name) { + mWapPushMan = null; + Log.v(LOG_TAG, "service disconnected."); + } + + public void onServiceConnected(ComponentName name, IBinder service) { + mWapPushMan = IWapPushManager.Stub.asInterface(service); + Log.v(LOG_TAG, "service connected."); + } + }; + + @Override + public void onStart() { + super.onStart(); + Log.v(LOG_TAG, "onStart bind WAPPushManager service " + + IWapPushManager.class.getName()); + this.bindService(new Intent(IWapPushManager.class.getName()), conn, + Context.BIND_AUTO_CREATE); + Log.v(LOG_TAG, "bind service done."); + } + + @Override + public void onDestroy() { + super.onDestroy(); + this.unbindService(conn); + } + +} diff --git a/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/DataVerify.java b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/DataVerify.java new file mode 100644 index 0000000..ef491fd --- /dev/null +++ b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/DataVerify.java @@ -0,0 +1,119 @@ +/* + * 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.smspush.unitTests; + +import android.app.Service; +import android.content.Context; +import android.content.Intent; +import android.os.IBinder; +import android.util.Log; + +import com.android.internal.util.HexDump; + +/** + * To verify that receiver application receives correct body data. + */ +public class DataVerify extends Service { + private static final String LOG_TAG = "WAP PUSH"; + private static final int TIME_WAIT = 100; + private static final int WAIT_COUNT = 100; + private static byte[] mLastReceivedPdu = null; + private static boolean sDataSet = false; + + private class IDataVerifyStub extends IDataVerify.Stub { + public Context mContext; + + public IDataVerifyStub() { + } + + boolean arrayCompare(byte[] arr1, byte[] arr2) { + int i; + + if (arr1 == null || arr2 == null) { + if (arr1 == null) { + Log.w(LOG_TAG, "arr1 is null"); + } else { + Log.w(LOG_TAG, "arr2 is null"); + } + return false; + } + + if (arr1.length != arr2.length) { + return false; + } + + for (i = 0; i < arr1.length; i++) { + if (arr1[i] != arr2[i]) return false; + } + return true; + } + + /** + * Compare pdu and received pdu + */ + public synchronized boolean verifyData(byte[] pdu) { + int cnt = 0; + + while (!sDataSet) { + // wait for the activity receive data. + try { + Thread.sleep(TIME_WAIT); + if (cnt++ > WAIT_COUNT) { + // don't wait more than 10 sec. + return false; + } + } catch (InterruptedException e) {} + } + + Log.v(LOG_TAG, "verify pdu"); + boolean ret = arrayCompare(pdu, mLastReceivedPdu); + return ret; + } + + /** + * Clear the old data. This method must be called before starting the test + */ + public void resetData() { + mLastReceivedPdu = null; + sDataSet = false; + } + } + + private final IDataVerifyStub binder = new IDataVerifyStub(); + + /** + * Constructor + */ + public DataVerify() { + } + + /** + * Receiver application must call this method when it receives the wap push message + */ + public static void SetLastReceivedPdu(byte[] pdu) { + mLastReceivedPdu = pdu; + sDataSet = true; + } + + @Override + public IBinder onBind(Intent arg0) { + return binder; + } + +} + + diff --git a/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/DrmReceiver.java b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/DrmReceiver.java new file mode 100644 index 0000000..5f5f121 --- /dev/null +++ b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/DrmReceiver.java @@ -0,0 +1,53 @@ +/* + * 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.smspush.unitTests; + +import android.content.BroadcastReceiver; +import android.content.Context; +import android.content.Intent; +import android.util.Log; + +import com.android.internal.util.HexDump; + +/** + * A sample wap push receiver application for existing framework + * This class is listening for "application/vnd.oma.drm.rights+xml" message + */ +public class DrmReceiver extends BroadcastReceiver { + private static final String LOG_TAG = "WAP PUSH"; + + @Override + public void onReceive(Context context, Intent intent) { + Log.d(LOG_TAG, "DrmReceiver received."); + + byte[] body; + byte[] header; + + body = intent.getByteArrayExtra("data"); + header = intent.getByteArrayExtra("header"); + + Log.d(LOG_TAG, "header:"); + Log.d(LOG_TAG, HexDump.dumpHexString(header)); + Log.d(LOG_TAG, "body:"); + Log.d(LOG_TAG, HexDump.dumpHexString(body)); + + DataVerify.SetLastReceivedPdu(body); + } + +} + + diff --git a/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/IDataVerify.aidl b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/IDataVerify.aidl new file mode 100644 index 0000000..f0670fa --- /dev/null +++ b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/IDataVerify.aidl @@ -0,0 +1,33 @@ +/* + * 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.smspush.unitTests; + +/** + * Interface to receiver application data verifyer class + */ +interface IDataVerify { + /** + * Verify data + */ + boolean verifyData(in byte[] pdu); + + /** + * Initialize data + */ + void resetData(); +} + diff --git a/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/ReceiverActivity.java b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/ReceiverActivity.java new file mode 100644 index 0000000..07f55ea --- /dev/null +++ b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/ReceiverActivity.java @@ -0,0 +1,55 @@ +/* + * 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.smspush.unitTests; + +import android.app.Activity; +import android.content.Intent; +import android.os.Bundle; +import android.util.Log; + +import com.android.internal.util.HexDump; + +/** + * Activity type receiver application + */ +public class ReceiverActivity extends Activity { + private static final String LOG_TAG = "WAP PUSH"; + + @Override + public void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + Log.d(LOG_TAG, "activity created!!"); + + Intent in = getIntent(); + byte[] body; + byte[] header; + + body = in.getByteArrayExtra("data"); + header = in.getByteArrayExtra("header"); + + Log.d(LOG_TAG, "header:"); + Log.d(LOG_TAG, HexDump.dumpHexString(header)); + Log.d(LOG_TAG, "body:"); + Log.d(LOG_TAG, HexDump.dumpHexString(body)); + + DataVerify.SetLastReceivedPdu(body); + + finish(); + + } +} + diff --git a/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/ReceiverService.java b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/ReceiverService.java new file mode 100644 index 0000000..b024bf5 --- /dev/null +++ b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/ReceiverService.java @@ -0,0 +1,63 @@ +/* + * 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.smspush.unitTests; + +import android.app.Service; +import android.content.Context; +import android.content.Intent; +import android.os.IBinder; +import android.util.Log; + +import com.android.internal.util.HexDump; + +/** + * Service type receiver application + */ +public class ReceiverService extends Service { + private static final String LOG_TAG = "WAP PUSH"; + + @Override + public void onCreate() { + super.onCreate(); + Log.d(LOG_TAG, "Receiver service created"); + } + + @Override + public IBinder onBind(Intent intent) { + return null; + } + + @Override + public int onStartCommand(Intent intent, int flags, int startId) { + Log.d(LOG_TAG, "Receiver service started"); + + byte[] body; + byte[] header; + body = intent.getByteArrayExtra("data"); + header = intent.getByteArrayExtra("header"); + + Log.d(LOG_TAG, "header:"); + Log.d(LOG_TAG, HexDump.dumpHexString(header)); + Log.d(LOG_TAG, "body:"); + Log.d(LOG_TAG, HexDump.dumpHexString(body)); + + DataVerify.SetLastReceivedPdu(body); + return START_STICKY; + } +} + + diff --git a/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/WapPushTest.java b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/WapPushTest.java new file mode 100644 index 0000000..9b0a36b --- /dev/null +++ b/packages/WAPPushManager/tests/src/com/android/smspush/unitTests/WapPushTest.java @@ -0,0 +1,2513 @@ +/* + * 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.smspush.unitTests; + +import android.app.Activity; +import android.content.ComponentName; +import android.content.Context; +import android.content.Intent; +import android.content.ServiceConnection; +import android.os.IBinder; +import android.os.RemoteException; +import android.provider.Telephony.Sms.Intents; +import android.test.ServiceTestCase; +import android.util.Log; +import android.util.Config; + +import com.android.internal.telephony.IccUtils; +import com.android.internal.telephony.IWapPushManager; +import com.android.internal.telephony.WapPushManagerParams; +import com.android.internal.telephony.WspTypeDecoder; +import com.android.internal.util.HexDump; +import com.android.smspush.WapPushManager; + +import java.util.Random; + +/** + * This is a simple framework for a test of a Service. See {@link android.test.ServiceTestCase + * ServiceTestCase} for more information on how to write and extend service tests. + * + * To run this test, you can type: + * adb shell am instrument -w \ + * -e class com.android.smspush.unitTests.WapPushTest \ + * com.android.smspush.unitTests/android.test.InstrumentationTestRunner + */ +public class WapPushTest extends ServiceTestCase<WapPushManager> { + private static final String LOG_TAG = "WAP PUSH"; + private static final boolean LOCAL_LOGV = false; + private static final int TIME_WAIT = 100; + + protected int mAppIdValue = 0x8002; + protected String mAppIdName = "x-wap-application:*"; + protected int mContentTypeValue = 0x030a; + protected String mContentTypeName = "application/vnd.wap.sic"; + + protected String mPackageName; + protected String mClassName; + + protected byte[] mGsmHeader = { + (byte) 0x00, // sc address + (byte) 0x40, // TP-MTI + (byte) 0x04, // sender address length? + (byte) 0x81, (byte) 0x55, (byte) 0x45, // sender address? + (byte) 0x00, // data schema + (byte) 0x00, // proto ID + (byte) 0x01, (byte) 0x60, (byte) 0x12, (byte) 0x31, + (byte) 0x74, (byte) 0x34, (byte) 0x63 // time stamp + }; + + protected byte[] mUserDataHeader = { + (byte) 0x07, // UDH len + (byte) 0x06, // header len + (byte) 0x05, // port addressing type? + (byte) 0x00, // dummy + (byte) 0x0B, (byte) 0x84, // dest port + (byte) 0x23, (byte) 0xF0 // src port + }; + + protected byte[] mWspHeader; + + protected byte[] mMessageBody = { + (byte) 0x00, + (byte) 0x01, + (byte) 0x02, + (byte) 0x03, + (byte) 0x04, + (byte) 0x05, + (byte) 0x06, + (byte) 0x07, + (byte) 0x08, + (byte) 0x09, + (byte) 0x0a, + (byte) 0x0b, + (byte) 0x0c, + (byte) 0x0d, + (byte) 0x0e, + (byte) 0x0f + }; + + protected int mWspHeaderStart; + protected int mWspHeaderLen; + protected int mWspContentTypeStart; + + /** + * OMA application ID in binary form + * http://www.openmobilealliance.org/tech/omna/omna-push-app-id.aspx + */ + final int[] OMA_APPLICATION_ID_VALUES = new int[] { + 0x00, + 0x01, + 0x02, + 0x03, + 0x04, + 0x05, + 0x06, + 0x07, + 0x08, + 0x09, + 0x0A, + 0x8000, + 0x8001, + 0x8002, + 0x8003, + 0x8004, + 0x8005, + 0x8006, + 0x8007, + 0x8008, + 0x8009, + 0x800B, + 0x8010 + }; + + /** + * OMA application ID in string form + * http://www.openmobilealliance.org/tech/omna/omna-push-app-id.aspx + */ + final String[] OMA_APPLICATION_ID_NAMES = new String[] { + "x-wap-application:*", + "x-wap-application:push.sia", + "x-wap-application:wml.ua", + "x-wap-application:wta.ua", + "x-wap-application:mms.ua", + "x-wap-application:push.syncml", + "x-wap-application:loc.ua", + "x-wap-application:syncml.dm", + "x-wap-application:drm.ua", + "x-wap-application:emn.ua", + "x-wap-application:wv.ua", + "x-wap-microsoft:localcontent.ua", + "x-wap-microsoft:IMclient.ua", + "x-wap-docomo:imode.mail.ua", + "x-wap-docomo:imode.mr.ua", + "x-wap-docomo:imode.mf.ua", + "x-motorola:location.ua", + "x-motorola:now.ua", + "x-motorola:otaprov.ua", + "x-motorola:browser.ua", + "x-motorola:splash.ua", + "x-wap-nai:mvsw.command", + "x-wap-openwave:iota.ua" + }; + + /** + * OMA content type in binary form + * http://www.openmobilealliance.org/tech/omna/omna-wsp-content-type.aspx + */ + final int[] OMA_CONTENT_TYPE_VALUES = new int[] { + 0x00, + 0x01, + 0x02, + 0x03, + 0x04, + 0x05, + 0x06, + 0x07, + 0x08, + 0x09, + 0x0A, + 0x0B, + 0x0C, + 0x0D, + 0x0E, + 0x0F, + 0x10, + 0x11, + 0x12, + 0x13, + 0x14, + 0x15, + 0x16, + 0x17, + 0x18, + 0x19, + 0x1A, + 0x1B, + 0x1C, + 0x1D, + 0x1E, + 0x1F, + 0x20, + 0x21, + 0x22, + 0x23, + 0x24, + 0x25, + 0x26, + 0x27, + 0x28, + 0x29, + 0x2A, + 0x2B, + 0x2C, + 0x2D, + 0x2E, + 0x2F, + 0x30, + 0x31, + 0x32, + 0x33, + 0x34, + 0x35, + 0x36, + 0x37, + 0x38, + 0x39, + 0x3A, + 0x3B, + 0x3C, + 0x3D, + 0x3E, + 0x3F, + 0x40, + 0x41, + 0x42, + 0x43, + 0x44, + 0x45, + 0x46, + 0x47, + 0x48, + 0x49, + 0x4A, + 0x4B, + 0x4C, + 0x4D, + 0x4E, + 0x4F, + 0x50, + 0x51, + 0x52, + 0x53, + 0x54, +// 0x55, +// 0x56, +// 0x57, +// 0x58, + 0x0201, + 0x0202, + 0x0203, + 0x0204, + 0x0205, + 0x0206, + 0x0207, + 0x0208, + 0x0209, + 0x020A, + 0x020B, + 0x020C, + 0x0300, + 0x0301, + 0x0302, + 0x0303, + 0x0304, + 0x0305, + 0x0306, + 0x0307, + 0x0308, + 0x0309, + 0x030A, + 0x030B, + 0x030C, + 0x030D, + 0x030E, + 0x030F, + 0x0310, + 0x0311, + 0x0312, + 0x0313, + 0x0314, + 0x0315, + 0x0316, + 0x0317, + 0x0318, + 0x0319, + 0x031A, + 0x031B + /*0x031C, + 0x031D*/ + }; + + /** + * OMA content type in string form + * http://www.openmobilealliance.org/tech/omna/omna-wsp-content-type.aspx + */ + final String[] OMA_CONTENT_TYPE_NAMES = new String[] { + "*/*", + "text/*", + "text/html", + "text/plain", + "text/x-hdml", + "text/x-ttml", + "text/x-vCalendar", + "text/x-vCard", + "text/vnd.wap.wml", + "text/vnd.wap.wmlscript", + "text/vnd.wap.wta-event", + "multipart/*", + "multipart/mixed", + "multipart/form-data", + "multipart/byterantes", + "multipart/alternative", + "application/*", + "application/java-vm", + "application/x-www-form-urlencoded", + "application/x-hdmlc", + "application/vnd.wap.wmlc", + "application/vnd.wap.wmlscriptc", + "application/vnd.wap.wta-eventc", + "application/vnd.wap.uaprof", + "application/vnd.wap.wtls-ca-certificate", + "application/vnd.wap.wtls-user-certificate", + "application/x-x509-ca-cert", + "application/x-x509-user-cert", + "image/*", + "image/gif", + "image/jpeg", + "image/tiff", + "image/png", + "image/vnd.wap.wbmp", + "application/vnd.wap.multipart.*", + "application/vnd.wap.multipart.mixed", + "application/vnd.wap.multipart.form-data", + "application/vnd.wap.multipart.byteranges", + "application/vnd.wap.multipart.alternative", + "application/xml", + "text/xml", + "application/vnd.wap.wbxml", + "application/x-x968-cross-cert", + "application/x-x968-ca-cert", + "application/x-x968-user-cert", + "text/vnd.wap.si", + "application/vnd.wap.sic", + "text/vnd.wap.sl", + "application/vnd.wap.slc", + "text/vnd.wap.co", + "application/vnd.wap.coc", + "application/vnd.wap.multipart.related", + "application/vnd.wap.sia", + "text/vnd.wap.connectivity-xml", + "application/vnd.wap.connectivity-wbxml", + "application/pkcs7-mime", + "application/vnd.wap.hashed-certificate", + "application/vnd.wap.signed-certificate", + "application/vnd.wap.cert-response", + "application/xhtml+xml", + "application/wml+xml", + "text/css", + "application/vnd.wap.mms-message", + "application/vnd.wap.rollover-certificate", + "application/vnd.wap.locc+wbxml", + "application/vnd.wap.loc+xml", + "application/vnd.syncml.dm+wbxml", + "application/vnd.syncml.dm+xml", + "application/vnd.syncml.notification", + "application/vnd.wap.xhtml+xml", + "application/vnd.wv.csp.cir", + "application/vnd.oma.dd+xml", + "application/vnd.oma.drm.message", + "application/vnd.oma.drm.content", + "application/vnd.oma.drm.rights+xml", + "application/vnd.oma.drm.rights+wbxml", + "application/vnd.wv.csp+xml", + "application/vnd.wv.csp+wbxml", + "application/vnd.syncml.ds.notification", + "audio/*", + "video/*", + "application/vnd.oma.dd2+xml", + "application/mikey", + "application/vnd.oma.dcd", + "application/vnd.oma.dcdc", +// "text/x-vMessage", +// "application/vnd.omads-email+wbxml", +// "text/x-vBookmark", +// "application/vnd.syncml.dm.notification", + "application/vnd.uplanet.cacheop-wbxml", + "application/vnd.uplanet.signal", + "application/vnd.uplanet.alert-wbxml", + "application/vnd.uplanet.list-wbxml", + "application/vnd.uplanet.listcmd-wbxml", + "application/vnd.uplanet.channel-wbxml", + "application/vnd.uplanet.provisioning-status-uri", + "x-wap.multipart/vnd.uplanet.header-set", + "application/vnd.uplanet.bearer-choice-wbxml", + "application/vnd.phonecom.mmc-wbxml", + "application/vnd.nokia.syncset+wbxml", + "image/x-up-wpng", + "application/iota.mmc-wbxml", + "application/iota.mmc-xml", + "application/vnd.syncml+xml", + "application/vnd.syncml+wbxml", + "text/vnd.wap.emn+xml", + "text/calendar", + "application/vnd.omads-email+xml", + "application/vnd.omads-file+xml", + "application/vnd.omads-folder+xml", + "text/directory;profile=vCard", + "application/vnd.wap.emn+wbxml", + "application/vnd.nokia.ipdc-purchase-response", + "application/vnd.motorola.screen3+xml", + "application/vnd.motorola.screen3+gzip", + "application/vnd.cmcc.setting+wbxml", + "application/vnd.cmcc.bombing+wbxml", + "application/vnd.docomo.pf", + "application/vnd.docomo.ub", + "application/vnd.omaloc-supl-init", + "application/vnd.oma.group-usage-list+xml", + "application/oma-directory+xml", + "application/vnd.docomo.pf2", + "application/vnd.oma.drm.roap-trigger+wbxml", + "application/vnd.sbm.mid2", + "application/vnd.wmf.bootstrap", + "application/vnc.cmcc.dcd+xml", + "application/vnd.sbm.cid", + "application/vnd.oma.bcast.provisioningtrigger", + /*"application/vnd.docomo.dm", + "application/vnd.oma.scidm.messages+xml"*/ + }; + + private IDataVerify mIVerify = null; + + ServiceConnection mConn = new ServiceConnection() { + public void onServiceConnected(ComponentName name, IBinder service) { + Log.v(LOG_TAG, "data verify interface connected."); + mIVerify = IDataVerify.Stub.asInterface(service); + } + public void onServiceDisconnected(ComponentName name) { + } + }; + + /** + * Main WapPushManager test module constructor + */ + public WapPushTest() { + super(WapPushManager.class); + mClassName = this.getClass().getName(); + mPackageName = this.getClass().getPackage().getName(); + } + + /** + * Initialize the verifier + */ + @Override + public void setUp() { + try { + super.setUp(); + // get verifier + getContext().bindService(new Intent(IDataVerify.class.getName()), + mConn, Context.BIND_AUTO_CREATE); + } catch (Exception e) { + Log.w(LOG_TAG, "super exception"); + } + // Log.d(LOG_TAG, "test setup"); + } + + private IWapPushManager mWapPush = null; + IWapPushManager getInterface() { + if (mWapPush != null) return mWapPush; + Intent startIntent = new Intent(); + startIntent.setClass(getContext(), WapPushManager.class); + IBinder service = bindService(startIntent); + + mWapPush = IWapPushManager.Stub.asInterface(service); + return mWapPush; + } + + /* + * All methods need to start with 'test'. + * Use various assert methods to pass/fail the test case. + */ + protected void utAddPackage(boolean need_sig, boolean more_proc) { + IWapPushManager iwapman = getInterface(); + + // insert new data + try { + assertTrue(iwapman.addPackage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, need_sig, more_proc)); + } catch (RemoteException e) { + assertTrue(false); + } + + // verify the data + WapPushManager wpman = getService(); + assertTrue(wpman.verifyData(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, need_sig, more_proc)); + } + + /** + * Add package test + */ + public void testAddPackage1() { + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + + utAddPackage(true, true); + mAppIdValue += 10; + utAddPackage(true, false); + mContentTypeValue += 20; + utAddPackage(false, true); + mContentTypeValue += 20; + utAddPackage(false, false); + + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + + // clean up data + try { + IWapPushManager iwapman = getInterface(); + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + mAppIdValue += 10; + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + mContentTypeValue += 20; + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + mContentTypeValue += 20; + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + } catch (RemoteException e) { + assertTrue(false); + } + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + } + + /** + * Add duprecated package test. + */ + public void testAddPackage2() { + try { + IWapPushManager iwapman = getInterface(); + + // set up data + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, 0, + false, false); + iwapman.addPackage(Integer.toString(mAppIdValue + 10), + Integer.toString(mContentTypeValue), mPackageName, mClassName, 0, + false, false); + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue + 10), mPackageName, mClassName, 0, + false, false); + + assertFalse(iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, 0, + false, false)); + assertFalse(iwapman.addPackage(Integer.toString(mAppIdValue + 10), + Integer.toString(mContentTypeValue), mPackageName, mClassName, 0, + false, false)); + assertFalse(iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue + 10), mPackageName, mClassName, 0, + false, false)); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + iwapman.deletePackage(Integer.toString(mAppIdValue + 10), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue + 10), mPackageName, mClassName); + } catch (RemoteException e) { + assertTrue(false); + } + } + + protected void utUpdatePackage(boolean need_sig, boolean more_proc) { + IWapPushManager iwapman = getInterface(); + + // insert new data + try { + assertTrue(iwapman.updatePackage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, need_sig, more_proc)); + } catch (RemoteException e) { + assertTrue(false); + } + + // verify the data + WapPushManager wpman = getService(); + assertTrue(wpman.verifyData( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, need_sig, more_proc)); + } + + /** + * Updating package test + */ + public void testUpdatePackage1() { + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + + // set up data + try { + IWapPushManager iwapman = getInterface(); + + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + 0, false, false); + mAppIdValue += 10; + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + 0, false, false); + mContentTypeValue += 20; + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + 0, false, false); + mContentTypeValue += 20; + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + 0, false, false); + } catch (RemoteException e) { + assertTrue(false); + } + + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + utUpdatePackage(false, false); + mAppIdValue += 10; + utUpdatePackage(false, true); + mContentTypeValue += 20; + utUpdatePackage(true, false); + mContentTypeValue += 20; + utUpdatePackage(true, true); + + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + + // clean up data + try { + IWapPushManager iwapman = getInterface(); + + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + mAppIdValue += 10; + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + mContentTypeValue += 20; + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + mContentTypeValue += 20; + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + } catch (RemoteException e) { + assertTrue(false); + } + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + } + + /** + * Updating invalid package test + */ + public void testUpdatePackage2() { + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + + try { + // set up data + IWapPushManager iwapman = getInterface(); + + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + 0, false, false); + assertFalse(iwapman.updatePackage( + Integer.toString(mAppIdValue + 10), + Integer.toString(mContentTypeValue), + mPackageName, mClassName, 0, false, false)); + assertFalse(iwapman.updatePackage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue + 10), + mPackageName, mClassName, 0, false, false)); + assertTrue(iwapman.updatePackage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + mPackageName + "dummy_data", mClassName, 0, false, false)); + assertTrue(iwapman.updatePackage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + mPackageName, mClassName + "dummy_data", 0, false, false)); + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, + mClassName + "dummy_data"); + } catch (RemoteException e) { + assertTrue(false); + } + } + + protected void utDeletePackage() { + IWapPushManager iwapman = getInterface(); + + try { + assertTrue(iwapman.deletePackage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + mPackageName, mClassName)); + } catch (RemoteException e) { + assertTrue(false); + } + + // verify the data + WapPushManager wpman = getService(); + assertTrue(!wpman.isDataExist( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + mPackageName, mClassName)); + } + + /** + * Deleting package test + */ + public void testDeletePackage1() { + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + + // set up data + try { + IWapPushManager iwapman = getInterface(); + + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + 0, false, false); + mAppIdValue += 10; + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + 0, false, false); + mContentTypeValue += 20; + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + 0, false, false); + mContentTypeValue += 20; + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + 0, false, false); + } catch (RemoteException e) { + assertTrue(false); + } + + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + utDeletePackage(); + mAppIdValue += 10; + utDeletePackage(); + mContentTypeValue += 20; + utDeletePackage(); + mContentTypeValue += 20; + utDeletePackage(); + + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + } + + /** + * Deleting invalid package test + */ + public void testDeletePackage2() { + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + + try { + // set up data + IWapPushManager iwapman = getInterface(); + + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + 0, false, false); + + assertFalse(iwapman.deletePackage(Integer.toString(mAppIdValue + 10), + Integer.toString(mContentTypeValue), mPackageName, mClassName)); + assertFalse(iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue + 20), mPackageName, mClassName)); + assertFalse(iwapman.deletePackage(Integer.toString(mAppIdValue + 10), + Integer.toString(mContentTypeValue + 20), mPackageName, mClassName)); + + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + + } catch (RemoteException e) { + assertTrue(false); + } + } + + + protected int encodeUint32(int uint32Val, byte[] arr, int start) { + int bit = 1; + int topbit = 0; + int encodeLen; + int tmpVal; + + assertTrue(uint32Val >= 0); + for (int i = 0; i < 31; i++) { + if ((bit & uint32Val) > 0) topbit = i; + bit = (bit << 1); + } + encodeLen = topbit/7 + 1; + if (arr == null) return encodeLen; + + //Log.d(LOG_TAG, "uint32Val = " + Integer.toHexString(uint32Val) + ", topbit = " + // + topbit + ", encodeLen = " + encodeLen); + + tmpVal = uint32Val; + for (int i = encodeLen - 1; i >= 0; i--) { + long val = 0; + if (i < encodeLen - 1) val = 0x80; + val |= tmpVal & 0x7f; + arr[start + i] = (byte) (val & 0xFF); + tmpVal = (tmpVal >> 7); + } + return encodeLen; + } + + protected int encodeShortInt(int sintVal, byte[] arr, int start) { + int encodeLen = 0; + + if (sintVal >= 0x80) return encodeLen; + encodeLen = 1; + arr[start] = (byte) (sintVal | 0x80); + return encodeLen; + } + + + /** + * Generate Random WSP header with integer application ID + */ + protected void createRandomWspHeader(byte[] arr, Random rd, int headerStart, + boolean noAppId) { + + boolean appIdAdded = false; + + Log.d(LOG_TAG, "headerStart = " + headerStart + ", appId = " + mAppIdValue + + "(" + Integer.toHexString(mAppIdValue) + ")"); + Log.d(LOG_TAG, "random arr length:" + arr.length); + String typename[] = new String[] { "short int", "long int", "string", "uint32"}; + + while (!appIdAdded) { + int type; + int index = headerStart; + int len = arr.length; + int i; + boolean addAppid = false; + int tmpVal = 0; + int tmpVal2 = 0; + + while (true) { + int add; + + /* + * field name + * 0: short int + * 1: long int + * 2: text + * (no uint for param value) + */ + type = rd.nextInt(3); + switch (type) { + case 0: // header short integer + if (index > 100 && !appIdAdded) addAppid = true; + add = 1; + break; + case 1: // header long int + add = 1 + rd.nextInt(29); + break; + default: // header string + add = 2 + rd.nextInt(10); + break; + } + if (index + add >= len) break; + + // fill header name + switch (type) { + case 0: // header short integer + if (!addAppid) { + do { + arr[index] = (byte) (0x80 | rd.nextInt(128)); + } while (arr[index] == (byte) 0xaf); + } else { + Log.d(LOG_TAG, "appId added."); + arr[index] = (byte) 0xaf; + // if noAppId case, appId fld must be decieved. + if (noAppId) arr[index]++; + } + break; + case 1: // header long int + arr[index] = (byte) (add - 1); + tmpVal2 = 0; + for (i = 1; i < add; i++) { + tmpVal = rd.nextInt(255); + tmpVal2 = (tmpVal2 << 8) | tmpVal; + arr[index + i] = (byte) tmpVal; + } + // don't set application id + if (tmpVal2 == 0x2f) arr[index + 1]++; + break; + default: // header string + for (i = 0; i < add - 1; i++) { + tmpVal = rd.nextInt(127); + if (tmpVal < 32) tmpVal= (32 + tmpVal); + arr[index + i] = (byte) tmpVal; + } + arr[index + i] = (byte) 0x0; + break; + } + + if (LOCAL_LOGV) { + Log.d(LOG_TAG, "field name index:" + index); + Log.d(LOG_TAG, "type:" + typename[type] + ", add:" + add); + if (type != 2) { + for (i = index; i< index + add; i++) { + System.out.print(Integer.toHexString(0xff & arr[i])); + System.out.print(' '); + } + } else { + System.out.print(Integer.toHexString(0xff & arr[index])); + System.out.print(' '); + String str = new String(arr, index + 1, add - 2); + for (i = 0; i < str.length(); i++) { + System.out.print(str.charAt(i)); + System.out.print(' '); + } + } + System.out.print('\n'); + } + index += add; + + + /* + * field value + * 0: short int + * 1: long int + * 2: text + * 3: uint + */ + if (addAppid) { + type = 1; + } else { + type = rd.nextInt(4); + } + switch (type) { + case 0: // header short integer + add = 1; + break; + case 1: // header long int + if (addAppid) { + int bit = 1; + int topBit = 0; + + for (i = 0; i < 31; i++) { + if ((mAppIdValue & bit) > 0) topBit = i; + bit = (bit << 1); + } + add = 2 + topBit/8; + } else { + add = 1 + rd.nextInt(29); + } + break; + case 2: // header string + add = 2 + rd.nextInt(10); + break; + default: // uint32 + add = 6; + } + if (index + add >= len) break; + + // fill field value + switch (type) { + case 0: // header short int + arr[index] = (byte) (0x80 | rd.nextInt(128)); + break; + case 1: // header long int + if (addAppid) { + addAppid = false; + appIdAdded = true; + + arr[index] = (byte) (add - 1); + tmpVal = mAppIdValue; + for (i = add; i > 1; i--) { + arr[index + i - 1] = (byte) (tmpVal & 0xff); + tmpVal = (tmpVal >> 8); + } + } else { + arr[index] = (byte) (add - 1); + for (i = 1; i < add; i++) { + arr[index + i] = (byte) rd.nextInt(255); + } + } + break; + case 2:// header string + for (i = 0; i < add - 1; i++) { + tmpVal = rd.nextInt(127); + if (tmpVal < 32) tmpVal= (32 + tmpVal); + arr[index + i] = (byte) tmpVal; + } + arr[index + i] = (byte) 0x0; + break; + default: // header uvarint + arr[index] = (byte) 31; + tmpVal = rd.nextInt(0x0FFFFFFF); + add = 1 + encodeUint32(tmpVal, null, index + 1); + encodeUint32(tmpVal, arr, index + 1); + break; + + } + + if (LOCAL_LOGV) { + Log.d(LOG_TAG, "field value index:" + index); + Log.d(LOG_TAG, "type:" + typename[type] + ", add:" + add); + if (type != 2) { + for (i = index; i< index + add; i++) { + System.out.print(Integer.toHexString(0xff & arr[i])); + System.out.print(' '); + } + } else { + System.out.print(Integer.toHexString(0xff & arr[index])); + System.out.print(' '); + String str = new String(arr, index + 1, add - 2); + for (i = 0; i < str.length(); i++) { + System.out.print(str.charAt(i)); + System.out.print(' '); + } + } + System.out.print('\n'); + } + index += add; + } + if (noAppId) break; + } + + Log.d(LOG_TAG, HexDump.dumpHexString(arr)); + } + + /** + * Generate Random WSP header with string application ID + */ + protected void createRandomWspHeaderStrAppId(byte[] arr, Random rd, int headerStart, + boolean randomStr) { + + boolean appIdAdded = false; + + Log.d(LOG_TAG, "random arr length:" + arr.length); + String typename[] = new String[] { "short int", "long int", "string", "uint32"}; + + while (!appIdAdded) { + int type; + int index = headerStart; + int len = arr.length; + int i; + boolean addAppid = false; + int tmpVal = 0; + int tmpVal2 = 0; + + while (true) { + int add; + + /* + * field name + * 0: short int + * 1: long int + * 2: text + * (no uint for param value) + */ + type = rd.nextInt(3); + switch (type) { + case 0: // header short integer + if (index > 100 && !appIdAdded) addAppid = true; + add = 1; + break; + case 1: // header long int + add = 1 + rd.nextInt(29); + break; + default: // header string + add = 2 + rd.nextInt(10); + break; + } + if (index + add >= len) break; + + // fill header name + switch (type) { + case 0: // header short integer + if (!addAppid) { + do { + arr[index] = (byte) (0x80 | rd.nextInt(128)); + } while (arr[index] == (byte) 0xaf); + } else { + Log.d(LOG_TAG, "appId added."); + arr[index] = (byte) 0xaf; + } + break; + case 1: // header long int + arr[index] = (byte) (add - 1); + tmpVal2 = 0; + for (i = 1; i < add; i++) { + tmpVal = rd.nextInt(255); + tmpVal2 = (tmpVal2 << 8) | tmpVal; + arr[index + i] = (byte) tmpVal; + } + // don't set application id + if (tmpVal2 == 0x2f) arr[index + 1]++; + break; + default: // header string + for (i = 0; i < add - 1; i++) { + tmpVal = rd.nextInt(127); + if (tmpVal < 32) tmpVal= (32 + tmpVal); + arr[index + i] = (byte) tmpVal; + } + arr[index + i] = (byte) 0x0; + break; + } + + if (LOCAL_LOGV) { + Log.d(LOG_TAG, "field name index:" + index); + Log.d(LOG_TAG, "type:" + typename[type] + ", add:" + add); + if (type != 2) { + for (i = index; i < index + add; i++) { + System.out.print(Integer.toHexString(0xff & arr[i])); + System.out.print(' '); + } + } else { + System.out.print(Integer.toHexString(0xff & arr[index])); + System.out.print(' '); + String str = new String(arr, index + 1, add - 2); + for (i = 0; i < str.length(); i++) { + System.out.print(str.charAt(i)); + System.out.print(' '); + } + } + System.out.print('\n'); + } + index += add; + + + /* + * field value + * 0: short int + * 1: long int + * 2: text + * 3: uint + */ + if (addAppid) { + type = 2; + } else { + type = rd.nextInt(4); + } + switch (type) { + case 0: // header short integer + add = 1; + break; + case 1: // header long int + add = 1 + rd.nextInt(29); + break; + case 2: // header string + if (addAppid) { + if (randomStr) { + add = 1 + rd.nextInt(10); + byte[] randStr= new byte[add]; + for (i = 0; i < add; i++) { + tmpVal = rd.nextInt(127); + if (tmpVal < 32) tmpVal= (32 + tmpVal); + randStr[i] = (byte) tmpVal; + } + mAppIdName = new String(randStr); + } + add = mAppIdName.length() + 1; + } else { + add = 2 + rd.nextInt(10); + } + break; + default: // uint32 + add = 6; + } + if (index + add >= len) break; + + // fill field value + switch (type) { + case 0: // header short int + arr[index] = (byte) (0x80 | rd.nextInt(128)); + break; + case 1: // header long int + arr[index] = (byte) (add - 1); + for (i = 1; i < add; i++) + arr[index + i] = (byte) rd.nextInt(255); + break; + case 2:// header string + if (addAppid) { + addAppid = false; + appIdAdded = true; + for (i = 0; i < add - 1; i++) { + arr[index + i] = (byte) (mAppIdName.charAt(i)); + } + Log.d(LOG_TAG, "mAppIdName added [" + mAppIdName + "]"); + } else { + for (i = 0; i < add - 1; i++) { + tmpVal = rd.nextInt(127); + if (tmpVal < 32) tmpVal= (32 + tmpVal); + arr[index + i] = (byte) tmpVal; + } + } + arr[index + i] = (byte) 0x0; + break; + default: // header uvarint + arr[index] = (byte) 31; + tmpVal = rd.nextInt(0x0FFFFFFF); + add = 1 + encodeUint32(tmpVal, null, index + 1); + encodeUint32(tmpVal, arr, index + 1); + break; + + } + + if (LOCAL_LOGV) { + Log.d(LOG_TAG, "field value index:" + index); + Log.d(LOG_TAG, "type:" + typename[type] + ", add:" + add); + if (type != 2) { + for (i = index; i < index + add; i++) { + System.out.print(Integer.toHexString(0xff & arr[i])); + System.out.print(' '); + } + } else { + System.out.print(Integer.toHexString(0xff & arr[index])); + System.out.print(' '); + String str = new String(arr, index + 1, add - 2); + for (i = 0; i < str.length(); i++) { + System.out.print(str.charAt(i)); + System.out.print(' '); + } + } + System.out.print('\n'); + } + index += add; + } + } + + Log.d(LOG_TAG, "headerStart = " + headerStart + ", mAppIdName = " + mAppIdName); + Log.d(LOG_TAG, HexDump.dumpHexString(arr)); + } + + protected byte[] createPDU(int testNum) { + byte[] array = null; + // byte[] wsp = null; + + switch (testNum) { + // sample pdu + case 1: + byte[] array1 = { + (byte) 0x00, // TID + (byte) 0x06, // Type = wap push + (byte) 0x00, // Length to be set later. + + // Content-Type + (byte) 0x03, (byte) 0x02, + (byte) ((mContentTypeValue >> 8) & 0xff), + (byte) (mContentTypeValue & 0xff), + + // Application-id + (byte) 0xaf, (byte) 0x02, + (byte) ((mAppIdValue >> 8) & 0xff), + (byte) (mAppIdValue& 0xff) + }; + array1[2] = (byte) (array1.length - 3); + mWspHeader = array1; + mWspHeaderStart = mGsmHeader.length + mUserDataHeader.length + 7; + mWspHeaderLen = array1.length; + break; + + // invalid wsp header + case 2: + byte[] array2 = { + (byte) 0x00, // invalid data + }; + mWspHeader = array2; + mWspHeaderStart = mGsmHeader.length + mUserDataHeader.length; + mWspHeaderLen = array2.length; + break; + + // random wsp header + case 3: + Random rd = new Random(); + int arrSize = 150 + rd.nextInt(100); + byte[] array3 = new byte[arrSize]; + int hdrEncodeLen; + + array3[0] = (byte) 0x0; + array3[1] = (byte) 0x6; + hdrEncodeLen = encodeUint32(array3.length, null, 2); + hdrEncodeLen = encodeUint32(array3.length - hdrEncodeLen - 2, array3, 2); + array3[hdrEncodeLen + 2] = (byte) 0x3; + array3[hdrEncodeLen + 3] = (byte) 0x2; + array3[hdrEncodeLen + 4] = (byte) ((mContentTypeValue >> 8) & 0xff); + array3[hdrEncodeLen + 5] = (byte) (mContentTypeValue & 0xff); + createRandomWspHeader(array3, rd, hdrEncodeLen + 6, false); + mWspHeaderStart = mGsmHeader.length + mUserDataHeader.length + hdrEncodeLen + 6; + mWspHeaderLen = array3.length; + + Log.d(LOG_TAG, "mContentTypeValue = " + mContentTypeValue + + "(" + Integer.toHexString(mContentTypeValue) + ")"); + + mWspHeader = array3; + break; + + // random wsp header w/o appid + case 4: + rd = new Random(); + arrSize = 150 + rd.nextInt(100); + array3 = new byte[arrSize]; + + array3[0] = (byte) 0x0; + array3[1] = (byte) 0x6; + hdrEncodeLen = encodeUint32(array3.length, null, 2); + hdrEncodeLen = encodeUint32(array3.length - hdrEncodeLen - 2, array3, 2); + array3[hdrEncodeLen + 2] = (byte) 0x3; + array3[hdrEncodeLen + 3] = (byte) 0x2; + array3[hdrEncodeLen + 4] = (byte) ((mContentTypeValue >> 8) & 0xff); + array3[hdrEncodeLen + 5] = (byte) (mContentTypeValue & 0xff); + createRandomWspHeader(array3, rd, hdrEncodeLen + 6, true); + mWspHeaderStart = mGsmHeader.length + mUserDataHeader.length + hdrEncodeLen + 6; + mWspHeaderLen = array3.length; + + Log.d(LOG_TAG, "mContentTypeValue = " + mContentTypeValue + + "(" + Integer.toHexString(mContentTypeValue) + ")"); + + mWspHeader = array3; + break; + + // random wsp header w/ random appid string + case 5: + rd = new Random(); + arrSize = 150 + rd.nextInt(100); + array3 = new byte[arrSize]; + + array3[0] = (byte) 0x0; + array3[1] = (byte) 0x6; + hdrEncodeLen = encodeUint32(array3.length, null, 2); + hdrEncodeLen = encodeUint32(array3.length - hdrEncodeLen - 2, array3, 2); + array3[hdrEncodeLen + 2] = (byte) 0x3; + array3[hdrEncodeLen + 3] = (byte) 0x2; + array3[hdrEncodeLen + 4] = (byte) ((mContentTypeValue >> 8) & 0xff); + array3[hdrEncodeLen + 5] = (byte) (mContentTypeValue & 0xff); + createRandomWspHeaderStrAppId(array3, rd, hdrEncodeLen + 6, true); + mWspHeaderStart = mGsmHeader.length + mUserDataHeader.length + hdrEncodeLen + 6; + mWspHeaderLen = array3.length; + + Log.d(LOG_TAG, "mContentTypeValue = " + mContentTypeValue + + "(" + Integer.toHexString(mContentTypeValue) + ")"); + + mWspHeader = array3; + break; + + // random wsp header w/ OMA appid string + case 6: + rd = new Random(); + arrSize = 150 + rd.nextInt(100); + array3 = new byte[arrSize]; + + array3[0] = (byte) 0x0; + array3[1] = (byte) 0x6; + hdrEncodeLen = encodeUint32(array3.length, null, 2); + hdrEncodeLen = encodeUint32(array3.length - hdrEncodeLen - 2, array3, 2); + array3[hdrEncodeLen + 2] = (byte) 0x3; + array3[hdrEncodeLen + 3] = (byte) 0x2; + array3[hdrEncodeLen + 4] = (byte) ((mContentTypeValue >> 8) & 0xff); + array3[hdrEncodeLen + 5] = (byte) (mContentTypeValue & 0xff); + createRandomWspHeaderStrAppId(array3, rd, hdrEncodeLen + 6, false); + mWspHeaderStart = mGsmHeader.length + mUserDataHeader.length + hdrEncodeLen + 6; + mWspHeaderLen = array3.length; + + Log.d(LOG_TAG, "mContentTypeValue = " + mContentTypeValue + + "(" + Integer.toHexString(mContentTypeValue) + ")"); + + mWspHeader = array3; + break; + + // random wsp header w/ OMA content type + case 7: + rd = new Random(); + arrSize = 150 + rd.nextInt(100); + array3 = new byte[arrSize]; + + array3[0] = (byte) 0x0; + array3[1] = (byte) 0x6; + hdrEncodeLen = encodeUint32(array3.length, null, 2); + hdrEncodeLen = encodeUint32(array3.length - hdrEncodeLen - 2, array3, 2); + + // encode content type + int contentLen = mContentTypeName.length(); + int next = 2 + hdrEncodeLen; + mWspContentTypeStart = mGsmHeader.length + mUserDataHeader.length + next; + // next += encodeUint32(contentLen, array3, next); + int i; + Log.d(LOG_TAG, "mContentTypeName = " + mContentTypeName + + ", contentLen = " + contentLen); + + for (i = 0; i < contentLen; i++) { + array3[next + i] = (byte) mContentTypeName.charAt(i); + } + array3[next + i] = (byte) 0x0; + + createRandomWspHeader(array3, rd, next + contentLen + 1, false); + mWspHeaderStart = mGsmHeader.length + mUserDataHeader.length + + next + contentLen + 1; + mWspHeaderLen = array3.length; + + mWspHeader = array3; + break; + + // random wsp header w/ OMA content type, OMA app ID + case 8: + rd = new Random(); + arrSize = 150 + rd.nextInt(100); + array3 = new byte[arrSize]; + + array3[0] = (byte) 0x0; + array3[1] = (byte) 0x6; + hdrEncodeLen = encodeUint32(array3.length, null, 2); + hdrEncodeLen = encodeUint32(array3.length - hdrEncodeLen - 2, array3, 2); + + // encode content type + contentLen = mContentTypeName.length(); + next = 2 + hdrEncodeLen; + mWspContentTypeStart = mGsmHeader.length + mUserDataHeader.length + next; + // next += encodeUint32(contentLen, array3, next); + Log.d(LOG_TAG, "mContentTypeName = " + mContentTypeName + + ", contentLen = " + contentLen); + + for (i = 0; i < contentLen; i++) { + array3[next + i] = (byte) mContentTypeName.charAt(i); + } + array3[next + i] = (byte) 0x0; + + createRandomWspHeaderStrAppId(array3, rd, next + contentLen + 1, false); + mWspHeaderStart = mGsmHeader.length + mUserDataHeader.length + + next + contentLen + 1; + mWspHeaderLen = array3.length; + + mWspHeader = array3; + break; + + default: + return null; + } + array = new byte[mGsmHeader.length + mUserDataHeader.length + mWspHeader.length + + mMessageBody.length]; + System.arraycopy(mGsmHeader, 0, array, 0, mGsmHeader.length); + System.arraycopy(mUserDataHeader, 0, array, + mGsmHeader.length, mUserDataHeader.length); + System.arraycopy(mWspHeader, 0, array, + mGsmHeader.length + mUserDataHeader.length, mWspHeader.length); + System.arraycopy(mMessageBody, 0, array, + mGsmHeader.length + mUserDataHeader.length + mWspHeader.length, + mMessageBody.length); + return array; + + } + + Intent createIntent(int pduType, int tranId) { + Intent intent = new Intent(); + intent.putExtra("transactionId", tranId); + intent.putExtra("pduType", pduType); + intent.putExtra("header", mGsmHeader); + intent.putExtra("data", mMessageBody); + // intent.putExtra("contentTypeParameters", null); + return intent; + } + + /** + * Message processing test, start activity + */ + public void testProcessMsg1() { + byte[] pdu = createPDU(1); + int headerLen = pdu.length - + (mGsmHeader.length + mUserDataHeader.length + mMessageBody.length); + int pduType = 6; + int tranId = 0; + String originalPackageName = mPackageName; + String originalClassName = mClassName; + + try { + + mClassName = "com.android.smspush.unitTests.ReceiverActivity"; + + // set up data + IWapPushManager iwapman = getInterface(); + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_ACTIVITY, false, false); + + assertTrue((iwapman.processMessage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + createIntent(pduType, tranId)) + & WapPushManagerParams.MESSAGE_HANDLED) == + WapPushManagerParams.MESSAGE_HANDLED); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + + } catch (RemoteException e) { + assertTrue(false); + } + + mPackageName = originalPackageName; + mClassName = originalClassName; + } + + /** + * Message processing test, start service + */ + public void testProcessMsg2() { + byte[] pdu = createPDU(1); + int headerLen = pdu.length - (mGsmHeader.length + + mUserDataHeader.length + mMessageBody.length); + int pduType = 6; + int tranId = 0; + String originalPackageName = mPackageName; + String originalClassName = mClassName; + + try { + + mClassName = "com.android.smspush.unitTests.ReceiverService"; + + // set up data + IWapPushManager iwapman = getInterface(); + + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, false, false); + + assertTrue((iwapman.processMessage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + createIntent(pduType, tranId)) + & WapPushManagerParams.MESSAGE_HANDLED) == + WapPushManagerParams.MESSAGE_HANDLED); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + + } catch (RemoteException e) { + assertTrue(false); + } + + mPackageName = originalPackageName; + mClassName = originalClassName; + } + + /** + * Message processing test, no signature + */ + public void testProcessMsg3() { + byte[] pdu = createPDU(1); + int headerLen = pdu.length - + (mGsmHeader.length + mUserDataHeader.length + mMessageBody.length); + int pduType = 6; + int tranId = 0; + String originalPackageName = mPackageName; + String originalClassName = mClassName; + + try { + + mPackageName = "com.android.development"; + mClassName = "com.android.development.Development"; + + // set up data + IWapPushManager iwapman = getInterface(); + + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, true, false); + + assertFalse((iwapman.processMessage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + createIntent(pduType, tranId)) + & WapPushManagerParams.MESSAGE_HANDLED) == + WapPushManagerParams.MESSAGE_HANDLED); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + + } catch (RemoteException e) { + assertTrue(false); + } + + mPackageName = originalPackageName; + mClassName = originalClassName; + } + + IDataVerify getVerifyInterface() { + while (mIVerify == null) { + // wait for the activity receive data. + try { + Thread.sleep(TIME_WAIT); + } catch (InterruptedException e) {} + } + return mIVerify; + } + + + /** + * Message processing test, received body data verification test + */ + public void testProcessMsg4() { + byte[] originalMessageBody = mMessageBody; + mMessageBody = new byte[] { + (byte) 0xee, + (byte) 0xff, + (byte) 0xee, + (byte) 0xff, + (byte) 0xee, + (byte) 0xff, + (byte) 0xee, + (byte) 0xff, + (byte) 0xee, + (byte) 0xff, + (byte) 0xee, + (byte) 0xff, + }; + + byte[] pdu = createPDU(1); + int headerLen = pdu.length - + (mGsmHeader.length + mUserDataHeader.length + mMessageBody.length); + int pduType = 6; + int tranId = 0; + String originalPackageName = mPackageName; + String originalClassName = mClassName; + + try { + IWapPushManager iwapman = getInterface(); + IDataVerify dataverify = getVerifyInterface(); + + dataverify.resetData(); + + // set up data + mClassName = "com.android.smspush.unitTests.ReceiverActivity"; + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_ACTIVITY, false, false); + + iwapman.processMessage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + createIntent(pduType, tranId)); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + + assertTrue(dataverify.verifyData(mMessageBody)); + + // set up data + dataverify.resetData(); + mClassName = "com.android.smspush.unitTests.ReceiverService"; + mMessageBody = new byte[] { + (byte) 0xaa, + (byte) 0xbb, + (byte) 0x11, + (byte) 0x22, + (byte) 0xaa, + (byte) 0xbb, + (byte) 0x11, + (byte) 0x22, + (byte) 0xaa, + (byte) 0xbb, + (byte) 0x11, + (byte) 0x22, + (byte) 0xaa, + (byte) 0xbb, + (byte) 0x11, + (byte) 0x22, + (byte) 0xaa, + (byte) 0xbb, + (byte) 0x11, + (byte) 0x22, + (byte) 0xaa, + (byte) 0xbb, + (byte) 0x11, + (byte) 0x22, + }; + pdu = createPDU(1); + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, false, false); + + iwapman.processMessage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + createIntent(pduType, tranId)); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + + // Log.d(LOG_TAG, HexDump.dumpHexString(mMessageBody)); + assertTrue(dataverify.verifyData(mMessageBody)); + } catch (RemoteException e) { + assertTrue(false); + } + + mPackageName = originalPackageName; + mClassName = originalClassName; + mMessageBody = originalMessageBody; + } + + /** + * Message processing test, send invalid sms data + */ + public void testProcessMsg5() { + byte[] pdu = createPDU(2); + int headerLen = pdu.length - + (mGsmHeader.length + mUserDataHeader.length + mMessageBody.length); + int pduType = 6; + int tranId = 0; + String originalPackageName = mPackageName; + String originalClassName = mClassName; + + try { + + mClassName = "com.android.smspush.unitTests.ReceiverActivity"; + + // set up data + IWapPushManager iwapman = getInterface(); + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_ACTIVITY, false, false); + + assertTrue((iwapman.processMessage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + createIntent(pduType, tranId)) + & WapPushManagerParams.MESSAGE_HANDLED) == + WapPushManagerParams.MESSAGE_HANDLED); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + + } catch (RemoteException e) { + assertTrue(false); + } + + mPackageName = originalPackageName; + mClassName = originalClassName; + } + + /** + * Message processing test, no receiver application + */ + public void testProcessMsg6() { + byte[] pdu = createPDU(1); + int headerLen = pdu.length - + (mGsmHeader.length + mUserDataHeader.length + mMessageBody.length); + int pduType = 6; + int tranId = 0; + String originalPackageName = mPackageName; + String originalClassName = mClassName; + + try { + + mClassName = "com.android.smspush.unitTests.NoReceiver"; + + // set up data + IWapPushManager iwapman = getInterface(); + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_ACTIVITY, false, false); + + assertFalse((iwapman.processMessage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + createIntent(pduType, tranId)) + & WapPushManagerParams.MESSAGE_HANDLED) == + WapPushManagerParams.MESSAGE_HANDLED); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + + // set up data + iwapman.addPackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, false, false); + + assertFalse((iwapman.processMessage( + Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), + createIntent(pduType, tranId)) + & WapPushManagerParams.MESSAGE_HANDLED) == + WapPushManagerParams.MESSAGE_HANDLED); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + Integer.toString(mContentTypeValue), mPackageName, mClassName); + + } catch (RemoteException e) { + assertTrue(false); + } + + mPackageName = originalPackageName; + mClassName = originalClassName; + } + + /** + * WspTypeDecoder test, normal pdu + */ + public void testDecoder1() { + boolean res; + int originalAppIdValue = mAppIdValue; + Random rd = new Random(); + + for (int i = 0; i < 10; i++) { + mAppIdValue = rd.nextInt(0xFFFF); + byte[] pdu = createPDU(1); + WspTypeDecoder pduDecoder = new WspTypeDecoder(pdu); + + res = pduDecoder.seekXWapApplicationId(mWspHeaderStart, + mWspHeaderStart + mWspHeaderLen - 1); + assertTrue(res); + + int index = (int) pduDecoder.getValue32(); + res = pduDecoder.decodeXWapApplicationId(index); + assertTrue(res); + + Log.d(LOG_TAG, "mAppIdValue: " + mAppIdValue + + ", val: " + pduDecoder.getValue32()); + assertTrue(mAppIdValue == (int) pduDecoder.getValue32()); + } + + mAppIdValue = originalAppIdValue; + } + + /** + * WspTypeDecoder test, no header + */ + public void testDecoder2() { + boolean res; + int originalAppIdValue = mAppIdValue; + Random rd = new Random(); + + mAppIdValue = rd.nextInt(0xFFFF); + byte[] pdu = createPDU(2); + WspTypeDecoder pduDecoder = new WspTypeDecoder(pdu); + + res = pduDecoder.seekXWapApplicationId(mWspHeaderStart, + mWspHeaderStart + mWspHeaderLen - 1); + assertFalse(res); + + mAppIdValue = originalAppIdValue; + } + + /** + * WspTypeDecoder test, decode appid test + */ + public void testDecoder3() { + boolean res; + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + Random rd = new Random(); + + for (int i = 0; i < 100; i++) { + mAppIdValue = rd.nextInt(0x0FFFFFFF); + mContentTypeValue = rd.nextInt(0x0FFF); + byte[] pdu = createPDU(3); + WspTypeDecoder pduDecoder = new WspTypeDecoder(pdu); + + res = pduDecoder.seekXWapApplicationId(mWspHeaderStart, + mWspHeaderStart + mWspHeaderLen - 1); + assertTrue(res); + + int index = (int) pduDecoder.getValue32(); + res = pduDecoder.decodeXWapApplicationId(index); + assertTrue(res); + + Log.d(LOG_TAG, "mAppIdValue: " + mAppIdValue + + ", val: " + pduDecoder.getValue32()); + assertTrue(mAppIdValue == (int) pduDecoder.getValue32()); + } + + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + } + + /* + public void testEnc() { + byte[] arr = new byte[20]; + int index = 0; + index += encodeUint32(0x87a5, arr, index); + index += encodeUint32(0x1, arr, index); + index += encodeUint32(0x9b, arr, index); + index += encodeUint32(0x10, arr, index); + index += encodeUint32(0xe0887, arr, index); + index += encodeUint32(0x791a23d0, arr, index); + + Log.d(LOG_TAG, HexDump.dumpHexString(arr)); + } + */ + + /** + * WspTypeDecoder test, no appid test + */ + public void testDecoder4() { + boolean res; + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + Random rd = new Random(); + + for (int i = 0; i < 100; i++) { + mAppIdValue = rd.nextInt(0x0FFFFFFF); + mContentTypeValue = rd.nextInt(0x0FFF); + byte[] pdu = createPDU(4); + WspTypeDecoder pduDecoder = new WspTypeDecoder(pdu); + + res = pduDecoder.seekXWapApplicationId(mWspHeaderStart, + mWspHeaderStart + mWspHeaderLen - 1); + assertFalse(res); + + } + + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + } + + /** + * WspTypeDecoder test, decode string appid test + */ + public void testDecoder5() { + boolean res; + String originalAppIdName = mAppIdName; + int originalContentTypeValue = mContentTypeValue; + Random rd = new Random(); + + for (int i = 0; i < 10; i++) { + mAppIdValue = rd.nextInt(0x0FFFFFFF); + mContentTypeValue = rd.nextInt(0x0FFF); + byte[] pdu = createPDU(5); + WspTypeDecoder pduDecoder = new WspTypeDecoder(pdu); + + res = pduDecoder.seekXWapApplicationId(mWspHeaderStart, + mWspHeaderStart + mWspHeaderLen - 1); + assertTrue(res); + + int index = (int) pduDecoder.getValue32(); + res = pduDecoder.decodeXWapApplicationId(index); + assertTrue(res); + + Log.d(LOG_TAG, "mAppIdValue: [" + mAppIdName + "], val: [" + + pduDecoder.getValueString() + "]"); + assertTrue(mAppIdName.equals(pduDecoder.getValueString())); + } + + mAppIdName = originalAppIdName; + mContentTypeValue = originalContentTypeValue; + } + + /** + * WspTypeDecoder test, decode string appid test + */ + public void testDecoder6() { + boolean res; + String originalAppIdName = mAppIdName; + int originalContentTypeValue = mContentTypeValue; + Random rd = new Random(); + + for (int i = 0; i < OMA_APPLICATION_ID_NAMES.length; i++) { + mAppIdName = OMA_APPLICATION_ID_NAMES[i]; + mContentTypeValue = rd.nextInt(0x0FFF); + byte[] pdu = createPDU(6); + WspTypeDecoder pduDecoder = new WspTypeDecoder(pdu); + + res = pduDecoder.seekXWapApplicationId(mWspHeaderStart, + mWspHeaderStart + mWspHeaderLen - 1); + assertTrue(res); + + int index = (int) pduDecoder.getValue32(); + res = pduDecoder.decodeXWapApplicationId(index); + assertTrue(res); + + Log.d(LOG_TAG, "mAppIdValue: [" + mAppIdName + "], val: [" + + pduDecoder.getValueString() + "]"); + assertTrue(mAppIdName.equals(pduDecoder.getValueString())); + } + + mAppIdName = originalAppIdName; + mContentTypeValue = originalContentTypeValue; + } + + /** + * WspTypeDecoder test, decode OMA content type + */ + public void testDecoder7() { + boolean res; + String originalAppIdName = mAppIdName; + int originalContentTypeValue = mContentTypeValue; + Random rd = new Random(); + + for (int i = 0; i < OMA_CONTENT_TYPE_NAMES.length; i++) { + mContentTypeName = OMA_CONTENT_TYPE_NAMES[i]; + byte[] pdu = createPDU(7); + WspTypeDecoder pduDecoder = new WspTypeDecoder(pdu); + + res = pduDecoder.decodeContentType(mWspContentTypeStart); + assertTrue(res); + + Log.d(LOG_TAG, "mContentTypeName: [" + mContentTypeName + "], val: [" + + pduDecoder.getValueString() + "]"); + assertTrue(mContentTypeName.equals(pduDecoder.getValueString())); + } + + mAppIdName = originalAppIdName; + mContentTypeValue = originalContentTypeValue; + } + + + /** + * Copied from WapPushOverSms. + * The code flow is not changed from the original. + */ + public int dispatchWapPdu(byte[] pdu, IWapPushManager wapPushMan) { + + if (Config.DEBUG) Log.d(LOG_TAG, "Rx: " + IccUtils.bytesToHexString(pdu)); + + int index = 0; + int transactionId = pdu[index++] & 0xFF; + int pduType = pdu[index++] & 0xFF; + int headerLength = 0; + + if ((pduType != WspTypeDecoder.PDU_TYPE_PUSH) && + (pduType != WspTypeDecoder.PDU_TYPE_CONFIRMED_PUSH)) { + if (Config.DEBUG) Log.w(LOG_TAG, "Received non-PUSH WAP PDU. Type = " + pduType); + return Intents.RESULT_SMS_HANDLED; + } + + WspTypeDecoder pduDecoder = new WspTypeDecoder(pdu); + + /** + * Parse HeaderLen(unsigned integer). + * From wap-230-wsp-20010705-a section 8.1.2 + * The maximum size of a uintvar is 32 bits. + * So it will be encoded in no more than 5 octets. + */ + if (pduDecoder.decodeUintvarInteger(index) == false) { + if (Config.DEBUG) Log.w(LOG_TAG, "Received PDU. Header Length error."); + return Intents.RESULT_SMS_GENERIC_ERROR; + } + headerLength = (int) pduDecoder.getValue32(); + index += pduDecoder.getDecodedDataLength(); + + int headerStartIndex = index; + + /** + * Parse Content-Type. + * From wap-230-wsp-20010705-a section 8.4.2.24 + * + * Content-type-value = Constrained-media | Content-general-form + * Content-general-form = Value-length Media-type + * Media-type = (Well-known-media | Extension-Media) *(Parameter) + * Value-length = Short-length | (Length-quote Length) + * Short-length = <Any octet 0-30> (octet <= WAP_PDU_SHORT_LENGTH_MAX) + * Length-quote = <Octet 31> (WAP_PDU_LENGTH_QUOTE) + * Length = Uintvar-integer + */ + if (pduDecoder.decodeContentType(index) == false) { + if (Config.DEBUG) Log.w(LOG_TAG, "Received PDU. Header Content-Type error."); + return Intents.RESULT_SMS_GENERIC_ERROR; + } + + String mimeType = pduDecoder.getValueString(); + long binaryContentType = pduDecoder.getValue32(); + index += pduDecoder.getDecodedDataLength(); + + byte[] header = new byte[headerLength]; + System.arraycopy(pdu, headerStartIndex, header, 0, header.length); + + byte[] intentData; + + if (mimeType != null && mimeType.equals(WspTypeDecoder.CONTENT_TYPE_B_PUSH_CO)) { + intentData = pdu; + } else { + int dataIndex = headerStartIndex + headerLength; + intentData = new byte[pdu.length - dataIndex]; + System.arraycopy(pdu, dataIndex, intentData, 0, intentData.length); + } + + /** + * Seek for application ID field in WSP header. + * If application ID is found, WapPushManager substitute the message + * processing. Since WapPushManager is optional module, if WapPushManager + * is not found, legacy message processing will be continued. + */ + if (pduDecoder.seekXWapApplicationId(index, index + headerLength - 1)) { + index = (int) pduDecoder.getValue32(); + pduDecoder.decodeXWapApplicationId(index); + String wapAppId = pduDecoder.getValueString(); + if (wapAppId == null) { + wapAppId = Integer.toString((int) pduDecoder.getValue32()); + } + + String contentType = ((mimeType == null) ? + Long.toString(binaryContentType) : mimeType); + if (Config.DEBUG) Log.v(LOG_TAG, "appid found: " + wapAppId + ":" + contentType); + + try { + boolean processFurther = true; + // IWapPushManager wapPushMan = mWapConn.getWapPushManager(); + if (wapPushMan == null) { + if (Config.DEBUG) Log.w(LOG_TAG, "wap push manager not found!"); + } else { + Intent intent = new Intent(); + intent.putExtra("transactionId", transactionId); + intent.putExtra("pduType", pduType); + intent.putExtra("header", header); + intent.putExtra("data", intentData); + intent.putExtra("contentTypeParameters", + pduDecoder.getContentParameters()); + + int procRet = wapPushMan.processMessage(wapAppId, contentType, intent); + if (Config.DEBUG) Log.v(LOG_TAG, "procRet:" + procRet); + if ((procRet & WapPushManagerParams.MESSAGE_HANDLED) > 0 + && (procRet & WapPushManagerParams.FURTHER_PROCESSING) == 0) { + processFurther = false; + } + } + if (!processFurther) { + return Intents.RESULT_SMS_HANDLED; + } + } catch (RemoteException e) { + if (Config.DEBUG) Log.w(LOG_TAG, "remote func failed..."); + } + } + if (Config.DEBUG) Log.v(LOG_TAG, "fall back to existing handler"); + + return Activity.RESULT_OK; + } + + protected byte[] retrieveWspBody() { + byte[] array = new byte[mWspHeader.length + mMessageBody.length]; + + System.arraycopy(mWspHeader, 0, array, 0, mWspHeader.length); + System.arraycopy(mMessageBody, 0, array, mWspHeader.length, mMessageBody.length); + return array; + } + + protected String getContentTypeName(int ctypeVal) { + int i; + + for (i = 0; i < OMA_CONTENT_TYPE_VALUES.length; i++) { + if (ctypeVal == OMA_CONTENT_TYPE_VALUES[i]) { + return OMA_CONTENT_TYPE_NAMES[i]; + } + } + return null; + } + + protected boolean isContentTypeMapped(int ctypeVal) { + int i; + + for (i = 0; i < OMA_CONTENT_TYPE_VALUES.length; i++) { + if (ctypeVal == OMA_CONTENT_TYPE_VALUES[i]) return true; + } + return false; + } + + /** + * Integration test 1, simple case + */ + public void testIntegration1() { + boolean res; + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + String originalAppIdName = mAppIdName; + String originalContentTypeName = mContentTypeName; + String originalClassName = mClassName; + byte[] originalMessageBody = mMessageBody; + Random rd = new Random(); + + mMessageBody = new byte[100 + rd.nextInt(100)]; + rd.nextBytes(mMessageBody); + + byte[] pdu = createPDU(1); + byte[] wappushPdu = retrieveWspBody(); + + + mClassName = "com.android.smspush.unitTests.ReceiverActivity"; + // Phone dummy = new DummyPhone(getContext()); + // Phone gsm = PhoneFactory.getGsmPhone(); + // GSMPhone gsm = new GSMPhone(getContext(), new SimulatedCommands(), null, true); + // WapPushOverSms dispatcher = new WapPushOverSms(dummy, null); + + try { + // set up data + IWapPushManager iwapman = getInterface(); + IDataVerify dataverify = getVerifyInterface(); + + dataverify.resetData(); + + if (isContentTypeMapped(mContentTypeValue)) { + // content type is mapped + mContentTypeName = getContentTypeName(mContentTypeValue); + Log.d(LOG_TAG, "mContentTypeValue mapping " + + mContentTypeName + ":" + mContentTypeValue); + } else { + mContentTypeName = Integer.toString(mContentTypeValue); + } + iwapman.addPackage(Integer.toString(mAppIdValue), + mContentTypeName, mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_ACTIVITY, false, false); + + dispatchWapPdu(wappushPdu, iwapman); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + mContentTypeName, mPackageName, mClassName); + + assertTrue(dataverify.verifyData(mMessageBody)); + } catch (RemoteException e) { + } + + + mClassName = originalClassName; + mAppIdName = originalAppIdName; + mContentTypeName = originalContentTypeName; + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + mMessageBody = originalMessageBody; + } + + /** + * Integration test 2, random mAppIdValue(int), all OMA content type + */ + public void testIntegration2() { + boolean res; + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + String originalAppIdName = mAppIdName; + String originalContentTypeName = mContentTypeName; + String originalClassName = mClassName; + byte[] originalMessageBody = mMessageBody; + Random rd = new Random(); + + IWapPushManager iwapman = getInterface(); + IDataVerify dataverify = getVerifyInterface(); + mClassName = "com.android.smspush.unitTests.ReceiverActivity"; + + for (int i = 0; i < OMA_CONTENT_TYPE_NAMES.length; i++) { + mContentTypeName = OMA_CONTENT_TYPE_NAMES[i]; + mAppIdValue = rd.nextInt(0x0FFFFFFF); + + mMessageBody = new byte[100 + rd.nextInt(100)]; + rd.nextBytes(mMessageBody); + + byte[] pdu = createPDU(7); + byte[] wappushPdu = retrieveWspBody(); + + try { + dataverify.resetData(); + // set up data + iwapman.addPackage(Integer.toString(mAppIdValue), + mContentTypeName, mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_ACTIVITY, false, false); + + dispatchWapPdu(wappushPdu, iwapman); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + mContentTypeName, mPackageName, mClassName); + + if (mContentTypeName.equals(WspTypeDecoder.CONTENT_TYPE_B_PUSH_CO)) { + assertTrue(dataverify.verifyData(wappushPdu)); + } else { + assertTrue(dataverify.verifyData(mMessageBody)); + } + } catch (RemoteException e) { + } + } + + + mClassName = originalClassName; + mAppIdName = originalAppIdName; + mContentTypeName = originalContentTypeName; + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + mMessageBody = originalMessageBody; + } + + /** + * Integration test 3, iterate OmaApplication ID, random binary content type + */ + public void testIntegration3() { + boolean res; + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + String originalAppIdName = mAppIdName; + String originalContentTypeName = mContentTypeName; + String originalClassName = mClassName; + byte[] originalMessageBody = mMessageBody; + Random rd = new Random(); + + IWapPushManager iwapman = getInterface(); + IDataVerify dataverify = getVerifyInterface(); + mClassName = "com.android.smspush.unitTests.ReceiverService"; + + for (int i = 0; i < OMA_APPLICATION_ID_NAMES.length; i++) { + mAppIdName = OMA_APPLICATION_ID_NAMES[i]; + mContentTypeValue = rd.nextInt(0x0FFF); + + mMessageBody = new byte[100 + rd.nextInt(100)]; + rd.nextBytes(mMessageBody); + + byte[] pdu = createPDU(6); + byte[] wappushPdu = retrieveWspBody(); + + try { + dataverify.resetData(); + // set up data + if (isContentTypeMapped(mContentTypeValue)) { + // content type is mapped to integer value + mContentTypeName = getContentTypeName(mContentTypeValue); + Log.d(LOG_TAG, "mContentTypeValue mapping " + + mContentTypeValue + ":" + mContentTypeName); + } else { + mContentTypeName = Integer.toString(mContentTypeValue); + } + + iwapman.addPackage(mAppIdName, + mContentTypeName, mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, false, false); + + dispatchWapPdu(wappushPdu, iwapman); + + // clean up data + iwapman.deletePackage(mAppIdName, + mContentTypeName, mPackageName, mClassName); + + if (mContentTypeName.equals(WspTypeDecoder.CONTENT_TYPE_B_PUSH_CO)) { + assertTrue(dataverify.verifyData(wappushPdu)); + } else { + assertTrue(dataverify.verifyData(mMessageBody)); + } + } catch (RemoteException e) { + } + } + + mClassName = originalClassName; + mAppIdName = originalAppIdName; + mContentTypeName = originalContentTypeName; + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + mMessageBody = originalMessageBody; + } + + /** + * Integration test 4, iterate OmaApplication ID, Oma content type + */ + public void testIntegration4() { + boolean res; + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + String originalAppIdName = mAppIdName; + String originalContentTypeName = mContentTypeName; + String originalClassName = mClassName; + byte[] originalMessageBody = mMessageBody; + Random rd = new Random(); + + IWapPushManager iwapman = getInterface(); + IDataVerify dataverify = getVerifyInterface(); + mClassName = "com.android.smspush.unitTests.ReceiverService"; + + for (int i = 0; i < OMA_APPLICATION_ID_NAMES.length + + OMA_CONTENT_TYPE_NAMES.length; i++) { + mAppIdName = OMA_APPLICATION_ID_NAMES[rd.nextInt(OMA_APPLICATION_ID_NAMES.length)]; + int contIndex = rd.nextInt(OMA_CONTENT_TYPE_NAMES.length); + mContentTypeName = OMA_CONTENT_TYPE_NAMES[contIndex]; + + mMessageBody = new byte[100 + rd.nextInt(100)]; + rd.nextBytes(mMessageBody); + + byte[] pdu = createPDU(8); + byte[] wappushPdu = retrieveWspBody(); + + try { + dataverify.resetData(); + // set up data + iwapman.addPackage(mAppIdName, + mContentTypeName, mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, false, false); + + dispatchWapPdu(wappushPdu, iwapman); + + // clean up data + iwapman.deletePackage(mAppIdName, + mContentTypeName, mPackageName, mClassName); + + if (mContentTypeName.equals(WspTypeDecoder.CONTENT_TYPE_B_PUSH_CO)) { + assertTrue(dataverify.verifyData(wappushPdu)); + } else { + assertTrue(dataverify.verifyData(mMessageBody)); + } + } catch (RemoteException e) { + } + } + + mClassName = originalClassName; + mAppIdName = originalAppIdName; + mContentTypeName = originalContentTypeName; + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + mMessageBody = originalMessageBody; + } + + /** + * Integration test 5, iterate binary OmaApplication ID, Oma binary content type + */ + public void testIntegration5() { + boolean res; + int originalAppIdValue = mAppIdValue; + int originalContentTypeValue = mContentTypeValue; + String originalAppIdName = mAppIdName; + String originalContentTypeName = mContentTypeName; + String originalClassName = mClassName; + byte[] originalMessageBody = mMessageBody; + Random rd = new Random(); + + IWapPushManager iwapman = getInterface(); + IDataVerify dataverify = getVerifyInterface(); + mClassName = "com.android.smspush.unitTests.ReceiverService"; + + for (int i = 0; i < OMA_APPLICATION_ID_VALUES.length + + OMA_CONTENT_TYPE_VALUES.length; i++) { + mAppIdValue = OMA_APPLICATION_ID_VALUES[rd.nextInt( + OMA_APPLICATION_ID_VALUES.length)]; + mContentTypeValue = + OMA_CONTENT_TYPE_VALUES[rd.nextInt(OMA_CONTENT_TYPE_VALUES.length)]; + + mMessageBody = new byte[100 + rd.nextInt(100)]; + rd.nextBytes(mMessageBody); + + byte[] pdu = createPDU(3); + byte[] wappushPdu = retrieveWspBody(); + + try { + dataverify.resetData(); + // set up data + if (isContentTypeMapped(mContentTypeValue)) { + // content type is mapped to integer value + mContentTypeName = getContentTypeName(mContentTypeValue); + Log.d(LOG_TAG, "mContentTypeValue mapping " + + mContentTypeValue + ":" + mContentTypeName); + } else { + mContentTypeName = Integer.toString(mContentTypeValue); + } + + iwapman.addPackage(Integer.toString(mAppIdValue), + mContentTypeName, mPackageName, mClassName, + WapPushManagerParams.APP_TYPE_SERVICE, false, false); + + dispatchWapPdu(wappushPdu, iwapman); + + // clean up data + iwapman.deletePackage(Integer.toString(mAppIdValue), + mContentTypeName, mPackageName, mClassName); + + if (mContentTypeName.equals(WspTypeDecoder.CONTENT_TYPE_B_PUSH_CO)) { + assertTrue(dataverify.verifyData(wappushPdu)); + } else { + assertTrue(dataverify.verifyData(mMessageBody)); + } + } catch (RemoteException e) { + } + } + + mClassName = originalClassName; + mAppIdName = originalAppIdName; + mContentTypeName = originalContentTypeName; + mAppIdValue = originalAppIdValue; + mContentTypeValue = originalContentTypeValue; + mMessageBody = originalMessageBody; + } + +} |