首页 > 编程语言 >安卓程序逆向入门

安卓程序逆向入门

时间:2023-08-16 17:22:38浏览次数:63  
标签:lang 逆向 入门 Ljava StringBuilder 安卓 v0 v2 代码

Step2

将smali代码,翻译成java代码。主要包括两件事,第一件事翻译checker代码,顺便找一下满足checker条件的输入,使得Task1:的输出为true;第二件事是翻译encoder代码。当然在做第一件事的时候为了正确调试程序,需要翻译CheckBox代码。所有的java代码都存储在smali2java目录下。

2-1

翻译checker代码,通过找到满足条件的输入来确保代码翻译正确。

思路

仔细阅读smali代码,求助chatgpt和互联网资料。先将大段的代码改成java代码块,如循环结构,字符串处理代码块等。

  1. 这是一段循环结构的smali代码,他将被转化为如下java代码
.line 9
:goto_b
array-length v7, v6  # 获取字符数组的长度,并将结果存储到寄存器v7中
if-ge v0, v7, :cond_1f  # 如果v0 >= v7,则跳转到标签cond_1f
.line 10
aget-char v7, v6, v0  # 获取字符数组中索引为v0的字符,并将结果存储到寄存器v7中
const/16 v8, 0x78  # 将字符'x'的ASCII码(0x78)存储到寄存器v8中
if-ne v7, v8, :cond_1c  # 如果v7 != v8,则跳转到标签cond_1c
.line 11
add-int/lit8 v2, v2, 0x1  # 将寄存器v2加1
.line 12
if-ne v2, v5, :cond_19  # 如果v2 != v5(1),则跳转到标签cond_19
move v4, v0  # 将当前索引v0存储到寄存器v4中
.line 14
:cond_19
if-ne v2, v9, :cond_1c  # 如果v2 != v9(2),则跳转到标签cond_1c
move v3, v0  # 将当前索引v0存储到寄存器v3中
.line 9
:cond_1c
add-int/lit8 v0, v0, 0x1  # 将v0加
goto :goto_b  # 跳转到标签goto_b
for (int i = 0; i < charArray.length; i++) {
  char c = charArray[i];
  if (c == 'x') {
      countX++;
      if (countX==1) {
          firstXIndex = i;
      }else if (countX==2) 
          lastXIndex = i;
  }
}
  1. 接下来是一段字符串转化的smali代码转java的例子
new-instance v1, Ljava/lang/StringBuilder;
invoke-direct {v1}, Ljava/lang/StringBuilder;-><init>()V
invoke-virtual {v1, v2}, Ljava/lang/StringBuilder;->append(Ljava/lang/String;)Ljava/lang/
checkBox.rawInfo = input;
  1. 仔细分辨函数传参的值和寄存器中值的变化,这在2-2中给我造成了不小的麻烦

一些在代码调试过程中使用到的命令行语句

./adb root
./adb push '/Users/aibot/Library/Mobile Documents/com~apple~CloudDocs/日常记录/暑期科研训练/proj3/lab3-1逆向(上)/smali/Box1.dex' /data/app
./adb shell  
cd /data/app
dalvikvm -cp Box.dex CheckBox  

javac CheckBox.java && java CheckBox
0keyx***x9**11
0keyx000x90011

结果

