Browse Source

zlib: prevent uncaught exception in zlibBuffer

If the accumulation of data for the final Buffer is greater than
kMaxLength it will throw an un-catchable RangeError. Instead now pass
the generated error to the callback.

PR-URL: https://github.com/nodejs/io.js/pull/1811
Reviewed-By: Fedor Indutny <fedor@indutny.com>
Reviewed-By: Trevor Norris <trev.norris@gmail.com>
v2.3.1-release
Michaël Zasso 10 years ago
committed by Trevor Norris
parent
commit
3806d875d3
  1. 20
      lib/zlib.js
  2. 22
      test/parallel/test-regress-GH-io-1811.js

20
lib/zlib.js

@ -5,6 +5,9 @@ const Transform = require('_stream_transform');
const binding = process.binding('zlib');
const util = require('util');
const assert = require('assert').ok;
const kMaxLength = process.binding('smalloc').kMaxLength;
const kRangeErrorMessage = 'Cannot create final Buffer. ' +
'It would be larger than 0x' + kMaxLength.toString(16) + ' bytes.';
// zlib doesn't provide these, so kludge them in following the same
// const naming scheme zlib uses.
@ -210,10 +213,18 @@ function zlibBuffer(engine, buffer, callback) {
}
function onEnd() {
var buf = Buffer.concat(buffers, nread);
var buf;
var err = null;
if (nread >= kMaxLength) {
err = new RangeError(kRangeErrorMessage);
} else {
buf = Buffer.concat(buffers, nread);
}
buffers = [];
callback(null, buf);
engine.close();
callback(err, buf);
}
}
@ -524,6 +535,11 @@ Zlib.prototype._processChunk = function(chunk, flushFlag, cb) {
throw error;
}
if (nread >= kMaxLength) {
this.close();
throw new RangeError(kRangeErrorMessage);
}
var buf = Buffer.concat(buffers, nread);
this.close();

22
test/parallel/test-regress-GH-io-1811.js

@ -0,0 +1,22 @@
'use strict';
const assert = require('assert');
// Change kMaxLength for zlib to trigger the error
// without having to allocate 1GB of buffers
const smalloc = process.binding('smalloc');
smalloc.kMaxLength = 128;
const zlib = require('zlib');
smalloc.kMaxLength = 0x3fffffff;
const encoded = new Buffer('H4sIAAAAAAAAA0tMHFgAAIw2K/GAAAAA', 'base64');
// Async
zlib.gunzip(encoded, function(err) {
assert.ok(err instanceof RangeError);
});
// Sync
assert.throws(function() {
zlib.gunzipSync(encoded);
}, RangeError);
Loading…
Cancel
Save