5

我有一个 apk 的源代码,包含几百个类。我需要在我的源代码中获取对 Android SDK 方法的所有调用的列表。我想过开发一个python脚本来解析所有的源,但似乎有太多的规则需要定义。我觉得这太复杂了。

有人有想法吗?还是有现有的工具可以做到这一点?

例如,如果代码如下所示:

class MyActivity extends Activity {
    @Override
    public void onCreate(Bundle savedInstanceState) {
        if (savedInstanceState.containsKey("toto")) {
            setContentView(R.layout.mylayout);
            this.uselessMethod();
        }
    }
    public int uselessMethod() {
        new Thread();
    }
}

我想得到这样的东西:

  • java.lang.Thread#<'init'>()
  • android.app.Activity#onCreate(Bundle) 无效
  • android.app.Activity#setContentView(int) 无效
  • android.os.Bundle#containsKey(String) 布尔值

谢谢。

4

3 回答 3

2

查看Doxygen以提取所有方法。您可能希望使用 EXTRACT_ALL http://www.doxygen.nl/manual/starting.html#extract_all假设您的源代码中的所有内容都应记录在案(如第三方方法)。

我是凭记忆工作的,只是在这里试了一下。我认为 Doxygen 是通过其他选项来实现的(请参阅:如何让 doxygen 为 c 函数生成调用和调用者图)。虽然使用 Graphviz/dot,Doxygen 确实会生成一个协作图,但它看起来不会提取出您要查找的内容,我认为这是列出所有方法调用,包括那些不在您的源树。

于 2013-04-29T14:30:17.410 回答
1

这个对我有用:

static void printMethods(Class cls)
{
    if(cls!=null){
        System.out.println();
        System.out.println("Printing Methods of "+cls.getName()+":");
        System.out.println();
        for(Method m:cls.getDeclaredMethods()){
            System.out.println(m.toString());
        }
    }
}

如何称呼它:

    printMethods(Class_Goes_Here);

例子:

    printMethods(java.lang.Boolean.class);

结果:

Printing Methods of java.lang.Boolean:

public static int java.lang.Boolean.compare(boolean,boolean)
public static boolean java.lang.Boolean.getBoolean(java.lang.String)
public static int java.lang.Boolean.hashCode(boolean)
public static boolean java.lang.Boolean.logicalAnd(boolean,boolean)
public static boolean java.lang.Boolean.logicalOr(boolean,boolean)
public static boolean java.lang.Boolean.logicalXor(boolean,boolean)
public static boolean java.lang.Boolean.parseBoolean(java.lang.String)
public static java.lang.String java.lang.Boolean.toString(boolean)
public static java.lang.Boolean java.lang.Boolean.valueOf(java.lang.String)
public static java.lang.Boolean java.lang.Boolean.valueOf(boolean)
public boolean java.lang.Boolean.booleanValue()
public int java.lang.Boolean.compareTo(java.lang.Boolean)
public int java.lang.Boolean.compareTo(java.lang.Object)
public boolean java.lang.Boolean.equals(java.lang.Object)
public int java.lang.Boolean.hashCode()
public java.lang.String java.lang.Boolean.toString()

让我知道您是否还有其他问题或疑问

— DiLDoST

于 2020-08-25T20:09:39.907 回答
0

在我对这个问题的最后回答 7 个月后:

当我再次仔细阅读您的问题时,我发现您需要的是 Stacktrace。我为您创建了一个简单的类来轻松完成此操作。

StacktraceUtils 类:

public static class StackTraceUtils
{
    public static ArrayList<StackTraceElement> getStackTrace(Thread thread)
    {
        ArrayList<StackTraceElement> l=new ArrayList<>();

        Thread k=thread;
        {
            StackTraceElement[] v=k.getStackTrace();

            for (int i=(v.length - 1);i >= 0;i--)
            {
                StackTraceElement ste=v[i];
                if (!(StackTraceUtils.class.getName().equals(ste.getClassName())))
                {
                    l.add(0, ste);
                }
                else
                {
                    break;
                }
            }
        }
        return l;
    }

    public static String getStackTraceString(Thread thread)
    {
        String p="";
        Thread k=thread;
        p += ((k.getName().equals("main") ?"[MAIN]": k.getName()) + " [" + k.getId() + "]" + (Thread.currentThread().getId() == k.getId() ?" [CURRENT]": "") + " : ");
        for (StackTraceElement ste:StackTraceUtils.getStackTrace(k))
        {
            p += "\n\t->\t" + ste;
        }
        return p.toString();
    }
}

您可以这样打印 Stacktrace ljke:

System.out.println(StackTraceUtils.getStackTraceString(Thread.currentThread()));

结果:

Thread-21 [10892] [CURRENT] : 
    ->  Main.main(Main.java:59)
    ->  Main.main(Main.java:17)
    ->  java.lang.reflect.Method.invoke(Native Method)
    ->  java.lang.Thread.run(Thread.java:764)
    ...

请不要忘记给我投票,我几乎不需要投票来帮助别人更多。如果是,也不要忘记回答...谢谢

— DiLDoST

于 2021-03-10T23:00:36.473 回答