找到了正确的密码:``0keyxkeyx90011,或者更确切的说是0keyx*x911`。代码存储在smali2java目录下。

image20230629142237402

image20230629195138710

2-2编解码

阅读编解码smali文件,然后将它的逻辑用java语言实现。

思路

首先观察smali文件,发现getSalt, byteToHexString,byteArrayToHexString等方法的代码量比较小;而encoding, check等方法的的代码量较多。因此先翻译代码量小的方法。之后再翻译代码量较多的方法。

byteToHexString为例演示

.method private byteToHexString(B)Ljava/lang/String;
.registers 6
.prologue
.line 58
.line 59
if-gez p1, :cond_4
.line 61
and-int/lit16 p1, p1, 0xff
.line 63
:cond_4
div-int/lit8 v0, p1, 0x10
.line 64
rem-int/lit8 v1, p1, 0x10
.line 65
new-instance v2, Ljava/lang/StringBuilder;
invoke-direct {v2}, Ljava/lang/StringBuilder;-><init>()V
iget-object v3, p0, LEncoder;->hexDigits:[Ljava/lang/String;
aget-object v0, v3, v0
invoke-virtual {v2, v0}, Ljava/lang/StringBuilder;->append(Ljava/lang/String;)Ljava/lang/StringBuilder;
move-result-object v0
iget-object v2, p0, LEncoder;->hexDigits:[Ljava/lang/String;
aget-object v1, v2, v1
invoke-virtual {v0, v1}, Ljava/lang/StringBuilder;->append(Ljava/lang/String;)Ljava/lang/StringBuilder;
move-result-object v0
invoke-virtual {v0}, Ljava/lang/StringBuilder;->toString()Ljava/lang/String;
move-result-object v0
return-object v0
.end method
private String byteToHexString(byte b) {
    int unsignedByte = b & 0xff;
    int highNibble = unsignedByte >>> 4;
    int lowNibble = unsignedByte & 0xf;
    return hexDigits[highNibble] + hexDigits[lowNibble];
}

通过分别取得一个字节高四位的值和低四位的值,并通过字典转化为字符。

接下来encoding为例,演示寄存器值的变化对代码逆向造成的影响。

.line 25
div-int/lit8 v4, v0, 0x3
invoke-virtual {v1, v4}, Ljava/lang/String;->charAt(I)C
move-result v4

encoding方法的第25行中出现对寄存器v1的操作,而在这行代码的前十几行都对v1没有操作。因此我找到函数初始化后对v1的操作

invoke-direct {p0}, LEncoder;->getSalt()Ljava/lang/String;
move-result-object v1
.line 17
new-instance v2, Ljava/lang/StringBuilder;
invoke-direct {v2}, Ljava/lang/StringBuilder;-><init>()V
invoke-virtual {v2, p1}, Ljava/lang/StringBuilder;->append(Ljava/lang/String;)Ljava/lang/StringBuilder;
move-result-object v2
invoke-virtual {v2, v1}, Ljava/lang/StringBuilder;->append(Ljava/lang/String;)Ljava/lang/StringBuilder;

可以看到上述的代码只是将slat的值暂时存在v1寄存器中,之后操作的分别是

p1v2。但是值得警惕的是,在之后的操作中v1p1的值并没有改变;而v2的值更新了。但是我在翻译代码时将这一段smali翻译成了String inputWithSalt = input + getSalt();这里错误的没有显示存储getSalt()方法的返回值。之后使用inputWithSalt的值替代getSalt()的原值。造成了盐值无法传递,decoder无法成功解码的严重错误。花了很长时间才发现。当然也不得不吐槽一下smali的循环结构是真的又臭又长。

结果

dalvikvm安卓模拟器上运行结果

dalvikvm -cp Box.dex CheckBox  
18307130341
70f01081050670f90a40710a10e10080731130b714e18b08
dalvikvm -cp Box.dex CheckBox 70f01081050670f90a40710a10e10080731130b714e18b08

image20230629143537873

javac逆向后代码运行结果

image20230629195102625

标签:lang,逆向,入门,Ljava,StringBuilder,安卓,v0,v2,代码
From: https://www.cnblogs.com/aibot/p/17635700.html

相关文章

  • 安卓程序开发入门
    Step1本步骤主要复习安卓软件开发的基本流程;实验共有四个要求,即编写一个会重启后自启动的位置显示,并具备在子进程中调用住进程UIChange函数功能的,同时能够使用反射方法调用libs库中依赖的jar文件的安卓app。按照实验指导书的要求依次实现上述要求。1-1后台服务实现了接收重启命......
  • 苹果app开发成本是否比安卓高?
    移动应用程序(APP)已经成为现代生活中不可或缺的一部分,而iOS和Android平台则是两个最主要的app发布平台。在开发一个APP时,成本是一个重要的考虑因素,而在苹果(iOS)和安卓(Android)这两个主要平台之间,是否存在开发成本的差异呢?让我们来深入探讨一下。开发工具和语言:ios开发:苹果的iOS平台使......
  • 紫光展锐T610(虎贲610)_芯片性能介绍_全国产安卓核心板定制
    紫光展锐T610核心板是影像全面升级的8核架构的4G移动平台。采用旗舰级DynamIQ架构设计,基于自主研发的第五代影像引擎Vivimagic解决方案,和高画质显示处理技术,为用户带来精致的高画质体验。展锐T610(虎贲610)安卓核心板基本概述虎贲T610处理器是由紫光展锐研发的一颗基于12nm工艺的4G芯......
  • python编程从入门到实践(第2版)学习笔记(变量,字符串)
    变量变量是一种可以赋给值的标签。每一个变量都指向一个相关联的值,下列代码中message即为变量,指向的值为“HelloPythonworld!”message="HelloPythonworld!"print(message)第二行的print()函数用于打印输出这个message变量所关联的值。且变量的值是可以修改的,p......
  • 高效提升工作效率,亚马逊云科技热门课程带你入门生成式AI
    当前人工智能仍处于飞速发展阶段,作为当下最先进的科学技术之一,相信大家对AIGC关注已久。今天,引用亚马逊云科技最新发布的七项生成式AI新功能来跟大家聊聊近期的热门生成式AI! 有人说,生成式AI将带来充满创造性的新世界;有人说,生成式AI热潮正在掀起一场新的科技革命;有人认为生成式AI将......
  • 安卓环境配置
    好久没搞android,一些基础配置忘得差不多了,这里慢慢回忆补充下。window:AndroidIDE需要FQ。gradle更新失败,一般是代理配置错误。需要修改代理,位置为:gradle/gradle.properties.一般代理不支持HTTPS,屏蔽即可。安装JavaSDK,https://www.oracle.com/cn/java/technologies/......
  • 1.C++入门以及简单顺序结构
    C++入门以及简单顺序结构一.编写一个简单的C++程序#include<iostream>usingnamespacestd;intmain(){ return0;}二.基础语法变量1.变量的概念变量本质上是一个装东西的盒子,并且只能存放一个值。2.变量的定义变量必须先定义,才可以使用inta=5;3.变量......
  • JS逆向日记 2
    0x1.源代码!function(){'usestrict';varc=q;functionx(){vary=['ver','1fa','.+)','rch','ist','.80','wXB','sio','app','ass','fb6','yQJ......
  • ❤️ GitHub Copilot 读心术揭秘,Copilot 逆向工程笔记
    总览你是否好奇GitHubCopilot如何知道你想写的内容?有时候它聪明得甚至好像读过你项目里其他文件一样,不要怀疑,它确实读过。这篇文章记录了我阅读一个对Copilot的逆向工程的笔记,一言以蔽之,Copilot使用了Jaccard相似度获取用户最近访问过的页面里与当前编辑内容最相似的代码......
  • Elasticsearch 保姆级入门篇
    Elasticsearch是一个分布式的、面向生产规模工作负载优化的搜索引擎。Kibana可以将Elasticsearch中的数据转化为直观的图表、图形和仪表盘。这篇文章,您将学习本地安装Elasticsearch和Kibana,以及使用开发工具/JavaSDK创建索引和搜索数据。1本地安装1.1创建网络我......