攻防世界-mobile(新手篇2)
jeb打开,分析关键代码,首先我们知道flag{}内的内容通过v4和v5加密得出的v3,最后为wigwrkaugala
,所以逆推出解密的步骤就能得到flag。分析参考:https://www.cnblogs.com/cainiao-chuanqi/p/13565030.html
先分析v4,得到是c的数组左移2位,结果是17 23 7 22 1 16 6 9 21 0 15 5 10 18 2 24 4 11 3 14 19 12 20 13 8 25
再分析v5,得到c的数组左移3位,结果是21 4 24 25 20 5 15 9 17 6 13 3 18 12 10 19 0 22 2 11 23 1 8 7 14 16
b类的a函数,该函数首先获取传进来的字符在字符串b.b中的索引,然后得到在b类中定义的整形数组中与该索引相等的在数组中的索引,然后调用b类的a()函数,将b类中数组与字符串左移一位,然后返回该数组索引。
a类中的a(int)函数,该函数首先获取与传进来的参数相等的数组中的值的索引,然后获取在字符串中索引为该数组索引的字符,最后返回该字符,当然,其中也调用a()函数,但是该函数要求等于25,所以形同虚设。
所以整理解密的脚本如下:
cipherText = 'wigwrkaugala'
aArray = [21,4,24,25,20,5,15,9,17,6,13,3,18,12,10,19,0,22,2,11,23,1,8,7,14,16]
aString = 'abcdefghijklmnopqrstuvwxyz'
bArray = [17,23,7,22,1,16,6,9,21,0,15,5,10,18,2,24,4,11,3,14,19,12,20,13,8,25]
bString = 'abcdefghijklmnopqrstuvwxyz'
def changeBArrayandString():
global bString
global bArray
chArray = bArray[0]
chString = bString[0:1]
for i in range(len(bArray) - 1):
bArray[i] = bArray[i + 1]
bArray[len(bArray) - 1] = chArray
bString = bString[1:]
bString += chString
def getBchar(ch):
v2 = bArray[ch]
arg = bString[v2]
changeBArrayandString()
return arg
def getAint(ch):
global aString
global aArray
v1 = aString.index(ch)
arg5 = aArray[v1]
return arg5
flag =''
for k in cipherText:
v0 = getAint(k)
flag += getBchar(v0)
print('flag{' + flag + '}')
0x01 RememberOther
压缩包解压后,得到一个word文档和apk,文档内容是不懂安卓,所以就只是和安卓扯了扯边,,,Have fun~
,点开可以看到需要输入用户名和一个16位的注册码。
jeb查看源代码,我们知道是经过checkSN函数的判断后,输出了一段字符,可能和flag有关,那么我们下一步就是要获取这个字符串,下面有三种方法。
方法1:我们能够在程序里看到输出的字符串是在程序中调用的,那它很可能存在程序的某段代码中,搜索发现,字符串在strings.xml中。
方法2:在分析checkSN函数时,惊奇地发现,在用户名和注册码都不填写的情况下会返回true。
方法3:分析checkSN函数可知,它是将用户名进行md5处理后,取所有的奇数位置的数字组合,组成16位sn再与注册码进行比较。
python脚本如下:
import hashlib
m = hashlib.md5()
m.update(b'123')
x = m.hexdigest()
sn = ''
for i in range(len(x)):
if i%2 == 0:
sn += x[i]
print (sn)
总之,最后得到b3241668ecbeb19921fdac5ac1aafa69
,解密下md5,得到YOU_KNOW_
,结合 word 中的提示,整理得到flag: YOU_KNOW_ANDROID
0x02 Ph0en1x-100
上模拟器,app功能是提交flag验证的。
上jeb分析代码,在主函数得到判断语句,接着往下分析。
encrypt和getFlag是从phcm库中调用的,导出库后,用ida分析。
encrypt函数,分析可知对字符串的每个字符的ascii值减一。
对于getFlag函数,由于该函数没有输入只有输出,所以可以通过APKIDE修改smali源码,在本来显示 Failed的地方,让其执行getFlag方法,将执行结果存入v1寄存器。
反编译后运行,可以得到一串字符串ek`fz@q2^x/t^fn0mF^6/^rb`qanqntfg^E`hq|
将字符串的ascii值移位得到flag
flag = ''
for i in c:
flag += chr(ord(i) + 1)
print(flag)
0x03 黑客精神
JEB进行反编译,发现在MainActivity点击按钮后就弹出弹框,而后跳转到RegActivity界面去,在该界面点击注册后,调用了so层函数saveSN。
跳转到saveSN函数所在的类MyApp,进一步分析代码。
接着分析libmyjni.so文件,在JNI_OnLoad函数中注册了initSN、saveSN和work函数,代码如下
用IDA分析so文件发现在java层注册的native函数都是动态注册的,发现对应的函数n1
、n2
、n3
。
setValue函数的作用是设置com/gdufs/xman/MyApp类的静态字段m的值,输入的注册码通过一系列的计算后得到的值,initSN函数会判断/sdcard/reg.dat文件的内容是否为"EoPAoY62@ElRD"
,如果得到的值正确,则输入的注册码即为flag。
输入"EoPAoY62@ElRD"
,通过模拟器进行查看。
0x04 easy-dex
dex里面包含了所有app代码,利用反编译工具可以获取java源码。理解并修改dex文件,就能更好的apk破解和防破解。
dex应该是藏在了so中,先寻找android_main函数,Native Activity的入口函数。qmemcpy函数将加密后的dex文件加载进来了,可以发现加密后的dex文件首地址为0x7004(IDA使用F5后,要使用那一块内存空间地址直接是以&unk地址命名的),长度为0x3ca10。
直接在静态下执行dump脚本
import idaapi
addr = 0x7004
size = 0x3ca10
with open('dump','wb') as f:
f.write(get_bytes(addr,size))
print('[+] dump end')
这里直接用大佬的python解密dex脚本
import zlib
with open('dump','rb') as f:
data1 = f.read()
data = list(data1)
count = 0
while True:
if count <= 0x59:
count_tmp = (int)(count / 10)
if count % 10 == 9:
size = 0x3ca10
size_tmp = (int)(size / 10)
xor = (count_tmp + 1) * size_tmp
if (size_tmp * count_tmp) < xor:
index = size_tmp * count_tmp
while size_tmp:
data[index] = data[index] ^ count
index = index + 1
size_tmp = size_tmp - 1
if count == 89:
while xor < size:
data[xor] = data[xor] ^ 0x59
xor = xor + 1
else:
break
count = count + 1
filebytes = bytes(data)
with open('easy-dex.dex','wb') as f1:
f1.write(zlib.decompress(filebytes))
print('[+] decrypt end')
jeb分析解压后的dex文件,MainActivity.java有一个按钮监听事件,触发后调用了a.java里面的onClick函数,调用了MainActivity里面的a函数。
编写脚本,求出密文iE3y2hEF1izgbVUfGKWQrUCtgFQFop7iEkbmRwWdwsZ1HdQGcPxRVAkWzV/eDC9N
|
|
再根据a函数,得出明文+key = 密文。
在string.xml资源文件中发现字符串I have a male fish and a female fish.
怀疑是TwoFish加密,输入key值和加密文本,得到flag。
0x05 你是谁
点击皇上的图片,听到语音“你是个好人,但是我们不适合。”,白色的圆可以被点击。
在MainActivity中找到注释中存在@Override // com.iflytek.cloud.InitListener
,搜索发现来源是科大讯飞的语音集成。在background类中发现编码,20667 25105 26159 36924
的中文unicode编码为傻我是逼
。
推理得出编码前的flag顺序应该是25105 26159 20667 36924
。