吾爱破解 - 52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 12683|回复: 6
收起左侧

[Android 讨论] 和平精英模拟器检测分析

  [复制链接]
MTPnb 发表于 2021-2-26 07:44
本帖最后由 MTPnb 于 2021-3-21 15:54 编辑

核心原理:读取elf头,判断机器类型是否为x86过检测方法(以雷电模拟器4为例):第一种方法(推荐使用这种方法):修改系统/system/lib中所有so的机器类型,改为arm,但是这样改了之后,加载so会报 unexpectede_machine,解决办法就是去掉系统加载so过程中判断机器类型的代码段。打开android7.1源码中linker_phdr.cpp,在VerifyElfHearder函数开头加上return true; 这样linker链接的时候就不会去判断elf头,也就不会报错,然后编译linker,把编译出来的linker替换掉模拟器中的/system/bin/linker,再重启模拟器即可。以后直接打开游戏就能过检测了。 {3711E302-4556-07A0-CEB5-11C342F011BD}.png 另外一种方法(内存改错了,有几率会10年):游戏打开后,再去修改系统的so,也能过检测,但是会被封1年。这是因为游戏打开的时候,/system/lib中的so会映射到内存中,相当于复制一份,还需要修改游戏内存中so的机器类型,可以通过/proc/$pid/maps文件查看游戏加载的so。  通过对游戏Lua对抗方案的代码段进行inlinehook,可以导出对应lua文件。例如:其中的detect_chicken就是用来检测鸡腿挂的。Scan_emulator_release用来检测模拟器,可以动态更新检测策略。Emu_info_collect用来收集模拟器信息,估计是用来追封用的吧。 lua.png 以下是 scan_emulator_release 的lua代码:
[Lua] 纯文本查看 复制代码
local function is_null(p)
        if p == 0 or p == nil then
                return true
        end
        return false
end

local function find_str(s1, s2)
        local n1,n2 = string.find(s1, s2, 1, true)
        if (n1 ~= nil and n2 ~= nil)
        then
                return true
        end
        return false
end

local function str_startswith(s1, s2)
        local n1, n2 = string.find(s1, s2, 1, true)
        if (n1 ~= nil and n2 ~= nil and n1 == 1)
        then
                return true
        end
        return false
end

