ext/nmatrix/nmatrix.h in nmatrix-0.1.0 vs ext/nmatrix/nmatrix.h in nmatrix-0.2.0

- old
+ new

@@ -41,18 +41,18 @@ #include <math.h> #include <string.h> #endif #ifdef BENCHMARK - // SOURCE: http://stackoverflow.com/questions/2349776/how-can-i-benchmark-a-c-program-easily + // SOURCE: http://stackoverflow.com/questions/2349776/how-can-i-benchmark-a-c-program-easily #ifdef __cplusplus #include <sys/ctime> #include <sys/cresource> #else #include <sys/time.h> #include <sys/resource.h> - #endif + #endif #endif #ifdef __cplusplus #include "nm_memory.h" #endif @@ -62,28 +62,28 @@ */ #define RUBY_ZERO INT2FIX(0) #ifndef SIZEOF_INT - #error SIZEOF_INT undefined + #error SIZEOF_INT undefined #else - #if SIZEOF_INT == 8 - #define DEFAULT_DTYPE INT64 - #define SIZE_T INT64 - #else - #if SIZEOF_INT == 4 - #define DEFAULT_DTYPE INT32 - #define SIZE_T INT32 - #else - #if SIZEOF_INT == 2 - #define DEFAULT_DTYPE INT16 - #define SIZE_T INT16 - #else - #error Unhandled SIZEOF_INT -- please #define SIZE_T and DEFAULT_DTYPE manually. - #endif - #endif - #endif + #if SIZEOF_INT == 8 + #define DEFAULT_DTYPE INT64 + #define SIZE_T INT64 + #else + #if SIZEOF_INT == 4 + #define DEFAULT_DTYPE INT32 + #define SIZE_T INT32 + #else + #if SIZEOF_INT == 2 + #define DEFAULT_DTYPE INT16 + #define SIZE_T INT16 + #else + #error Unhandled SIZEOF_INT -- please #define SIZE_T and DEFAULT_DTYPE manually. + #endif + #endif + #endif #endif /* * == Macros for Concurrent C and C++ Header Maintenance * @@ -117,42 +117,42 @@ * return enumerator_init(enumerator_allocate(rb_cEnumerator), obj, meth, argc, argv); * } */ //opening portion -- this allows unregistering any objects in use before returning - #define RETURN_SIZED_ENUMERATOR_PRE do { \ - if (!rb_block_given_p()) { + #define RETURN_SIZED_ENUMERATOR_PRE do { \ + if (!rb_block_given_p()) { //remaining portion - #ifdef RUBY_2 - #ifndef RETURN_SIZED_ENUMERATOR - #undef RETURN_SIZED_ENUMERATOR - // Ruby 2.0 and higher has rb_enumeratorize_with_size instead of rb_enumeratorize. - // We want to support both in the simplest way possible. - #define RETURN_SIZED_ENUMERATOR(obj, argc, argv, size_fn) \ + #ifdef RUBY_2 + #ifndef RETURN_SIZED_ENUMERATOR + #undef RETURN_SIZED_ENUMERATOR + // Ruby 2.0 and higher has rb_enumeratorize_with_size instead of rb_enumeratorize. + // We want to support both in the simplest way possible. + #define RETURN_SIZED_ENUMERATOR(obj, argc, argv, size_fn) \ return rb_enumeratorize_with_size((obj), ID2SYM(rb_frame_this_func()), (argc), (argv), (size_fn)); \ } \ } while (0) - #endif - #else - #undef RETURN_SIZED_ENUMERATOR - #define RETURN_SIZED_ENUMERATOR(obj, argc, argv, size_fn) \ - return rb_enumeratorize((obj), ID2SYM(rb_frame_this_func()), (argc), (argv)); \ + #endif + #else + #undef RETURN_SIZED_ENUMERATOR + #define RETURN_SIZED_ENUMERATOR(obj, argc, argv, size_fn) \ + return rb_enumeratorize((obj), ID2SYM(rb_frame_this_func()), (argc), (argv)); \ } \ } while (0) - #endif + #endif #define NM_DECL_ENUM(enum_type, name) nm::enum_type name #define NM_DECL_STRUCT(type, name) type name; #define NM_DEF_STORAGE_ELEMENTS \ NM_DECL_ENUM(dtype_t, dtype); \ size_t dim; \ size_t* shape; \ size_t* offset; \ - int count; \ - STORAGE* src; + int count; \ + STORAGE* src; #define NM_DEF_STORAGE_CHILD_STRUCT_PRE(name) struct name : STORAGE { #define NM_DEF_STORAGE_STRUCT_POST(name) }; #define NM_DEF_STORAGE_STRUCT \ @@ -178,14 +178,14 @@ #define NM_DEF_STORAGE_ELEMENTS \ NM_DECL_ENUM(dtype_t, dtype); \ size_t dim; \ size_t* shape; \ size_t* offset; \ - int count; \ - STORAGE* src; + int count; \ + NM_DECL_STRUCT(STORAGE*, src); #define NM_DEF_STORAGE_CHILD_STRUCT_PRE(name) typedef struct NM_ ## name { \ - NM_DEF_STORAGE_ELEMENTS; + NM_DEF_STORAGE_ELEMENTS; #define NM_DEF_STORAGE_STRUCT_POST(name) } NM_ ## name; #define NM_DEF_STORAGE_STRUCT \ typedef struct NM_STORAGE { \ @@ -205,11 +205,11 @@ /* * Types */ -#define NM_NUM_DTYPES 13 // data/data.h +#define NM_NUM_DTYPES 10 // data/data.h #define NM_NUM_STYPES 3 // storage/storage.h //#ifdef __cplusplus //namespace nm { //#endif @@ -218,23 +218,20 @@ NM_DEF_ENUM(stype_t, DENSE_STORE = 0, LIST_STORE = 1, YALE_STORE = 2); /* Data Type */ -NM_DEF_ENUM(dtype_t, BYTE = 0, // unsigned char - INT8 = 1, // char - INT16 = 2, // short - INT32 = 3, // int - INT64 = 4, // long - FLOAT32 = 5, // float - FLOAT64 = 6, // double - COMPLEX64 = 7, // Complex64 class - COMPLEX128 = 8, // Complex128 class - RATIONAL32 = 9, // Rational32 class - RATIONAL64 = 10, // Rational64 class - RATIONAL128 = 11, // Rational128 class - RUBYOBJ = 12); // Ruby VALUE type +NM_DEF_ENUM(dtype_t, BYTE = 0, // unsigned char + INT8 = 1, // char + INT16 = 2, // short + INT32 = 3, // int + INT64 = 4, // long + FLOAT32 = 5, // float + FLOAT64 = 6, // double + COMPLEX64 = 7, // Complex64 class + COMPLEX128 = 8, // Complex128 class + RUBYOBJ = 9); // Ruby VALUE type NM_DEF_ENUM(symm_t, NONSYMM = 0, SYMM = 1, SKEW = 2, HERM = 3, @@ -248,20 +245,20 @@ /* struct STORAGE */ NM_DEF_STORAGE_STRUCT; /* Dense Storage */ NM_DEF_STORAGE_CHILD_STRUCT_PRE(DENSE_STORAGE); // struct DENSE_STORAGE : STORAGE { - void* elements; // should go first to align with void* a in yale and NODE* first in list. - size_t* stride; + void* elements; // should go first to align with void* a in yale and NODE* first in list. + size_t* stride; NM_DEF_STORAGE_STRUCT_POST(DENSE_STORAGE); // }; /* Yale Storage */ NM_DEF_STORAGE_CHILD_STRUCT_PRE(YALE_STORAGE); - void* a; // should go first - size_t ndnz; // Strictly non-diagonal non-zero count! - size_t capacity; - size_t* ija; + void* a; // should go first + size_t ndnz; // Strictly non-diagonal non-zero count! + size_t capacity; + size_t* ija; NM_DEF_STORAGE_STRUCT_POST(YALE_STORAGE); // FIXME: NODE and LIST should be put in some kind of namespace or something, at least in C++. NM_DEF_STRUCT_PRE(NODE); // struct NODE { size_t key; @@ -273,13 +270,13 @@ NM_DECL_STRUCT(NODE*, first); // NODE* first; NM_DEF_STRUCT_POST(LIST); // }; /* List-of-Lists Storage */ NM_DEF_STORAGE_CHILD_STRUCT_PRE(LIST_STORAGE); // struct LIST_STORAGE : STORAGE { - // List storage specific elements. - void* default_val; - NM_DECL_STRUCT(LIST*, rows); // LIST* rows; + // List storage specific elements. + void* default_val; + NM_DECL_STRUCT(LIST*, rows); // LIST* rows; NM_DEF_STORAGE_STRUCT_POST(LIST_STORAGE); // }; /* NMATRIX Object */ @@ -327,11 +324,11 @@ #define NM_DEFAULT_VAL(val) (NM_STORAGE_LIST(val)->default_val) #define NM_DENSE_COUNT(val) (nm_storage_count_max_elements(NM_STORAGE_DENSE(val))) #define NM_DENSE_ELEMENTS(val) (NM_STORAGE_DENSE(val)->elements) #define NM_SIZEOF_DTYPE(val) (DTYPE_SIZES[NM_DTYPE(val)]) -#define NM_REF(val,slice) (RefFuncs[NM_STYPE(val)]( NM_STORAGE(val), slice, NM_SIZEOF_DTYPE(val) )) +#define NM_REF(val,slice) (RefFuncs[NM_STYPE(val)]( NM_STORAGE(val), slice, NM_SIZEOF_DTYPE(val) )) #define NM_MAX(a,b) (((a)>(b))?(a):(b)) #define NM_MIN(a,b) (((a)>(b))?(b):(a)) #define NM_SWAP(a,b,tmp) {(tmp)=(a);(a)=(b);(b)=(tmp);} @@ -346,55 +343,66 @@ #define NM_IsNVector(obj) \ (rb_obj_is_kind_of(obj, cNVector) == Qtrue) #define RB_P(OBJ) \ - rb_funcall(rb_stderr, rb_intern("print"), 1, rb_funcall(OBJ, rb_intern("object_id"), 0)); \ - rb_funcall(rb_stderr, rb_intern("puts"), 1, rb_funcall(OBJ, rb_intern("inspect"), 0)); + rb_funcall(rb_stderr, rb_intern("print"), 1, rb_funcall(OBJ, rb_intern("object_id"), 0)); \ + rb_funcall(rb_stderr, rb_intern("puts"), 1, rb_funcall(OBJ, rb_intern("inspect"), 0)); #ifdef __cplusplus typedef VALUE (*METHOD)(...); //}; // end of namespace nm #endif +// In the init code below, we need to use NMATRIX for c++ and NM_NMATRIX for c +// this macro chooses the correct one: +#ifdef __cplusplus + #define _NMATRIX NMATRIX + #define _STORAGE STORAGE +#else + #define _NMATRIX NM_NMATRIX + #define _STORAGE NM_STORAGE +#endif + /* * Functions */ #ifdef __cplusplus - extern "C" { #endif - void Init_nmatrix(); + void Init_nmatrix(); + // External API + VALUE rb_nmatrix_dense_create(NM_DECL_ENUM(dtype_t, dtype), size_t* shape, size_t dim, void* elements, size_t length); + VALUE rb_nvector_dense_create(NM_DECL_ENUM(dtype_t, dtype), void* elements, size_t length); - // External API - VALUE rb_nmatrix_dense_create(NM_DECL_ENUM(dtype_t, dtype), size_t* shape, size_t dim, void* elements, size_t length); - VALUE rb_nvector_dense_create(NM_DECL_ENUM(dtype_t, dtype), void* elements, size_t length); + NM_DECL_ENUM(dtype_t, nm_dtype_guess(VALUE)); // (This is a function) + NM_DECL_ENUM(dtype_t, nm_dtype_min(VALUE)); - NM_DECL_ENUM(dtype_t, nm_dtype_guess(VALUE)); // (This is a function) - NM_DECL_ENUM(dtype_t, nm_dtype_min(VALUE)); - // Non-API functions needed by other cpp files. - NMATRIX* nm_create(NM_DECL_ENUM(stype_t, stype), STORAGE* storage); - NMATRIX* nm_cast_with_ctype_args(NMATRIX* self, NM_DECL_ENUM(stype_t, new_stype), NM_DECL_ENUM(dtype_t, new_dtype), void* init_ptr); - VALUE nm_cast(VALUE self, VALUE new_stype_symbol, VALUE new_dtype_symbol, VALUE init); - void nm_mark(NMATRIX* mat); - void nm_delete(NMATRIX* mat); - void nm_delete_ref(NMATRIX* mat); + _NMATRIX* nm_create(NM_DECL_ENUM(stype_t, stype), _STORAGE* storage); + _NMATRIX* nm_cast_with_ctype_args(_NMATRIX* self, NM_DECL_ENUM(stype_t, new_stype), NM_DECL_ENUM(dtype_t, new_dtype), void* init_ptr); + VALUE nm_cast(VALUE self, VALUE new_stype_symbol, VALUE new_dtype_symbol, VALUE init); + void nm_mark(_NMATRIX* mat); + void nm_delete(_NMATRIX* mat); + void nm_delete_ref(_NMATRIX* mat); void nm_register_values(VALUE* vals, size_t n); void nm_register_value(VALUE* val); void nm_unregister_value(VALUE* val); void nm_unregister_values(VALUE* vals, size_t n); - void nm_register_storage(NM_DECL_ENUM(stype_t, stype), const STORAGE* storage); - void nm_unregister_storage(NM_DECL_ENUM(stype_t, stype), const STORAGE* storage); - void nm_register_nmatrix(NMATRIX* nmatrix); - void nm_unregister_nmatrix(NMATRIX* nmatrix); - void nm_completely_unregister_value(VALUE* val); + void nm_register_storage(NM_DECL_ENUM(stype_t, stype), const _STORAGE* storage); + void nm_unregister_storage(NM_DECL_ENUM(stype_t, stype), const _STORAGE* storage); + void nm_register_nmatrix(_NMATRIX* nmatrix); + void nm_unregister_nmatrix(_NMATRIX* nmatrix); + void nm_completely_unregister_value(VALUE* val); + #ifdef __cplusplus } - #endif + +#undef _NMATRIX +#undef _STORAGE #endif // NMATRIX_H