From b86bf0822905cbeb20e9d6e2dedf2b2edd98c144 Mon Sep 17 00:00:00 2001 From: Jean-Marie Mineau Date: Wed, 2 Apr 2025 16:45:26 +0200 Subject: [PATCH] model delegate last behavior --- patcher/src/code_loading_patcher.rs | 24 ++++++++++++++++-------- patcher/src/dex_types.rs | 2 ++ 2 files changed, 18 insertions(+), 8 deletions(-) diff --git a/patcher/src/code_loading_patcher.rs b/patcher/src/code_loading_patcher.rs index 1535325..5f7a704 100644 --- a/patcher/src/code_loading_patcher.rs +++ b/patcher/src/code_loading_patcher.rs @@ -5,14 +5,9 @@ use androscalpel::{Apk, DexString, IdType, VisitorMut}; use anyhow::{Context, Result}; use clap::ValueEnum; +use crate::dex_types::DELEGATE_LAST_CLASS_LOADER; use crate::runtime_data::RuntimeData; -// TODO TODO TODO TODO TODO TODO TODO TODO TODO TODO TODO -// -// INSERT EMPTY CLASS LOADERS WHEN ID REFERS TO UNKNOWN CLASS LOADER -// -// TODO TODO TODO TODO TODO TODO TODO TODO TODO TODO TODO - #[derive(ValueEnum, Debug, PartialEq, Clone, Copy, Default)] pub enum CodePatchingStrategy { #[default] @@ -70,7 +65,10 @@ fn insert_code_model_class_loaders(apk: &mut Apk, runtime_data: &mut RuntimeData apk.add_code(file, crate::labeling, false)?; } - assert!(!class_loaders.contains_key(&dyn_data.classloader)); + assert!( + !class_loaders.contains_key(&dyn_data.classloader), + "The same class loader should not appear twice in runtime_data.dyn_code_load" + ); let classes = apk.list_classes(); let mut class_loader = ClassLoader { @@ -305,7 +303,14 @@ impl ClassLoader<'_> { ty: &IdType, class_loaders: &HashMap, ) -> Option { - // TODO: Implemente different class loader behaviors + // TODO: Check Platform Classes + if self.class == *DELEGATE_LAST_CLASS_LOADER { + if let Some(new_ty) = self.renamed_classes.get(ty) { + return Some(new_ty.clone()); + } else if self.apk().get_class(ty).is_some() { + return Some(ty.clone()); + } + } if let Some(ref parent_id) = self.parent { if let Some(parent) = class_loaders.get(parent_id) { if let Some(new_ty) = parent.get_ref_new_name(ty, class_loaders) { @@ -315,6 +320,9 @@ impl ClassLoader<'_> { log::warn!("Class Loader {}({}) has parent {}, but parent was not found in class loader list", self.id, self.class.__str__(), parent_id); } } + if self.class == *DELEGATE_LAST_CLASS_LOADER { + return None; + } if let Some(new_ty) = self.renamed_classes.get(ty) { Some(new_ty.clone()) } else if self.apk().get_class(ty).is_some() { diff --git a/patcher/src/dex_types.rs b/patcher/src/dex_types.rs index 110a388..08f5d6f 100644 --- a/patcher/src/dex_types.rs +++ b/patcher/src/dex_types.rs @@ -102,6 +102,8 @@ pub(crate) static SCAL_TO_OBJ_DOUBLE: LazyLock = LazyLock::new(|| { pub(crate) static OBJECT_TY: LazyLock = LazyLock::new(|| IdType::from_smali("Ljava/lang/Object;").unwrap()); +pub(crate) static DELEGATE_LAST_CLASS_LOADER: LazyLock = + LazyLock::new(|| IdType::from_smali("Ldalvik/system/DelegateLastClassLoader;").unwrap()); /// Get the method that convert a object to its scalar conterpart (eg `java.lang.Integer` to `int` with /// `Ljava/lang/Integer;->intValue()I`)