对某登录站点的JS前端逆向思路

前言

js逆向一直没有相关了解,虽然目前渗透遇见的不是很多,大多数遇见的要么不加密,要么无法实现其加密流程,不过最近看到了一个较为简单的站点正好能够逆向出来,就做了简单记录。本文旨在介绍js逆向的一些基础思路,希望能对初学js前端逆向的师傅有所帮助。

JS定位

在我们寻找JS源代码时,如果直接翻看全部的js文件以来寻找自己想要的一部分,无疑是复杂繁琐的,且工作量巨大,有点类似大海捞针,因此这里我们需要借助一些巧妙的办法来快速定位某标签的js语句,具体方法如下。

元素审查定位

当我们不确定某处的js文件位置时,可以使用F12,点击元素审查,然后点击登录处,观察事件监听器

此时可以观察到login.js文件出现,接下来就可以去对应文件下继续深入。

发现check函数,寻找check函数

此时发现加密是secret函数,再继续跟secert函数就可以了解其整体流程。

全局搜索法

像我们常见的登录框,他们要提交的加密参数一般名为password,或者加密为Crypto加密,因此我们可以全局搜索此类关键字,进而寻找我们需要找的关键加密js语句,进而实现js逆向。

具体操作也很简单,这里简单举个例子。

首先打开F12,随便点击一个元素,而后ctrl+shift+f,接下来全局搜索关键词即可

此时含关键词的语句映入眼帘,像一些css文件中的直接略过即可,而后即可找到真正生成密码的地方

接下来便可以深入secret,了解加密方法。

帮助网安学习,全套资料S信领取:

① 网安学习成长路径思维导图

② 60+网安经典常用工具包

③ 100+SRC漏洞分析报告

④ 150+网安攻防实战技术电子书

⑤ 最权威CISSP 认证考试指南+题库

⑥ 超1800页CTF实战技巧手册

⑦ 最新网安大厂面试题合集(含答案)

⑧ APP客户端安全检测指南(安卓+IOS)

Onclick定位

像一些登录点是存在着onclick属性的,如若该属性值是js函数,那么就极有可能是我们要寻找的js加密函数,而后进行寻找相关函数即可。

注:图参考自cony1大师傅。

cony1大师傅的图为例进行简单讲解

这里发现ssologin函数,接下来寻找该函数

此时即可发现相关js语句。

实战

某登录站点js逆向

找到一个登录站点,随意输入

发现用户名和密码均被加密,接下来ctrl+shift+f,全局搜索password字段,寻找加密点

第一个这里明显是输入框的password,且是注释,肯定不是这里,接着寻找,后来到

整体代码如下

