C++代码利用zlib检测Android apk应用加固类型

基本原理: 通过读取apk文件(实际就是zip)中的特征文件,来判断应用是否加固。开源的APKID中主要使用pyhon和yara规则,比我这个更加全面

1, 编译zlib和minizip

bash 复制代码
#buid zilb
cd YOUR_PATH
git clone https://gitclone.com/github.com/madler/zlib.git
mv zlib zlib-src
cd zlib-src/
./configure --prefix=${YOUR_PATH}/zlib/out
make
make test
make install

#build minizip
cd contrib/minizip/
make
cp -raf *.h ../../out/include/
cp -raf ioapi.o  ../../out/lib/libioapi.a
cp -raf unzip.o  ../../out/lib/libunzip.a
cp -raf zip.o  ../../out/lib/libzip.a

最后得到库文件

bash 复制代码
#show file
zlib-src/out$ ls include/
crypt.h  ioapi.h  iowin32.h  mztools.h  unzip.h  zconf.h  zip.h  zlib.h
zlib-src/out$ ls lib/
libioapi.a  libunzip.a  libz.a  libzip.a  libz.so  libz.so.1  libz.so.1.3.0.1-motley  pkgconfig

2,编写主程序

先将已经编译好的zlib和minizip拷贝到代码目录

bash 复制代码
#main code
cd YOUR_PATH
cp -raf zlib-src/out ./zlib-out

编写main.cpp

bash 复制代码
#include <iostream>
#include <string>
#include "zip.h"
#include "unzip.h"

bool debug = true;

std::string IsAndroidApkProtect(std::string &fileName)
{
        std::string EncryptType;

        std::string temp = fileName;

        if("libtup.so"  == temp || "libexec.so" == temp || "libshell.so" == temp  || "mix.dex" == temp)
        {
                EncryptType = "腾讯";
                return EncryptType;
        }
        else if("libsgmain.so"  == temp || "aliprotect.dat" == temp || "libsgsecuritybody.so" == temp || "libmobisec.so" == temp)
        {
                EncryptType = "阿里聚安全";
                return EncryptType;
        }
        else if("libchaosvmp.so"  == temp || "libddog.so" == temp || "libfdog.so" == temp )
        {
                EncryptType = "娜迦";
                return EncryptType;
        }
        else if("libkwscmm.so" == temp  ||  "libkwscr.so" == temp || "libkwslinker.so" == temp)
        {
                EncryptType = "几维安全";
                return EncryptType;
        }
        else if("libtosprotection.x86.so"== temp  ||  "libtosprotection.armeabi-v7a.so" == temp || "libtosprotection.armeabi.so" == temp)
        {
                EncryptType = "腾讯御安全";
                return EncryptType;
        }
        else if("libsecexe.so" == temp  ||  "libtosprotection.armeabi-v7a.so" == temp || "libtosprotection.armeabi.so" == temp)
        {
                EncryptType = "梆梆免费版";
                return EncryptType;
        }
        else if("libDexHelper.so" == temp  ||  "libDexHelper-x86.so" == temp )
        {
                EncryptType = "梆梆企业版";
                return EncryptType;
        }
        else if("libexec.so" == temp  ||  "libexecmain.so" == temp || "ijiami.dat" == temp )
        {
                EncryptType = "爱加密免费版";
                return EncryptType;
        }
        else if("libprotectClass.so" == temp  ||  "libjiagu.so" == temp || "libjiagu_art.so" == temp  || "libjiagu_x86.so" == temp)
        {
                EncryptType = "360";
                return EncryptType;
        }
        else if("libegis.so" == temp  ||  "libNSaferOnly.so" == temp )
        {
                EncryptType = "通付盾";
                return EncryptType;
        }
        else if("ijiami.ajm" == temp )
        {
                EncryptType = "爱加密企业版";
                return EncryptType;
        }
        else if("libedog.so" == temp )
        {
                EncryptType = "娜迦企业版";
                return EncryptType;
        }
        else if("libnqshield.so" == temp )
        {
                EncryptType = "网秦";
                return EncryptType;
        }
        else if("librsprotect.so" == temp )
        {
                EncryptType = "瑞星";
                return EncryptType;
        }
        else if("libbaiduprotect.so" == temp )
        {
                EncryptType = "百度";
                return EncryptType;
        }
        else if("libapssec.so" == temp )
        {
                EncryptType = "盛大加密";
                return EncryptType;
        }
        else if("libx3g.so" == temp )
        {
                EncryptType = "顶像科技";
                return EncryptType;
        }
        else if("libAPKProtect.so" == temp )
        {
                EncryptType = "APKProtect";
                return EncryptType;
        }
        else if("libnesec.so" == temp )
        {
                EncryptType = "网易易盾";
                return EncryptType;
        }


        EncryptType = "";
        return EncryptType;

}


