Permalink
Browse files

test: move test fixture native bindings from the main src/ dir to a s…

…eparate test/ native binding
  • Loading branch information...
1 parent 329ed4f commit 3db3eeb205e7e96a385228370f5d06174c4838b1 @TooTallNate TooTallNate committed May 12, 2012
Showing with 138 additions and 41 deletions.
  1. +0 −34 src/ffi.cc
  2. +0 −4 src/ffi.h
  3. +8 −0 test/binding.gyp
  4. +106 −0 test/ffi_tests.cc
  5. +24 −3 test/foreign_function.js
View
@@ -26,13 +26,6 @@ Handle<Value> WrapPointer(char *ptr, size_t length) {
void FFI::InitializeStaticFunctions(Handle<Object> target) {
Local<Object> o = Object::New();
- // atoi and abs here for testing purposes
- o->Set(String::NewSymbol("atoi"), WrapPointer((char *)atoi));
-
- // Windows has multiple `abs` signatures, so we need to manually disambiguate
- int (*absPtr)(int)(abs);
- o->Set(String::NewSymbol("abs"), WrapPointer((char *)absPtr));
-
// dl functions used by the DynamicLibrary JS class
o->Set(String::NewSymbol("dlopen"), WrapPointer((char *)dlopen));
o->Set(String::NewSymbol("dlclose"), WrapPointer((char *)dlclose));
@@ -52,7 +45,6 @@ void FFI::InitializeBindings(Handle<Object> target) {
NODE_SET_METHOD(target, "ffi_prep_cif", FFIPrepCif);
NODE_SET_METHOD(target, "ffi_call", FFICall);
NODE_SET_METHOD(target, "ffi_call_async", FFICallAsync);
- NODE_SET_METHOD(target, "strtoul", Strtoul);
// `ffi_status` enum values
SET_ENUM_VALUE(FFI_OK);
@@ -118,32 +110,6 @@ void FFI::InitializeBindings(Handle<Object> target) {
}
/*
- * Hard-coded `strtoul` binding, for the benchmarks.
- *
- * args[0] - the string number to convert to a real Number
- * args[1] - a "buffer" instance to write into (the "endptr")
- * args[2] - the base (0 means autodetect)
- */
-
-Handle<Value> FFI::Strtoul(const Arguments &args) {
- HandleScope scope;
- char buf[128];
- int base;
- char **endptr;
-
- args[0]->ToString()->WriteUtf8(buf);
-
- Local<Value> endptr_arg = args[0];
- endptr = (char **)Buffer::Data(endptr_arg.As<Object>());
-
- base = args[2]->Int32Value();
-
- unsigned long val = strtoul(buf, endptr, base);
-
- return scope.Close(Integer::NewFromUnsigned(val));
-}
-
-/*
* Function that creates and returns an `ffi_cif` pointer from the given return
* value type and argument types.
*
View
@@ -1,7 +1,3 @@
-#include <stdio.h>
-#include <stdlib.h>
-#include <stdarg.h>
-#include <string.h>
#include <limits.h>
#include <errno.h>
#define __STDC_LIMIT_MACROS true
View
@@ -0,0 +1,8 @@
+{
+ 'targets': [
+ {
+ 'target_name': 'ffi_tests',
+ 'sources': [ 'ffi_tests.cc' ]
+ }
+ ]
+}
View
@@ -0,0 +1,106 @@
+#include <stdlib.h>
+#include "v8.h"
+#include "node.h"
+#include "node_buffer.h"
+
+using namespace v8;
+using namespace node;
+
+namespace {
+
+/*
+ * Test struct definition used in the test harness functions below.
+ */
+
+typedef struct box {
+ int width;
+ int height;
+} _box;
+
+/*
+ * Accepts a struct by value, and returns a struct by value.
+ */
+
+box double_box(box input) {
+ box rtn;
+ rtn.width = input.width * 2;
+ rtn.height = input.height * 2;
+ return rtn;
+}
+
+/*
+ * Accepts a struct by value, and returns an int.
+ */
+
+int area_box(box input) {
+ return input.width * input.height;
+}
+
+/*
+ * Accepts a box pointer and returns an int.
+ */
+
+int area_box_ptr(box *input) {
+ return input->width * input->height;
+}
+
+/*
+ * Hard-coded `strtoul` binding, for the benchmarks.
+ *
+ * args[0] - the string number to convert to a real Number
+ * args[1] - a "buffer" instance to write into (the "endptr")
+ * args[2] - the base (0 means autodetect)
+ */
+
+Handle<Value> Strtoul(const Arguments &args) {
+ HandleScope scope;
+ char buf[128];
+ int base;
+ char **endptr;
+
+ args[0]->ToString()->WriteUtf8(buf);
+
+ Local<Value> endptr_arg = args[0];
+ endptr = (char **)Buffer::Data(endptr_arg.As<Object>());
+
+ base = args[2]->Int32Value();
+
+ unsigned long val = strtoul(buf, endptr, base);
+
+ return scope.Close(Integer::NewFromUnsigned(val));
+}
+
+
+void wrap_pointer_cb(char *data, void *hint) {
+ //fprintf(stderr, "wrap_pointer_cb\n");
+}
+
+Handle<Object> WrapPointer(char *ptr) {
+ void *user_data = NULL;
+ size_t length = 0;
+ Buffer *buf = Buffer::New(ptr, length, wrap_pointer_cb, user_data);
+ return buf->handle_;
+}
+
+void Initialize(Handle<Object> target) {
+ HandleScope scope;
+
+ // atoi and abs here for testing purposes
+ target->Set(String::NewSymbol("atoi"), WrapPointer((char *)atoi));
+
+ // Windows has multiple `abs` signatures, so we need to manually disambiguate
+ int (*absPtr)(int)(abs);
+ target->Set(String::NewSymbol("abs"), WrapPointer((char *)absPtr));
+
+ // hard-coded `strtoul` binding, for the benchmarks
+ NODE_SET_METHOD(target, "strtoul", Strtoul);
+
+ // also need to test these custom functions
+ target->Set(String::NewSymbol("double_box"), WrapPointer((char *)double_box));
+ target->Set(String::NewSymbol("area_box"), WrapPointer((char *)area_box));
+ target->Set(String::NewSymbol("area_box_ptr"), WrapPointer((char *)area_box_ptr));
+}
+
+} // anonymous namespace
+
+NODE_MODULE(ffi_tests, Initialize);
@@ -1,29 +1,50 @@
var expect = require('expect.js')
+ , ref = require('ref')
+ , Struct = require('ref-struct')
, ffi = require('../')
+ , bindings = require('./build/Release/ffi_tests')
describe('ForeignFunction', function () {
afterEach(gc)
+ // same struct as defined in ffi_tests.cc
+ var box = Struct({
+ width: ref.types.int
+ , height: ref.types.int
+ })
+
it('should call the static "abs" bindings', function () {
- var _abs = ffi.Bindings.StaticFunctions.abs
+ var _abs = bindings.abs
var abs = ffi.ForeignFunction(_abs, 'int', [ 'int' ])
expect(abs).to.be.a('function')
expect(abs(-1234)).to.equal(1234)
})
it('should call the static "atoi" bindings', function () {
- var _atoi = ffi.Bindings.StaticFunctions.atoi
+ var _atoi = bindings.atoi
var atoi = ffi.ForeignFunction(_atoi, 'int', [ 'string' ])
expect(atoi).to.be.a('function')
expect(atoi('1234')).to.equal(1234)
})
+ it('should call the static "double_box" bindings', function () {
+ var double_box = ffi.ForeignFunction(bindings.double_box, box, [ box ])
+ var b = new box
+ assert(b instanceof box)
+ b.width = 4
+ b.height = 5
+ var out = double_box(b)
+ assert(out instanceof box)
+ assert.equal(8, out.width)
+ assert.equal(10, out.height)
+ })
+
describe('async', function () {
it('should call the static "abs" bindings asynchronously', function (done) {
- var _abs = ffi.Bindings.StaticFunctions.abs
+ var _abs = bindings.abs
var abs = ffi.ForeignFunction(_abs, 'int', [ 'int' ])
expect(abs).to.be.a('function')

0 comments on commit 3db3eeb

Please sign in to comment.