ruby 复制代码
        function check() {            //这里将用户名,密码加密            var code = 'letu@levle';            var yname = $("#yname").val();            if (yname == '') {                alert("用户名不能为空");                return false;            } else {                var newName = secret(yname, code, false);                $("#xname").val(newName);            }​            var ypassword = $("#ypassword").val();            if (ypassword == '') {                alert("密码不能为空");                return false;            } else {                var newPassword = secret(ypassword, code, false);                $("#xpassword").val(newPassword);            }        }

可以看出js代码逻辑并不难,首先提取出ypassword标签下的内容,而后验证其是否为空,若不为空,则对其进行secret函数处理,很明显,这个secret函数就是加密函数,所以我们接下来跟进此加密函数

这里直接给出了iv和key,所以接下来打断点调试就行了,而后打上断点

接下来开始随便输入密码提交,而后来到调试界面

选中code.substring(16)得到keyf3991777154f4bd0

选中code.substring(0,16)得到偏移量ace43e65106a77f6

下方也给出了Padding和mode分别是Pkcs7CBC,所以接下来直接解密即可,在网络中我们可以看到提交后加密的账密

拿去随便找个AES解密网站

与所输入的进行比对

成功得到正确结果

接下来编写脚本即可,直接将字典的内容全部进行加密,而后放入burp进行爆破

scss 复制代码
import base64from Crypto.Cipher import AESfrom Crypto.Hash import MD5from Crypto.Util.Padding import pad​#填入AES的key和ivkey = 'f3991777154f4bd0'iv = 'ace43e65106a77f6'​def AES_Encrypt(data):    global key    global iv    cipher = AES.new(key.encode('utf-8'), AES.MODE_CBC, iv.encode('utf-8'))    paddingdata = pad(data.encode('utf-8'),AES.block_size)    encrypted = cipher.encrypt(paddingdata)    #print(base64.b64encode(encrypted).decode())    return base64.b64encode(encrypted).decode()​password = []with open('password.txt','r',encoding='utf-8') as f:    for i in f:        password.append(i.strip())with open('password_aes.txt','w',encoding='utf-8') as w:    for i in password:        data = AES_Encrypt(i)+'\n'        w.write(data)

数据长度明显与错误时不一致,不过这里也未成功进入后台,有二次验证,Google验证码无从下手,故点到为止。

某道js逆向

接下来进行抓包

这里我们首先注意一下每次不同点在哪,以此为入口点来进行下去,因此我们多次刷新界面抓包,同样的参数观察包的参数哪个值是不同的

从上图可以看出signmysticTime是变化的,因此接下来针对这两个变量进行深入,如果我们能够控制这两个变量,那么我们就可以实现直接脚本请求得到翻译对应的语句。

所以接下来首先从sign开始,我们首先进行F12,而后输入ctrl+shift+f全局搜索关键词

这里可以发现出现了js中含有sign关键字的,但像这个inpage.js他明显不是我们要找的js语句,因此继续往下寻找(输入sign:更容易找到对应函数)。这里我们找到如下语句

相关代码如下

javascript 复制代码
const u = "fanyideskweb"              , d = "webfanyi"              , m = "client,mysticTime,product"              , p = "1.0.0"              , g = "web"              , b = "fanyi.web"              , A = 1              , h = 1              , f = 1              , v = "wifi"              , O = 0;            function y(e) {                return c.a.createHash("md5").update(e).digest()            }            function j(e) {                return c.a.createHash("md5").update(e.toString()).digest("hex")            }            function k(e, t) {                return j(`client=${u}&mysticTime=${e}&product=${d}&key=${t}`)            }            function E(e, t) {                const o = (new Date).getTime();                return {                    sign: k(o, e),                    client: u,                    product: d,                    appVersion: p,                    vendor: g,                    pointParam: m,                    mysticTime: o,                    keyfrom: b,                    mid: A,                    screen: h,                    model: f,                    network: v,                    abtest: O,                    yduuid: t || "abcdefg"                }            }

这里可以看到sign是由函数k构成的,同时注意到这里也给出了k的参数,k是由client=fanyideskweb&mysticTime=${e}&product=webfanyi&key=${t}所组成的,此时再看函数E,o是时间戳,e这里未知,这时候该怎么办呢,先看看他是不是固定值,当自己不确定在哪下断点调试时,就在附近的几个可疑点都打下断点,观察e的值即可

经观察,这里的e值是固定的,即fsdsogkndfokasodnaso,此时k(o,e)中的参数我们都了解了,但我们注意到k函数中是有j在外包裹的,因此我们需要对j函数进行相关了解

vbscript 复制代码
function j(e) {                return c.a.createHash("md5").update(e.toString()).digest("hex")            }

明显的md5加密,因此到这里也就都清楚了。

当我们进行请求时,首先获取当前的时间戳,此作为参数之一,同时与client等参数值组合,进行md5加密,就组成了sign的值。对于mysticTime这个参数,我们从k函数也了解到它其实就是时间戳,因此两个变化的参数到目前就都了解其生成过程了。

接下来尝试写python脚本

sql 复制代码
import hashlibimport timeimport requests​requests.packages.urllib3.disable_warnings()headers = {"Content-Length": "312","Pragma": "no-cache","Cache-Control": "no-cache","Sec-Ch-Ua": "\"Google Chrome\";v=\"119\", \"Chromium\";v=\"119\", \"Not?A_Brand\";v=\"24\"","Accept": "application/json, text/plain, */*","Content-Type": "application/x-www-form-urlencoded","Sec-Ch-Ua-Mobile":"?0","User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/119.0.0.0 Safari/537.36","Sec-Ch-Ua-Platform": "\"Windows\"","Origin": "https://fanyi.youdao.com","Sec-Fetch-Site": "same-site","Sec-Fetch-Mode": "cors","Sec-Fetch-Dest": "empty","Referer": "https://fanyi.youdao.com/","Accept-Encoding": "gzip, deflate",}Cookie = {"OUTFOX_SEARCH_USER_ID":"239978291@10.130.108.41","OUTFOX_SEARCH_USER_ID_NCOO":"520521807.43848985"}url = ""word = input("请输入翻译内容:")localtime = str(int(time.time() * 1000))canshu = "client=fanyideskweb&mysticTime={}&product=webfanyi&key=fsdsogkndfokasodnaso".format(localtime)sign = hashlib.md5(canshu.encode(encoding='utf8')).hexdigest()data = {    "i": f"{word}",    "from": "auto",    "to": "",    "dictResult": "true",    "keyid": "webfanyi",    "sign": sign,    "client": "fanyideskweb",    "product": "webfanyi",    "appVersion": "1.0.0",    "vendor": "web",    "pointParam": "client,mysticTime,product",    "mysticTime": localtime,    "keyfrom": "fanyi.web"}res = requests.post(url=url,headers=headers,cookies=Cookie,data=data,verify=False)print(res.text)

此时便得到了加密数据,解密同理,不再阐述。

相关推荐
我要洋人死1 小时前
导航栏及下拉菜单的实现
前端·css·css3
科技探秘人1 小时前
Chrome与火狐哪个浏览器的隐私追踪功能更好
前端·chrome
科技探秘人1 小时前
Chrome与傲游浏览器性能与功能的深度对比
前端·chrome
JerryXZR1 小时前
前端开发中ES6的技术细节二
前端·javascript·es6
七星静香1 小时前
laravel chunkById 分块查询 使用时的问题
java·前端·laravel
q2498596931 小时前
前端预览word、excel、ppt
前端·word·excel
小华同学ai1 小时前
wflow-web:开源啦 ,高仿钉钉、飞书、企业微信的审批流程设计器,轻松打造属于你的工作流设计器
前端·钉钉·飞书
Gavin_9151 小时前
【JavaScript】模块化开发
前端·javascript·vue.js
懒大王爱吃狼3 小时前
Python教程:python枚举类定义和使用
开发语言·前端·javascript·python·python基础·python编程·python书籍
逐·風7 小时前
unity关于自定义渲染、内存管理、性能调优、复杂物理模拟、并行计算以及插件开发
前端·unity·c#