bool checkApkProtect(const std::string& apkPath) {
    bool isProctected = false;

    unzFile zipFile = unzOpen(apkPath.c_str());
    if (zipFile == NULL) {
        std::cerr << "Cannot open " << apkPath << std::endl;
        return false;
    }

    if (unzGoToFirstFile(zipFile) != UNZ_OK) {
        unzClose(zipFile);
        std::cerr << "Cannot read files from " << apkPath << std::endl;
        return false;
    }

    std::string libPath = "lib/";
    do {
        char filename[256];
        unzGetCurrentFileInfo(zipFile, NULL, filename, sizeof(filename), NULL, 0, NULL, 0);
        std::string fileStr(filename);

        // 检查文件是否在lib目录下,并且是.so文件
        if (fileStr.substr(0, libPath.size()) == libPath && fileStr.size() > 3 &&
            fileStr.substr(fileStr.size() - 3) == ".so") {
            size_t lastHashPos = fileStr.find_last_of('/');
            std::string temp = fileStr.substr(lastHashPos + 1);
            if(debug){
                std::cout << "Found .so file: " << temp << std::endl;
            }
            std::string resultStr = IsAndroidApkProtect(temp);
            if(!resultStr.empty()){
                std::cout << "Protect Result: " << resultStr << std::endl;
                isProctected = true;
                break;
            }
        }

        if (unzGoToNextFile(zipFile) != UNZ_OK) {
            break;
        }
    } while (true);

    unzClose(zipFile);

    if(!isProctected)
            std::cout << "未检测到加固" << std::endl;

    return isProctected;
}

int main(int argc, char* argv[]) {
    if (argc < 2) {
        std::cerr << "Usage: " << argv[0] << " <apk_file_path>" << std::endl;
        return 1;
    }

    std::string apkFilePath = argv[1];
    checkApkProtect(apkFilePath);

    return 0;
}

3,编写Makefile

g++ main.cpp -o main -I xxx/include/ -L xxx/lib/ -l ioapi -l unzip -l zip -lz

定义编译器

CC := g++

ZIP_DEPS_PATH := ./zlib-out/

ZIP_INCLUDE := $(ZIP_DEPS_PATH)/include

ZIP_LIB :=$(ZIP_DEPS_PATH)/lib

定义编译选项

CFLAGS=-Wall -Wextra -std=c++11 -I $(ZIP_INCLUDE) -L $(ZIP_LIB) -l ioapi -l unzip -l zip -lz

目标文件

TARGET=apk_protect_detector

源文件

SRCS=main.cpp

目标文件

OBJS=$(patsubst %.cpp, %.o, $(SRCS))

默认目标

all: $(TARGET)

链接目标

$(TARGET): $(OBJS)

$(CC) $(CFLAGS) -o $@ $^

从.cpp文件生成.o文件

%.o: %.cpp

$(CC) $(CFLAGS) -c $< -o $@

清理编译生成的文件

clean:

rm -f $(OBJS) $(TARGET)

声明伪目标

.PHONY: all clean

4, 编译

make

g++ -Wall -Wextra -std=c++11 -I ./zlib-out//include -L ./zlib-out//lib -l ioapi -l unzip -l zip -lz -c main.cpp -o main.o

g++ -Wall -Wextra -std=c++11 -I ./zlib-out//include -L ./zlib-out//lib -l ioapi -l unzip -l zip -lz -o apk_protect_detector main.o

5, 测试

./apk_protect_detector yizhifu-10.88.10.apk

Found .so file: libapm_bitmaps.so

Found .so file: libijkengine-mp3.so

Found .so file: libjitdealer.so

Found .so file: libAlipayBitmapNative.so

Found .so file: libutility.so

Found .so file: libdatabase_sqlcrypto.so

Found .so file: libarthook.so

Found .so file: libsgnocaptchaso-5.5.8.so

Found .so file: libv8worker-native.so

Found .so file: libgetuiext3.so

Found .so file: libwind.so

Found .so file: libmpaas_crypto.so

Found .so file: libc++_shared.so

Found .so file: libjsengine-api.so

Found .so file: libhoks.so

Found .so file: libjsengine-platform.so

Found .so file: libnllvm1624349491.so

Found .so file: libAPMUOCPLIB.so

Found .so file: libandfix.so

Found .so file: libjdcard.so

Found .so file: libcrashsdk.so

Found .so file: libCryptoOperAd.so

Found .so file: libdexpatch_x86.so

Found .so file: libbestpaysheild.so

Found .so file: libturbojpeg.so

Found .so file: libDexHelper-x86.so
Protect Result: 梆梆企业版

总结:

目前代码只是一个基础,正确性还需要验证,后期还需要优化执行速度

相关推荐
hunandede27 分钟前
av_image_get_buffer_size 和 av_image_fill_arrays
c++
怀澈1222 小时前
高性能服务器模型之Reactor(单线程版本)
linux·服务器·网络·c++
闲暇部落2 小时前
‌Kotlin中的?.和!!主要区别
android·开发语言·kotlin
chnming19872 小时前
STL关联式容器之set
开发语言·c++
威桑2 小时前
MinGW 与 MSVC 的区别与联系及相关特性分析
c++·mingw·msvc
熬夜学编程的小王3 小时前
【C++篇】深度解析 C++ List 容器:底层设计与实现揭秘
开发语言·数据结构·c++·stl·list
yigan_Eins3 小时前
【数论】莫比乌斯函数及其反演
c++·经验分享·算法
Mr.133 小时前
什么是 C++ 中的初始化列表?它的作用是什么?初始化列表和在构造函数体内赋值有什么区别?
开发语言·c++
阿史大杯茶3 小时前
AtCoder Beginner Contest 381(ABCDEF 题)视频讲解
数据结构·c++·算法
C++忠实粉丝3 小时前
计算机网络socket编程(3)_UDP网络编程实现简单聊天室
linux·网络·c++·网络协议·计算机网络·udp