某知乎APP - X-Zse-96

news2024/11/24 3:42:21

⚠️前言⚠️

本文仅用于学术交流。
学习探讨逆向知识,欢迎私信共享学习心得。
如有侵权,联系博主删除。
请勿商用,否则后果自负。

接口网址

app 版本: 8.10.0
aHR0cHM6Ly93d3cuemhpaHUuY29tL2FwaS92NC9zZWFyY2hfdjM=

在这里插入图片描述

加密位置分析

> 老规矩,jadx打开,先全局检索一下。

在这里插入图片描述

  • 居然没有搜到任何结果,应该做了混淆
> 由于 X-Zse-96 参数存在于headers中,全局检索一下 addHeader 看有没有啥线索

在这里插入图片描述

  • 发现在添加请求头信息的时候,字段名貌似通过 H.d 做了转换,这也可能是我们搜不到关键词的原因
> frida hook H.d,通过判断 result 减少日志打印,方便我们查看
Java.perform(function () {
    var h = Java.use('com.secneo.apkwrapper.H');
    h.d.implementation = function(str){
        var result = this.d(str);
        if(result == 'X-Zse-96'){
            send('arg: ' + str);
            send('result :' + result);
        }
        return result;
    };
})

在这里插入图片描述

  • 果然是通过H.d方法转换的,那我们可以直接检索一下 G51CEEF09BA7DF27F 来看一下
> 全局检索 G51CEEF09BA7DF27F,这结果就很少了,来看一下这个 addHeader

在这里插入图片描述
在这里插入图片描述

  • 就是这里了,那 H.d(“G38CD8525”) + new String(this.f61339c.encode(encrypt)) 有可能就是我们想要的最终结果
> H.d(“G38CD8525”) 的结果是什么?我们通过 frida hook 固定参数的形式来看一下
Java.perform(function () {
    var h = Java.use('com.secneo.apkwrapper.H');
    h.d.implementation = function(str){
        str = "G38CD8525";
        var result = this.d(str);
        send('arg: ' + str);
        send('result :' + result);
        return result;
    };
})

在这里插入图片描述

  • 这不就是 X-Zse-96 的特征值嘛,那我们只需要搞定 new String(this.f61339c.encode(encrypt)) 就可以拿到加密值了

加密逻辑分析

> 首先来看一下这个 a3 是怎么生成,hook 一下这个 a 方法

在这里插入图片描述
在这里插入图片描述

  • 通过 hook 的结果可以看出它参数由4部分组成
  • 101_1_1.0+接口路径及参数+app版本号+Bearer 2.1rDb…
  • 最后一部分经多次测试也是固定不变的,所以对于我们来说唯一需要传递的参数就是 接口的路径及参数
>>这个 a 是一个单独的方法不需要hook,我们直接扣代码即可,代码如下:

在这里插入图片描述

private static String a(String str) throws Exception{
        return String.format("%032X", new BigInteger(1, MessageDigest.getInstance("MD5").digest(str.getBytes())));
    }
  • 到这里我们就得到了 a3 的值
> 下面来看一下 encrypt 是怎么生成的

在这里插入图片描述

  • 发现生成 encrypt 值的方法存在于接口类b中,那么一定会在某个地方有一个类继承了这个b,并实现了 encrypt 方法
  • 全局检索一下关键词 接口类 b 所在包名, 这就很明了了。在这里插入图片描述
  • 最终就会找到这个方法
    在这里插入图片描述
>> frida hook 一下这个a方法

在这里插入图片描述

  • 三个参数:参数1 - a3.toLowerCase().getBytes()
  • 参数 2,3 固定值,不要问为什么,一步步方法跟过来你就知道了。😀 😀 😀
>> 参数搞明白之后我们再回头看这个 a 方法

