[Soot-list] java.lang.RuntimeException: cannot set body for non-concrete method!

Eric Bodden eric.bodden at ec-spride.de
Wed Jan 23 02:44:26 EST 2013


Thanks Michael, that's useful feedback.

I will think about how we can provide a better error message.

W.r.t. your example I wonder whether you know the option all-reachable:
http://www.sable.mcgill.ca/soot/tutorial/phase/

This automatically assumes all methods of application classes to be
reachable. It may just give you what you want.

Eric

On 22 January 2013 20:35, Michael Faes <rolve at trick17.ch> wrote:
> While preparing the example, I found the problem. At least that's what I
> think. Here is the "minimal" code that reproduces the exception:
>
> ------------------------------------------------
> import java.util.LinkedList;
> import java.util.List;
>
> import soot.PackManager;
> import soot.Scene;
> import soot.SootClass;
> import soot.SootMethod;
> import soot.options.Options;
>
> public class NonConcreteMethodBug {
>
>     public static void main(final String[] args) {
>         Options.v().set_whole_program(true);
>         Options.v().parse(new String[] {"TestInterface"});
>
>         for(final Object name : Options.v().classes())
>             Scene.v().forceResolve((String) name, SootClass.BODIES);
>
>         Scene.v().loadNecessaryClasses();
>         Scene.v().setEntryPoints(allPublicMethods());
>
>         PackManager.v().runPacks();
>     }
>
>     private static List<SootMethod> allPublicMethods() {
>         List<SootMethod> entryPoints = new LinkedList<SootMethod>();
>         for(final Object name : Options.v().classes()) {
>             List<SootMethod> methods = Scene.v().getSootClass(
>                     (String) name).getMethods();
>             for(final SootMethod method : methods)
>                 if(method.isPublic())
>                     entryPoints.add(method);
>         }
>         return entryPoints;
>     }
> }
>
> interface TestInterface {
>     void doSomething();
> }
> ------------------------------------------------
>
> By looking at it like that, you immediately see that I am adding interface
> (abstract) methods as entry points. And this is what seems to cause the
> problem. If I add the necessary check:
>
> if(method.isPublic() && !method.isAbstract()
>     entryPoints.add(method);
>
> the exception no longer occurs.
>
> Of course it doesn't make any sense to add abstract methods as entry points,
> so this is my fault. But I think it would be good if Soot handled this error
> more nicely, either by ignoring abstract entry point methods or by checking
> it in the setEntryPoints() method and throwing an exception with a
> meaningful error message.
>
> In any case, thank you very much for helping me here.
>
>
> Michael
>
>
> -------- Original-Nachricht --------
> Betreff: Re: [Soot-list] java.lang.RuntimeException: cannot set body for
> non-concrete method!
> Von: Eric Bodden <eric.bodden at ec-spride.de>
> An: Michael Faes <rolve at trick17.ch>
> Datum: 22.01.2013 17:18
>
>
>> Michael can you maybe prepare a minimal example (including your driver
>> class) that would allow us to reproduce the bug?
>>
>> A simple workaround would be to change processNewMethod to include...
>>          if( !m.hasActiveBody() ) {
>>              return;
>>          }
>> ... but I fear that this may just be masking the actual bug.
>>
>> Eric
>>
>> On 22 January 2013 09:51, Michael Faes <rolve at trick17.ch> wrote:
>>>
>>> Hi
>>>
>>> Thank you for the answers. I'm not sure how to implement Andrea's
>>> approach
>>> as I'm using custom class resolving and loading code. Based on your
>>> article
>>> (http://www.bodden.de/2012/07/26/soot-custom-entry-points/), I understand
>>> it
>>> is not recommended to call the main method in that case.
>>>
>>> Michael
>>>
>>> -------- Original-Nachricht --------
>>> Betreff: Re: [Soot-list] java.lang.RuntimeException: cannot set body for
>>> non-concrete method!
>>> Von: Eric Bodden <eric.bodden at ec-spride.de>
>>> An: Andrea Mattavelli <andrea.mattavelli at usi.ch>
>>> Datum: 21.01.2013 18:05
>>>
>>>
>>>> Hello.
>>>>
>>>> The method looks as follows:
>>>>
>>>>       private void processNewMethod( SootMethod m ) {
>>>>           if( m.isNative() || m.isPhantom() ) {
>>>>               return;
>>>>           }
>>>>           Body b = m.retrieveActiveBody();
>>>>           getImplicitTargets( m );
>>>>           findReceivers(m, b);
>>>>       }
>>>>
>>>> I think that the check above is correct because "m" in this particular
>>>> setting should usually always be a concrete method. If it is not then
>>>> something odd has happened before. I also suspect a problem with
>>>> phantom refs.
>>>>
>>>> Could you try the approach that Andrea suggested to see if that helps?
>>>>
>>>> Cheers,
>>>> Eric
>>>>
>>>>
>>>
>>
>>
>>
>



-- 
Eric Bodden, Ph.D., http://sse.ec-spride.de/ http://bodden.de/
Head of Secure Software Engineering Group at EC SPRIDE
Tel: +49 6151 16-75422    Fax: +49 6151 16-72051
Room 3.2.14, Mornewegstr. 30, 64293 Darmstadt


More information about the Soot-list mailing list