From 7e6cd07a09ff4eba43d77236cf7c44a5f1ca5294 Mon Sep 17 00:00:00 2001 From: Li Date: Mon, 22 Apr 2024 12:51:55 +1200 Subject: [PATCH] Add PS Certification feature --- app/src/main/AndroidManifest.xml | 2 +- .../com/psmreborn/nopsmdrm/MainActivity.java | 29 ++- ...{Installer.java => NoPsmDrmInstaller.java} | 169 ++++++------------ .../java/com/psmreborn/nopsmdrm/Root.java | 124 +++++++++++++ .../pscertified/CertifiedDeviceEntry.java | 44 +++++ .../pscertified/CertifiedDeviceList.java | 28 +++ .../pscertified/PlayStationCertified.java | 53 ++++++ .../pscertified/PsCertificatesInstaller.java | 104 +++++++++++ app/src/main/res/layout/activity_main.xml | 1 + .../raw/aditional_certified_devices_list.dat | 107 +++++++++++ app/src/main/res/raw/device_list2.dat | 39 ++++ app/src/main/res/raw/ps_certified_jar.jar | Bin 0 -> 689 bytes .../main/res/raw/ps_certified_permission.xml | 11 ++ 13 files changed, 598 insertions(+), 113 deletions(-) rename app/src/main/java/com/psmreborn/nopsmdrm/{Installer.java => NoPsmDrmInstaller.java} (70%) create mode 100644 app/src/main/java/com/psmreborn/nopsmdrm/Root.java create mode 100644 app/src/main/java/com/psmreborn/nopsmdrm/pscertified/CertifiedDeviceEntry.java create mode 100644 app/src/main/java/com/psmreborn/nopsmdrm/pscertified/CertifiedDeviceList.java create mode 100644 app/src/main/java/com/psmreborn/nopsmdrm/pscertified/PlayStationCertified.java create mode 100644 app/src/main/java/com/psmreborn/nopsmdrm/pscertified/PsCertificatesInstaller.java create mode 100644 app/src/main/res/raw/aditional_certified_devices_list.dat create mode 100644 app/src/main/res/raw/device_list2.dat create mode 100644 app/src/main/res/raw/ps_certified_jar.jar create mode 100644 app/src/main/res/raw/ps_certified_permission.xml diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 0773224..a25367f 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -4,7 +4,7 @@ - + { +// Sorry if this is kinda hard to follow ... + +public class NoPsmDrmInstaller extends AsyncTask { + protected static Boolean psCertify = false; private boolean wasError = false; private String errorMsg = ""; - private ProgressDialog dialog = null; private Context ctx = null; private StringEncryptor stringEncryptor = null; - private String busyboxBinary = ""; - public Installer(Context context){ + private PlayStationCertified playStationCertified = null; + + public NoPsmDrmInstaller(Context context){ this.ctx = context; this.stringEncryptor = new StringEncryptor(this.ctx); } @@ -45,83 +45,6 @@ public class Installer extends AsyncTask { Log.e("INSTALLER",errorMsg); throw new Exception(msg); } - private static void writeTxtFile(String txtFile, String txt) throws IOException { - Log.i("INSTALLER", "Writing: "+txtFile); - FileWriter txtStream = new FileWriter(txtFile); - txtStream.write(txt); - txtStream.close(); - } - private void copyTo(InputStream inpStream, OutputStream outStream) throws IOException { - int totalRead = 0; - byte[] buffer = new byte[0x1000]; - - do { - totalRead = inpStream.read(buffer, 0, buffer.length); - outStream.write(buffer, 0, totalRead); - } - while(totalRead >= buffer.length); - - outStream.flush(); - } - - private void unpackResource(int resourceId, File outputFile) throws IOException { - InputStream resourceStream = ctx.getResources().openRawResource(resourceId); - - FileOutputStream fs = new FileOutputStream(outputFile); - copyTo(resourceStream, fs); - fs.close(); - - resourceStream.close(); - } - - private boolean fileExistRoot(String filename) throws Shell.ShellDiedException { - int res = Shell.Pool.SU.run(new String[] { this.busyboxBinary + " stat '" + filename +"'" }); - return res == 0; - } - - private void moveFileRoot(String filename, String destFilename) throws Exception { - int res = Shell.Pool.SU.run(new String[] { this.busyboxBinary +" mv '"+ filename + "' '" +destFilename +"'"}); - if(res != 0){ - this.setError("Failed to rename "+filename+" to "+ destFilename); - } - } - private void mkdirAndChmodChown(String directory, int chmod, String chown) throws Shell.ShellDiedException { - Shell.Pool.SU.run(new String[]{ - this.busyboxBinary + " mkdir '" + directory +"'", - this.busyboxBinary + " chmod " + String.valueOf(chmod) +" '"+directory+"'", - this.busyboxBinary + " chown " + chown +":"+chown+" '"+directory+"'" - }); - } - private void copyChmodAndChown(String srcFile, String dstFile, int chmod, String chown) throws Exception { - int res = Shell.Pool.SU.run(new String[]{ - this.busyboxBinary + " cp '" + srcFile +"' '"+dstFile+"'", - this.busyboxBinary + " chmod " + String.valueOf(chmod) +" '"+dstFile+"'", - this.busyboxBinary + " chown " + chown +":"+chown+" '"+dstFile+"'" - }); - - if(res != 0){ - this.setError("Failed to copy & change mode."); - return; - } - } - - - private void setupBusyBox() throws Exception { - Log.i("INSTALLER","Creating busybox binary"); - File tmpFile = new File(ctx.getCacheDir(), "busybox"); - tmpFile.createNewFile(); - - if(tmpFile.setExecutable(true,false)) { - unpackResource(R.raw.busybox, tmpFile); - this.busyboxBinary = tmpFile.getAbsolutePath(); - } - else { - this.setError("failed to extract busybox binary."); - return; - } - - } - private void generateDeviceFingerprint(String outputFilename) throws FileNotFoundException, UnsupportedEncodingException { @@ -178,16 +101,24 @@ public class Installer extends AsyncTask { } private void backupPsm() throws Exception { - String psmSdcardFolder = new File(Environment.getExternalStorageDirectory(), "psm").getAbsolutePath(); - new File(psmSdcardFolder).mkdirs(); - String filename = "psm_"+getDateTime(); - int res = Shell.Pool.SU.run(new String[]{this.busyboxBinary + " tar c '" + getPsmApp().dataDir + "' -f '" + new File(psmSdcardFolder, filename+".tar").getAbsolutePath()+"'"}); - if (res != 0) { - this.setError("Failed to backup existing PSM data. (exit code: " + res + ")"); - return; + String psmFilesDir = new File(getPsmApp().dataDir, "files").getAbsolutePath(); + String psmKdcDir = new File(psmFilesDir, "kdc").getAbsolutePath(); + String psmActFile = new File(psmKdcDir, "act.dat").getAbsolutePath(); + + // check if "act.dat" exists -- they've been here before ... + if(fileExistRoot(psmActFile)) { + String psmSdcardFolder = new File(Environment.getExternalStorageDirectory(), "psm").getAbsolutePath(); + new File(psmSdcardFolder).mkdirs(); + String filename = "psm_"+getDateTime(); + + // tar up the files + tarRoot(getPsmApp().dataDir,new File(psmSdcardFolder, filename+".tar").getAbsolutePath()); + + // generate device fingerprint file + generateDeviceFingerprint(new File(psmSdcardFolder, filename + "_DEV.txt").getAbsolutePath()); } - generateDeviceFingerprint(new File(psmSdcardFolder, filename + "_DEV.txt").getAbsolutePath()); + } private void makeDirs() throws PackageManager.NameNotFoundException, Shell.ShellDiedException { @@ -197,14 +128,14 @@ public class Installer extends AsyncTask { mkdirAndChmodChown(new File(getPsmApp().dataDir, "databases").getAbsolutePath(), 771, String.valueOf(stringEncryptor.getPsmUid())); } - private void patchSharedPrefs() throws Exception { + private void installSharedPrefs() throws Exception { // get the path to the shared_prefs folder String sharedPrefsPath = new File(getPsmApp().dataDir, "shared_prefs").getAbsolutePath(); // check if signininfo.xml file exists or not ... boolean signinInfoExist = fileExistRoot(new File(sharedPrefsPath, "SigninInfo.xml").getAbsolutePath()); if (!signinInfoExist) { // if file not found ... - // then generate our own shared_prefs + // then generate our own shared_prefs // encrypt the actual strings, username, password, etc String emailAddress = stringEncryptor.encryptString("nopsmdrm@transrights.lgbt"); @@ -275,6 +206,25 @@ public class Installer extends AsyncTask { copyChmodAndChown(libraryDbFile, rlibraryDbFile, 660, String.valueOf(stringEncryptor.getPsmUid())); } + private void installDeviceList() throws PackageManager.NameNotFoundException, IOException, Shell.ShellDiedException { + String cacheFolder = new File(getPsmApp().dataDir, "cache").getAbsolutePath(); + + // extract the regular device list ... + String rdeviceList2 = new File(cacheFolder, "deviceList2.dat").getAbsolutePath(); + String cdeviceList2 = new File(ctx.getCacheDir(), "deviceList2.dat").getAbsolutePath(); + + unpackResource(R.raw.device_list2, new File(cdeviceList2)); + copyChmodAndChown(cdeviceList2, rdeviceList2, 660, String.valueOf(stringEncryptor.getPsmUid())); + + + // extract the additional certified devices list ... + String radditionalCerts = new File(cacheFolder, "addtionalCertifiedDevList.dat").getAbsolutePath(); + String cadditionalCerts = new File(ctx.getCacheDir(), "addtionalCertifiedDevList.dat").getAbsolutePath(); + + unpackResource(R.raw.aditional_certified_devices_list, new File(cadditionalCerts)); + copyChmodAndChown(cadditionalCerts, radditionalCerts, 660, String.valueOf(stringEncryptor.getPsmUid())); + + } @Override protected void onPreExecute() { Shell.setRedirectDeprecated(false); @@ -285,20 +235,26 @@ public class Installer extends AsyncTask { dialog.setIndeterminate(true); dialog.setCancelable(false); dialog.show(); + } + @Override protected Void doInBackground(Void... voids) { try { - setupBusyBox(); + Root.setContext(ctx); if (isPsmInstalled()) { backupPsm(); makeDirs(); - patchSharedPrefs(); + installSharedPrefs(); + installDeviceList(); installNoPsmDrmModules(); installDatabase(); } + else{ + this.setError("PSM app is not installed."); + } } catch(Exception e){ this.wasError = true; @@ -309,6 +265,7 @@ public class Installer extends AsyncTask { return null; } + @Override protected void onPostExecute(Void result) { dialog.dismiss(); @@ -318,24 +275,14 @@ public class Installer extends AsyncTask { .setTitle("Error Occurred.") .setMessage(this.errorMsg) .setCancelable(false) - .setPositiveButton("Ok", new DialogInterface.OnClickListener() { - @Override - public void onClick(DialogInterface dialog, int which) { - - } - }).show(); + .setPositiveButton("Ok",null).show(); } else{ new AlertDialog.Builder((Activity)ctx) .setTitle("Installed!") - .setMessage("Your PSM Application was patched successfully!\nNote: WI-FI has to be turned off for games to work.") + .setMessage("Your PSM Application was patched successfully!\n\nNote: WI-FI has to be turned off for games to work.") .setCancelable(false) - .setPositiveButton("Ok", new DialogInterface.OnClickListener() { - @Override - public void onClick(DialogInterface dialog, int which) { - - } - }).show(); + .setPositiveButton("Ok", null).show(); } } } diff --git a/app/src/main/java/com/psmreborn/nopsmdrm/Root.java b/app/src/main/java/com/psmreborn/nopsmdrm/Root.java new file mode 100644 index 0000000..c948971 --- /dev/null +++ b/app/src/main/java/com/psmreborn/nopsmdrm/Root.java @@ -0,0 +1,124 @@ +package com.psmreborn.nopsmdrm; + +import android.content.Context; +import android.util.Log; + +import java.io.File; +import java.io.FileOutputStream; +import java.io.FileWriter; +import java.io.IOException; +import java.io.InputStream; +import java.io.OutputStream; + +import eu.chainfire.libsuperuser.Shell; + +public class Root { + private static String busyboxBinary = null; + private static Context ctx = null; + + public static boolean fileExistRoot(String filename) throws Shell.ShellDiedException { + Log.i("ROOT", "FileExistRoot: " + filename); + int res = Shell.Pool.SU.run(new String[] { busyboxBinary + " stat '" + filename +"'" }); + return res == 0; + } + + public static void tarRoot(String src, String dst) throws IOException, Shell.ShellDiedException { + Log.i("ROOT", "TarRoot: " + src + " : "+ dst); + int res = Shell.Pool.SU.run(new String[]{busyboxBinary + " tar c '" + src + "' -f '" + dst +"'"}); + if (res != 0) { + throw new IOException("Failed to tar " + src); + } + } + public static void remountRo(String foldername) throws IOException, Shell.ShellDiedException { + Log.i("ROOT", "Remounting as RO: " + foldername); + int res = Shell.Pool.SU.run(new String[] { busyboxBinary +" mount -o ro,remount '"+foldername+"'"} + ); + if(res != 0){ + throw new IOException("Failed to remmount as RO: "+foldername); + } + } + public static void remountRw(String foldername) throws IOException, Shell.ShellDiedException { + Log.i("ROOT", "Remounting as RW: " + foldername); + int res = Shell.Pool.SU.run(new String[] { busyboxBinary +" mount -o rw,remount '"+foldername+"'"} + ); + if(res != 0){ + throw new IOException("Failed to remmount as RW: "+foldername); + } + } + public static void moveFileRoot(String filename, String destFilename) throws IOException, Shell.ShellDiedException { + Log.i("ROOT", "MoveRoot: " + filename + " : "+ destFilename); + int res = Shell.Pool.SU.run(new String[] { busyboxBinary +" mv '"+ filename + "' '" +destFilename +"'"}); + if(res != 0){ + throw new IOException("Failed to rename "+filename+" to "+ destFilename); + } + } + public static void mkdirAndChmodChown(String directory, int chmod, String chown) throws Shell.ShellDiedException { + Log.i("ROOT", "MkdirAndChown: " + directory); + Shell.Pool.SU.run(new String[]{ + busyboxBinary + " mkdir '" + directory +"'", + busyboxBinary + " chmod " + String.valueOf(chmod) +" '"+directory+"'", + busyboxBinary + " chown " + chown +":"+chown+" '"+directory+"'" + }); + } + public static void copyChmodAndChown(String srcFile, String dstFile, int chmod, String chown) throws IOException, Shell.ShellDiedException { + Log.i("ROOT", "CopyAndChown: " + srcFile +" : "+dstFile); + int res = Shell.Pool.SU.run(new String[]{ + busyboxBinary + " cp '" + srcFile +"' '"+dstFile+"'", + busyboxBinary + " chmod " + String.valueOf(chmod) +" '"+dstFile+"'", + busyboxBinary + " chown " + chown +":"+chown+" '"+dstFile+"'" + }); + + if(res != 0){ + throw new IOException("Failed to copy & change mode."); + } + } + private static void copyTo(InputStream inpStream, OutputStream outStream) throws IOException { + int totalRead = 0; + byte[] buffer = new byte[0x1000]; + + do { + totalRead = inpStream.read(buffer, 0, buffer.length); + outStream.write(buffer, 0, totalRead); + } + while(totalRead >= buffer.length); + + outStream.flush(); + } + public static void unpackResource(int resourceId, File outputFile) throws IOException { + Log.i("ROOT", "Unpacking resource to : " + outputFile); + InputStream resourceStream = ctx.getResources().openRawResource(resourceId); + + FileOutputStream fs = new FileOutputStream(outputFile); + copyTo(resourceStream, fs); + fs.close(); + + resourceStream.close(); + } + public static void writeTxtFile(String txtFile, String txt) throws IOException { + Log.i("ROOT", "Writing: " + txtFile); + FileWriter txtStream = new FileWriter(txtFile); + txtStream.write(txt); + txtStream.close(); + } + private static void setupBusyBox() throws IOException { + Log.i("ROOT","Creating busybox binary"); + File tmpFile = new File(ctx.getCacheDir(), "busybox"); + if(!tmpFile.exists()){ + tmpFile.createNewFile(); + + if(tmpFile.setExecutable(true,false)) { + unpackResource(R.raw.busybox, tmpFile); + } + else { + throw new IOException("failed to extract busybox binary."); + } + } + + busyboxBinary = tmpFile.getAbsolutePath(); + } + + public static void setContext(Context context) throws IOException { + ctx = context; + setupBusyBox(); + } +} diff --git a/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/CertifiedDeviceEntry.java b/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/CertifiedDeviceEntry.java new file mode 100644 index 0000000..c6f65d1 --- /dev/null +++ b/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/CertifiedDeviceEntry.java @@ -0,0 +1,44 @@ +package com.psmreborn.nopsmdrm.pscertified; + + +public class CertifiedDeviceEntry { + String deviceName = null; + int maxApiVersion = Integer.MAX_VALUE; + int minApiVersion = 0; + + public String getDeviceName(){ + return deviceName; + } + public int getMinApiVersion(){ + return minApiVersion; + } + public int getMaxApiVersion(){ + return maxApiVersion; + } + + public boolean checkDevice(String device, int osVer){ + if(deviceName.equals(device)){ + if(osVer < maxApiVersion){ + if(osVer > minApiVersion){ + return true; + } + } + } + return false; + } + + public CertifiedDeviceEntry(String deviceName, int minApiVersion, int maxApiVersion) { + this.deviceName = deviceName; + this.minApiVersion = minApiVersion; + this.maxApiVersion = maxApiVersion; + } + + public CertifiedDeviceEntry(String deviceName, int minApiVersion) { + this.deviceName = deviceName; + this.minApiVersion = minApiVersion; + } + + public CertifiedDeviceEntry(String deviceName) { + this.deviceName = deviceName; + } +} \ No newline at end of file diff --git a/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/CertifiedDeviceList.java b/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/CertifiedDeviceList.java new file mode 100644 index 0000000..d0480ef --- /dev/null +++ b/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/CertifiedDeviceList.java @@ -0,0 +1,28 @@ +package com.psmreborn.nopsmdrm.pscertified; + +public class CertifiedDeviceList { + private String manufacturer = null; + private CertifiedDeviceEntry[] deviceEntrys = null; + public String getManufacturer() { + return manufacturer; + } + public CertifiedDeviceEntry[] getCertifiedDeviceEntries() { + return deviceEntrys; + } + + public boolean checkDevice(String manufacturer, String device, int osVer){ + + if(this.manufacturer.equals(manufacturer)){ + for(int i = 0; i < deviceEntrys.length; i++){ + if(deviceEntrys[i].checkDevice(device, osVer)){ + return true; + } + } + } + return false; + } + public CertifiedDeviceList(String manufacturer, CertifiedDeviceEntry[] devices){ + this.manufacturer = manufacturer; + this.deviceEntrys = devices; + } +} \ No newline at end of file diff --git a/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/PlayStationCertified.java b/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/PlayStationCertified.java new file mode 100644 index 0000000..808de6c --- /dev/null +++ b/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/PlayStationCertified.java @@ -0,0 +1,53 @@ +package com.psmreborn.nopsmdrm.pscertified; + +import android.content.Context; +import android.os.Build; + + +import java.util.Arrays; +import java.util.HashSet; + + + +public class PlayStationCertified { + + private static CertifiedDeviceList[] certifiedDevices = { + new CertifiedDeviceList("Sony", new CertifiedDeviceEntry[] {new CertifiedDeviceEntry("SO-02E"), new CertifiedDeviceEntry("C6602"), new CertifiedDeviceEntry("C6603"), new CertifiedDeviceEntry("C6616"), new CertifiedDeviceEntry("C6606"), new CertifiedDeviceEntry("SOL22"), new CertifiedDeviceEntry("C6502"), new CertifiedDeviceEntry("C6503"), new CertifiedDeviceEntry("C6506"), new CertifiedDeviceEntry("SGP321"), new CertifiedDeviceEntry("SGP312"), new CertifiedDeviceEntry("SGP311"), new CertifiedDeviceEntry("SGP341"), new CertifiedDeviceEntry("SO-03E"), new CertifiedDeviceEntry("SGP351"), new CertifiedDeviceEntry("SO-04E"), new CertifiedDeviceEntry("C5503"), new CertifiedDeviceEntry("C5502"), new CertifiedDeviceEntry("L36h"), new CertifiedDeviceEntry("L35h"), new CertifiedDeviceEntry("M36h"), new CertifiedDeviceEntry("C5303"), new CertifiedDeviceEntry("C5306"), new CertifiedDeviceEntry("C5302"), new CertifiedDeviceEntry("M35h"), new CertifiedDeviceEntry("M35c"), new CertifiedDeviceEntry("C2105"), new CertifiedDeviceEntry("C2104"), new CertifiedDeviceEntry("S36h"), new CertifiedDeviceEntry("C1904"), new CertifiedDeviceEntry("C1905"), new CertifiedDeviceEntry("C2004"), new CertifiedDeviceEntry("C2005"), new CertifiedDeviceEntry("SOL23"), new CertifiedDeviceEntry("C6903"), new CertifiedDeviceEntry("SO-01F"), new CertifiedDeviceEntry("C6906"), new CertifiedDeviceEntry("C6902"), new CertifiedDeviceEntry("C6916"), new CertifiedDeviceEntry("C6833"), new CertifiedDeviceEntry("C6806"), new CertifiedDeviceEntry("C6802"), new CertifiedDeviceEntry("SOL24"), new CertifiedDeviceEntry("SGP412"), new CertifiedDeviceEntry("SO-02F"), new CertifiedDeviceEntry("D5503"), new CertifiedDeviceEntry("SO-04F"), new CertifiedDeviceEntry("C6843"), new CertifiedDeviceEntry("XL39h"), new CertifiedDeviceEntry("M51w"), new CertifiedDeviceEntry("D5303"), new CertifiedDeviceEntry("D5322"), new CertifiedDeviceEntry("D5306"), new CertifiedDeviceEntry("D5316"), new CertifiedDeviceEntry("D5316N"), new CertifiedDeviceEntry("D2303"), new CertifiedDeviceEntry("D2306"), new CertifiedDeviceEntry("D2305"), new CertifiedDeviceEntry("D2302"), new CertifiedDeviceEntry("D2403"), new CertifiedDeviceEntry("D2406"), new CertifiedDeviceEntry("S50h"), new CertifiedDeviceEntry("D6502"), new CertifiedDeviceEntry("D6503"), new CertifiedDeviceEntry("SO-03F"), new CertifiedDeviceEntry("D6543"), new CertifiedDeviceEntry("SOL25"), new CertifiedDeviceEntry("D6563"), new CertifiedDeviceEntry("SGP541"), new CertifiedDeviceEntry("SGP521"), new CertifiedDeviceEntry("SO-05F"), new CertifiedDeviceEntry("SOT21"), new CertifiedDeviceEntry("SGP551"), new CertifiedDeviceEntry("SGP511"), new CertifiedDeviceEntry("SGP512"), new CertifiedDeviceEntry("D6542"), new CertifiedDeviceEntry("M35t"), new CertifiedDeviceEntry("M35ts"), new CertifiedDeviceEntry("SO-01C"), new CertifiedDeviceEntry("SO-02C"), new CertifiedDeviceEntry("SO-02D"), new CertifiedDeviceEntry("SO-03D"), new CertifiedDeviceEntry("IS12S"), new CertifiedDeviceEntry("LT26i") }), new CertifiedDeviceList("Sony Ericsson", new CertifiedDeviceEntry[] { new CertifiedDeviceEntry("R800i"), new CertifiedDeviceEntry("R800a"), new CertifiedDeviceEntry("R800x"), new CertifiedDeviceEntry("R800at") }), + new CertifiedDeviceList("HTC", new CertifiedDeviceEntry[] { new CertifiedDeviceEntry("primou", 15) }), + new CertifiedDeviceList("SHARP", new CertifiedDeviceEntry[] { new CertifiedDeviceEntry("SH09D", 15), new CertifiedDeviceEntry("SHI16", 15) , new CertifiedDeviceEntry("SBM106SH", 15) , new CertifiedDeviceEntry("SBM203SH", 16) }), + new CertifiedDeviceList("FUJITSU MOBILE COMMUNICATIONS LIMITED", new CertifiedDeviceEntry[] { new CertifiedDeviceEntry("F05E", 15) }), + }; + + private Context ctx; + public PlayStationCertified(Context context){ + ctx = context; + } + + private boolean isInDeviceList() { + String brand = Build.BRAND; + String manufacturer = Build.MANUFACTURER; + int osVer = Build.VERSION.SDK_INT; + + for(int i = 0; i < certifiedDevices.length; i++){ + if(certifiedDevices[i].checkDevice(manufacturer, brand, osVer)){ + return true; + } + } + + + return false; + } + + public boolean isPlaystationCertified() { + // check for signature file + HashSet installedFrameworks = new HashSet(Arrays.asList(ctx.getPackageManager().getSystemSharedLibraryNames())); + if(installedFrameworks.contains("com.playstation.playstationcertified")){ + return true; + } + else { + // check devList2 and additionalCertifiedDevList + return isInDeviceList(); + } + } + +} diff --git a/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/PsCertificatesInstaller.java b/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/PsCertificatesInstaller.java new file mode 100644 index 0000000..b571029 --- /dev/null +++ b/app/src/main/java/com/psmreborn/nopsmdrm/pscertified/PsCertificatesInstaller.java @@ -0,0 +1,104 @@ +package com.psmreborn.nopsmdrm.pscertified; + +import static com.psmreborn.nopsmdrm.Root.*; + +import com.psmreborn.nopsmdrm.MainActivity; +import com.psmreborn.nopsmdrm.NoPsmDrmInstaller; +import com.psmreborn.nopsmdrm.R; +import com.psmreborn.nopsmdrm.Root; + +import android.app.Activity; +import android.app.AlertDialog; +import android.app.ProgressDialog; +import android.content.Context; +import android.content.DialogInterface; +import android.os.AsyncTask; +import android.os.PowerManager; + + +import java.io.File; +import java.io.IOException; + +import eu.chainfire.libsuperuser.Shell; + +public class PsCertificatesInstaller extends AsyncTask { + private ProgressDialog dialog = null; + private boolean wasError = false; + private String errorMsg = ""; + Context ctx = null; + + public void installPlaystationCertification() throws IOException, Shell.ShellDiedException { + // remount /system as read-write + remountRw("/system"); + + String cpsCertifiedPerms = new File(ctx.getCacheDir(), "com.playstation.playstationcertified.xml").getAbsolutePath(); + String cpsCertifiedjar = new File(ctx.getCacheDir(), "com.playstation.playstationcertified.jar").getAbsolutePath(); + + unpackResource(R.raw.ps_certified_permission, new File(cpsCertifiedPerms)); + unpackResource(R.raw.ps_certified_jar, new File(cpsCertifiedjar)); + + String rpsCertifiedPerms = "/system/etc/permissions/com.playstation.playstationcertified.xml"; + String rpsCertifiedJar = "/system/framework/com.playstation.playstationcertified.jar"; + + copyChmodAndChown(cpsCertifiedPerms, rpsCertifiedPerms, 644, "root"); + copyChmodAndChown(cpsCertifiedjar, rpsCertifiedJar, 644, "root"); + + // make it read-only again. + remountRo("/system"); + } + + public PsCertificatesInstaller(Context context) { + this.ctx = context; + } + + @Override + protected void onPreExecute() { + Shell.setRedirectDeprecated(false); + + dialog = new ProgressDialog(ctx); + dialog.setTitle("Installing PlayStation Certificates ..."); + dialog.setMessage("Please Wait ..."); + dialog.setIndeterminate(true); + dialog.setCancelable(false); + dialog.show(); + } + @Override + protected Void doInBackground(Void... voids) { + try { + Root.setContext(ctx); + installPlaystationCertification(); + } + catch(Exception e){ + this.wasError = true; + this.errorMsg = e.getMessage(); + return null; + } + return null; + } + + @Override + protected void onPostExecute(Void result) { + dialog.dismiss(); + + if(wasError) { + new AlertDialog.Builder((Activity)ctx) + .setTitle("Error Occurred.") + .setMessage(this.errorMsg) + .setCancelable(false) + .setPositiveButton("Ok",null).show(); + } + else{ + new AlertDialog.Builder((Activity)ctx) + .setTitle("Installed!") + .setMessage("Your device is now \"Playstation Certified\"\n(You may have to reboot for changes to take effect)\n\nWould you like to patch the PSM application also?") + .setCancelable(false) + .setPositiveButton("Yes", new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialogInterface, int i) { + (new NoPsmDrmInstaller(PsCertificatesInstaller.this.ctx)).execute(); + } + }) + .setNegativeButton("No", null).show(); + } + } +} diff --git a/app/src/main/res/layout/activity_main.xml b/app/src/main/res/layout/activity_main.xml index 1ee52ae..a67d681 100644 --- a/app/src/main/res/layout/activity_main.xml +++ b/app/src/main/res/layout/activity_main.xml @@ -7,6 +7,7 @@ android:paddingRight="10dp" android:paddingBottom="10dp" android:keepScreenOn="true" + android:noHistory="true" android:orientation="vertical">