فئة OWASP: MASVS-PLATFORM: Platform Interaction
نظرة عامة
تحدث إعادة توجيه النية عندما يتمكّن المهاجم من التحكّم جزئيًا أو كليًا في محتويات نية مستخدَمة لتشغيل مكوّن جديد في سياق تطبيق متوفّر فيه ثغرة أمنية.
يمكن تقديم النية المستخدَمة لإطلاق المكوّن الجديد بعدة طرق،
ويكون الأكثر شيوعًا إما نية مُسلسلة في حقل extras
أو نية تم تجميعها
في سلسلة وتحليلها. يمكن أن يؤدي التحكّم الجزئي في المَعلمات أيضًا إلى النتيجة
نفسها.
التأثير
وقد يختلف التأثير. يمكن للمهاجم تنفيذ ميزات داخلية في التطبيق المعرض للاختراق، أو يمكنه الوصول إلى مكوّنات خاصة مثل عناصر ContentProvider التي لم يتم تصديرها.
إجراءات التخفيف
بشكل عام، لا تعرض الميزات ذات الصلة بإعادة توجيه النوايا المُدمَجة. في الحالات التي لا يمكن فيها تجنُّب استخدام هذه التقنيات، يُرجى تطبيق أساليب التخفيف التالية:
- يجب إزالة أي معلومات غير ضرورية من الحِزمة. من المهم التحقق من العلامات
أو إزالتها (
FLAG_GRANT_READ_URI_PERMISSION, FLAG_GRANT_WRITE_URI_PERMISSION, FLAG_GRANT_PERSISTABLE_URI_PERMISSION, and FLAG_GRANT_PREFIX_URI_PERMISSION
)، والتحقّق من مكان إعادة توجيه الطلب. يمكن لفريقIntentSanitizer
مساعدتك في هذه العملية. - استخدِم عناصر
PendingIntent
. ويؤدي ذلك إلى منع تصدير المكوّن ويجعل نية الإجراء المستهدَف غير قابلة للتغيير.
يمكن للتطبيقات التحقّق من المكان الذي تتم إعادة توجيه النية إليه باستخدام طرق مثل methods
ResolveActivity
:
Kotlin
val intent = getIntent()
// Get the component name of the nested intent.
val forward = intent.getParcelableExtra<Parcelable>("key") as Intent
val name: ComponentName = forward.resolveActivity(packageManager)
// Check that the package name and class name contain the expected values.
if (name.packagename == "safe_package" && name.className == "safe_class") {
// Redirect the nested intent.
startActivity(forward)
}
Java
Intent intent = getIntent()
// Get the component name of the nested intent.
Intent forward = (Intent) intent.getParcelableExtra("key");
ComponentName name = forward.resolveActivity(getPackageManager());
// Check that the package name and class name contain the expected values.
if (name.getPackageName().equals("safe_package") &&
name.getClassName().equals("safe_class")) {
// Redirect the nested intent.
startActivity(forward);
}
يمكن للتطبيقات استخدام IntentSanitizer
باستخدام منطق مشابه مما يلي:
Kotlin
val intent = IntentSanitizer.Builder()
.allowComponent("com.example.ActivityA")
.allowData("com.example")
.allowType("text/plain")
.build()
.sanitizeByThrowing(intent)
Java
Intent intent = new IntentSanitizer.Builder()
.allowComponent("com.example.ActivityA")
.allowData("com.example")
.allowType("text/plain")
.build()
.sanitizeByThrowing(intent);
الحماية التلقائية
- يقدّم Android 16 حلّاً لتعزيز الأمان بشكل تلقائي لاستغلالات إعادة توجيه Intent.
أخطاء شائعة
- التحقّق مما إذا كانت
getCallingActivity()
تعرِض قيمة غير فارغة يمكن للتطبيقات الضارّة تقديم قيمة فارغة لهذه الدالة. - بافتراض أنّ
checkCallingPermission()
تعمل في جميع السياقات، أو أنّ المحاولة تُعرِض استثناءً عندما تُعيد عددًا صحيحًا.
ميزات تصحيح الأخطاء
بالنسبة إلى التطبيقات التي تستهدف الإصدار 12 من نظام التشغيل Android (المستوى 31 من واجهة برمجة التطبيقات) أو الإصدارات الأحدث، يمكنك تفعيل ميزة تصحيح الأخطاء التي تساعدك في بعض الحالات في رصد ما إذا كان تطبيقك يؤدي إلى بدء عملية غير آمنة لطلب.
إذا نفَّذ تطبيقك كلا الإجراءَين التاليَين، يرصد النظام
بدء تشغيل نية غير آمنة، وتحدث مخالفة StrictMode
:
- يُفكّ تطبيقك حزمة هدف مُدمَج من البيانات الإضافية لهدف تم إرساله.
- يبدأ تطبيقك على الفور أحد مكوّنات التطبيق باستخدام هذا الإجراء المُدمَج، مثل
تمرير الإجراء إلى
startActivity()
أوstartService()
أوbindService()
.