在这里插入图片描述

  • 我们需要搞定三个方法就可以得到 encrypt
  • 首先 b.b, 这个方法直接扣代码就可以了
    在这里插入图片描述
    1. CryptoTool.laesEncryptByteArr,此方法存在于 native 层,可以 hook 得到
      在这里插入图片描述
    1. b.a,和 b.b 一样也是直接扣代码即可
      在这里插入图片描述
  • 至此,encrypt 值就搞定了。
> 下面进入最后一步,发现这个 encode 的方法也是一个接口类

在这里插入图片描述在这里插入图片描述

  • 同样的方法看一下这个 a 是在哪里复现的。。。这里 encrypt 传过来之后通过 j.a 生成 a2,并返回
    在这里插入图片描述
  • j.a 其实就是做了一个 Base64 加密
    在这里插入图片描述
  • 至此,X-Zse-96 加密逻辑就全部分析结束了。

Xposed hook

关键代码:  这里只保留关键性逻辑
@Action("x-zse-96")
public class ZhihuHandler implements RequestHandler {
    @AutoBind
    private String p1; // 以base64的形式传入
    
    @Override
    public void handleRequest(SekiroRequest sekiroRequest, SekiroResponse sekiroResponse) {
        try {
            log("进来了。。。 开始生成 x_zse_96。。。");
            String p1_decode = new String(Base64.decode(p1, 2));
            log(p1_decode);
            // System.out.println("******************helloword*****************************");
            StringBuilder sb = new StringBuilder();
            String temp_str = "101_1_1.0+" + p1_decode + "+8.10.0+Bearer 2.1...";
            sb.append(temp_str);
            String result = sb.toString().substring(0, sb.length() - 1);
            String a3 = a(result);
            byte[] barr_a3 = a3.toLowerCase().getBytes();
            // 生成变量 encrypt   b.b(CryptoTool.laesEncryptByteArr(b.a(bArr, str, bArr2), str, bArr2), str, bArr2);
            String arg2_str = "541a3a5896...";
            byte[] arg3_barr = new byte[]{ ... };
            byte[] result_ba = b_a(barr_a3, arg2_str, arg3_barr);
            // hook so层方法 aesEncryptByteArr
            final Class<?> clazz = XposedHelpers.findClass("com.bangcle.CryptoTool", HookZhihu.loadPackageParam.classLoader);
            // 注意标明返回值类型 (byte[])  静态方法可以直接使用类名调用
            byte[] result_CryptoTool = (byte[]) XposedHelpers.callStaticMethod(clazz,"laesEncryptByteArr",new Object[]{result_ba,arg2_str,arg3_barr});
            byte[] encrypt = b_b(result_CryptoTool, arg2_str, arg3_barr);
            String x_zse_96 = "1.0_" + new String(Base64.encodeToString(encrypt, 2).getBytes());
            sekiroResponse.success(x_zse_96);
        }catch (Exception e){
            e.printStackTrace();
        }
    }

    // throws Exception 表示的是本方法不处理异常,交给被调用处处理
    private static String a(String str) throws Exception{
        return String.format("%032X", new BigInteger(1, MessageDigest.getInstance("MD5").digest(str.getBytes())));
    }

    public static byte[] b_a(byte[] bArr, String str, byte[] bArr2) {
       	...
    }

    public static byte[] b_b(byte[] bArr, String str, byte[] bArr2) {
        ...
     }
}

最终成果展示

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1633038.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

MySQL从入门到高级 --- 3.DML基本操作

文章目录 第三章&#xff1a;3.基本操作 - DML3.1 数据插入3.2 数据修改3.3 数据删除3.4 练习 第三章&#xff1a; 3.基本操作 - DML DML&#xff1a;数据操作语言&#xff0c;用来对数据中表的数据记录进行更新 关键字&#xff1a; insert 插入 delete 删除 update 更新 …

CLIP是啥?

论文地址&#xff1a;https://arxiv.org/pdf/2103.00020v1 代码地址&#xff1a;GitHub - openai/CLIP: CLIP (Contrastive Language-Image Pretraining), Predict the most relevant text snippet given an image 题目解读 Transferable Visual model指不使用特定数据集的数…

