From 2a65c3dc8fbf0e445e0d2d3218324cd745e419d4 Mon Sep 17 00:00:00 2001 From: topjohnwu Date: Sat, 27 Oct 2018 15:08:11 -0400 Subject: [PATCH] Prepare for new database implementation --- .../com/topjohnwu/magisk/MagiskManager.java | 6 +- .../magisk/adapters/PolicyAdapter.java | 6 +- .../magisk/adapters/SectionedAdapter.java | 6 +- .../magisk/adapters/SuLogAdapter.java | 39 ++++---- .../com/topjohnwu/magisk/asyncs/PatchAPK.java | 1 - .../topjohnwu/magisk/container/Policy.java | 17 ++-- .../magisk/container/SuLogEntry.java | 19 ++-- .../topjohnwu/magisk/database/MagiskDB.java | 60 ++++++++++++ ...atabaseHelper.java => MagiskDBLegacy.java} | 94 +++++++++---------- .../magisk/fragments/SuperuserFragment.java | 2 +- 10 files changed, 146 insertions(+), 104 deletions(-) create mode 100644 app/src/full/java/com/topjohnwu/magisk/database/MagiskDB.java rename app/src/full/java/com/topjohnwu/magisk/database/{MagiskDatabaseHelper.java => MagiskDBLegacy.java} (81%) diff --git a/app/src/full/java/com/topjohnwu/magisk/MagiskManager.java b/app/src/full/java/com/topjohnwu/magisk/MagiskManager.java index 8a0f48bb0..96e01bb2d 100644 --- a/app/src/full/java/com/topjohnwu/magisk/MagiskManager.java +++ b/app/src/full/java/com/topjohnwu/magisk/MagiskManager.java @@ -6,7 +6,7 @@ import android.content.res.Configuration; import android.preference.PreferenceManager; import android.text.TextUtils; -import com.topjohnwu.magisk.database.MagiskDatabaseHelper; +import com.topjohnwu.magisk.database.MagiskDB; import com.topjohnwu.magisk.database.RepoDatabaseHelper; import com.topjohnwu.magisk.utils.LocaleManager; import com.topjohnwu.magisk.utils.RootUtils; @@ -22,7 +22,7 @@ public class MagiskManager extends ContainerApp { // Global resources public SharedPreferences prefs; - public MagiskDatabaseHelper mDB; + public MagiskDB mDB; public RepoDatabaseHelper repoDB; public MagiskManager() { @@ -38,7 +38,7 @@ public class MagiskManager extends ContainerApp { Shell.Config.setInitializer(RootUtils.class); prefs = PreferenceManager.getDefaultSharedPreferences(this); - mDB = MagiskDatabaseHelper.getInstance(); + mDB = MagiskDB.getInstance(); String pkg = mDB.getStrings(Const.Key.SU_MANAGER, null); if (pkg != null && getPackageName().equals(Const.ORIG_PKG_NAME)) { diff --git a/app/src/full/java/com/topjohnwu/magisk/adapters/PolicyAdapter.java b/app/src/full/java/com/topjohnwu/magisk/adapters/PolicyAdapter.java index 51e110bf6..8a9d622d7 100644 --- a/app/src/full/java/com/topjohnwu/magisk/adapters/PolicyAdapter.java +++ b/app/src/full/java/com/topjohnwu/magisk/adapters/PolicyAdapter.java @@ -16,7 +16,7 @@ import com.topjohnwu.magisk.components.CustomAlertDialog; import com.topjohnwu.magisk.components.ExpandableView; import com.topjohnwu.magisk.components.SnackbarMaker; import com.topjohnwu.magisk.container.Policy; -import com.topjohnwu.magisk.database.MagiskDatabaseHelper; +import com.topjohnwu.magisk.database.MagiskDB; import com.topjohnwu.magisk.utils.FingerprintHelper; import java.util.HashSet; @@ -30,11 +30,11 @@ import butterknife.BindView; public class PolicyAdapter extends RecyclerView.Adapter { private List policyList; - private MagiskDatabaseHelper dbHelper; + private MagiskDB dbHelper; private PackageManager pm; private Set expandList = new HashSet<>(); - public PolicyAdapter(List list, MagiskDatabaseHelper db, PackageManager pm) { + public PolicyAdapter(List list, MagiskDB db, PackageManager pm) { policyList = list; dbHelper = db; this.pm = pm; diff --git a/app/src/full/java/com/topjohnwu/magisk/adapters/SectionedAdapter.java b/app/src/full/java/com/topjohnwu/magisk/adapters/SectionedAdapter.java index 39fd040b1..5781e8346 100644 --- a/app/src/full/java/com/topjohnwu/magisk/adapters/SectionedAdapter.java +++ b/app/src/full/java/com/topjohnwu/magisk/adapters/SectionedAdapter.java @@ -2,6 +2,7 @@ package com.topjohnwu.magisk.adapters; import android.view.ViewGroup; +import androidx.annotation.NonNull; import androidx.recyclerview.widget.RecyclerView; public abstract class SectionedAdapter @@ -9,8 +10,9 @@ public abstract class SectionedAdapter { - private List> logEntryList; + private List> logEntries; private Set itemExpanded, sectionExpanded; - private MagiskDatabaseHelper suDB; - private Cursor suLogCursor = null; + private MagiskDB suDB; - public SuLogAdapter(MagiskDatabaseHelper db) { + public SuLogAdapter(MagiskDB db) { suDB = db; - logEntryList = Collections.emptyList(); + logEntries = Collections.emptyList(); sectionExpanded = new HashSet<>(); itemExpanded = new HashSet<>(); } @Override public int getSectionCount() { - return logEntryList.size(); + return logEntries.size(); } @Override public int getItemCount(int section) { - return sectionExpanded.contains(section) ? logEntryList.get(section).size() : 0; + return sectionExpanded.contains(section) ? logEntries.get(section).size() : 0; } @Override @@ -60,8 +58,7 @@ public class SuLogAdapter extends SectionedAdapter { RotateAnimation rotate; @@ -69,11 +66,11 @@ public class SuLogAdapter extends SectionedAdapter { if (holder.isExpanded()) { holder.collapse(); - itemExpanded.remove(sqlPosition); + itemExpanded.remove(realIdx); } else { holder.expand(); - itemExpanded.add(sqlPosition); + itemExpanded.add(realIdx); } }); holder.appName.setText(entry.appName); @@ -106,10 +102,7 @@ public class SuLogAdapter extends SectionedAdapter{ appName = Utils.getAppLabel(info, pm); } - public Policy(Cursor c, PackageManager pm) throws PackageManager.NameNotFoundException { - uid = c.getInt(c.getColumnIndex("uid")); - packageName = c.getString(c.getColumnIndex("package_name")); - policy = c.getInt(c.getColumnIndex("policy")); - until = c.getLong(c.getColumnIndex("until")); - logging = c.getInt(c.getColumnIndex("logging")) != 0; - notification = c.getInt(c.getColumnIndex("notification")) != 0; + public Policy(ContentValues values, PackageManager pm) throws PackageManager.NameNotFoundException { + uid = values.getAsInteger("uid"); + packageName = values.getAsString("package_name"); + policy = values.getAsInteger("policy"); + until = values.getAsInteger("until"); + logging = values.getAsInteger("logging") != 0; + notification = values.getAsInteger("notification") != 0; info = pm.getApplicationInfo(packageName, 0); if (info.uid != uid) throw new PackageManager.NameNotFoundException(); appName = info.loadLabel(pm).toString(); } - + public ContentValues getContentValues() { ContentValues values = new ContentValues(); values.put("uid", uid); diff --git a/app/src/full/java/com/topjohnwu/magisk/container/SuLogEntry.java b/app/src/full/java/com/topjohnwu/magisk/container/SuLogEntry.java index 4fd905aea..b9410fc51 100644 --- a/app/src/full/java/com/topjohnwu/magisk/container/SuLogEntry.java +++ b/app/src/full/java/com/topjohnwu/magisk/container/SuLogEntry.java @@ -1,7 +1,6 @@ package com.topjohnwu.magisk.container; import android.content.ContentValues; -import android.database.Cursor; import com.topjohnwu.magisk.utils.LocaleManager; @@ -22,15 +21,15 @@ public class SuLogEntry { appName = policy.appName; } - public SuLogEntry(Cursor c) { - fromUid = c.getInt(c.getColumnIndex("from_uid")); - fromPid = c.getInt(c.getColumnIndex("from_pid")); - toUid = c.getInt(c.getColumnIndex("to_uid")); - packageName = c.getString(c.getColumnIndex("package_name")); - appName = c.getString(c.getColumnIndex("app_name")); - command = c.getString(c.getColumnIndex("command")); - action = c.getInt(c.getColumnIndex("action")) != 0; - date = new Date(c.getLong(c.getColumnIndex("time"))); + public SuLogEntry(ContentValues values) { + fromUid = values.getAsInteger("from_uid"); + packageName = values.getAsString("package_name"); + appName = values.getAsString("app_name"); + fromPid = values.getAsInteger("from_pid"); + command = values.getAsString("command"); + toUid = values.getAsInteger("to_uid"); + action = values.getAsInteger("action") != 0; + date = new Date(values.getAsLong("time")); } public ContentValues getContentValues() { diff --git a/app/src/full/java/com/topjohnwu/magisk/database/MagiskDB.java b/app/src/full/java/com/topjohnwu/magisk/database/MagiskDB.java new file mode 100644 index 000000000..c10646f02 --- /dev/null +++ b/app/src/full/java/com/topjohnwu/magisk/database/MagiskDB.java @@ -0,0 +1,60 @@ +package com.topjohnwu.magisk.database; + +import com.topjohnwu.magisk.Const; +import com.topjohnwu.magisk.container.Policy; +import com.topjohnwu.magisk.container.SuLogEntry; +import com.topjohnwu.magisk.utils.Utils; + +import java.io.File; +import java.util.List; + +import androidx.annotation.NonNull; + +public abstract class MagiskDB { + + public static final int DATABASE_VER = 6; + public static final int OLD_DATABASE_VER = 5; + public static final String POLICY_TABLE = "policies"; + public static final String LOG_TABLE = "logs"; + public static final String SETTINGS_TABLE = "settings"; + public static final String STRINGS_TABLE = "strings"; + public static final File LEGACY_MANAGER_DB = + new File(Utils.fmt("/sbin/.core/db-%d/magisk.db", Const.USER_ID)); + + @NonNull + public static MagiskDB getInstance() { + return MagiskDBLegacy.newInstance(); + } + + public abstract void clearOutdated(); + + public void deletePolicy(Policy policy) { + deletePolicy(policy.uid); + } + + public abstract void deletePolicy(String pkg); + + public abstract void deletePolicy(int uid); + + public abstract Policy getPolicy(int uid); + + public abstract void addPolicy(Policy policy); + + public abstract void updatePolicy(Policy policy); + + public abstract List getPolicyList(); + + public abstract List> getLogs(); + + public abstract void addLog(SuLogEntry log); + + public abstract void clearLogs(); + + public abstract void setSettings(String key, int value); + + public abstract int getSettings(String key, int defaultValue); + + public abstract void setStrings(String key, String value); + + public abstract String getStrings(String key, String defaultValue); +} diff --git a/app/src/full/java/com/topjohnwu/magisk/database/MagiskDatabaseHelper.java b/app/src/full/java/com/topjohnwu/magisk/database/MagiskDBLegacy.java similarity index 81% rename from app/src/full/java/com/topjohnwu/magisk/database/MagiskDatabaseHelper.java rename to app/src/full/java/com/topjohnwu/magisk/database/MagiskDBLegacy.java index 08b3624fb..350267eae 100644 --- a/app/src/full/java/com/topjohnwu/magisk/database/MagiskDatabaseHelper.java +++ b/app/src/full/java/com/topjohnwu/magisk/database/MagiskDBLegacy.java @@ -4,6 +4,7 @@ import android.content.ContentValues; import android.content.Context; import android.content.pm.PackageManager; import android.database.Cursor; +import android.database.DatabaseUtils; import android.database.sqlite.SQLiteDatabase; import android.os.Build; import android.os.Process; @@ -21,46 +22,29 @@ import com.topjohnwu.magisk.utils.Utils; import com.topjohnwu.superuser.Shell; import com.topjohnwu.superuser.io.SuFile; -import java.io.File; import java.text.DateFormat; import java.util.ArrayList; import java.util.Collections; import java.util.Date; import java.util.List; -import androidx.annotation.NonNull; - -public class MagiskDatabaseHelper { - - private static final int DATABASE_VER = 6; - private static final int OLD_DATABASE_VER = 5; - private static final String POLICY_TABLE = "policies"; - private static final String LOG_TABLE = "logs"; - private static final String SETTINGS_TABLE = "settings"; - private static final String STRINGS_TABLE = "strings"; - private static final File MANAGER_DB = - new File(Utils.fmt("/sbin/.core/db-%d/magisk.db", Const.USER_ID)); +public class MagiskDBLegacy extends MagiskDB { private PackageManager pm; private SQLiteDatabase db; - @NonNull - public static MagiskDatabaseHelper getInstance() { + static MagiskDBLegacy newInstance() { try { - return new MagiskDatabaseHelper(); + return new MagiskDBLegacy(); } catch (Exception e) { // Let's cleanup everything and try again Shell.su("db_clean '*'").exec(); - return new MagiskDatabaseHelper(); + return new MagiskDBLegacy(); } } - private MagiskDatabaseHelper() { + private MagiskDBLegacy() { pm = Data.MM().getPackageManager(); - init(); - } - - private void init() { db = openDatabase(); db.disableWriteAheadLogging(); int version = Data.magiskVersionCode >= Const.MAGISK_VER.DBVER_SIX ? DATABASE_VER : OLD_DATABASE_VER; @@ -79,7 +63,7 @@ public class MagiskDatabaseHelper { MagiskManager mm = Data.MM(); Context de = Build.VERSION.SDK_INT >= Build.VERSION_CODES.N ? mm.createDeviceProtectedStorageContext() : mm; - if (!MANAGER_DB.canWrite()) { + if (!LEGACY_MANAGER_DB.canWrite()) { if (!Shell.rootAccess() || Data.magiskVersionCode < 0) { // We don't want the app to crash, create a db and return return mm.openOrCreateDatabase("su.db", Context.MODE_PRIVATE, null); @@ -102,7 +86,7 @@ public class MagiskDatabaseHelper { Shell.su("db_setup " + Process.myUid()).exec(); } // Not using legacy mode, open the mounted global DB - return SQLiteDatabase.openOrCreateDatabase(MANAGER_DB, null); + return SQLiteDatabase.openOrCreateDatabase(LEGACY_MANAGER_DB, null); } private void onUpgrade(SQLiteDatabase db, int oldVersion) { @@ -159,27 +143,23 @@ public class MagiskDatabaseHelper { // Policies db.execSQL( "CREATE TABLE IF NOT EXISTS " + POLICY_TABLE + " " + - "(uid INT, package_name TEXT, policy INT, " + - "until INT, logging INT, notification INT, " + - "PRIMARY KEY(uid))"); + "(uid INT, package_name TEXT, policy INT, " + + "until INT, logging INT, notification INT, " + + "PRIMARY KEY(uid))"); // Logs db.execSQL( "CREATE TABLE IF NOT EXISTS " + LOG_TABLE + " " + - "(from_uid INT, package_name TEXT, app_name TEXT, from_pid INT, " + - "to_uid INT, action INT, time INT, command TEXT)"); + "(from_uid INT, package_name TEXT, app_name TEXT, from_pid INT, " + + "to_uid INT, action INT, time INT, command TEXT)"); // Settings db.execSQL( "CREATE TABLE IF NOT EXISTS " + SETTINGS_TABLE + " " + - "(key TEXT, value INT, PRIMARY KEY(key))"); - } - - public void flush() { - db.close(); - init(); + "(key TEXT, value INT, PRIMARY KEY(key))"); } + @Override public void clearOutdated() { // Clear outdated policies db.delete(POLICY_TABLE, Utils.fmt("until > 0 AND until < %d", System.currentTimeMillis() / 1000), null); @@ -187,23 +167,24 @@ public class MagiskDatabaseHelper { db.delete(LOG_TABLE, Utils.fmt("time < %d", System.currentTimeMillis() - Data.suLogTimeout * 86400000), null); } - public void deletePolicy(Policy policy) { - deletePolicy(policy.uid); - } - + @Override public void deletePolicy(String pkg) { db.delete(POLICY_TABLE, "package_name=?", new String[] { pkg }); } + @Override public void deletePolicy(int uid) { db.delete(POLICY_TABLE, Utils.fmt("uid=%d", uid), null); } + @Override public Policy getPolicy(int uid) { Policy policy = null; try (Cursor c = db.query(POLICY_TABLE, null, Utils.fmt("uid=%d", uid), null, null, null, null)) { if (c.moveToNext()) { - policy = new Policy(c, pm); + ContentValues values = new ContentValues(); + DatabaseUtils.cursorRowToContentValues(c, values); + policy = new Policy(values, pm); } } catch (PackageManager.NameNotFoundException e) { deletePolicy(uid); @@ -212,21 +193,26 @@ public class MagiskDatabaseHelper { return policy; } + @Override public void addPolicy(Policy policy) { db.replace(POLICY_TABLE, null, policy.getContentValues()); } + @Override public void updatePolicy(Policy policy) { db.update(POLICY_TABLE, policy.getContentValues(), Utils.fmt("uid=%d", policy.uid), null); } - public List getPolicyList(PackageManager pm) { + @Override + public List getPolicyList() { try (Cursor c = db.query(POLICY_TABLE, null, Utils.fmt("uid/100000=%d", Const.USER_ID), null, null, null, null)) { List ret = new ArrayList<>(c.getCount()); while (c.moveToNext()) { try { - Policy policy = new Policy(c, pm); + ContentValues values = new ContentValues(); + DatabaseUtils.cursorRowToContentValues(c, values); + Policy policy = new Policy(values, pm); ret.add(policy); } catch (PackageManager.NameNotFoundException e) { // The app no longer exist, remove from DB @@ -238,11 +224,12 @@ public class MagiskDatabaseHelper { } } - public List> getLogStructure() { - try (Cursor c = db.query(LOG_TABLE, new String[] { "time" }, Utils.fmt("from_uid/100000=%d", Const.USER_ID), + @Override + public List> getLogs() { + try (Cursor c = db.query(LOG_TABLE, null, Utils.fmt("from_uid/100000=%d", Const.USER_ID), null, null, null, "time DESC")) { - List> ret = new ArrayList<>(); - List list = null; + List> ret = new ArrayList<>(); + List list = null; String dateString = null, newString; while (c.moveToNext()) { Date date = new Date(c.getLong(c.getColumnIndex("time"))); @@ -252,25 +239,25 @@ public class MagiskDatabaseHelper { list = new ArrayList<>(); ret.add(list); } - list.add(c.getPosition()); + ContentValues values = new ContentValues(); + DatabaseUtils.cursorRowToContentValues(c, values); + list.add(new SuLogEntry(values)); } return ret; } } - public Cursor getLogCursor() { - return db.query(LOG_TABLE, null, Utils.fmt("from_uid/100000=%d", Const.USER_ID), - null, null, null, "time DESC"); - } - + @Override public void addLog(SuLogEntry log) { db.insert(LOG_TABLE, null, log.getContentValues()); } + @Override public void clearLogs() { db.delete(LOG_TABLE, null, null); } + @Override public void setSettings(String key, int value) { ContentValues data = new ContentValues(); data.put("key", key); @@ -278,6 +265,7 @@ public class MagiskDatabaseHelper { db.replace(SETTINGS_TABLE, null, data); } + @Override public int getSettings(String key, int defaultValue) { int value = defaultValue; try (Cursor c = db.query(SETTINGS_TABLE, null, "key=?",new String[] { key }, null, null, null)) { @@ -288,6 +276,7 @@ public class MagiskDatabaseHelper { return value; } + @Override public void setStrings(String key, String value) { if (value == null) { db.delete(STRINGS_TABLE, "key=?", new String[] { key }); @@ -299,6 +288,7 @@ public class MagiskDatabaseHelper { } } + @Override public String getStrings(String key, String defaultValue) { String value = defaultValue; try (Cursor c = db.query(STRINGS_TABLE, null, "key=?",new String[] { key }, null, null, null)) { diff --git a/app/src/full/java/com/topjohnwu/magisk/fragments/SuperuserFragment.java b/app/src/full/java/com/topjohnwu/magisk/fragments/SuperuserFragment.java index 8e07b66fc..b699554ce 100644 --- a/app/src/full/java/com/topjohnwu/magisk/fragments/SuperuserFragment.java +++ b/app/src/full/java/com/topjohnwu/magisk/fragments/SuperuserFragment.java @@ -48,7 +48,7 @@ public class SuperuserFragment extends BaseFragment { } private void displayPolicyList() { - List policyList = mm.mDB.getPolicyList(pm); + List policyList = mm.mDB.getPolicyList(); if (policyList.size() == 0) { emptyRv.setVisibility(View.VISIBLE);