Class MethodRenamer

  • All Implemented Interfaces:
    IJbcoTransform

    public class MethodRenamer
    extends SceneTransformer
    implements IJbcoTransform
    Creates new method names using names of fields or generates randomly. New names are unique through the whole application.

    Some methods cannot be renamed:

    • main methods
    • constructors
    • static initializers
    (these methods are filtered by names)
    • ones that override/implement library methods

    To find methods from last group the next approach is used. All superclasses and interfaces that processing class extends / implements are collected. The children of that items are taken and united together along with processing class. The same action is performed for every item of the obtained result until the full "tree" is not created. Then from this tree, the classes that do not have methods with similar to searching signature, are removed. The left items that have SootClass.isLibraryClass() true are searching ones.

    This complex approach is used to detect indirect inheritance. Consider next example:

                                ,--------.
                                |A       |
                                |--------|
                                |--------|
                                |method()|
                                `--------'
                                  /    \
                                 /      \
     ,-----------------------------.  ,--------.       ,--------. ,--------------------------------.
     |D                            |  |B       |       |E       | | Note: E is a library interface |
     |-----------------------------|  |--------|       |--------| `--------------------------------'
     |-----------------------------|  |--------|       |--------|
     |method()                     |  |method()|       |method()|
     |method(java.lang.String, int)|  `--------'       `--------'
     `-----------------------------'           \      /
                                      ,------------------------.
                                      |C                       |
                                      |------------------------|
                                      |------------------------|
                                      |method()                |
                                      |method(java.lang.String)|
                                      |method(long, int)       |
                                      `------------------------'
     
    Thus when D#method() is processed, it must not be renamed as there is class C that implements library one (E#method()).

    After applying this transformer the next result is expected:

    • #method() is not renamed in any application classes as it overrides one from library
    • #method(java.lang.String), #method(long, int) and #method(java.lang.String, int) are renamed and have the same name. Such renaming behaviour allows having renaming map for every class with old method name as a key and new method name as a value
    Since:
    24-Jan-2006
    Author:
    Michael Batchelder, Pavel Nesterovich