ホームページ  >  記事  >  運用・保守  >  Android リバースエンジニアリングにおける smari 複合クラスの例の分析

Android リバースエンジニアリングにおける smari 複合クラスの例の分析

WBOY
WBOY転載
2023-05-12 16:22:131540ブラウズ

1.java Complex Class

何も理解できない場合は、JAVA の概要または構築方法を参照してください。
Android リバースエンジニアリングにおける smari 複合クラスの例の分析

ここにコードを投稿してください。とてもシンプルで難しくありません。

2.smali code

Java コードを smali コードに変換する必要があります。Java を smali に参照できます。

Android リバースエンジニアリングにおける smari 複合クラスの例の分析

Android リバースエンジニアリングにおける smari 複合クラスの例の分析

モジュールで見てみましょう。

2.1 最初のモジュール - 情報モジュール


Android リバースエンジニアリングにおける smari 複合クラスの例の分析

このモジュールは、クラス名などを示す基本情報です。それを知っていますが、Good は分析にはあまり役に立ちません。

2.2 2 番目のモジュール - 構築方法


Android リバースエンジニアリングにおける smari 複合クラスの例の分析

# 文ごとに分析してみましょう。前の分析で重複がある場合は、繰り返さないでください。ただし、リンクは提供されます。

.method public constructor <init>(Ljava/lang/String;I)V</init>

この文は

.methodpublicconstructor<init>(Ljava/lang/String;I)v</init>
2.2.1 .method

メソッドを意味します

2.2.2 public

変更メソッド、パブリック プロパティ

2.2.3 コンストラクター

ここでのコンストラクターとは、このメソッドがコンストラクター メソッドであることを意味します

2.2.4 <init> </init>

コンパイル後、Java はインスタンス コンストラクターと呼ばれるバイトコード ファイルに メソッドを生成します。このインスタンス コンストラクターはステートメント ブロック、変数を初期化し、親クラスのコンストラクターを呼び出し、他の操作は メソッド、および収束の順序 (ここでは非静的変数とステートメント ブロックのみについて説明します) は次のとおりです:

  1. 親クラス変数の初期化

  2. 親クラス ステートメント ブロック

  3. ##親クラス コンストラクター

  4. ##サブクラス変数の初期化
  5. #サブクラス ステートメント ブロック
  6. サブクラス コンストラクター
  7. メソッドへのいわゆる収束とは、これらの操作が < に入れられることを意味します。 ;init> 実行用
2.2.5 (Ljava/lang/String;I)

括弧内の内容は最初に Ljava/lang/String で、ここでは最初のパラメータが次のとおりであるとします。文字列型。
;

最後に I があります。これは、Ljava/lang にも属する int 型パラメータがあることを意味します。
2.2.6 v

最後に v がありますが、これは void を意味します。つまり、戻り値の型はありません。

2 番目の文の意味を見てみましょう。

.registers 6

6 を登録します。ここのレジスタは v0 ~ v5 から始まります。これはわかりやすいですね。

3 番目の文。

.prologue

オープニングとは番組の始まりを意味します。

4 番目の文。

.line 10

コードの 10 行目の意味。

5 番目の文は次のとおりです:

invoke-direct {p0}, Ljava/lang/Object;-><init>()V</init>

まずこの文を分解します。

invoke-direct{p0}Ljava/lang/Object;-><init>
()
V</init>
invoke-direct
はメソッド呼び出しを意味します。

{p0}
p0 は最初のパラメータを意味します。ただし、ここには最初のパラメータがありません。デフォルトはこれです。渡すパラメータは p1 から数え始めます。

Ljava/lang/Object;-><init></init>
Call

メソッド

()にはコンテンツがありません。つまり、パラメータがありません。 v は void と同等なので、ここでは繰り返しません。

6 番目の文は

iput-object p1, p0, LPerson;->name:Ljava/lang/String;

Break it down

iput-object p1,p0LPerson;->name:Ljava/lang/String;
iput-object p1, p0 は p1 の内容を p0 に与えることを意味します。

LPerson;->name:Ljava/lang/String;
この文の意味は、person クラスから name という名前の属性と型 String を取得し、p0 を変更することです。実際、これは this.name.

7 番目の文

iput p2, p0, LPerson;->age:I

も 2 つの部分に分かれています。

iput p2, p0LPerson;->age:I

iput p2, p0

、ここではp2の値をp0に代入します

LPerson;->age:I
年齢のデータ型がintであることを示しています。 String は基本的なデータ型ではないため、2 つのプロパティの呼び出しが異なることに気づくかもしれません。したがって、基本データ型が iput の場合は、iput-object が使用されます。

