首页
社区
课程
招聘
[原创]Android逆向入门之switch
发表于: 2013-10-30 09:52 6805

[原创]Android逆向入门之switch

2013-10-30 09:52
6805
标 题: Android逆向入门之switch
作 者: 0x明天去要饭
时 间: 2013-10-30 9:50:00
链 接: http://bbs.pediy.com/showthread.php?p=1235203
原 文: http://www.sanwho.com/229.html(带语法着色)

一、效果展示



        密钥处的文本框id为txtValue,程序将根据输入密钥的长度判断注册是否成功(为演示方便所以挑了非常简单的注册算法),密钥有8位、12位、16位、20位4种,分别对应标准版、专业版、企业版、旗舰版。

二、Java源代码

         Java源文件名为SwitchActivity.java,核心代码如下:
  
Button.OnClickListener onClickListener = new Button.OnClickListener()
{
    @Override
    public void onClick(View v)
    {
        switch (v.getId())
        {
        case R.id.btnSubmit:
            EditText txtValue = (EditText) findViewById(R.id.txtValue);
            int len = txtValue.getText().toString().length();
            switch (len)
            {
            case 8:
                MessageBox("注册码有效, 适用于标准版");
                break;
 
            case 12:
                MessageBox("注册码有效, 适用于专业版");
                break;
 
            case 16:
                MessageBox("注册码有效, 适用于企业版");
                break;
 
            case 20:
                MessageBox("注册码有效, 适用于旗舰版");
                break;
            default:
                MessageBox("注册码无效!");
                break;
            }
            break;
        }
    }
};
 
/*
 * 弹出提示
 */
private void MessageBox(String str)
{      
    Toast.makeText(this, str, Toast.LENGTH_LONG).show();
}

三、反编译成java



通过反编译可以发现:

反编译出来的switch语句在结构解析上存在一点问题,但是基本不影响阅读。

四、反编译成.smali

        反编译后会得到两个文件,一个为SwitchActivity.smali,一个为SwitchActivity$1.smali,核心代码在SwitchActivity$1.smali这个文件中,详细分析如下:

# onClick方法
.method public onClick(Landroid/view/View;)V
    .locals 4
    .parameter “v”

    .prologue
    .line 37
    invoke-virtual {p1}, Landroid/view/View;->getId()I

    move-result v2   # v2 = p1.getId();

    packed-switch v2, :pswitch_data_0  # switch(v2), 通过pswitch_data_0进行匹配

    #———– switch出口开始 ———-
    .line 65
    :goto_0
    return-void
    #———– switch出口结束 ———-

    .line 40
    :pswitch_0    # switch(v2)入口
    iget-object v2, p0, Lcom/sanwho/crackdemo/SwitchActivity$1;->this$0:Lcom/sanwho/crackdemo/SwitchActivity;

    const v3, 0x7f080008    # txtValue Id

    invoke-virtual {v2, v3}, Lcom/sanwho/crackdemo/SwitchActivity;->findViewById(I)Landroid/view/View;

    move-result-object v1   # v1为txtValue的View对象;

    check-cast v1, Landroid/widget/EditText;  # 把txtValue转换成EditText对象

    .line 41
    .local v1, txtValue:Landroid/widget/EditText;
    invoke-virtual {v1}, Landroid/widget/EditText;->getText()Landroid/text/Editable;

    move-result-object v2   # v2 = txtValue.getText();

    invoke-interface {v2}, Landroid/text/Editable;->toString()Ljava/lang/String;

    move-result-object v2   # v2 = txtValue.getText().toString();

    invoke-virtual {v2}, Ljava/lang/String;->length()I

    move-result v0          # v0 = txtValue.getText().toString().length();

    .line 42
    .local v0, len:I
    sparse-switch v0, :sswitch_data_0  # switch(v0), 通过sswitch_data_0表进行匹配

    # —– default开始 —–
    .line 60
    iget-object v2, p0, Lcom/sanwho/crackdemo/SwitchActivity$1;->this$0:Lcom/sanwho/crackdemo/SwitchActivity;

    const-string v3, “\u6ce8\u518c\u7801\u65e0\u6548!”   # 注册码无效

    #calls: Lcom/sanwho/crackdemo/SwitchActivity;->MessageBox(Ljava/lang/String;)V
    # SwitchActivity.MessageBox(“注册码无效”);
    invoke-static {v2, v3}, Lcom/sanwho/crackdemo/SwitchActivity;->access$0(Lcom/sanwho/crackdemo/SwitchActivity;Ljava/lang/String;)V

    goto :goto_0
    # —– default结束 —–

    # —– case 8开始 —–
    .line 45
    :sswitch_0    # 对应sparse-switch表中的第一项, 即8
    iget-object v2, p0, Lcom/sanwho/crackdemo/SwitchActivity$1;->this$0:Lcom/sanwho/crackdemo/SwitchActivity;

    const-string v3, “\u6ce8\u518c\u7801\u6709\u6548, \u9002\u7528\u4e8e\u6807\u51c6\u7248″   # 注册码有效, 适用于标准版

    #calls: Lcom/sanwho/crackdemo/SwitchActivity;->MessageBox(Ljava/lang/String;)V
    # SwitchActivity.MessageBox(“注册码有效, 适用于标准版”);
    invoke-static {v2, v3}, Lcom/sanwho/crackdemo/SwitchActivity;->access$0(Lcom/sanwho/crackdemo/SwitchActivity;Ljava/lang/String;)V

    goto :goto_0
    # —– case 8结束 —–

    # —– case 12开始 —–
    .line 49
    :sswitch_1    # 对应sparse-switch表中的第二项, 即12
    iget-object v2, p0, Lcom/sanwho/crackdemo/SwitchActivity$1;->this$0:Lcom/sanwho/crackdemo/SwitchActivity;

    const-string v3, “\u6ce8\u518c\u7801\u6709\u6548, \u9002\u7528\u4e8e\u4e13\u4e1a\u7248″   # 注册码有效, 适用于专业版

    #calls: Lcom/sanwho/crackdemo/SwitchActivity;->MessageBox(Ljava/lang/String;)V
    # SwitchActivity.MessageBox(“注册码有效, 适用于专业版”);
    invoke-static {v2, v3}, Lcom/sanwho/crackdemo/SwitchActivity;->access$0(Lcom/sanwho/crackdemo/SwitchActivity;Ljava/lang/String;)V

    goto :goto_0
    # —– case 12结束 —–

    # —– case 16开始 —–
    .line 53
    :sswitch_2    # 对应sparse-switch表中的第三项, 即16
    iget-object v2, p0, Lcom/sanwho/crackdemo/SwitchActivity$1;->this$0:Lcom/sanwho/crackdemo/SwitchActivity;

    const-string v3, “\u6ce8\u518c\u7801\u6709\u6548, \u9002\u7528\u4e8e\u4f01\u4e1a\u7248″   # 注册码有效, 适用于企业版

    #calls: Lcom/sanwho/crackdemo/SwitchActivity;->MessageBox(Ljava/lang/String;)V
    # SwitchActivity.MessageBox(“注册码有效, 适用于企业版”);
    invoke-static {v2, v3}, Lcom/sanwho/crackdemo/SwitchActivity;->access$0(Lcom/sanwho/crackdemo/SwitchActivity;Ljava/lang/String;)V

    goto :goto_0
    # —– case 16结束 —–

    # —– case 20开始 —–
    .line 57
    :sswitch_3    # 对应sparse-switch表中的第四项, 即20
    iget-object v2, p0, Lcom/sanwho/crackdemo/SwitchActivity$1;->this$0:Lcom/sanwho/crackdemo/SwitchActivity;

    const-string v3, “\u6ce8\u518c\u7801\u6709\u6548, \u9002\u7528\u4e8e\u65d7\u8230\u7248″  # 注册码有效, 适用于旗舰版

    #calls: Lcom/sanwho/crackdemo/SwitchActivity;->MessageBox(Ljava/lang/String;)V
    # SwitchActivity.MessageBox(“注册码有效, 适用于旗舰版”);
    invoke-static {v2, v3}, Lcom/sanwho/crackdemo/SwitchActivity;->access$0(Lcom/sanwho/crackdemo/SwitchActivity;Ljava/lang/String;)V

    goto :goto_0
    # —– case 20结束 —–

    # —– 第一重switch表开始 —–
    .line 37
    :pswitch_data_0
    .packed-switch 0x7f080004
        :pswitch_0
    .end packed-switch
    # —– 第一重switch表结束 —–

    # —– 第二重switch表开始 —–
    .line 42
    :sswitch_data_0
    .sparse-switch
        0×8 -> :sswitch_0   # case(8), 跳到sswitch_0
        0xc -> :sswitch_1    # case(12), 跳到sswitch_1
        0×10 -> :sswitch_2 # case(16), 跳到sswitch_2
        0×14 -> :sswitch_3  # case(20), 跳到sswitch_3
    .end sparse-switch
    # —– 第二重switch表结束 —–
.end method

相关文件下载: android逆向入门之switch.rar

[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

上传的附件:
收藏
免费 0
支持
分享
最新回复 (0)
游客
登录 | 注册 方可回帖
返回
//