local function str_endswith(s1, s2)
        local n1, n2 = string.find(s1, s2, 1, true)
        if (n1 ~= nil and n2 ~= nil and n2 == #s1)
        then
                return true
        end
        return false
end

local function open_file_exists(s_path)
        local is_valid_path = false
        if (str_startswith(s_path,"/system/") or
                str_startswith(s_path,"/data/") or
                str_startswith(s_path,"/lib/") or
                str_startswith(s_path,"/sbin/") or
                str_startswith(s_path,"/sys/")) and
                (str_endswith(s_path,".so")) then
                is_valid_path = true
        end
        if not is_valid_path then
                return false
        end
        local f = io.open(s_path, "r")
        if f then io.close(f) end
        return f ~= nil
end

local function bin2hex(s)
        s=string.gsub(s,"(.)",function (x) return string.format("%02X",string.byte(x)) end)
        return s
end

local function basename(str)
        local name = string.gsub(str, "(.*[\\/])(.*)", "%2")
        return name
end

local function check_elf_file_x86_emulator(file_path)
        local ret = 0
        if not open_file_exists(file_path) then
                return ret
        end
        local f = io.open(file_path,'rb')
        if f then
                local sizes = f:seek("end")
                if sizes > 1024 then
                        f:seek("set")
                        local content = f:read(4)
                        local hexstr = bin2hex(content)
                        if hexstr == "7F454C46" then
                                local is_32_64 = f:read(1)
                                hexstr = bin2hex(is_32_64)
                                if hexstr == "01" then
                                        f:seek("set",18)
                                        local cpu_type = f:read(2)
                                        hexstr = bin2hex(cpu_type)
                                        if hexstr == "0300" then
                                                ret = 1
                                        end
                                end
                        end
                end
                f:close()
        end
        return ret
end

local function get_int_value(key, deft)
        local value = TssSDK.get_value_by_key(key)
        if not is_null(value) then
                local int_val = tonumber(value)
                if int_val then
                        return int_val
                end
        end
        return deft
end

local g_mark_scan_flag = "llua_ser_20200421_scanned"
local g_module_cnt = 0
local g_libc_files_cnt = 0
local g_has_x86_file = 0
local g_x86_file_name = ""
local g_tp_ver = ""
local g_libhoudini_file_name = ""
local g_libhoudini_file_size = 0

local function save_scan_result()
        TssSDK.set_key_and_value("LEMC", ""..g_module_cnt)
        TssSDK.set_key_and_value("LEFC", ""..g_libc_files_cnt)
        TssSDK.set_key_and_value("LEHX", ""..g_has_x86_file)
        TssSDK.set_key_and_value("LEXN", g_x86_file_name)
        TssSDK.set_key_and_value("LETV", g_tp_ver)
        TssSDK.set_key_and_value("LENM", g_libhoudini_file_name)
        TssSDK.set_key_and_value("LESZ", ""..g_libhoudini_file_size)
end

local function load_scan_result()
        g_module_cnt = get_int_value("LEMC", 0)
        g_libc_files_cnt = get_int_value("LEFC", 0)
        g_has_x86_file = get_int_value("LEHX", 0)
        g_x86_file_name = TssSDK.get_value_by_key("LEXN")
        g_tp_ver = TssSDK.get_value_by_key("LETV")
        g_libhoudini_file_name = TssSDK.get_value_by_key("LENM")
        g_libhoudini_file_size = get_int_value("LESZ", 0)
end

local function get_tp_ver()
        local try_cnt = 0
        local err_msg = ""
        local err_code = 0
        local dev_path = "/dev/virtpipe-sec"
        while (try_cnt < 3) do
                try_cnt = try_cnt + 1
                local ret, acode = TssSDK.access(dev_path)
                if (ret ~= 0) then
                        err_msg = "unfound"
                        err_code = acode
                else
                        local session = TssSDK.OpenWBSession()
                        if (is_null(session)) then
                                err_msg = "open_failed"
                                local file, err, ocode = io.open(dev_path, "r+")
                                if (file) then
                                        file:close()
                                end
                                if (ocode ~= nil) then
                                        err_code = ocode
                                else
                                        err_code = 0
                                end
                        else
                                local tp_ver = TssSDK.SendWBCmd(session, "func=WB_GetTPShellVersion")
                                TssSDK.CloseWBSession(session)
                                if (is_null(tp_ver) or type(tp_ver) ~= "string") then
                                        err_msg = "get_failed"
                                        err_code = 0
                                else
                                        return tp_ver.."-"..tostring(0)
                                end
                        end
                end
                TssSDK.sleep(1000)
        end
        return err_msg.."-"..tostring(err_code)
end

local function scan_emulator()
        local try_cnt = 5
        local handle = TssSDK.open_tphm()
        while (try_cnt > 0 and is_null(handle)) do
                TssSDK.sleep(1000)
                handle = TssSDK.open_tphm()
                try_cnt = try_cnt - 1
        end
        if is_null(handle) then
                return
        end

        local libc_name = "libc.so"
        local libc_files = {}
        local libhoudini_name = "houdini"
        while g_module_cnt < 10000 do
                local module_info = TssSDK.enum_tphm(handle)
                if is_null(module_info) then
                        break
                end
                g_module_cnt = g_module_cnt + 1

                local module_name = TssSDK.get_tphm_name(module_info)
                local module_size = TssSDK.get_tphm_size(module_info)
                if not is_null(module_name) and not is_null(module_size) then
                        local file_name = basename(module_name)
                        if find_str(file_name, libc_name) then
                                if libc_files[module_name] == nil then
                                        g_libc_files_cnt = g_libc_files_cnt + 1
                                        libc_files[module_name] = {}
                                end
                        elseif find_str(file_name, libhoudini_name) then
                                if g_libhoudini_file_name == "" then
                                        g_libhoudini_file_size = module_size
                                        g_libhoudini_file_name = module_name
                                end
                        end

                        if g_has_x86_file == 0 then
                                g_has_x86_file = check_elf_file_x86_emulator(module_name)
                                if g_has_x86_file == 1 then
                                        g_x86_file_name = module_name
                                        g_tp_ver = get_tp_ver()
                                end
                        end
                end
        end
        save_scan_result()
        TssSDK.close_tphm(handle)
end

local function get_report_cnt()
        local cnt = get_int_value("LERC", 0)
        cnt = cnt % 1000 + 1
        TssSDK.set_key_and_value("LERC", ""..cnt)
        return cnt
end

local function report_emulator()
        local emu_name = TssSDK.QueryStr("emulator_name")
        local maybe_emu = 1
        if (emu_name == "NotEmulator")
        then
                maybe_emu = 0
        end

        local is_download = TssSDK.IsEnabled("simulate", 0)
        local report_cnt = get_report_cnt()
        local info = tostring(g_has_x86_file).."|"..tostring(g_libc_files_cnt).."|"..tostring(g_libhoudini_file_size).."|"..tostring(maybe_emu).."|"..tostring(report_cnt)
        TssSDK.set_key_and_value("li_emu", info)
        TssSDK.ReportQosByGame(8, 2020061700, g_has_x86_file, g_libc_files_cnt, g_libhoudini_file_size, g_module_cnt, maybe_emu, is_download, report_cnt, 2, emu_name..','..g_libhoudini_file_name, g_tp_ver..','..g_x86_file_name)
end

local function has_scanned()
        return (not is_null(TssSDK.get_value_by_key(g_mark_scan_flag)))
end

local function set_scanned()
        TssSDK.set_key_and_value(g_mark_scan_flag, "1")
end

local function do_exec()
        if TssSDK.get_platform() ~= 0 then
                return
        end

        if (has_scanned()) then
                load_scan_result()
        else
                scan_emulator()
                set_scanned()
        end

        report_emulator()
end

local function exec()
        local ver = TssSDK.get_sdk_version()
        if is_null(ver) then
                return
        end

        local target_ver = "3.7.13.548645"
        if ver < target_ver then
                return
        end

        do_exec()
end

exec()

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

谢大门 发表于 2021-4-5 08:59
大神,能不能弄个小红书模拟器登录过检测的啊,万分感谢

免费评分

参与人数 2吾爱币 -6 收起 理由
侃遍天下无二人 -2 哈哈哈哈,你们把版主的分都扣完了
涛之雨 -4 此为违规行为,请遵守论坛版规!

查看全部评分

MIr李 发表于 2021-3-23 09:47
大神,能不能弄个小红书模拟器登录过检测的啊,万分感谢

免费评分

参与人数 1吾爱币 -8 收起 理由
涛之雨 -8 广告贴,请遵守论坛版规!

查看全部评分

chan00132154 发表于 2021-4-8 08:21
还是第一种方法比较好。你获取就让你获取。获取我想给你的
头像被屏蔽
18922192568 发表于 2021-4-11 02:08
提示: 该帖被管理员或版主屏蔽
夕阳未必西下 发表于 2021-5-22 22:36
找不到文件在哪里
aswcy815174418 发表于 2021-5-25 17:35
chan00132154 发表于 2021-4-8 08:21
还是第一种方法比较好。你获取就让你获取。获取我想给你的

你有没有linux,我没这系统,学校网速不到1MB吐了,太慢了,下载了安卓7.1源码,找到了linker_phdr,windows编译不了,很难受
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则

返回列表

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2024-12-23 04:07

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表