【代码随想录刷题记录】LeetCode844比较含退格的字符

题目地址 1. 思路 1.1 基本思路 拿到这个题&#xff0c;我们要单独写一个函数去将退格后的字符串结果返回出来&#xff08;生成退格后的真实的字符串&#xff09;&#xff0c;我还是想魔改 O ( n ) O(n) O(n)时间复杂度的删除数组元素的算法&#xff1a;【代码随想录刷题记录…

认识Linux及一些基本

目录 linux简介&#xff1a; 1. 发展史 UNIX发展的历史 Linux发展历史 2. 开源 3. 企业应用现状 Linux在服务器领域的发展 Linux在桌面领域的发展 Linux在移动嵌入式领域的发展 Linux在云计算/大数据领域的发展 4. 发行版本 Debian Ubuntu 红帽企业级Linux Cent…

LLDP简介

LLDP简介 定义 LLDP&#xff08;Link Layer Discovery Protocol&#xff09;是IEEE 802.1ab中定义的链路层发现协议。LLDP是一种标准的二层发现方式&#xff0c;可以将本端设备的管理地址、设备标识、接口标识等信息组织起来&#xff0c;并发布给自己的邻居设备&#xff0c;邻…

国产Sora诞生!清华团队发布Vidu大模型,可直接生成16秒视频

大模型之争已从单模态转向多模态。 4月27日&#xff0c;在2024中关村论坛年会未来人工智能先锋论坛上&#xff0c;清华大学联合北京生数科技有限公司正式发布了文生视频大模型——Vidu。 在会议上&#xff0c;清华大学人工智能研究院副院长、生数科技首席科学家朱军对外展示了…

溪谷软件:游戏联运有多简单?

游戏联运&#xff0c;即游戏联合运营&#xff0c;是一种游戏运营模式&#xff0c;涉及到多个平台或公司共同推广和运营同一款游戏。对于开发者而言&#xff0c;游戏联运的简化程度可能因具体情况而异&#xff0c;但以下是一些因素&#xff0c;使得游戏联运在某种程度上变得更加…

​水滴式饲料粉碎机:创新设计与卓越性能的完美结合

水滴式饲料粉碎机是一种新型的饲料加工设备&#xff0c;其新颖的设计理念和工作性能受到了广大养殖户和饲料生产厂家的青睐。水滴式饲料粉碎机之所以受到如此广泛的关注&#xff0c;不仅是因为其G效、节能的特点&#xff0c;更是因为其新颖的结构设计&#xff0c;使得饲料加工过…

Cesium.js(3):Cesium查看器、场景、实体、数据源介绍

1 Cesium的四大类说明 1.1 Viewer查看器类 Viewer是cesium的查看器类&#xff0c;第一个参数是地图主窗口DIV的容器ID&#xff0c;第二个参数option是Viewer的可选设置参数&#xff0c;包含图层、地形时间系统等参数&#xff0c;种类多样&#xff0c;主要作用是对视口中各个组…

【Python的魅力】:利用Pygame实现游戏坦克大战——含完整源码

文章目录 一、游戏运行效果二、代码实现2.1 项目搭建2.2 加载我方坦克2.3 加载敌方坦克2.4 添加爆炸效果2.5 坦克大战之音效处理 三、完整代码 一、游戏运行效果 二、代码实现 坦克大战游戏 2.1 项目搭建 本游戏主要分为两个对象&#xff0c;分别是我方坦克和敌方坦克。用户可…

数据结构复习指导之数组和特殊矩阵

文章目录 数组和特殊矩阵 考纲内容 复习提示 前言 1.数组的定义 2.数组的存储结构 3.特殊矩阵的压缩存储 3.1对称矩阵 3.2三角矩阵 3.3三对角矩阵 4.稀疏矩阵 5.知识回顾 数组和特殊矩阵 考纲内容 &#xff08;一&#xff09;栈和队列的基本概念 &#xff08;二&a…