8 番目の文

 sget-object v0, Ljava/lang/System;->out:Ljava/io/PrintStream;

Decomposition

 sget-object v0
 Ljava/lang/System;->out:
 Ljava/io/PrintStream;
sget-object v0 は、取得後に満たされるものを v0 に与えることです。

Ljava/io/PrintStream;

これは、このクラスに

Ljava/lang/System;->out: メソッドがあることを意味します。 9 番目の文

new-instance v1, Ljava/lang/StringBuilder;

v1 用の新しい StringBuilder クラスを作成します。

10 番目の文

invoke-direct {v1}, Ljava/lang/StringBuilder;-><init>()V</init>

は前の文と似ており、コンストラクターから v1 を呼び出します。

11 番目の文

const-string v2, "name:"

const-string 定数文字列。 v2、コンテンツは名前です:

12 番目の文

 invoke-virtual {v1, v2}, Ljava/lang/StringBuilder;->append(Ljava/lang/String;)Ljava/lang/StringBuilder;

詳しく説明すると、

invoke-virtual {v1, v2}Ljava/lang/StringBuilder;->append(Ljava/lang/String;)Ljava/lang/StringBuilder;
invoke-virtual {v1, v2} は仮想メソッドを呼び出します。

->append(Ljava/lang/String;)Ljava/lang/StringBuilder;

append という名前の関数を呼び出します。パラメータは String 型、戻り値は StringBuilder 型です。
13 番目の文

move-result-object v1

は、前の文の結果を v1 レジスタに渡すことです。

之后的内容就是相似的了。
Android リバースエンジニアリングにおける smari 複合クラスの例の分析

有兴趣可以自己继续向下分析。

2.3 方法模块

这个模块在之前的一篇文章里已经说过了,这里就不再啰嗦了。

2.4 练习

这个练习我们就自己添加一个构造方法。

.method public constructor <init>()V    .registers 1
    invoke-direct {p0}, Ljava/lang/Object;-><init>()V
    return-void
.end method</init></init>

这个是我们自己写的一个构造方法。无参无返回值。

编译成jar文件进行查看。


Android リバースエンジニアリングにおける smari 複合クラスの例の分析

0x02 smali类相互调用

1. java代码

在0x01的前提上我们再写一个调用demo。

public class Demo{
    public static void main(String[]args)    {
        Person p=new Person("zhuzhu",14);
    }
}

代码很简单。

2.smali代码

这里我们要使用

javac -source 1.6 -target 1.6 *.java

编译所有.java文件

然后使用

dx --dex --output=demo.dex *.class

把所有的.class文件编译成dex文件。


Android リバースエンジニアリングにおける smari 複合クラスの例の分析

我们来主要看看main函数。

.method public static main([Ljava/lang/String;)V
    .registers 4

    .prologue
    .line 4
    new-instance v0, LPerson;

    const-string v1, "zhuzhu"    const/16 v2, 0xe    invoke-direct {v0, v1, v2}, LPerson;-><init>(Ljava/lang/String;I)V

    .line 5    return-void.end method</init>
new-instance v0, LPerson;

新建一个类,v0

const-string v1, "zhuzhu"

然后定义一个常量 v1。

const/16 v2, 0xe

定义一个16位的常量

invoke-direct {v0, v1, v2}, LPerson;-><init>(Ljava/lang/String;I)V</init>

调用Person类的构造方法,然后把v0,v1,v2当做参数传进去。

其实类之前的交互调用其实并不难。

3.总结

我们调用其他类的时候。

1.new-instance 实例化一个对象
2.invoke-direct 调用构造方法

0x03 小练习(甜点)

首先来看看我们写的程序。

Android リバースエンジニアリングにおける smari 複合クラスの例の分析

然后是手写的smali代码。

.class public LPd;
.super Ljava/lang/Object;
.source "Pd.java"# direct methods
.method public constructor <init>()V
    .registers 1    .prologue
    invoke-direct {p0}, Ljava/lang/Object;-><init>()V

    return-void.end method

.method public static main([Ljava/lang/String;)V

    .registers 4    .prologue

    new-instance v0,LPerson;

    invoke-direct {v0}, LPerson;-><init>()V

    return-void.end method</init></init></init>

以上がAndroid リバースエンジニアリングにおける smari 複合クラスの例の分析の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事はyisu.comで複製されています。侵害がある場合は、admin@php.cn までご連絡ください。