new signature checking method

This commit is contained in:
Xinto 2020-10-02 18:43:16 +04:00
parent fa7ba49d93
commit 46978f2f6f
3 changed files with 61 additions and 4 deletions

View File

@ -1,7 +1,6 @@
package com.vanced.manager.model
import android.content.Context
import android.content.pm.PackageManager
import android.graphics.drawable.Drawable
import android.os.Build
import androidx.core.content.ContextCompat
@ -11,6 +10,7 @@ import androidx.databinding.ObservableInt
import com.beust.klaxon.JsonObject
import com.vanced.manager.BuildConfig.ENABLE_SIGNATURE_CHECK
import com.vanced.manager.R
import com.vanced.manager.utils.AppUtils.doSignaturesMatch
import com.vanced.manager.utils.AppUtils.managerPkg
import com.vanced.manager.utils.AppUtils.vancedRootPkg
import com.vanced.manager.utils.PackageHelper.isPackageInstalled
@ -37,9 +37,9 @@ open class DataModel(
fun fetch() = CoroutineScope(Dispatchers.IO).launch {
isAppInstalled.set(isPackageInstalled(appPkg, context.packageManager))
isOfficial.set(doSignaturesMatch(managerPkg, appPkg, context))
versionName.set(jsonObject.get()?.string("version")?.removeSuffix("-vanced") ?: context.getString(R.string.unavailable))
installedVersionName.set(getPkgVersionName(isAppInstalled.get(), appPkg))
isOfficial.set(doSignaturesMatch(managerPkg, appPkg))
versionCode.set(jsonObject.get()?.int("versionCode") ?: 0)
installedVersionCode.set(getPkgVersionCode(isAppInstalled.get(), appPkg))
buttonTxt.set(compareInt(installedVersionCode.get(), versionCode.get()))
@ -55,7 +55,7 @@ open class DataModel(
val pm = context.packageManager
return if (toCheck) {
if (ENABLE_SIGNATURE_CHECK) {
if (doSignaturesMatch(managerPkg, pkg) || appPkg == vancedRootPkg)
if (isOfficial.get() || appPkg == vancedRootPkg)
pm.getPackageInfo(pkg, 0).versionName.removeSuffix("-vanced")
else
pm.getPackageInfo(pkg, 0).versionName.removeSuffix("-vanced") + " (${context.getString(R.string.unofficial)})"
@ -66,12 +66,15 @@ open class DataModel(
}
}
/*
private fun doSignaturesMatch(pkg1: String, pkg2: String): Boolean =
if (isPackageInstalled(pkg2, context.packageManager))
context.packageManager.checkSignatures(pkg1, pkg2) == PackageManager.SIGNATURE_MATCH
else
true
*/
@Suppress("DEPRECATION")
private fun getPkgVersionCode(toCheck: Boolean, pkg: String): Int {
return if (toCheck) {

View File

@ -1,6 +1,5 @@
package com.vanced.manager.ui.fragments
import android.content.Context
import android.graphics.Color
import android.graphics.drawable.ColorDrawable
import android.os.Bundle

View File

@ -1,8 +1,11 @@
package com.vanced.manager.utils
import android.annotation.SuppressLint
import android.content.Context
import android.content.Intent
import android.content.pm.PackageInstaller
import android.content.pm.PackageManager
import android.os.Build
import androidx.lifecycle.LiveData
import androidx.lifecycle.MutableLiveData
import androidx.localbroadcastmanager.content.LocalBroadcastManager
@ -13,6 +16,7 @@ import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.delay
import kotlinx.coroutines.launch
import java.security.MessageDigest
object AppUtils {
@ -55,6 +59,57 @@ object AppUtils {
}
}
fun doSignaturesMatch(pkg1: String, pkg2: String, context: Context): Boolean {
val apk1sig = getApplicationSignature(pkg1, context)
val apk2sig = getApplicationSignature(pkg2, context)
return apk2sig.containsAll(apk1sig)
}
@SuppressLint("PackageManagerGetSignatures")
fun getApplicationSignature(packageName: String, context: Context): List<String> {
val signatureList: List<String>
return try {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
val sig = context.packageManager.getPackageInfo(packageName, PackageManager.GET_SIGNING_CERTIFICATES).signingInfo
signatureList = if (sig.hasMultipleSigners()) {
sig.apkContentsSigners.map {
val msgDigest = MessageDigest.getInstance("SHA")
msgDigest.update(it.toByteArray())
bytesToHex(msgDigest.digest())
}
} else {
sig.signingCertificateHistory.map {
val msgDigest = MessageDigest.getInstance("SHA")
msgDigest.update(it.toByteArray())
bytesToHex(msgDigest.digest())
}
}
} else {
val sig = context.packageManager.getPackageInfo(packageName, PackageManager.GET_SIGNATURES).signatures
signatureList = sig.map {
val msgDigest = MessageDigest.getInstance("SHA")
msgDigest.update(it.toByteArray())
bytesToHex(msgDigest.digest())
}
}
signatureList
} catch (e: Exception) {
emptyList()
}
}
private fun bytesToHex(bytes: ByteArray): String {
val hexArray = charArrayOf('0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F')
val hexChars = CharArray(bytes.size * 2)
var v: Int
for (j in bytes.indices) {
v = bytes[j].toInt() and 0xFF
hexChars[j * 2] = hexArray[v.ushr(4)]
hexChars[j * 2 + 1] = hexArray[v and 0x0F]
}
return String(hexChars)
}
private fun getErrorMessage(status: String, context: Context): String {
return when {
status.contains("INSTALL_FAILED_ABORTED") -> context.getString(R.string.installation_aborted)