Skip to content

Commit

Permalink
test files
Browse files Browse the repository at this point in the history
  • Loading branch information
splitice committed Sep 30, 2024
1 parent 8827486 commit 84a7197
Show file tree
Hide file tree
Showing 5 changed files with 194 additions and 0 deletions.
123 changes: 123 additions & 0 deletions test_lac/loadAndCrash.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,123 @@
/**
* Load and modify part of fs to ensure writeFile will crash after writing 5000 bytes
*/
var fs = require('fs');

function rethrow() {
// Only enable in debug mode. A backtrace uses ~1000 bytes of heap space and
// is fairly slow to generate.
if (DEBUG) {
var backtrace = new Error();
return function(err) {
if (err) {
backtrace.stack = err.name + ': ' + err.message +
backtrace.stack.substr(backtrace.name.length);
throw backtrace;
}
};
}

return function(err) {
if (err) {
throw err; // Forgot a callback but don't know where? Use NODE_DEBUG=fs
}
};
}

function maybeCallback(cb) {
return typeof cb === 'function' ? cb : rethrow();
}

function isFd(path) {
return (path >>> 0) === path;
}

function assertEncoding(encoding) {
if (encoding && !Buffer.isEncoding(encoding)) {
throw new Error('Unknown encoding: ' + encoding);
}
}

var onePassDone = false;
function writeAll(fd, isUserFd, buffer, offset, length, position, callback_) {
var callback = maybeCallback(arguments[arguments.length - 1]);

if (onePassDone) { process.exit(1); } // Crash on purpose before rewrite done
var l = Math.min(5000, length); // Force write by chunks of 5000 bytes to ensure data will be incomplete on crash

// write(fd, buffer, offset, length, position, callback)
fs.write(fd, buffer, offset, l, position, function(writeErr, written) {
if (writeErr) {
if (isUserFd) {
if (callback) callback(writeErr);
} else {
fs.close(fd, function() {
if (callback) callback(writeErr);
});
}
} else {
onePassDone = true;
if (written === length) {
if (isUserFd) {
if (callback) callback(null);
} else {
fs.close(fd, callback);
}
} else {
offset += written;
length -= written;
if (position !== null) {
position += written;
}
writeAll(fd, isUserFd, buffer, offset, length, position, callback);
}
}
});
}

fs.writeFile = function(path, data, options, callback_) {
var callback = maybeCallback(arguments[arguments.length - 1]);

if (!options || typeof options === 'function') {
options = { encoding: 'utf8', mode: 438, flag: 'w' }; // Mode 438 == 0o666 (compatibility with older Node releases)
} else if (typeof options === 'string') {
options = { encoding: options, mode: 438, flag: 'w' }; // Mode 438 == 0o666 (compatibility with older Node releases)
} else if (typeof options !== 'object') {
throwOptionsError(options);
}

assertEncoding(options.encoding);

var flag = options.flag || 'w';

if (isFd(path)) {
writeFd(path, true);
return;
}

fs.open(path, flag, options.mode, function(openErr, fd) {
if (openErr) {
if (callback) callback(openErr);
} else {
writeFd(fd, false);
}
});

function writeFd(fd, isUserFd) {
var buffer = (data instanceof Buffer) ? data : new Buffer('' + data,
options.encoding || 'utf8');
var position = /a/.test(flag) ? null : 0;

writeAll(fd, isUserFd, buffer, 0, buffer.length, position, callback);
}
};




// End of fs modification
var Nedb = require('../lib/datastore.js')
, db = new Nedb({ filename: 'workspace/lac.db' })
;

db.loadDatabase();
67 changes: 67 additions & 0 deletions test_lac/openFds.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
var fs = require('fs')
, child_process = require('child_process')
, [AsyncWaterfall, AsyncWhilst] = [require('async/waterfall'), require('async/whilst')]
, Nedb = require('../nedb/datastore')
, db = new Nedb({ filename: './workspace/openfds.db', autoload: true })
, N = 64 // Half the allowed file descriptors
, i, fds
;

function multipleOpen (filename, N, callback) {
AsyncWhilst( function () { return i < N; }
, function (cb) {
fs.open(filename, 'r', function (err, fd) {
i ++;
if (fd) { fds.push(fd); }
return cb(err);
});
}
, callback);
}

AsyncWaterfall([
// Check that ulimit has been set to the correct value
function (cb) {
i = 0;
fds = [];
multipleOpen('./test_lac/openFdsTestFile', 2 * N + 1, function (err) {
if (!err) { console.log("No error occured while opening a file too many times"); }
fds.forEach(function (fd) { fs.closeSync(fd); });
return cb();
})
}
, function (cb) {
i = 0;
fds = [];
multipleOpen('./test_lac/openFdsTestFile2', N, function (err) {
if (err) { console.log('An unexpected error occured when opening file not too many times: ' + err); }
fds.forEach(function (fd) { fs.closeSync(fd); });
return cb();
})
}
// Then actually test NeDB persistence
, function () {
db.remove({}, { multi: true }, function (err) {
if (err) { console.log(err); }
db.insert({ hello: 'world' }, function (err) {
if (err) { console.log(err); }

i = 0;
AsyncWhilst( function () { return i < 2 * N + 1; }
, function (cb) {
db.persistence.persistCachedDatabase(function (err) {
if (err) { return cb(err); }
i ++;
return cb();
});
}
, function (err) {
if (err) { console.log("Got unexpected error during one peresistence operation: " + err); }
}
);

});
});
}
]);

2 changes: 2 additions & 0 deletions test_lac/openFdsLaunch.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
ulimit -n 128
node ./test_lac/openFds.test.js
1 change: 1 addition & 0 deletions test_lac/openFdsTestFile
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Random stuff
1 change: 1 addition & 0 deletions test_lac/openFdsTestFile2
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Some other random stuff

0 comments on commit 84a7197

Please sign in to comment.