From cbfca1df4e0843345df147b645e8df8faf71db6c Mon Sep 17 00:00:00 2001 From: Tobias Blaschke Date: Sun, 2 Mar 2014 11:43:54 +0100 Subject: [PATCH] Call setIntent when starting a Component. Before the Intent would only have been set by calling .attach (if doBootSequence is enabled). Attach is only called when the modell is filled with instructions. This new variant calls setIntent when creating the wrapper for the model (getMethodAs). This is much better! --- .../callgraph/androidModel/AndroidModel.java | 7 +++- .../stubs/AndroidStartComponentTool.java | 38 +++++++++++++++++++ 2 files changed, 44 insertions(+), 1 deletion(-) diff --git a/com.ibm.wala.dalvik/src/com/ibm/wala/dalvik/ipa/callgraph/androidModel/AndroidModel.java b/com.ibm.wala.dalvik/src/com/ibm/wala/dalvik/ipa/callgraph/androidModel/AndroidModel.java index ee843a4ac..909b1402a 100644 --- a/com.ibm.wala.dalvik/src/com/ibm/wala/dalvik/ipa/callgraph/androidModel/AndroidModel.java +++ b/com.ibm.wala.dalvik/src/com/ibm/wala/dalvik/ipa/callgraph/androidModel/AndroidModel.java @@ -720,6 +720,7 @@ public class AndroidModel /* makes SummarizedMethod */ defaults.add(unpackedIntent); } } + final SSAValue intent = acc.firstExtends(AndroidTypes.Intent, cha); final AndroidStartComponentTool tool = new AndroidStartComponentTool(getClassHierarchy(), asMethod, flags, caller, instructionFactory, acc, pm, redirect, self, info, callerNd); @@ -734,9 +735,13 @@ public class AndroidModel /* makes SummarizedMethod */ // TODO: Check, that caller is an activity where necessary! - // TODO: Call Activity.setIntent //final SSAValue iBinder = tool.fetchIBinder(androidContext); //tool.assignIBinder(iBinder, allActivities); + if (intent != null) { + tool.setIntent(intent, allActivities); + } else if (! info.isSystemService()) { // it's normal for SystemServices + logger.warn("Got no Intent in call to: {} as {}", this.name, asMethod); + } // Call the model { diff --git a/com.ibm.wala.dalvik/src/com/ibm/wala/dalvik/ipa/callgraph/androidModel/stubs/AndroidStartComponentTool.java b/com.ibm.wala.dalvik/src/com/ibm/wala/dalvik/ipa/callgraph/androidModel/stubs/AndroidStartComponentTool.java index a9776a77b..1defd8bf2 100644 --- a/com.ibm.wala.dalvik/src/com/ibm/wala/dalvik/ipa/callgraph/androidModel/stubs/AndroidStartComponentTool.java +++ b/com.ibm.wala.dalvik/src/com/ibm/wala/dalvik/ipa/callgraph/androidModel/stubs/AndroidStartComponentTool.java @@ -255,6 +255,8 @@ public class AndroidStartComponentTool { final IClass iCaller = cha.lookupClass(caller); final IClass iActivity = cha.lookupClass(AndroidTypes.Activity); + final IClass iApp = cha.lookupClass(AndroidTypes.Application); + final IClass iService = cha.lookupClass(AndroidTypes.Service); logger.debug("Fetching caller context..."); final SSAValue androidContext; @@ -297,6 +299,16 @@ public class AndroidStartComponentTool { this.callerContext = AndroidTypes.AndroidContextType.CONTEXT_BRIDGE; logger.info("Caller has android-context type: BridgeContext"); return androidContext; + } else if (cha.isAssignableFrom(iApp, iCaller)) { + androidContext = self; + this.callerContext = AndroidTypes.AndroidContextType.APPLICATION; + logger.info("Caller has android-context type: Application"); + return androidContext; + } else if (cha.isAssignableFrom(iService, iCaller)) { + androidContext = self; + this.callerContext = AndroidTypes.AndroidContextType.SERVICE; + logger.info("Caller has android-context type: Service"); + return androidContext; } else { throw new UnsupportedOperationException("Can not handle the callers android-context of " + caller); } @@ -439,6 +451,32 @@ public class AndroidStartComponentTool { } } + /** + * Call Activity.setIntent. + */ + public void setIntent(SSAValue intent, List allActivities) { + if (intent == null) { + throw new IllegalArgumentException("Null-Intent"); + } + logger.info("Assigning the intent"); + // TODO: Use Phi? + for (SSAValue activity : allActivities) { + logger.debug("\tto: {}", activity); + + final int callPC = redirect.getNextProgramCounter(); + final Selector mSel = Selector.make("setIntent(Landroid/content/Intent;)V"); + final MethodReference mRef = MethodReference.findOrCreate(AndroidTypes.Activity, mSel); + final CallSiteReference site = CallSiteReference.make(callPC, mRef, IInvokeInstruction.Dispatch.VIRTUAL); + final SSAValue exception = pm.getException(); + final List params = new ArrayList(1); + params.add(activity); + params.add(intent); + final SSAInstruction invokation = instructionFactory.InvokeInstruction(callPC, params, exception, site); + redirect.addStatement(invokation); + } + } + + /** * Grab mResultCode and mResultData.