pcap4j - Android Proguard/R8 配置
pcap4j - Android Proguard/R8 Configuration
我在 Android 上使用 pcap4j,在 Debug Build 上一切正常。
但是在发布版本中激活 Proguard/R8 时会抛出以下异常:
java.lang.IllegalStateException: Unsupported target: class org.pcap4j.packet.IpV4Rfc1349Tos
at org.pcap4j.packet.factory.PacketFactoryBinder.getPacketFactory(SourceFile:2)
at org.pcap4j.packet.factory.PacketFactories.getFactory(SourceFile:2)
at org.pcap4j.packet.IpV4Packet$IpV4Header.<init>(SourceFile:6)
at org.pcap4j.packet.IpV4Packet.<init>(SourceFile:2)
at org.pcap4j.packet.IpV4Packet.newPacket(SourceFile:2)
at org.pcap4j.packet.factory.StaticEtherTypePacketFactory.newInstance(SourceFile:10)
at org.pcap4j.packet.factory.StaticEtherTypePacketFactory.newInstance(SourceFile:1)
at org.pcap4j.packet.IpSelector.newPacket(SourceFile:8)
作为解决此问题的方法,如果我添加此规则,它就可以正常工作:
-keep class org.pcap4j.packet.**
但根据上述规则,所有 类 都由收缩器保留且未优化
我的问题是如何编写更严格的规则来最大限度地缩小 pcap4j 并保持功能而不会抛出异常
我也尝试过以下规则,但仍然崩溃:
-keepclassmembernames class org.pcap4j.packet.**
-keepclassmembers class org.pcap4j.packet.**
-keepnames class org.pcap4j.packet.**
因此,另一种解决方法是在这种情况下保留此 2 类,一切都会正常进行:
-keep class org.pcap4j.packet.IpV4Packet
-keep class org.pcap4j.packet.IpV4Rfc1349Tos
但我要求的是 "general" 规则,因为在这种情况下,该应用程序可能会使用其他 类,如上文所述。
谢谢
为给定库提供特定规则通常需要深入了解库的工作方式,特别是库在何处使用反射。在完美的世界中,库提供者将包含所需的规则,请参阅[库模块的开发注意事项]。(https://developer.android.com/studio/projects/android-library#Considerations)。
当 R8(或 Proguard)处理代码时,它将跟踪所有可从 classes/methods/fields 访问的代码,这些代码指定由给定的规则保留。这适用于除反射之外的所有代码。当使用反射时,通常期望反射的项目存在,并且仍然具有它们的原始名称。因此反映的项目通常需要保留规则。
请注意,在简单的情况下会处理反射,例如:
Class.forName("com.example.MyClass")
此处跟踪将跟踪classcom.example.MyClass
,如果启用混淆,class也可以重命名,然后常量字符串也会被重写。
我在 Android 上使用 pcap4j,在 Debug Build 上一切正常。 但是在发布版本中激活 Proguard/R8 时会抛出以下异常:
java.lang.IllegalStateException: Unsupported target: class org.pcap4j.packet.IpV4Rfc1349Tos
at org.pcap4j.packet.factory.PacketFactoryBinder.getPacketFactory(SourceFile:2)
at org.pcap4j.packet.factory.PacketFactories.getFactory(SourceFile:2)
at org.pcap4j.packet.IpV4Packet$IpV4Header.<init>(SourceFile:6)
at org.pcap4j.packet.IpV4Packet.<init>(SourceFile:2)
at org.pcap4j.packet.IpV4Packet.newPacket(SourceFile:2)
at org.pcap4j.packet.factory.StaticEtherTypePacketFactory.newInstance(SourceFile:10)
at org.pcap4j.packet.factory.StaticEtherTypePacketFactory.newInstance(SourceFile:1)
at org.pcap4j.packet.IpSelector.newPacket(SourceFile:8)
作为解决此问题的方法,如果我添加此规则,它就可以正常工作:
-keep class org.pcap4j.packet.**
但根据上述规则,所有 类 都由收缩器保留且未优化
我的问题是如何编写更严格的规则来最大限度地缩小 pcap4j 并保持功能而不会抛出异常
我也尝试过以下规则,但仍然崩溃:
-keepclassmembernames class org.pcap4j.packet.**
-keepclassmembers class org.pcap4j.packet.**
-keepnames class org.pcap4j.packet.**
因此,另一种解决方法是在这种情况下保留此 2 类,一切都会正常进行:
-keep class org.pcap4j.packet.IpV4Packet
-keep class org.pcap4j.packet.IpV4Rfc1349Tos
但我要求的是 "general" 规则,因为在这种情况下,该应用程序可能会使用其他 类,如上文所述。
谢谢
为给定库提供特定规则通常需要深入了解库的工作方式,特别是库在何处使用反射。在完美的世界中,库提供者将包含所需的规则,请参阅[库模块的开发注意事项]。(https://developer.android.com/studio/projects/android-library#Considerations)。
当 R8(或 Proguard)处理代码时,它将跟踪所有可从 classes/methods/fields 访问的代码,这些代码指定由给定的规则保留。这适用于除反射之外的所有代码。当使用反射时,通常期望反射的项目存在,并且仍然具有它们的原始名称。因此反映的项目通常需要保留规则。
请注意,在简单的情况下会处理反射,例如:
Class.forName("com.example.MyClass")
此处跟踪将跟踪classcom.example.MyClass
,如果启用混淆,class也可以重命名,然后常量字符串也会被重写。