数据结构六:线性表之顺序栈的设计

目录 一、栈的应用场景 二、栈的基本概念和结构 2.1 栈的基本概念 2.2 栈的结构 2.3 栈的实现方式 三、顺序栈的接口函数实现 3.0 顺序栈的概念和结构 3.1 顺序栈的接口函数 3.2 顺序栈的设计&#xff08;结构体&#xff09; 3.3 顺序栈的初始化 3.4 入栈&#x…

Python转换文本文件为PDF文档,绘制文本到PDF文档页面

文本文件因其轻便、易编辑的优势&#xff0c;常用于日常文字记录与数据交换&#xff1b;而PDF文档则以高保真、格式稳定和良好的阅读体验&#xff0c;成为正式报告、文献发布等场景的首选。将文本文件转为PDF&#xff0c;在PDF内精准绘制文本&#xff0c;旨在兼顾内容的规范呈现…

云计算革新:以太网 Scale-UP 网络为 GPU 加速赋能

谈谈基于以太网的GPU Scale-UP网络 Intel Gaudi-3 采用 RoCE 互联技术&#xff0c;促进了 Scale-UP 解决方案。业界专家 Jim Keller 倡导以太网替代 NVLink。Tenstorrent 成功应用以太网实现片上网络互联。RoCE 和以太网已成为互联解决方案的新兴趋势&#xff0c;为高性能计算提…

区块链技术--编译BSV源码(v1.0.1)

编译好的可执行文件bitcoin-cli 和 bitcoind 下载: https://github.com/youngqqcn/QBlockChainNotes/blob/master/BTC%E7%B3%BB%E5%B1%B1%E5%AF%A8%E5%B8%81/my_bsv_v1.0.1.tar.gz 安装 libminiupnpc wget https://download-ib01.fedoraproject.org/pub/epel/7/x86_64/Packa…

商店数据(六)

目录 41.短信发送记录表 42.职员登录记录表 43.会员登录记录表 ​44.后台菜单表 45.商城信息表 46.消息队列表 47.移动端首页按钮管理表 48.商城导航表 41.短信发送记录表 CREATE TABLE wst_log_sms (smsId int(11) NOT NULL AUTO_INCREMENT COMMENT 自增ID,smsSrc t…

IOCP实现UDP Server

IOCP实现UDP Server 1、IOCP原理图 参考文献1&#xff1a;IOCP详解-阿里云开发者社区 (aliyun.com) 参考文献2&#xff1a;IOCP编程之基本原理 - 史D芬周 - 博客园 (cnblogs.com) 原理图 同步以及异步 2、UDP Server代码以及测试代码 // iocpudpdemo.cpp : 此文件包含 &qu…

再谈钓鱼邮件

再谈钓鱼邮件 概述 最近对邮件的防御策略进行了更新&#xff0c;结合威胁情报和安全沙箱对收到的钓鱼邮件进行了分析&#xff0c;期望这些案例能对大家有所帮助。 网关上拦截的钓鱼邮件基本可以分三个类别&#xff1a;链接钓鱼邮件、附件钓鱼邮件以及邮件头伪造钓鱼邮件&…

在谷歌浏览器访问特定的网站 提示此网站无法提供安全连接

1、问题描述&#xff1a; 最近通过谷歌浏览器访问某些网址提示此网站无法提供安全连接&#xff0c;换一个浏览器就能正确打开&#xff01; 例子如下&#xff1a; 访问 https://baijiahao.baidu.com/s?id1788533041823242656 2、查找原因 通过控制台发现请求未有响应码&#xf…

【数据分析面试】34.填充NaN值 (Python:groupby/sort_value/ffill)

题目&#xff1a;填充NaN值 &#xff08;Python) 给定一个包含三列的DataFrame&#xff1a;client_id、ranking、value 编写一个函数&#xff0c;将value列中的NaN值用相同client_id的前一个非NaN值填充&#xff0c;按升序排列。 如果不存在前一个client_id&#xff0c;则返…