Google Play Protect拦截应用之系统签名

什么是 Google Play Protect ?

Google 于2017年推出的Android端有害软件查杀功能组件,类似于Windows端的Windows安全中心。主要用于查杀sideload(也就是我们通常说的apk包)的应用,GPP(Google Play Protect)认为Google Play的审核是靠谱的,所以不会怎么去动在架GP包。

不知道各位小伙伴有没有在开启谷歌服务的设备安装Apk时,遇到过下面这种Harmful app blocked的提示?

领导一开始让我解决这个问题,我测试了无数次,在不同的手机有的设备会出现,有的设备不会出现,我是丈二和尚摸不着头脑,一脸懵逼!经过一段时间的测试,这个问题就被搁置了。

直到后来在网上看到有文章介绍 Android系统组件的签名可以规避Google Play Protect拦截应用 的方案,于是就开始了尝试。

一、制作系统签名

签名文件

签名文件需要用到的文件有两个platform.pk8platform.x509.pem,由于我们的应用不属于定制主板开发,因此使用Android源码的这两个文件就行。 这里我直接通过ChatGPT找到了AOSP镜像在GitHub上的仓库,进去搜索就得到了我需要的文件,然后下载这两个文件到本地待使用。

快捷访问aosp-mirror

签名工具keytool-importkeypair

签名工具也可以直接从GitHub上面下载,快捷访问keytool-importkeypair

注意事项:下载的文件名称应该同网上的文件名称一致,我本地下载下来后,发现后缀会自动加一个txt,如果你也有的话,需要手动去掉。

签名方法

第一步

现在你已经有签名文件platform.pk8platform.x509.pem,签名工具文件keytool-importkeypair,先将他们放在同一个文件夹。为了方便管理,最好是单独在项目根目录下创建文件夹keystores

第二步

在文件夹keystores下创建signature.sh脚本文件,脚本文件内容如下:

sh 复制代码
sh keytool-importkeypair -k ./xxx.jks -p myjks -pk8 platform.pk8 -cert platform.x509.pem -alias signApk

指令详解:

  • -k ./xxx.jks------./xxx.jks指输出的签名文件地址
  • -p myjks------myjks签名文件密码
  • -alias signApk------signApk签名文件别名
  • 这里的签名文件密码属于storePassword,默认情况下storePassword和别名的keyPassword属于同一个

第三步

AndroidStudio中可以打开脚本文件,点击左上角的绿色三角符号运行脚本

当然,也可以通过其它方式来运行脚本文件。如果是在windows下的话,双击脚本文件便可以得到运行;如果是在Linux环境下,可直接执行。有疑问可以问问大模型。

脚本执行成功后就可以得到系统签名了。

storePasswordkeyPassword补充事宜

如果你需要分别设置密钥库密码和密钥条目的密码,可以使用以下步骤:

1.创建密钥库(带密钥库密码):
sh 复制代码
keytool -genkeypair -alias tempAlias -keyalg RSA -keysize 2048 -keystore my-release-key.jks -storepass storePassword -validity 10000

这里会提示你输入密钥条目的密码(keyPassword),可以与密钥库密码(storePassword)不同。

2.导入私钥和证书

使用 keytool-importkeypair 时,如果工具支持单独的密钥条目密码,你可以设置两个密码。假设你的 keytool-importkeypair 脚本不支持单独指定密钥条目密码,你可以手动创建密钥库,然后导入私钥和证书:

sh 复制代码
openssl pkcs8 -topk8 -inform PEM -outform DER -in platform.pk8 -out platform.der -nocrypt
    keytool -importkeystore -deststorepass storePassword -destkeypass keyPassword -destkeystore my-release-key.jks -srckeystore platform.p12 -srcstoretype PKCS12 -srcstorepass keyPassword -alias signApk

这将需要你先将私钥和证书转换为PKCS12格式,然后再导入到JKS中。

实际操作示例

1. 创建带有密钥库密码的密钥库
sh 复制代码
keytool -genkeypair -alias tempAlias -keyalg RSA -keysize 2048 -keystore my-release-key.jks -storepass myjks -keypass mykeypass -validity 10000
2. 删除临时密钥条目(如果你只想保留导入的密钥):
sh 复制代码
keytool -delete -alias tempAlias -keystore my-release-key.jks -storepass myjks
3. 使用转换和导入
sh 复制代码
openssl pkcs8 -topk8 -inform PEM -outform DER -in platform.pk8 -out platform.der -nocrypt
    openssl pkcs12 -export -in platform.x509.pem -inkey platform.der -out platform.p12 -name signApk -passout pass:mykeypass
    keytool -importkeystore -deststorepass myjks -destkeypass mykeypass -destkeystore my-release-key.jks -srckeystore platform.p12 -srcstoretype PKCS12 -srcstorepass mykeypass -alias signApk

通过这些步骤,你可以分别设置密钥库密码(storePassword)和密钥条目密码(keyPassword)。在上面的例子中,myjks 是密钥库密码,而 mykeypass 是密钥条目的密码。

系统签名的使用和解惑

使用签名

上面制作好了系统签名后,就可以替换项目里面的签名文件了。

groovy 复制代码
signingConfigs{
	...

	debug{
		storeFile file("../sign/system.jks")
		storePassword "harmful"
		keyAlias "harmful"
		keyPassword "harmful"

		v1SigningEnabled true
		v2SigningEnabled true
	}
}

