在一个运行于DOS环境下的汇编语言程序中,int 21h 的使用是非常频繁的,因为它提供了与操作系统进行交互的主要手段。每当程序需要进行输入输出操作、访问文件、控制屏幕显示、管理内存或是结束程序等操作时,通常都会调用 int 21h 来实现这些功能。
image.png (313.87 KB, 下载次数: 0)
下载附件
2024-8-26 20:07 上传
image.png (140.48 KB, 下载次数: 0)
下载附件
2024-8-26 20:05 上传
mov ah, 9: 这里将9送入AH寄存器中,9是DOS中断调用功能号,对应于“输出$-terminated字符串到标准输出(通常是显示器)”的功能。int 21h: 最后,通过执行INT 21h指令,程序触发DOS中断,调用之前设置好的功能号9的服务。DOS会读取DX寄存器中的地址作为字符串的起始位置,然后将该地址指向的字符串输出到屏幕上。SI默认就使用DS
image.png (179.7 KB, 下载次数: 0)
下载附件
2024-8-26 20:06 上传
其实除了静态分析也可以直接box走起​
[C] 纯文本查看 复制代码#include
int main()
{
unsigned char data[20] = {
0x76, 0x0E, 0x77, 0x14, 0x60, 0x06, 0x7D, 0x04, 0x6B, 0x1E, 0x41, 0x2A, 0x44, 0x2B, 0x5C, 0x03,
0x3B, 0x0B, 0x33, 0x05,
};
for(int i=0; i
baby unity
https://bbs.kanxue.com/thread-278275.htm题目附件下载以后发现是il2cpp的脚本处理方式(和平时一般做的mono的不一样)将几个文件脱upx壳后用010 editor检查"\baby unity_Data\il2cpp_data\Metadata\global-metadata.dat"文件,发现文件头为AF 1B B1 FA无异常
通过https://github.com/Perfare/Il2CppDumper/下载工具说明里面提到的命令行格式为:Il2CppDumper.exe executable-file global-metadata output-directory用了这个没整起也不知道原因是什么直接使用下载好的工具里面的Il2CppDumper.exe打开,在下载的题目的路径里面依次选中GameAssembly.dll以及"\baby unity_Data\il2cpp_data\Metadata\global-metadata.dat"(其实本来按照教程应该是libil2cpp.so文件,即 apk的dll,但这个不是apk是exe)然后这个地方的GameAssembly相当于so文件运行成功
image.png (113.63 KB, 下载次数: 0)
下载附件
2024-8-26 20:08 上传
然后就在il2cppdumper的下载目录下面出现Dummydll以及下图
image.png (42.93 KB, 下载次数: 0)
下载附件
2024-8-26 20:08 上传
这个是Dummy.dll下面的
image.png (130.5 KB, 下载次数: 0)
下载附件
2024-8-26 20:09 上传
使用dnspy 32打开Assembly-Csharp
然后可以看到加密函数名称用IDA64打开GameAssembly.dll使用script file 导入文件,依次选择ida py3和script.json
根据最开始上面贴的教程没有选择导入然后分析界面的函数名称就清晰很多了,直接在函数窗口搜索对应的两个函数,checkflag和encrypt分析逻辑如下
最后一步即为比较加密后的flag和已知字符串,双击获得该字符串
脚本:import base64
​
//已知经过处理后的字符串
​
v7_str = "XIcKYJU8Buh:UeV:BKN{U[JvUL??VuZ?CXJ;AX^{Ae]gA[]gUecb@K]ei^22"
​
//将字符串转换为字节
​
reversed_v7_bytes = bytes(v7_str, 'utf-8')
​
//Step 2: 对字节进行异或操作还原
​
//因为Python字节是单字节的,所以我们不需要按对进行操作
​
reversed_v7_recovered = bytearray()
for i, byte in enumerate(reversed_v7_bytes):
reversed_v7_recovered.append(byte ^ 0xF)
​
//Step 4: Base64解码(假设v7_str已经是Base64编码过的)
​
//注意:由于不清楚原始的Base64编码是否有padding,这里假设没有padding
​
try:
v5_decoded = base64.b64decode(reversed_v7_recovered)
except Exception as e:
print(f"Base64解码时发生错误: {e}")
v5_decoded = None
​
print("尝试还原的原始字节数组v5:", v5_decoded)
XYCTF{389f6900-e12d-4c54-a85d-64a54af9f84c}DebugMe题目提示需要debugger,于是查看该apk附件的xml发现没有debugger,所以在模拟器上使用mt管理器添加调试权限步骤可参考
《安卓逆向这档事》五、1000-7=?&动态调试&Log插桩(随便找个地方加到application里面就行了,加中间省事)形如这样
然后再保存以后再安装,然后可以尝试将修改后的apk导出,用jadx查看xml发现添加成功(有点多此一举,可以直接mt看)android:debuggable="true"
(上面这个不行,记下来告诫自己)
设置断点然后开始运行,附上进程即可获得flag
针对这个题,接着去看了下安卓的东西linux或者安卓下的proc保留的是当前进程下面的进程号,文件句柄之类的这里提一下proc下面的self,cmdline,environ(当前程序的环境变量,如果flag放在环境变量里面,可以读取这个去找flag),然后非预期也是和这个地方有关DEX可执行文件,因为后续使用kotlin编写的最后与java是兼容的,所以后续的dex也可以使用jadx进行反编译jeb可进行动态跟踪这里复习一下apktool解包命令apktool d重新打包apktool b出题人说混淆器用的BlackObfuscator,depth设的高了点,好像有些版本的jadx直接报错了
混淆可以通过jeb去掉,可以去smali改debug的if判定出flag
调试层面也可以通过jadx,在adb路径处直接填写待调试exe的路径即可