Merge branch 'master' into HEAD
Conflicts: lib/fs.js wscript
This commit is contained in:
commit
28211519b6
2
deps/libeio/Changes
vendored
2
deps/libeio/Changes
vendored
@ -18,7 +18,9 @@ TODO: maybe add mincore support? available on at least darwin, solaris, linux, f
|
||||
- "outbundled" from IO::AIO.
|
||||
- eio_set_max_polltime did not properly convert time to ticks.
|
||||
- tentatively support darwin in sendfile.
|
||||
- fix freebsd/darwin sendfile.
|
||||
- also use sendfile emulation for ENOTSUP and EOPNOTSUPP
|
||||
error codes.
|
||||
- add OS-independent EIO_MT_* and EIO_MS_* flag enums.
|
||||
- add eio_statvfs/eio_fstatvfs.
|
||||
|
||||
|
46
deps/libeio/eio.c
vendored
46
deps/libeio/eio.c
vendored
@ -51,6 +51,7 @@
|
||||
#include <errno.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/statvfs.h>
|
||||
#include <limits.h>
|
||||
#include <fcntl.h>
|
||||
#include <assert.h>
|
||||
@ -82,7 +83,7 @@
|
||||
# include <dirent.h>
|
||||
|
||||
/* POSIX_SOURCE is useless on bsd's, and XOPEN_SOURCE is unreliable there, too */
|
||||
# if __freebsd || defined __NetBSD__ || defined __OpenBSD__
|
||||
# if __FreeBSD__ || defined __NetBSD__ || defined __OpenBSD__
|
||||
# define _DIRENT_HAVE_D_TYPE /* sigh */
|
||||
# define D_INO(de) (de)->d_fileno
|
||||
# define D_NAMLEN(de) (de)->d_namlen
|
||||
@ -108,7 +109,7 @@
|
||||
#if HAVE_SENDFILE
|
||||
# if __linux
|
||||
# include <sys/sendfile.h>
|
||||
# elif __freebsd || defined __APPLE__
|
||||
# elif __FreeBSD__ || defined __APPLE__
|
||||
# include <sys/socket.h>
|
||||
# include <sys/uio.h>
|
||||
# elif __hpux
|
||||
@ -138,6 +139,11 @@
|
||||
# define NAME_MAX 4096
|
||||
#endif
|
||||
|
||||
/* used for readlink etc. */
|
||||
#ifndef PATH_MAX
|
||||
# define PATH_MAX 4096
|
||||
#endif
|
||||
|
||||
/* buffer size for various temporary buffers */
|
||||
#define EIO_BUFSIZE 65536
|
||||
|
||||
@ -911,7 +917,7 @@ eio__sendfile (int ofd, int ifd, off_t offset, size_t count, etp_worker *self)
|
||||
# if __linux
|
||||
res = sendfile (ofd, ifd, &offset, count);
|
||||
|
||||
# elif __freebsd
|
||||
# elif __FreeBSD__
|
||||
/*
|
||||
* Of course, the freebsd sendfile is a dire hack with no thoughts
|
||||
* wasted on making it similar to other I/O functions.
|
||||
@ -920,8 +926,16 @@ eio__sendfile (int ofd, int ifd, off_t offset, size_t count, etp_worker *self)
|
||||
off_t sbytes;
|
||||
res = sendfile (ifd, ofd, offset, count, 0, &sbytes, 0);
|
||||
|
||||
if (res < 0 && sbytes)
|
||||
/* maybe only on EAGAIN: as usual, the manpage leaves you guessing */
|
||||
#if 0 /* according to the manpage, this is correct, but broken behaviour */
|
||||
/* freebsd' sendfile will return 0 on success */
|
||||
/* freebsd 8 documents it as only setting *sbytes on EINTR and EAGAIN, but */
|
||||
/* not on e.g. EIO or EPIPE - sounds broken */
|
||||
if ((res < 0 && (errno == EAGAIN || errno == EINTR) && sbytes) || res == 0)
|
||||
res = sbytes;
|
||||
#endif
|
||||
|
||||
/* according to source inspection, this is correct, and useful behaviour */
|
||||
if (sbytes)
|
||||
res = sbytes;
|
||||
}
|
||||
|
||||
@ -931,7 +945,8 @@ eio__sendfile (int ofd, int ifd, off_t offset, size_t count, etp_worker *self)
|
||||
off_t sbytes = count;
|
||||
res = sendfile (ifd, ofd, offset, &sbytes, 0, 0);
|
||||
|
||||
if (res < 0 && errno == EAGAIN && sbytes)
|
||||
/* according to the manpage, sbytes is always valid */
|
||||
if (sbytes)
|
||||
res = sbytes;
|
||||
}
|
||||
|
||||
@ -1577,6 +1592,11 @@ static void eio_execute (etp_worker *self, eio_req *req)
|
||||
case EIO_FSTAT: ALLOC (sizeof (EIO_STRUCT_STAT));
|
||||
req->result = fstat (req->int1, (EIO_STRUCT_STAT *)req->ptr2); break;
|
||||
|
||||
case EIO_STATVFS: ALLOC (sizeof (EIO_STRUCT_STATVFS));
|
||||
req->result = statvfs (req->ptr1, (EIO_STRUCT_STATVFS *)req->ptr2); break;
|
||||
case EIO_FSTATVFS: ALLOC (sizeof (EIO_STRUCT_STATVFS));
|
||||
req->result = fstatvfs (req->int1, (EIO_STRUCT_STATVFS *)req->ptr2); break;
|
||||
|
||||
case EIO_CHOWN: req->result = chown (req->ptr1, req->int2, req->int3); break;
|
||||
case EIO_FCHOWN: req->result = fchown (req->int1, req->int2, req->int3); break;
|
||||
case EIO_CHMOD: req->result = chmod (req->ptr1, (mode_t)req->int2); break;
|
||||
@ -1595,8 +1615,8 @@ static void eio_execute (etp_worker *self, eio_req *req)
|
||||
case EIO_SYMLINK: req->result = symlink (req->ptr1, req->ptr2); break;
|
||||
case EIO_MKNOD: req->result = mknod (req->ptr1, (mode_t)req->int2, (dev_t)req->int3); break;
|
||||
|
||||
case EIO_READLINK: ALLOC (NAME_MAX);
|
||||
req->result = readlink (req->ptr1, req->ptr2, NAME_MAX); break;
|
||||
case EIO_READLINK: ALLOC (PATH_MAX);
|
||||
req->result = readlink (req->ptr1, req->ptr2, PATH_MAX); break;
|
||||
|
||||
case EIO_SYNC: req->result = 0; sync (); break;
|
||||
case EIO_FSYNC: req->result = fsync (req->int1); break;
|
||||
@ -1733,6 +1753,11 @@ eio_req *eio_fstat (int fd, int pri, eio_cb cb, void *data)
|
||||
REQ (EIO_FSTAT); req->int1 = fd; SEND;
|
||||
}
|
||||
|
||||
eio_req *eio_fstatvfs (int fd, int pri, eio_cb cb, void *data)
|
||||
{
|
||||
REQ (EIO_FSTATVFS); req->int1 = fd; SEND;
|
||||
}
|
||||
|
||||
eio_req *eio_futime (int fd, double atime, double mtime, int pri, eio_cb cb, void *data)
|
||||
{
|
||||
REQ (EIO_FUTIME); req->int1 = fd; req->nv1 = atime; req->nv2 = mtime; SEND;
|
||||
@ -1814,6 +1839,11 @@ eio_req *eio_lstat (const char *path, int pri, eio_cb cb, void *data)
|
||||
return eio__1path (EIO_LSTAT, path, pri, cb, data);
|
||||
}
|
||||
|
||||
eio_req *eio_statvfs (const char *path, int pri, eio_cb cb, void *data)
|
||||
{
|
||||
return eio__1path (EIO_STATVFS, path, pri, cb, data);
|
||||
}
|
||||
|
||||
eio_req *eio_unlink (const char *path, int pri, eio_cb cb, void *data)
|
||||
{
|
||||
return eio__1path (EIO_UNLINK, path, pri, cb, data);
|
||||
|
18
deps/libeio/eio.h
vendored
18
deps/libeio/eio.h
vendored
@ -60,6 +60,10 @@ typedef int (*eio_cb)(eio_req *req);
|
||||
# define EIO_STRUCT_STAT struct stat
|
||||
#endif
|
||||
|
||||
#ifndef EIO_STRUCT_STATVFS
|
||||
# define EIO_STRUCT_STATVFS struct statvfs
|
||||
#endif
|
||||
|
||||
/* for readdir */
|
||||
|
||||
/* eio_readdir flags */
|
||||
@ -133,6 +137,7 @@ enum {
|
||||
EIO_READ, EIO_WRITE,
|
||||
EIO_READAHEAD, EIO_SENDFILE,
|
||||
EIO_STAT, EIO_LSTAT, EIO_FSTAT,
|
||||
EIO_STATVFS, EIO_FSTATVFS,
|
||||
EIO_TRUNCATE, EIO_FTRUNCATE,
|
||||
EIO_UTIME, EIO_FUTIME,
|
||||
EIO_CHMOD, EIO_FCHMOD,
|
||||
@ -239,6 +244,7 @@ eio_req *eio_readahead (int fd, off_t offset, size_t length, int pri, eio_cb cb,
|
||||
eio_req *eio_read (int fd, void *buf, size_t length, off_t offset, int pri, eio_cb cb, void *data);
|
||||
eio_req *eio_write (int fd, void *buf, size_t length, off_t offset, int pri, eio_cb cb, void *data);
|
||||
eio_req *eio_fstat (int fd, int pri, eio_cb cb, void *data); /* stat buffer=ptr2 allocated dynamically */
|
||||
eio_req *eio_fstatvfs (int fd, int pri, eio_cb cb, void *data); /* stat buffer=ptr2 allocated dynamically */
|
||||
eio_req *eio_futime (int fd, eio_tstamp atime, eio_tstamp mtime, int pri, eio_cb cb, void *data);
|
||||
eio_req *eio_ftruncate (int fd, off_t offset, int pri, eio_cb cb, void *data);
|
||||
eio_req *eio_fchmod (int fd, mode_t mode, int pri, eio_cb cb, void *data);
|
||||
@ -257,6 +263,7 @@ eio_req *eio_unlink (const char *path, int pri, eio_cb cb, void *data);
|
||||
eio_req *eio_readlink (const char *path, int pri, eio_cb cb, void *data); /* result=ptr2 allocated dynamically */
|
||||
eio_req *eio_stat (const char *path, int pri, eio_cb cb, void *data); /* stat buffer=ptr2 allocated dynamically */
|
||||
eio_req *eio_lstat (const char *path, int pri, eio_cb cb, void *data); /* stat buffer=ptr2 allocated dynamically */
|
||||
eio_req *eio_statvfs (const char *path, int pri, eio_cb cb, void *data); /* stat buffer=ptr2 allocated dynamically */
|
||||
eio_req *eio_mknod (const char *path, mode_t mode, dev_t dev, int pri, eio_cb cb, void *data);
|
||||
eio_req *eio_link (const char *path, const char *new_path, int pri, eio_cb cb, void *data);
|
||||
eio_req *eio_symlink (const char *path, const char *new_path, int pri, eio_cb cb, void *data);
|
||||
@ -277,13 +284,14 @@ void eio_grp_cancel (eio_req *grp); /* cancels all sub requests but not the g
|
||||
/* request api */
|
||||
|
||||
/* true if the request was cancelled, useful in the invoke callback */
|
||||
#define EIO_CANCELLED(req) ((req)->flags & EIO_FLAG_CANCELLED)
|
||||
#define EIO_CANCELLED(req) ((req)->flags & EIO_FLAG_CANCELLED)
|
||||
|
||||
#define EIO_RESULT(req) ((req)->result)
|
||||
#define EIO_RESULT(req) ((req)->result)
|
||||
/* returns a pointer to the result buffer allocated by eio */
|
||||
#define EIO_BUF(req) ((req)->ptr2)
|
||||
#define EIO_STAT_BUF(req) ((EIO_STRUCT_STAT *)EIO_BUF(req))
|
||||
#define EIO_PATH(req) ((char *)(req)->ptr1)
|
||||
#define EIO_BUF(req) ((req)->ptr2)
|
||||
#define EIO_STAT_BUF(req) ((EIO_STRUCT_STAT *)EIO_BUF(req))
|
||||
#define EIO_STATVFS_BUF(req) ((EIO_STRUCT_STATVFS *)EIO_BUF(req))
|
||||
#define EIO_PATH(req) ((char *)(req)->ptr1)
|
||||
|
||||
/* submit a request for execution */
|
||||
void eio_submit (eio_req *req);
|
||||
|
4
deps/libeio/libeio.m4
vendored
4
deps/libeio/libeio.m4
vendored
@ -64,7 +64,7 @@ AC_CACHE_CHECK(for sendfile, ac_cv_sendfile, [AC_LINK_IFELSE([
|
||||
# include <sys/types.h>
|
||||
#if __linux
|
||||
# include <sys/sendfile.h>
|
||||
#elif __freebsd || defined __APPLE__
|
||||
#elif __FreeBSD__ || defined __APPLE__
|
||||
# include <sys/socket.h>
|
||||
# include <sys/uio.h>
|
||||
#elif __hpux
|
||||
@ -80,7 +80,7 @@ int main(void)
|
||||
ssize_t res;
|
||||
#if __linux
|
||||
res = sendfile (fd, fd, offset, count);
|
||||
#elif __freebsd
|
||||
#elif __FreeBSD__
|
||||
res = sendfile (fd, fd, offset, count, 0, &offset, 0);
|
||||
#elif __hpux
|
||||
res = sendfile (fd, fd, offset, count, 0, 0);
|
||||
|
6
deps/libeio/wscript
vendored
6
deps/libeio/wscript
vendored
@ -67,7 +67,7 @@ def configure(conf):
|
||||
# include <sys/types.h>
|
||||
#if __linux
|
||||
# include <sys/sendfile.h>
|
||||
#elif __freebsd
|
||||
#elif __FreeBSD__ || defined(__APPLE__)
|
||||
# include <sys/socket.h>
|
||||
# include <sys/uio.h>
|
||||
#elif __hpux
|
||||
@ -83,8 +83,10 @@ def configure(conf):
|
||||
ssize_t res;
|
||||
#if __linux
|
||||
res = sendfile (fd, fd, offset, count);
|
||||
#elif __freebsd
|
||||
#elif __FreeBSD__
|
||||
res = sendfile (fd, fd, offset, count, 0, &offset, 0);
|
||||
#elif __APPLE__
|
||||
res = sendfile (fd, fd, offset, &offset, 0, 0);
|
||||
#elif __hpux
|
||||
res = sendfile (fd, fd, offset, count, 0, 0);
|
||||
#endif
|
||||
|
18
doc/api.txt
18
doc/api.txt
@ -154,22 +154,10 @@ Send a signal to a process. +pid+ is the process id and +signal+ is the
|
||||
signal to send; for example, "SIGINT" or "SIGUSR1". See kill(2) for more
|
||||
information.
|
||||
|
||||
+process.compile(source, scriptOrigin)+::
|
||||
Just like +eval()+ except that you can specify a +scriptOrigin+ for better
|
||||
error reporting.
|
||||
+process.compile(code, scriptOrigin)+::
|
||||
Similar to +eval()+ except that you can specify a +scriptOrigin+ for better
|
||||
error reporting and the +code+ cannot see the local scope.
|
||||
|
||||
+process.mixin([deep], target, object1, [objectN])+ ::
|
||||
Extend one object with one or more others, returning the modified object.
|
||||
If no target is specified, the +GLOBAL+ namespace itself is extended.
|
||||
Keep in mind that the target object will be modified, and will be returned
|
||||
from +process.mixin()+.
|
||||
+
|
||||
If a boolean true is specified as the first argument, Node performs a deep
|
||||
copy, recursively copying any objects it finds. Otherwise, the copy will
|
||||
share structure with the original object(s).
|
||||
+
|
||||
Undefined properties are not copied. However, properties inherited from the
|
||||
object's prototype will be copied over.
|
||||
|
||||
== System module
|
||||
|
||||
|
@ -1,6 +1,8 @@
|
||||
var sys = require('./sys'),
|
||||
events = require('events');
|
||||
|
||||
var fs = exports;
|
||||
|
||||
exports.Stats = process.Stats;
|
||||
|
||||
process.Stats.prototype._checkModeProperty = function (property) {
|
||||
|
17
lib/ini.js
17
lib/ini.js
@ -1,22 +1,25 @@
|
||||
exports.parse = function(d) {
|
||||
var trim = function(str) { return str.replace(/^\s\s*/, '').replace(/\s\s*$/, ''); }
|
||||
var ini = {'-':{}};
|
||||
|
||||
var section = '-';
|
||||
|
||||
var lines = d.split('\n');
|
||||
for (var i=0; i<lines.length; i++) {
|
||||
var line = lines[i].trim(),
|
||||
rem = line.indexOf(";");
|
||||
|
||||
var re = /(.*)=(.*)|\[([a-z:\.0-9_\s]+)\]/i;
|
||||
if (rem !== -1) line = line.substr(0, rem);
|
||||
|
||||
var match = lines[i].match(re);
|
||||
var re = /^\[([^\]]*)\]$|^([^=]+)(=(.*))?$/i;
|
||||
|
||||
var match = line.match(re);
|
||||
if (match != null) {
|
||||
if (match[3] != undefined) {
|
||||
section = match[3];
|
||||
if (match[1] != undefined) {
|
||||
section = match[1].trim();
|
||||
ini[section] = {};
|
||||
} else {
|
||||
var key = trim(match[1]);
|
||||
var value = trim(match[2]);
|
||||
var key = match[2].trim(),
|
||||
value = (match[3]) ? (match[4] || "").trim() : true;
|
||||
ini[section][key] = value;
|
||||
}
|
||||
}
|
||||
|
53
src/node.cc
53
src/node.cc
@ -426,7 +426,7 @@ static Handle<Value> Loop(const Arguments& args) {
|
||||
}
|
||||
|
||||
static Handle<Value> Unloop(const Arguments& args) {
|
||||
fprintf(stderr, "Node.js Depreciation: Don't use process.unloop(). It will be removed soon.\n");
|
||||
fprintf(stderr, "Deprecation: Don't use process.unloop(). It will be removed soon.\n");
|
||||
HandleScope scope;
|
||||
int how = EVUNLOOP_ONE;
|
||||
if (args[0]->IsString()) {
|
||||
@ -610,6 +610,7 @@ int getmem(size_t *rss, size_t *vsize) {
|
||||
struct kinfo_proc *kinfo = NULL;
|
||||
pid_t pid;
|
||||
int nprocs;
|
||||
size_t page_size = getpagesize();
|
||||
|
||||
pid = getpid();
|
||||
|
||||
@ -619,7 +620,7 @@ int getmem(size_t *rss, size_t *vsize) {
|
||||
kinfo = kvm_getprocs(kd, KERN_PROC_PID, pid, &nprocs);
|
||||
if (kinfo == NULL) goto error;
|
||||
|
||||
*rss = kinfo->ki_rssize * PAGE_SIZE;
|
||||
*rss = kinfo->ki_rssize * page_size;
|
||||
*vsize = kinfo->ki_size;
|
||||
|
||||
kvm_close(kd);
|
||||
@ -858,6 +859,53 @@ Handle<Value> DLOpen(const v8::Arguments& args) {
|
||||
return Undefined();
|
||||
}
|
||||
|
||||
// evalcx(code, sandbox={})
|
||||
// Executes code in a new context
|
||||
Handle<Value> EvalCX(const Arguments& args) {
|
||||
HandleScope scope;
|
||||
|
||||
Local<String> code = args[0]->ToString();
|
||||
Local<Object> sandbox = args.Length() > 1 ? args[1]->ToObject()
|
||||
: Object::New();
|
||||
// Create the new context
|
||||
Persistent<Context> context = Context::New();
|
||||
|
||||
// Copy objects from global context, to our brand new context
|
||||
Handle<Array> keys = sandbox->GetPropertyNames();
|
||||
|
||||
int i;
|
||||
for (i = 0; i < keys->Length(); i++) {
|
||||
Handle<String> key = keys->Get(Integer::New(i))->ToString();
|
||||
Handle<Value> value = sandbox->Get(key);
|
||||
context->Global()->Set(key, value->ToObject()->Clone());
|
||||
}
|
||||
|
||||
// Enter and compile script
|
||||
context->Enter();
|
||||
|
||||
// Catch errors
|
||||
TryCatch try_catch;
|
||||
|
||||
Local<Script> script = Script::Compile(code, String::New("evalcx"));
|
||||
Handle<Value> result;
|
||||
|
||||
if (script.IsEmpty()) {
|
||||
result = ThrowException(try_catch.Exception());
|
||||
} else {
|
||||
result = script->Run();
|
||||
if (result.IsEmpty()) {
|
||||
result = ThrowException(try_catch.Exception());
|
||||
}
|
||||
}
|
||||
|
||||
// Clean up, clean up, everybody everywhere!
|
||||
context->DetachGlobal();
|
||||
context->Exit();
|
||||
context.Dispose();
|
||||
|
||||
return scope.Close(result);
|
||||
}
|
||||
|
||||
Handle<Value> Compile(const Arguments& args) {
|
||||
HandleScope scope;
|
||||
|
||||
@ -1065,6 +1113,7 @@ static void Load(int argc, char *argv[]) {
|
||||
// define various internal methods
|
||||
NODE_SET_METHOD(process, "loop", Loop);
|
||||
NODE_SET_METHOD(process, "unloop", Unloop);
|
||||
NODE_SET_METHOD(process, "evalcx", EvalCX);
|
||||
NODE_SET_METHOD(process, "compile", Compile);
|
||||
NODE_SET_METHOD(process, "_byteLength", ByteLength);
|
||||
NODE_SET_METHOD(process, "reallyExit", Exit);
|
||||
|
89
src/node.js
89
src/node.js
@ -45,6 +45,7 @@ node.dns.createConnection = removed("node.dns.createConnection() has moved. Use
|
||||
// Module
|
||||
|
||||
var internalModuleCache = {};
|
||||
var extensionCache = {};
|
||||
|
||||
function Module (id, parent) {
|
||||
this.id = id;
|
||||
@ -99,7 +100,12 @@ process.assert = function (x, msg) {
|
||||
// Dual licensed under the MIT and GPL licenses.
|
||||
// http://docs.jquery.com/License
|
||||
// Modified for node.js (formely for copying properties correctly)
|
||||
var mixinMessage;
|
||||
process.mixin = function() {
|
||||
if (!mixinMessage) {
|
||||
mixinMessage = 'deprecation warning: process.mixin will be removed from node-core future releases.\n'
|
||||
process.stdio.writeError(mixinMessage);
|
||||
}
|
||||
// copy reference to target object
|
||||
var target = arguments[0] || {}, i = 1, length = arguments.length, deep = false, source;
|
||||
|
||||
@ -478,9 +484,15 @@ function findModulePath (id, dirs, callback) {
|
||||
path.join(dir, id + ".js"),
|
||||
path.join(dir, id + ".node"),
|
||||
path.join(dir, id, "index.js"),
|
||||
path.join(dir, id, "index.addon")
|
||||
path.join(dir, id, "index.node")
|
||||
];
|
||||
|
||||
var ext;
|
||||
for (ext in extensionCache) {
|
||||
locations.push(path.join(dir, id + ext));
|
||||
locations.push(path.join(dir, id, 'index' + ext));
|
||||
}
|
||||
|
||||
function searchLocations () {
|
||||
var location = locations.shift();
|
||||
if (!location) {
|
||||
@ -495,7 +507,7 @@ function findModulePath (id, dirs, callback) {
|
||||
} else {
|
||||
return searchLocations();
|
||||
}
|
||||
})
|
||||
});
|
||||
|
||||
// if sync
|
||||
} else {
|
||||
@ -515,8 +527,13 @@ function resolveModulePath(request, parent) {
|
||||
var id, paths;
|
||||
if (request.charAt(0) == "." && (request.charAt(1) == "/" || request.charAt(1) == ".")) {
|
||||
// Relative request
|
||||
var exts = ['js', 'node'], ext;
|
||||
for (ext in extensionCache) {
|
||||
exts.push(ext.slice(1));
|
||||
}
|
||||
|
||||
var parentIdPath = path.dirname(parent.id +
|
||||
(path.basename(parent.filename).match(/^index\.(js|addon)$/) ? "/" : ""));
|
||||
(path.basename(parent.filename).match(new RegExp('^index\\.(' + exts.join('|') + ')$')) ? "/" : ""));
|
||||
id = path.join(parentIdPath, request);
|
||||
// debug("RELATIVE: requested:"+request+" set ID to: "+id+" from "+parent.id+"("+parentIdPath+")");
|
||||
paths = [path.dirname(parent.filename)];
|
||||
@ -584,6 +601,32 @@ function loadModule (request, parent, callback) {
|
||||
};
|
||||
|
||||
|
||||
// This function allows the user to register file extensions to custom
|
||||
// Javascript 'compilers'. It accepts 2 arguments, where ext is a file
|
||||
// extension as a string. E.g. '.coffee' for coffee-script files. compiler
|
||||
// is the second argument, which is a function that gets called then the
|
||||
// specified file extension is found. The compiler is passed a single
|
||||
// argument, which is, the file contents, which need to be compiled.
|
||||
//
|
||||
// The function needs to return the compiled source, or an non-string
|
||||
// variable that will get attached directly to the module exports. Example:
|
||||
//
|
||||
// require.registerExtension('.coffee', function(content) {
|
||||
// return doCompileMagic(content);
|
||||
// });
|
||||
function registerExtension(ext, compiler) {
|
||||
if ('string' !== typeof ext && false === /\.\w+$/.test(ext)) {
|
||||
throw new Error('require.registerExtension: First argument not a valid extension string.');
|
||||
}
|
||||
|
||||
if ('function' !== typeof compiler) {
|
||||
throw new Error('require.registerExtension: Second argument not a valid compiler function.');
|
||||
}
|
||||
|
||||
extensionCache[ext] = compiler;
|
||||
}
|
||||
|
||||
|
||||
Module.prototype.loadSync = function (filename) {
|
||||
debug("loadSync " + JSON.stringify(filename) + " for module " + JSON.stringify(this.id));
|
||||
|
||||
@ -649,6 +692,12 @@ Module.prototype._loadContent = function (content, filename) {
|
||||
// remove shebang
|
||||
content = content.replace(/^\#\!.*/, '');
|
||||
|
||||
// Compile content if needed
|
||||
var ext = path.extname(filename);
|
||||
if (extensionCache[ext]) {
|
||||
content = extensionCache[ext](content);
|
||||
}
|
||||
|
||||
function requireAsync (url, cb) {
|
||||
loadModule(url, self, cb);
|
||||
}
|
||||
@ -660,19 +709,27 @@ Module.prototype._loadContent = function (content, filename) {
|
||||
require.paths = process.paths;
|
||||
require.async = requireAsync;
|
||||
require.main = process.mainModule;
|
||||
// create wrapper function
|
||||
var wrapper = "(function (exports, require, module, __filename, __dirname) { "
|
||||
+ content
|
||||
+ "\n});";
|
||||
require.registerExtension = registerExtension;
|
||||
|
||||
try {
|
||||
var compiledWrapper = process.compile(wrapper, filename);
|
||||
var dirName = path.dirname(filename);
|
||||
if (filename === process.argv[1])
|
||||
process.checkBreak();
|
||||
compiledWrapper.apply(self.exports, [self.exports, require, self, filename, dirName]);
|
||||
} catch (e) {
|
||||
return e;
|
||||
|
||||
if ('string' === typeof content) {
|
||||
// create wrapper function
|
||||
var wrapper = "(function (exports, require, module, __filename, __dirname) { "
|
||||
+ content
|
||||
+ "\n});";
|
||||
|
||||
try {
|
||||
var compiledWrapper = process.compile(wrapper, filename);
|
||||
var dirName = path.dirname(filename);
|
||||
if (filename === process.argv[1]) {
|
||||
process.checkBreak();
|
||||
}
|
||||
compiledWrapper.apply(self.exports, [self.exports, require, self, filename, dirName]);
|
||||
} catch (e) {
|
||||
return e;
|
||||
}
|
||||
} else {
|
||||
self.exports = content;
|
||||
}
|
||||
};
|
||||
|
||||
@ -763,4 +820,4 @@ process.loop();
|
||||
|
||||
process.emit("exit");
|
||||
|
||||
})
|
||||
});
|
||||
|
10
test/fixtures/fixture.ini
vendored
10
test/fixtures/fixture.ini
vendored
@ -1,10 +1,18 @@
|
||||
; a comment
|
||||
root=something
|
||||
|
||||
url = http://example.com/?foo=bar
|
||||
|
||||
[ the section with whitespace ]
|
||||
this has whitespace = yep ; and a comment; and then another
|
||||
|
||||
just a flag, no value.
|
||||
|
||||
[section]
|
||||
one=two
|
||||
Foo=Bar
|
||||
this=Your Mother!
|
||||
blank=
|
||||
blank=
|
||||
|
||||
[Section Two]
|
||||
something else=blah
|
||||
|
1
test/fixtures/registerExt.test
vendored
Normal file
1
test/fixtures/registerExt.test
vendored
Normal file
@ -0,0 +1 @@
|
||||
this is custom source
|
1
test/fixtures/registerExt2.test
vendored
Normal file
1
test/fixtures/registerExt2.test
vendored
Normal file
@ -0,0 +1 @@
|
||||
This is for the object return test
|
27
test/simple/test-eval-cx.js
Normal file
27
test/simple/test-eval-cx.js
Normal file
@ -0,0 +1,27 @@
|
||||
require("../common");
|
||||
|
||||
debug('evalcx a string');
|
||||
var result = process.evalcx('"passed";');
|
||||
assert.equal('passed', result);
|
||||
|
||||
debug('evalcx a thrown error');
|
||||
assert.throws(function() {
|
||||
process.evalcx('throw new Error("test");');
|
||||
});
|
||||
|
||||
hello = 5;
|
||||
process.evalcx('hello = 2');
|
||||
assert.equal(5, hello);
|
||||
|
||||
|
||||
code = "foo = 1; bar = 2;";
|
||||
foo = 2;
|
||||
obj = { foo : 0 };
|
||||
process.evalcx(code, obj);
|
||||
|
||||
/* TODO?
|
||||
assert.equal(1, obj.foo);
|
||||
assert.equal(2, obj.bar);
|
||||
*/
|
||||
|
||||
assert.equal(2, foo);
|
@ -14,7 +14,30 @@ fs.readFile(p,function(err, data) {
|
||||
|
||||
var iniContents = parse(data);
|
||||
assert.equal(typeof iniContents, 'object');
|
||||
assert.deepEqual(iniContents,{"-":{"root":"something"},"section":{"one":"two","Foo":"Bar","this":"Your Mother!","blank":""},"Section Two":{"something else":"blah","remove":"whitespace"}})
|
||||
|
||||
var expect =
|
||||
{ "-" :
|
||||
{ "root" : "something"
|
||||
, "url" : "http://example.com/?foo=bar"
|
||||
}
|
||||
, "the section with whitespace" :
|
||||
{ "this has whitespace" : "yep"
|
||||
, "just a flag, no value." : true
|
||||
}
|
||||
, "section" :
|
||||
{ "one" : "two"
|
||||
, "Foo" : "Bar"
|
||||
, "this" : "Your Mother!"
|
||||
, "blank" : ""
|
||||
}
|
||||
, "Section Two" :
|
||||
{ "something else" : "blah"
|
||||
, "remove" : "whitespace"
|
||||
}
|
||||
};
|
||||
|
||||
assert.deepEqual(iniContents, expect,
|
||||
"actual: \n"+inspect(iniContents) +"\n≠\nexpected:\n"+inspect(expect))
|
||||
|
||||
assert.equal(iniContents['-']['root'],'something');
|
||||
assert.equal(iniContents['section']['blank'],'');
|
||||
|
@ -63,6 +63,24 @@ require.async('../fixtures/a', function (err, a) {
|
||||
assert.equal("A", a.A());
|
||||
});
|
||||
|
||||
debug('load custom file types with registerExtension');
|
||||
require.registerExtension('.test', function(content) {
|
||||
assert.equal("this is custom source\n", content);
|
||||
|
||||
return content.replace("this is custom source", "exports.test = 'passed'");
|
||||
});
|
||||
|
||||
assert.equal(require('../fixtures/registerExt').test, "passed");
|
||||
|
||||
debug('load custom file types that return non-strings');
|
||||
require.registerExtension('.test', function(content) {
|
||||
return {
|
||||
custom: 'passed'
|
||||
};
|
||||
});
|
||||
|
||||
assert.equal(require('../fixtures/registerExt2').custom, 'passed');
|
||||
|
||||
process.addListener("exit", function () {
|
||||
assert.equal(true, a.A instanceof Function);
|
||||
assert.equal("A done", a.A());
|
||||
|
77
wscript
77
wscript
@ -32,6 +32,12 @@ def set_options(opt):
|
||||
, help='Build with -lefence for debugging [Default: False]'
|
||||
, dest='efence'
|
||||
)
|
||||
opt.add_option( '--system'
|
||||
, action='store_true'
|
||||
, default=False
|
||||
, help='Build using system libraries and headers (like a debian build) [Default: False]'
|
||||
, dest='system'
|
||||
)
|
||||
|
||||
def mkdir_p(dir):
|
||||
if not os.path.exists (dir):
|
||||
@ -106,6 +112,7 @@ def configure(conf):
|
||||
if not conf.env.CC: conf.fatal('c compiler not found')
|
||||
|
||||
conf.env["USE_DEBUG"] = Options.options.debug
|
||||
conf.env["USE_SYSTEM"] = Options.options.system
|
||||
|
||||
conf.check(lib='dl', uselib_store='DL')
|
||||
if not sys.platform.startswith("sunos"):
|
||||
@ -145,12 +152,19 @@ def configure(conf):
|
||||
conf.fatal("Cannot find nsl library")
|
||||
|
||||
conf.sub_config('deps/libeio')
|
||||
conf.sub_config('deps/libev')
|
||||
|
||||
if sys.platform.startswith("sunos"):
|
||||
conf_subproject(conf, 'deps/udns', 'LIBS="-lsocket -lnsl" ./configure')
|
||||
if not Options.options.system:
|
||||
conf.sub_config('deps/libev')
|
||||
if sys.platform.startswith("sunos"):
|
||||
conf_subproject(conf, 'deps/udns', 'LIBS="-lsocket -lnsl" ./configure')
|
||||
else:
|
||||
conf_subproject(conf, 'deps/udns', './configure')
|
||||
else:
|
||||
conf_subproject(conf, 'deps/udns', './configure')
|
||||
if not conf.check(lib='v8', uselib_store='V8'):
|
||||
conf.fatal("Cannot find V8")
|
||||
if not conf.check(lib='ev', uselib_store='EV'):
|
||||
conf.fatal("Cannot find libev")
|
||||
if conf.check(lib='udns', uselib_store='UDNS'):
|
||||
conf.fatal("Cannot find udns")
|
||||
|
||||
conf.define("HAVE_CONFIG_H", 1)
|
||||
|
||||
@ -278,15 +292,22 @@ def build_v8(bld):
|
||||
bld.install_files('${PREFIX}/include/node/', 'deps/v8/include/*.h')
|
||||
|
||||
def build(bld):
|
||||
bld.add_subdirs('deps/libeio deps/libev')
|
||||
if not bld.env["USE_SYSTEM"]:
|
||||
bld.add_subdirs('deps/libeio deps/libev')
|
||||
build_udns(bld)
|
||||
build_v8(bld)
|
||||
else:
|
||||
bld.add_subdirs('deps/libeio')
|
||||
|
||||
|
||||
build_udns(bld)
|
||||
build_v8(bld)
|
||||
|
||||
### evcom
|
||||
evcom = bld.new_task_gen("cc")
|
||||
evcom.source = "deps/evcom/evcom.c"
|
||||
evcom.includes = "deps/evcom/ deps/libev/"
|
||||
if not bld.env["USE_SYSTEM"]:
|
||||
evcom.includes = "deps/evcom/ deps/libev/"
|
||||
else:
|
||||
evcom.includes = "deps/evcom/"
|
||||
evcom.name = "evcom"
|
||||
evcom.target = "evcom"
|
||||
evcom.uselib = "GPGERROR GNUTLS"
|
||||
@ -361,19 +382,31 @@ def build(bld):
|
||||
src/node_timer.cc
|
||||
src/node_idle_watcher.cc
|
||||
"""
|
||||
node.includes = """
|
||||
src/
|
||||
deps/v8/include
|
||||
deps/libev
|
||||
deps/udns
|
||||
deps/libeio
|
||||
deps/evcom
|
||||
deps/http_parser
|
||||
deps/coupling
|
||||
"""
|
||||
node.add_objects = 'ev eio evcom http_parser coupling'
|
||||
node.uselib_local = ''
|
||||
node.uselib = 'GNUTLS GPGERROR UDNS V8 EXECINFO DL KVM SOCKET NSL EFENCE'
|
||||
if not bld.env["USE_SYSTEM"]:
|
||||
node.includes = """
|
||||
src/
|
||||
deps/v8/include
|
||||
deps/libev
|
||||
deps/udns
|
||||
deps/libeio
|
||||
deps/evcom
|
||||
deps/http_parser
|
||||
deps/coupling
|
||||
"""
|
||||
node.add_objects = 'ev eio evcom http_parser coupling'
|
||||
node.uselib_local = ''
|
||||
node.uselib = 'GNUTLS GPGERROR UDNS V8 EXECINFO DL KVM SOCKET NSL'
|
||||
else:
|
||||
node.includes = """
|
||||
src/
|
||||
deps/libeio
|
||||
deps/evcom
|
||||
deps/http_parser
|
||||
deps/coupling
|
||||
"""
|
||||
node.add_objects = 'eio evcom http_parser coupling'
|
||||
node.uselib_local = 'eio'
|
||||
node.uselib = 'EV GNUTLS GPGERROR UDNS V8 EXECINFO DL KVM SOCKET NSL'
|
||||
|
||||
node.install_path = '${PREFIX}/lib'
|
||||
node.install_path = '${PREFIX}/bin'
|
||||
|
Loading…
x
Reference in New Issue
Block a user