buildTypes {
	debug {
		signingConfig signingConfigs.debug
		proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
	}
	...
}

运行之后确实没有上面Harmful app blocked的弹窗提示了

分析签名

那么系统签名究竟做了什么呢?

查看系统签名文件

sh 复制代码
keytool -list -v -keystore AndroidOSSign.jks -alias androidOSSign
  • AndroidOSSign.jks签名文件
  • androidOSSign别名

使用上面的命令后,会要求输入密码,输入密码后就可以看到下面的信息了

ruby 复制代码
别名: androidOSSign
创建日期: 2024年6月7日
条目类型: PrivateKeyEntry
证书链长度: 1
证书[1]:
所有者: EMAILADDRESS=android@android.com, CN=Android, OU=Android, O=Android, L=Mountain View, ST=California, C=US
发布者: EMAILADDRESS=android@android.com, CN=Android, OU=Android, O=Android, L=Mountain View, ST=California, C=US
序列号: b3998086d056cffa
生效时间: Wed Apr 16 06:40:50 CST 2008, 失效时间: Sun Sep 02 06:40:50 CST 2035
证书指纹:
         SHA1: 27:19:6E:38:6B:87:5E:76:AD:F7:00:E7:EA:84:E4:C6:EE:E3:3D:FA
         SHA256: C8:A2:E9:BC:CF:59:7C:2F:B6:DC:66:BE:E2:93:FC:13:F2:FC:47:EC:77:BC:6B:2B:0D:52:C1:1F:51:19:2A:B8
签名算法名称: MD5withRSA(禁用)
主体公共密钥算法: 2048 位 RSA 密钥
版本: 3

扩展:

#1: ObjectId: 2.5.29.35 Criticality=false
AuthorityKeyIdentifier [
KeyIdentifier [
0000: 4F E4 A0 B3 DD 9C BA 29   F7 1D 72 87 C4 E7 C3 8F  O......)..r.....
0010: 20 86 C2 99                                         ...
]
[EMAILADDRESS=android@android.com, CN=Android, OU=Android, O=Android, L=Mountain View, ST=California, C=US]
SerialNumber: [    b3998086 d056cffa]
]

#2: ObjectId: 2.5.29.19 Criticality=false
BasicConstraints:[
  CA:true
  PathLen: no limit
]

#3: ObjectId: 2.5.29.14 Criticality=false
SubjectKeyIdentifier [
KeyIdentifier [
0000: 4F E4 A0 B3 DD 9C BA 29   F7 1D 72 87 C4 E7 C3 8F  O......)..r.....
0010: 20 86 C2 99                                         ...
]
]


Warning:
证书 使用的 MD5withRSA 签名算法被视为存在安全风险而且被禁用。

我们重点关注一下所有者和发布者的信息:

ini 复制代码
所有者: EMAILADDRESS=android@android.com, CN=Android, OU=Android, O=Android, L=Mountain View, ST=California, C=US
发布者: EMAILADDRESS=android@android.com, CN=Android, OU=Android, O=Android, L=Mountain View, ST=California, C=US

所有者 (Owner) 和发布者 (Issuer) 字段包含以下信息:

  • CN (Common Name):通常是个人的姓名或服务器名称。
  • OU (Organizational Unit):组织单位。
  • O (Organization):组织名称(公司)。
  • L (Locality):城市或地方。
  • ST (State):州或省。
  • C (Country):国家。
  • 在自签名证书中,所有者和发布者是同一个实体。这意味着证书是由它所代表的实体自己签署的。自签名证书的所有者和发布者字段内容是相同的。

手动创建系统签名

看来系统签名主要是对所有者和发布者的信息进行了处理,那么我们可以自己进行设置吗?

当然,我们也可以根据上面的信息手动创建一个自签名,也可以得到和系统签名一个效果。

综上,我们基本上就可以解决签名的问题了。

但是,还有最后一个问题:

这个时候发现好像系统签名也不是每次都有用了。不管是通过AndroidStudio Run还是通过assemble进行打包后安装,都会时不时的出现Send app for a securitycheck的提示。虽然比起Harmful app blocked弹窗危害性没有那么大,但是也还是挺膈应人的。

我后来发现每次通过Build/Generate Signed Bundle or APK打包后安装,则没有这个弹窗了。由于测试的设备仅有一个设备,这个瓜就不保真了!

相关推荐
张拭心14 小时前
春节后,有些公司明确要求 AI 经验了
android·前端·人工智能
张拭心14 小时前
Android 17 来了!新特性介绍与适配建议
android·前端
Kapaseker17 小时前
Compose 进阶—巧用 GraphicsLayer
android·kotlin
黄林晴17 小时前
Android17 为什么重写 MessageQueue
android
阿巴斯甜2 天前
Android 报错:Zip file '/Users/lyy/develop/repoAndroidLapp/l-app-android-ble/app/bu
android
Kapaseker2 天前
实战 Compose 中的 IntrinsicSize
android·kotlin
xq95272 天前
Andorid Google 登录接入文档
android
黄林晴2 天前
告别 Modifier 地狱,Compose 样式系统要变天了
android·android jetpack
冬奇Lab2 天前
Android触摸事件分发、手势识别与输入优化实战
android·源码阅读
城东米粉儿2 天前
Android MediaPlayer 笔记
android