You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
lua-zmq/src/pre_generated-zmq.nobj.c

2391 lines
64 KiB
C

/***********************************************************************************************
************************************************************************************************
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!!!!!!!! Warning this file was generated from a set of *.nobj.lua definition files !!!!!!!!!!!!!
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
************************************************************************************************
***********************************************************************************************/
#include "lua.h"
#include "lauxlib.h"
#include "lualib.h"
#include <string.h>
#include "zmq.h"
#define REG_PACKAGE_IS_CONSTRUCTOR 0
#define REG_OBJECTS_AS_GLOBALS 0
#define OBJ_DATA_HIDDEN_METATABLE 1
#define LUAJIT_FFI 1
#define USE_FIELD_GET_SET_METHODS 0
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#ifdef _MSC_VER
/* define some types that we need. */
typedef __int32 int32_t;
typedef unsigned __int32 uint32_t;
#define FUNC_UNUSED
#else
#include <stdint.h>
#define FUNC_UNUSED __attribute__((unused))
#endif
#if defined(__GNUC__) && (__GNUC__ >= 4)
#define assert_obj_type(type, obj) \
assert(__builtin_types_compatible_p(typeof(obj), type *))
#else
#define assert_obj_type(type, obj)
#endif
#ifndef obj_type_free
#define obj_type_free(type, obj) do { \
assert_obj_type(type, obj); \
free((obj)); \
} while(0)
#endif
#ifndef obj_type_new
#define obj_type_new(type, obj) do { \
assert_obj_type(type, obj); \
(obj) = malloc(sizeof(type)); \
} while(0)
#endif
typedef struct obj_type obj_type;
typedef void (*base_caster_t)(void **obj);
typedef void (*dyn_caster_t)(void **obj, obj_type **type);
#define OBJ_TYPE_FLAG_WEAK_REF (1<<0)
#define OBJ_TYPE_SIMPLE (1<<1)
struct obj_type {
dyn_caster_t dcaster; /**< caster to support casting to sub-objects. */
int32_t id; /**< type's id. */
uint32_t flags; /**< type's flags (weak refs) */
const char *name; /**< type's object name. */
};
typedef struct obj_base {
int32_t id;
base_caster_t bcaster;
} obj_base;
typedef enum obj_const_type {
CONST_UNKOWN = 0,
CONST_BOOLEAN = 1,
CONST_NUMBER = 2,
CONST_STRING = 3
} obj_const_type;
typedef struct obj_const {
const char *name; /**< constant's name. */
const char *str;
double num;
obj_const_type type;
} obj_const;
typedef enum obj_field_type {
TYPE_UNKOWN = 0,
TYPE_UINT8 = 1,
TYPE_UINT16 = 2,
TYPE_UINT32 = 3,
TYPE_UINT64 = 4,
TYPE_INT8 = 5,
TYPE_INT16 = 6,
TYPE_INT32 = 7,
TYPE_INT64 = 8,
TYPE_DOUBLE = 9,
TYPE_FLOAT = 10,
TYPE_STRING = 11
} obj_field_type;
typedef struct obj_field {
const char *name; /**< field's name. */
uint32_t offset; /**< offset to field's data. */
obj_field_type type; /**< field's data type. */
uint32_t flags; /**< is_writable:1bit */
} obj_field;
typedef struct reg_sub_module {
obj_type *type;
int is_package;
const luaL_reg *pub_funcs;
const luaL_reg *methods;
const luaL_reg *metas;
const obj_base *bases;
const obj_field *fields;
const obj_const *constants;
} reg_sub_module;
#define OBJ_UDATA_FLAG_OWN (1<<0)
#define OBJ_UDATA_FLAG_LOOKUP (1<<1)
#define OBJ_UDATA_LAST_FLAG (OBJ_UDATA_FLAG_LOOKUP)
typedef struct obj_udata {
void *obj;
uint32_t flags; /**< lua_own:1bit */
} obj_udata;
/* use static pointer as key to weak userdata table. */
static char *obj_udata_weak_ref_key = "obj_udata_weak_ref_key";
#if LUAJIT_FFI
typedef struct ffi_export_symbol {
const char *name;
void *sym;
} ffi_export_symbol;
#endif
#define obj_type_id_zmq_msg_t 0
#define obj_type_zmq_msg_t_check(L, _index) \
(zmq_msg_t *)obj_simple_udata_luacheck(L, _index, &(obj_type_zmq_msg_t))
#define obj_type_zmq_msg_t_delete(L, _index, flags) \
(zmq_msg_t *)obj_simple_udata_luadelete(L, _index, &(obj_type_zmq_msg_t), flags)
#define obj_type_zmq_msg_t_push(L, obj, flags) \
obj_simple_udata_luapush(L, obj, sizeof(zmq_msg_t), &(obj_type_zmq_msg_t))
#define obj_type_id_ZMQ_Socket 1
#define obj_type_ZMQ_Socket_check(L, _index) \
obj_udata_luacheck(L, _index, &(obj_type_ZMQ_Socket))
#define obj_type_ZMQ_Socket_delete(L, _index, flags) \
obj_udata_luadelete(L, _index, &(obj_type_ZMQ_Socket), flags)
#define obj_type_ZMQ_Socket_push(L, obj, flags) \
obj_udata_luapush_weak(L, (void *)obj, &(obj_type_ZMQ_Socket), flags)
#define obj_type_id_ZMQ_Ctx 2
#define obj_type_ZMQ_Ctx_check(L, _index) \
obj_udata_luacheck(L, _index, &(obj_type_ZMQ_Ctx))
#define obj_type_ZMQ_Ctx_delete(L, _index, flags) \
obj_udata_luadelete(L, _index, &(obj_type_ZMQ_Ctx), flags)
#define obj_type_ZMQ_Ctx_push(L, obj, flags) \
obj_udata_luapush_weak(L, (void *)obj, &(obj_type_ZMQ_Ctx), flags)
typedef int ZMQ_Error;
static void error_code__ZMQ_Error__push(lua_State *L, ZMQ_Error err);
static obj_type obj_type_zmq_msg_t = { NULL, 0, OBJ_TYPE_SIMPLE, "zmq_msg_t" };
static obj_type obj_type_ZMQ_Socket = { NULL, 1, OBJ_TYPE_FLAG_WEAK_REF, "ZMQ_Socket" };
static obj_type obj_type_ZMQ_Ctx = { NULL, 2, OBJ_TYPE_FLAG_WEAK_REF, "ZMQ_Ctx" };
#ifndef REG_PACKAGE_IS_CONSTRUCTOR
#define REG_PACKAGE_IS_CONSTRUCTOR 1
#endif
#ifndef REG_OBJECTS_AS_GLOBALS
#define REG_OBJECTS_AS_GLOBALS 0
#endif
#ifndef OBJ_DATA_HIDDEN_METATABLE
#define OBJ_DATA_HIDDEN_METATABLE 1
#endif
static FUNC_UNUSED obj_udata *obj_udata_toobj(lua_State *L, int _index) {
obj_udata *ud;
size_t len;
/* make sure it's a userdata value. */
ud = (obj_udata *)lua_touserdata(L, _index);
if(ud == NULL) {
luaL_typerror(L, _index, "userdata"); /* is not a userdata value. */
}
/* verify userdata size. */
len = lua_objlen(L, _index);
if(len != sizeof(obj_udata)) {
/* This shouldn't be possible */
luaL_error(L, "invalid userdata size: size=%d, expected=%d", len, sizeof(obj_udata));
}
return ud;
}
static FUNC_UNUSED int obj_udata_is_compatible(lua_State *L, obj_udata *ud, void **obj, base_caster_t *caster, obj_type *type) {
obj_base *base;
obj_type *ud_type;
lua_pushlightuserdata(L, type);
lua_rawget(L, LUA_REGISTRYINDEX); /* type's metatable. */
if(lua_rawequal(L, -1, -2)) {
*obj = ud->obj;
/* same type no casting needed. */
return 1;
} else {
/* Different types see if we can cast to the required type. */
lua_rawgeti(L, -2, type->id);
base = lua_touserdata(L, -1);
lua_pop(L, 1); /* pop obj_base or nil */
if(base != NULL) {
*caster = base->bcaster;
/* get the obj_type for this userdata. */
lua_pushliteral(L, ".type");
lua_rawget(L, -3); /* type's metatable. */
ud_type = lua_touserdata(L, -1);
lua_pop(L, 1); /* pop obj_type or nil */
if(base == NULL) {
luaL_error(L, "bad userdata, missing type info.");
return 0;
}
/* check if userdata is a simple object. */
if(ud_type->flags & OBJ_TYPE_SIMPLE) {
*obj = ud;
} else {
*obj = ud->obj;
}
return 1;
}
}
return 0;
}
static FUNC_UNUSED obj_udata *obj_udata_luacheck_internal(lua_State *L, int _index, void **obj, obj_type *type) {
obj_udata *ud;
base_caster_t caster = NULL;
/* make sure it's a userdata value. */
ud = (obj_udata *)lua_touserdata(L, _index);
if(ud != NULL) {
/* check object type by comparing metatables. */
if(lua_getmetatable(L, _index)) {
if(obj_udata_is_compatible(L, ud, obj, &(caster), type)) {
lua_pop(L, 2); /* pop both metatables. */
/* apply caster function if needed. */
if(caster != NULL && *obj != NULL) {
caster(obj);
}
/* check object pointer. */
if(*obj == NULL) {
luaL_error(L, "null %s", type->name); /* object was garbage collected? */
}
return ud;
}
}
}
luaL_typerror(L, _index, type->name); /* is not a userdata value. */
return NULL;
}
static FUNC_UNUSED void *obj_udata_luacheck(lua_State *L, int _index, obj_type *type) {
void *obj = NULL;
obj_udata_luacheck_internal(L, _index, &(obj), type);
return obj;
}
static FUNC_UNUSED void *obj_udata_luadelete(lua_State *L, int _index, obj_type *type, int *flags) {
void *obj;
obj_udata *ud = obj_udata_luacheck_internal(L, _index, &(obj), type);
*flags = ud->flags;
/* null userdata. */
ud->obj = NULL;
ud->flags = 0;
/* clear the metatable to invalidate userdata. */
lua_pushnil(L);
lua_setmetatable(L, _index);
return obj;
}
static FUNC_UNUSED void obj_udata_luapush(lua_State *L, void *obj, obj_type *type, int flags) {
obj_udata *ud;
/* convert NULL's into Lua nil's. */
if(obj == NULL) {
lua_pushnil(L);
return;
}
/* check for type caster. */
if(type->dcaster) {
(type->dcaster)(&obj, &type);
}
/* create new userdata. */
ud = (obj_udata *)lua_newuserdata(L, sizeof(obj_udata));
ud->obj = obj;
ud->flags = flags;
/* get obj_type metatable. */
lua_pushlightuserdata(L, type);
lua_rawget(L, LUA_REGISTRYINDEX); /* type's metatable. */
lua_setmetatable(L, -2);
}
static FUNC_UNUSED void obj_udata_luapush_weak(lua_State *L, void *obj, obj_type *type, int flags) {
obj_udata *ud;
/* convert NULL's into Lua nil's. */
if(obj == NULL) {
lua_pushnil(L);
return;
}
/* check for type caster. */
if(type->dcaster) {
(type->dcaster)(&obj, &type);
}
/* get objects weak table. */
lua_pushlightuserdata(L, obj_udata_weak_ref_key);
lua_rawget(L, LUA_REGISTRYINDEX); /* weak ref table. */
/* lookup userdata instance from pointer. */
lua_pushlightuserdata(L, obj);
lua_rawget(L, -2);
if(!lua_isnil(L, -1)) {
lua_remove(L, -2); /* remove objects table. */
return;
}
lua_pop(L, 1); /* pop nil. */
/* create new userdata. */
ud = (obj_udata *)lua_newuserdata(L, sizeof(obj_udata));
/* init. obj_udata. */
ud->obj = obj;
ud->flags = flags;
/* get obj_type metatable. */
lua_pushlightuserdata(L, type);
lua_rawget(L, LUA_REGISTRYINDEX); /* type's metatable. */
lua_setmetatable(L, -2);
/* add weak reference to object. */
lua_pushlightuserdata(L, obj); /* push object pointer as the 'key' */
lua_pushvalue(L, -2); /* push object's udata */
lua_rawset(L, -4); /* add weak reference to object. */
lua_remove(L, -2); /* remove objects table. */
}
/* default object equal method. */
static FUNC_UNUSED int obj_udata_default_equal(lua_State *L) {
obj_udata *ud1 = obj_udata_toobj(L, 1);
obj_udata *ud2 = obj_udata_toobj(L, 2);
lua_pushboolean(L, (ud1->obj == ud2->obj));
return 1;
}
/* default object tostring method. */
static FUNC_UNUSED int obj_udata_default_tostring(lua_State *L) {
obj_udata *ud = obj_udata_toobj(L, 1);
/* get object's metatable. */
lua_getmetatable(L, 1);
lua_remove(L, 1); /* remove userdata. */
/* get the object's name from the metatable */
lua_getfield(L, 1, ".name");
lua_remove(L, 1); /* remove metatable */
/* push object's pointer */
lua_pushfstring(L, ": %p, flags=%d", ud->obj, ud->flags);
lua_concat(L, 2);
return 1;
}
/*
* Simple userdata objects.
*/
static FUNC_UNUSED void *obj_simple_udata_toobj(lua_State *L, int _index) {
void *ud;
/* make sure it's a userdata value. */
ud = lua_touserdata(L, _index);
if(ud == NULL) {
luaL_typerror(L, _index, "userdata"); /* is not a userdata value. */
}
return ud;
}
static FUNC_UNUSED void * obj_simple_udata_luacheck(lua_State *L, int _index, obj_type *type) {
void *ud;
/* make sure it's a userdata value. */
ud = lua_touserdata(L, _index);
if(ud != NULL) {
/* check object type by comparing metatables. */
if(lua_getmetatable(L, _index)) {
lua_pushlightuserdata(L, type);
lua_rawget(L, LUA_REGISTRYINDEX); /* type's metatable. */
if(lua_rawequal(L, -1, -2)) {
lua_pop(L, 2); /* pop both metatables. */
return ud;
}
}
}
luaL_typerror(L, _index, type->name); /* is not a userdata value. */
return NULL;
}
static FUNC_UNUSED void * obj_simple_udata_luadelete(lua_State *L, int _index, obj_type *type, int *flags) {
void *obj;
obj = obj_simple_udata_luacheck(L, _index, type);
*flags = OBJ_UDATA_FLAG_OWN;
/* clear the metatable to invalidate userdata. */
lua_pushnil(L);
lua_setmetatable(L, _index);
return obj;
}
static FUNC_UNUSED void obj_simple_udata_luapush(lua_State *L, void *obj, int size, obj_type *type)
{
/* create new userdata. */
void *ud = lua_newuserdata(L, size);
memcpy(ud, obj, size);
/* get obj_type metatable. */
lua_pushlightuserdata(L, type);
lua_rawget(L, LUA_REGISTRYINDEX); /* type's metatable. */
lua_setmetatable(L, -2);
}
/* default simple object equal method. */
static FUNC_UNUSED int obj_simple_udata_default_equal(lua_State *L) {
void *ud1 = obj_simple_udata_toobj(L, 1);
size_t len1 = lua_objlen(L, 1);
void *ud2 = obj_simple_udata_toobj(L, 2);
size_t len2 = lua_objlen(L, 2);
if(len1 == len2) {
lua_pushboolean(L, (memcmp(ud1, ud2, len1) == 0));
} else {
lua_pushboolean(L, 0);
}
return 1;
}
/* default simple object tostring method. */
static FUNC_UNUSED int obj_simple_udata_default_tostring(lua_State *L) {
void *ud = obj_simple_udata_toobj(L, 1);
/* get object's metatable. */
lua_getmetatable(L, 1);
lua_remove(L, 1); /* remove userdata. */
/* get the object's name from the metatable */
lua_getfield(L, 1, ".name");
lua_remove(L, 1); /* remove metatable */
/* push object's pointer */
lua_pushfstring(L, ": %p", ud);
lua_concat(L, 2);
return 1;
}
static int obj_constructor_call_wrapper(lua_State *L) {
/* replace '__call' table with constructor function. */
lua_pushvalue(L, lua_upvalueindex(1));
lua_replace(L, 1);
/* call constructor function with all parameters after the '__call' table. */
lua_call(L, lua_gettop(L) - 1, LUA_MULTRET);
/* return all results from constructor. */
return lua_gettop(L);
}
static void obj_type_register_constants(lua_State *L, const obj_const *constants, int tab_idx) {
/* register constants. */
while(constants->name != NULL) {
lua_pushstring(L, constants->name);
switch(constants->type) {
case CONST_BOOLEAN:
lua_pushboolean(L, constants->num != 0.0);
break;
case CONST_NUMBER:
lua_pushnumber(L, constants->num);
break;
case CONST_STRING:
lua_pushstring(L, constants->str);
break;
default:
lua_pushnil(L);
break;
}
lua_rawset(L, tab_idx - 2);
constants++;
}
}
static void obj_type_register_package(lua_State *L, const reg_sub_module *type_reg) {
obj_type *type = type_reg->type;
const luaL_reg *reg_list = type_reg->pub_funcs;
/* create public functions table. */
if(reg_list != NULL && reg_list[0].name != NULL) {
/* register functions */
luaL_register(L, NULL, reg_list);
}
obj_type_register_constants(L, type_reg->constants, -1);
lua_pop(L, 1); /* drop package table */
}
static void obj_type_register(lua_State *L, const reg_sub_module *type_reg, int priv_table) {
const luaL_reg *reg_list;
obj_type *type = type_reg->type;
const obj_base *base = type_reg->bases;
if(type_reg->is_package == 1) {
return obj_type_register_package(L, type_reg);
}
/* create public functions table. */
reg_list = type_reg->pub_funcs;
if(reg_list != NULL && reg_list[0].name != NULL) {
/* register "constructors" as to object's public API */
luaL_register(L, NULL, reg_list); /* fill public API table. */
/* make public API table callable as the default constructor. */
lua_newtable(L); /* create metatable */
lua_pushliteral(L, "__call");
lua_pushcfunction(L, reg_list[0].func); /* push first constructor function. */
lua_pushcclosure(L, obj_constructor_call_wrapper, 1); /* make __call wrapper. */
lua_rawset(L, -3); /* metatable.__call = <default constructor> */
lua_setmetatable(L, -2);
lua_pop(L, 1); /* pop public API table, don't need it any more. */
/* create methods table. */
lua_newtable(L);
} else {
/* register all methods as public functions. */
}
luaL_register(L, NULL, type_reg->methods); /* fill methods table. */
luaL_newmetatable(L, type->name); /* create metatable */
lua_pushliteral(L, ".name");
lua_pushstring(L, type->name);
lua_rawset(L, -3); /* metatable['.name'] = "<object_name>" */
lua_pushliteral(L, ".type");
lua_pushlightuserdata(L, type);
lua_rawset(L, -3); /* metatable['.type'] = lightuserdata -> obj_type */
lua_pushlightuserdata(L, type);
lua_pushvalue(L, -2); /* dup metatable. */
lua_rawset(L, LUA_REGISTRYINDEX); /* REGISTRY[type] = metatable */
#if LUAJIT_FFI
/* add metatable to 'priv_table' */
lua_pushstring(L, type->name);
lua_pushvalue(L, -2); /* dup metatable. */
lua_rawset(L, priv_table); /* priv_table["<object_name>"] = metatable */
#endif
luaL_register(L, NULL, type_reg->metas); /* fill metatable */
/* add obj_bases to metatable. */
while(base->id >= 0) {
lua_pushlightuserdata(L, (void *)base);
lua_rawseti(L, -2, base->id);
base++;
}
obj_type_register_constants(L, type_reg->constants, -2);
lua_pushliteral(L, "__index");
lua_pushvalue(L, -3); /* dup methods table */
lua_rawset(L, -3); /* metatable.__index = methods */
#if OBJ_DATA_HIDDEN_METATABLE
lua_pushliteral(L, "__metatable");
lua_pushvalue(L, -3); /* dup methods table */
lua_rawset(L, -3); /* hide metatable:
metatable.__metatable = methods */
#endif
lua_pop(L, 2); /* drop metatable & methods */
}
static FUNC_UNUSED int lua_checktype_ref(lua_State *L, int _index, int _type) {
luaL_checktype(L,_index,_type);
lua_pushvalue(L,_index);
return luaL_ref(L, LUA_REGISTRYINDEX);
}
#if LUAJIT_FFI
static int nobj_udata_new_ffi(lua_State *L) {
size_t size = luaL_checkinteger(L, 1);
void *ud;
luaL_checktype(L, 2, LUA_TTABLE);
lua_settop(L, 2);
/* create userdata. */
ud = lua_newuserdata(L, size);
lua_replace(L, 1);
/* set userdata's metatable. */
lua_setmetatable(L, 1);
return 1;
}
static int nobj_try_loading_ffi(lua_State *L, const char *ffi_mod_name,
const char *ffi_init_code, const ffi_export_symbol *ffi_exports, int priv_table)
{
int err;
/* export symbols to priv_table. */
while(ffi_exports->name != NULL) {
lua_pushstring(L, ffi_exports->name);
lua_pushlightuserdata(L, ffi_exports->sym);
lua_settable(L, priv_table);
ffi_exports++;
}
err = luaL_loadbuffer(L, ffi_init_code, strlen(ffi_init_code), ffi_mod_name);
if(0 == err) {
lua_pushvalue(L, -2); /* dup C module's table. */
lua_pushvalue(L, priv_table); /* move priv_table to top of stack. */
lua_remove(L, priv_table);
lua_pushcfunction(L, nobj_udata_new_ffi);
err = lua_pcall(L, 3, 0, 0);
}
if(err) {
const char *msg = "<err not a string>";
if(lua_isstring(L, -1)) {
msg = lua_tostring(L, -1);
}
printf("Failed to install FFI-based bindings: %s\n", msg);
lua_pop(L, 1); /* pop error message. */
}
return err;
}
#endif
static const char zmq_ffi_lua_code[] = "\
local _M, _priv, udata_new = ...\n\
\n\
local band = bit.band\n\
local d_getmetatable = debug.getmetatable\n\
local d_setmetatable = debug.setmetatable\n\
\n\
-- try loading luajit's ffi\n\
local stat, ffi=pcall(require,\"ffi\")\n\
if not stat then\n\
return\n\
end\n\
-- check if ffi is disabled.\n\
if disable_ffi then\n\
print(\"FFI disabled: Using standard Lua api interface.\")\n\
return\n\
end\n\
\n\
local OBJ_UDATA_FLAG_OWN = 1\n\
local OBJ_UDATA_FLAG_LOOKUP = 2\n\
local OBJ_UDATA_LAST_FLAG = OBJ_UDATA_FLAG_LOOKUP\n\
\n\
local OBJ_TYPE_FLAG_WEAK_REF = 1\n\
local OBJ_TYPE_SIMPLE = 2\n\
\n\
ffi.cdef[[\n\
\n\
typedef struct obj_type obj_type;\n\
\n\
typedef void (*base_caster_t)(void **obj);\n\
\n\
typedef void (*dyn_caster_t)(void **obj, obj_type **type);\n\
\n\
struct obj_type {\n\
dyn_caster_t dcaster; /**< caster to support casting to sub-objects. */\n\
int32_t id; /**< type's id. */\n\
uint32_t flags; /**< type's flags (weak refs) */\n\
const char *name; /**< type's object name. */\n\
};\n\
\n\
typedef struct obj_base {\n\
int32_t id;\n\
base_caster_t bcaster;\n\
} obj_base;\n\
\n\
typedef struct obj_udata {\n\
void *obj;\n\
uint32_t flags; /**< lua_own:1bit */\n\
} obj_udata;\n\
\n\
]]\n\
\n\
local obj_type_ptr = ffi.typeof\"obj_type *\"\n\
local obj_udata_ptr = ffi.typeof\"obj_udata *\"\n\
local obj_simple_udata_ptr = ffi.typeof\"void *\"\n\
local obj_udata_size = ffi.sizeof\"obj_udata\"\n\
\n\
-- cache mapping of cdata to userdata\n\
local weak_objects = setmetatable({}, { __mode = \"v\" })\n\
\n\
local function obj_udata_luacheck_internal(obj, type_mt)\n\
local obj_mt = d_getmetatable(obj)\n\
if obj_mt == type_mt then\n\
-- convert userdata to cdata.\n\
return obj_udata_ptr(obj)\n\
end\n\
error(\"(expected `\" .. type_mt['.name'] .. \"`, got \" .. type(obj) .. \")\", 3)\n\
end\n\
\n\
local function obj_udata_luacheck(obj, type_mt)\n\
local ud = obj_udata_luacheck_internal(obj, type_mt)\n\
return ud.obj\n\
end\n\
\n\
local function obj_udata_luadelete(ud_obj, type_mt)\n\
local ud = obj_udata_luacheck_internal(ud_obj, type_mt)\n\
local obj, flags = ud.obj, ud.flags\n\
-- null userdata.\n\
ud.obj = nil\n\
ud.flags = 0\n\
-- invalid userdata, by setting the metatable to nil.\n\
d_setmetatable(ud_obj, nil)\n\
return obj, flags\n\
end\n\
\n\
local function obj_udata_luapush(obj, type_mt, obj_type, flags)\n\
if obj == nil then return end\n\
\n\
-- apply type's dynamic caster.\n\
if obj_type.dcaster ~= nil then\n\
local obj_ptr = ffi.new(\"void *[1]\", obj)\n\
local type_ptr = ffi.new(\"obj_type *[1]\", obj_type)\n\
obj_type.dcaster(obj_ptr, type_ptr)\n\
obj = obj_ptr[1]\n\
type = type_ptr[1]\n\
end\n\
\n\
-- create new userdata\n\
ud_obj = udata_new(obj_udata_size, type_mt)\n\
local ud = obj_udata_ptr(ud_obj)\n\
-- init. object\n\
ud.obj = obj\n\
ud.flags = flags\n\
\n\
return ud_obj\n\
end\n\
\n\
local function obj_udata_luapush_weak(obj, type_mt, obj_type, flags)\n\
if obj == nil then return end\n\
\n\
-- apply type's dynamic caster.\n\
if obj_type.dcaster ~= nil then\n\
local obj_ptr = ffi.new(\"void *[1]\", obj)\n\
local type_ptr = ffi.new(\"obj_type *[1]\", obj_type)\n\
obj_type.dcaster(obj_ptr, type_ptr)\n\
obj = obj_ptr[1]\n\
type = type_ptr[1]\n\
end\n\
\n\
-- lookup object in weak ref. table.\n\
local obj_key = tonumber(ffi.cast('uintptr_t', obj))\n\
local ud_obj = weak_objects[obj_key]\n\
if ud_obj ~= nil then return ud_obj end\n\
\n\
-- create new userdata\n\
ud_obj = udata_new(obj_udata_size, type_mt)\n\
local ud = obj_udata_ptr(ud_obj)\n\
-- init. object\n\
ud.obj = obj\n\
ud.flags = flags\n\
\n\
-- cache weak reference to object.\n\
weak_objects[obj_key] = ud_obj\n\
\n\
return ud_obj\n\
end\n\
\n\
local function obj_simple_udata_luacheck(ud_obj, type_mt)\n\
local obj_mt = d_getmetatable(ud_obj)\n\
if obj_mt == type_mt then\n\
-- convert userdata to cdata.\n\
return obj_simple_udata_ptr(ud_obj)\n\
end\n\
error(\"(expected `\" .. type_mt['.name'] .. \"`, got \" .. type(ud_obj) .. \")\", 3)\n\
end\n\
\n\
local function obj_simple_udata_luadelete(ud_obj, type_mt)\n\
local c_obj = obj_simple_udata_luacheck(ud_obj, type_mt)\n\
-- invalid userdata, by setting the metatable to nil.\n\
d_setmetatable(ud_obj, nil)\n\
return c_obj, OBJ_UDATA_FLAG_OWN\n\
end\n\
\n\
local function obj_simple_udata_luapush(c_obj, size, type_mt)\n\
if c_obj == nil then return end\n\
\n\
-- create new userdata\n\
ud_obj = udata_new(size, type_mt)\n\
local data = obj_simple_udata_ptr(ud_obj)\n\
-- init. object\n\
ffi.copy(data, c_obj, size)\n\
\n\
return ud_obj\n\
end\n\
\n\
ffi.cdef[[\n\
typedef const char * (*get_zmq_strerror_func)();\n\
\n\
typedef int ZMQ_Error;\n\
\n\
\n\
typedef struct zmq_msg_t\n\
{\n\
void *content;\n\
unsigned char flags;\n\
unsigned char vsm_size;\n\
unsigned char vsm_data [30]; /* that '30' is from 'MAX_VSM_SIZE' */\n\
} zmq_msg_t;\n\
\n\
typedef void (zmq_free_fn) (void *data, void *hint);\n\
\n\
int zmq_msg_init (zmq_msg_t *msg);\n\
int zmq_msg_init_size (zmq_msg_t *msg, size_t size);\n\
int zmq_msg_init_data (zmq_msg_t *msg, void *data, size_t size, zmq_free_fn *ffn, void *hint);\n\
\n\
\n\
ZMQ_Error zmq_msg_close(zmq_msg_t * this);\n\
\n\
ZMQ_Error zmq_msg_close(zmq_msg_t * this);\n\
\n\
ZMQ_Error zmq_msg_move(zmq_msg_t * this, zmq_msg_t * src);\n\
\n\
ZMQ_Error zmq_msg_copy(zmq_msg_t * this, zmq_msg_t * src);\n\
\n\
void * zmq_msg_data(zmq_msg_t * this);\n\
\n\
size_t zmq_msg_size(zmq_msg_t * this);\n\
\n\
typedef void * ZMQ_Socket;\n\
\n\
ZMQ_Error zmq_close(ZMQ_Socket * this);\n\
\n\
ZMQ_Error zmq_bind(ZMQ_Socket * this, const char * addr);\n\
\n\
ZMQ_Error zmq_connect(ZMQ_Socket * this, const char * addr);\n\
\n\
int zmq_setsockopt (void *s, int option, const void *optval, size_t optvallen);\n\
int zmq_getsockopt (void *s, int option, void *optval, size_t *optvallen);\n\
\n\
ZMQ_Error zmq_send(ZMQ_Socket * this, zmq_msg_t * msg, int flags);\n\
\n\
typedef ZMQ_Error (*simple_zmq_send_func)(ZMQ_Socket sock, const char *data, size_t data_len, int flags);\n\
\n\
ZMQ_Error zmq_recv(ZMQ_Socket * this, zmq_msg_t * msg, int flags);\n\
\n\
typedef void * ZMQ_Ctx;\n\
\n\
ZMQ_Error zmq_term(ZMQ_Ctx * this);\n\
\n\
ZMQ_Socket zmq_socket(ZMQ_Ctx * this, int type);\n\
\n\
ZMQ_Ctx zmq_init(int io_threads);\n\
\n\
ZMQ_Error zmq_device(int device, ZMQ_Socket insock, ZMQ_Socket outsock);\n\
\n\
\n\
]]\n\
\n\
local zmq_msg_t_mt = _priv[\"zmq_msg_t\"]\n\
local zmq_msg_t_type = obj_type_ptr(zmq_msg_t_mt[\".type\"])\n\
local zmq_msg_t_meth = zmq_msg_t_mt.__index\n\
local zmq_msg_t_objects = setmetatable({}, { __mode = \"k\" })\n\
\n\
local function obj_type_zmq_msg_t_check(ud_obj)\n\
local c_obj = zmq_msg_t_objects[ud_obj]\n\
if c_obj == nil then\n\
-- cdata object not in cache\n\
c_obj = obj_simple_udata_luacheck(ud_obj, zmq_msg_t_mt)\n\
zmq_msg_t_objects[ud_obj] = c_obj\n\
end\n\
return c_obj\n\
end\n\
\n\
local function obj_type_zmq_msg_t_delete(ud_obj)\n\
zmq_msg_t_objects[ud_obj] = nil\n\
return obj_simple_udata_luadelete(ud_obj, zmq_msg_t_mt)\n\
end\n\
\n\
local zmq_msg_t_sizeof = ffi.sizeof\"zmq_msg_t\"\n\
local function obj_type_zmq_msg_t_push(c_obj)\n\
local ud_obj = obj_simple_udata_luapush(c_obj, zmq_msg_t_sizeof, zmq_msg_t_mt)\n\
zmq_msg_t_objects[ud_obj] = c_obj\n\
return ud_obj\n\
end\n\
\n\
\n\
local ZMQ_Socket_mt = _priv[\"ZMQ_Socket\"]\n\
local ZMQ_Socket_type = obj_type_ptr(ZMQ_Socket_mt[\".type\"])\n\
local ZMQ_Socket_meth = ZMQ_Socket_mt.__index\n\
local ZMQ_Socket_objects = setmetatable({}, { __mode = \"k\" })\n\
\n\
local function obj_type_ZMQ_Socket_check(ud_obj)\n\
local c_obj = ZMQ_Socket_objects[ud_obj]\n\
if c_obj == nil then\n\
-- cdata object not in cache\n\
c_obj = obj_udata_luacheck(ud_obj, ZMQ_Socket_mt)\n\
ZMQ_Socket_objects[ud_obj] = c_obj\n\
end\n\
return c_obj\n\
end\n\
\n\
local function obj_type_ZMQ_Socket_delete(ud_obj)\n\
ZMQ_Socket_objects[ud_obj] = nil\n\
return obj_udata_luadelete(ud_obj, ZMQ_Socket_mt)\n\
end\n\
\n\
local function obj_type_ZMQ_Socket_push(c_obj, flags)\n\
local ud_obj = obj_udata_luapush_weak(c_obj, ZMQ_Socket_mt, ZMQ_Socket_type, flags)\n\
ZMQ_Socket_objects[ud_obj] = c_obj\n\
return ud_obj\n\
end\n\
\n\
\n\
local ZMQ_Ctx_mt = _priv[\"ZMQ_Ctx\"]\n\
local ZMQ_Ctx_type = obj_type_ptr(ZMQ_Ctx_mt[\".type\"])\n\
local ZMQ_Ctx_meth = ZMQ_Ctx_mt.__index\n\
local ZMQ_Ctx_objects = setmetatable({}, { __mode = \"k\" })\n\
\n\
local function obj_type_ZMQ_Ctx_check(ud_obj)\n\
local c_obj = ZMQ_Ctx_objects[ud_obj]\n\
if c_obj == nil then\n\
-- cdata object not in cache\n\
c_obj = obj_udata_luacheck(ud_obj, ZMQ_Ctx_mt)\n\
ZMQ_Ctx_objects[ud_obj] = c_obj\n\
end\n\
return c_obj\n\
end\n\
\n\
local function obj_type_ZMQ_Ctx_delete(ud_obj)\n\
ZMQ_Ctx_objects[ud_obj] = nil\n\
return obj_udata_luadelete(ud_obj, ZMQ_Ctx_mt)\n\
end\n\
\n\
local function obj_type_ZMQ_Ctx_push(c_obj, flags)\n\
local ud_obj = obj_udata_luapush_weak(c_obj, ZMQ_Ctx_mt, ZMQ_Ctx_type, flags)\n\
ZMQ_Ctx_objects[ud_obj] = c_obj\n\
return ud_obj\n\
end\n\
\n\
\n\
local zmq_mt = _M\n\
local zmq_meth = _M\n\
local zmq_func = _M\n\
\n\
\n\
local C = ffi.load(\"zmq\",false)\n\
\n\
local OBJ_UDATA_CTX_SHOULD_FREE = (OBJ_UDATA_LAST_FLAG * 2)\n\
\n\
local get_zmq_strerror = ffi.new(\"get_zmq_strerror_func\", _priv[\"get_zmq_strerror\"])\n\
\n\
local C_get_zmq_strerror = get_zmq_strerror\n\
-- make nicer wrapper for exported error function.\n\
local function get_zmq_strerror()\n\
return ffi.string(C_get_zmq_strerror())\n\
end\n\
\n\
local function error_code__ZMQ_Error__push(err)\n\
local err_str\n\
if(0 ~= err) then\n\
err_str = get_zmq_strerror();\n\
end\n\
\n\
return err_str\n\
end\n\
\n\
\n\
-- Start \"zmq_msg_t\" FFI interface\n\
-- method: delete\n\
function zmq_msg_t_meth.delete(self)\n\
local this,this_flags = obj_type_zmq_msg_t_delete(self)\n\
if(band(this_flags,OBJ_UDATA_FLAG_OWN) == 0) then return end\n\
local rc_zmq_msg_close\n\
rc_zmq_msg_close = C.zmq_msg_close(this)\n\
-- check for error.\n\
local rc_zmq_msg_close_err\n\
if (0 ~= rc_zmq_msg_close) then\n\
rc_zmq_msg_close = false\n\
rc_zmq_msg_close_err = error_code__ZMQ_Error__push(rc_zmq_msg_close)\n\
else\n\
rc_zmq_msg_close = true\n\
end\n\
return rc_zmq_msg_close, rc_zmq_msg_close_err\n\
end\n\
\n\
-- method: close\n\
function zmq_msg_t_meth.close(self)\n\
local this = obj_type_zmq_msg_t_check(self)\n\
local rc_zmq_msg_close\n\
rc_zmq_msg_close = C.zmq_msg_close(this)\n\
-- check for error.\n\
local rc_zmq_msg_close_err\n\
if (0 ~= rc_zmq_msg_close) then\n\
rc_zmq_msg_close = false\n\
rc_zmq_msg_close_err = error_code__ZMQ_Error__push(rc_zmq_msg_close)\n\
else\n\
rc_zmq_msg_close = true\n\
end\n\
return rc_zmq_msg_close, rc_zmq_msg_close_err\n\
end\n\
\n\
-- method: move\n\
function zmq_msg_t_meth.move(self, src)\n\
local this = obj_type_zmq_msg_t_check(self)\n\
src = obj_type_zmq_msg_t_check(src)\n\
local rc_zmq_msg_move\n\
rc_zmq_msg_move = C.zmq_msg_move(this, src)\n\
-- check for error.\n\
local rc_zmq_msg_move_err\n\
if (0 ~= rc_zmq_msg_move) then\n\
rc_zmq_msg_move = false\n\
rc_zmq_msg_move_err = error_code__ZMQ_Error__push(rc_zmq_msg_move)\n\
else\n\
rc_zmq_msg_move = true\n\
end\n\
return rc_zmq_msg_move, rc_zmq_msg_move_err\n\
end\n\
\n\
-- method: copy\n\
function zmq_msg_t_meth.copy(self, src)\n\
local this = obj_type_zmq_msg_t_check(self)\n\
src = obj_type_zmq_msg_t_check(src)\n\
local rc_zmq_msg_copy\n\
rc_zmq_msg_copy = C.zmq_msg_copy(this, src)\n\
-- check for error.\n\
local rc_zmq_msg_copy_err\n\
if (0 ~= rc_zmq_msg_copy) then\n\
rc_zmq_msg_copy = false\n\
rc_zmq_msg_copy_err = error_code__ZMQ_Error__push(rc_zmq_msg_copy)\n\
else\n\
rc_zmq_msg_copy = true\n\
end\n\
return rc_zmq_msg_copy, rc_zmq_msg_copy_err\n\
end\n\
\n\
-- method: set_data\n\
function zmq_msg_t_meth.set_data(self, data)\n\
local this = obj_type_zmq_msg_t_check(self)\n\
local data_len = #data\n\
local err\n\
-- check message data size.\n\
if (C.zmq_msg_size(this) ~= data_len) then\n\
-- need to resize message.\n\
C.zmq_msg_close(this); -- close old message, to free old data.\n\
err = C.zmq_msg_init_size(this, data_len); -- re-initialize message.\n\
if (0 ~= err) then\n\
error(\"set_data() failed: \" .. get_zmq_strerror());\n\
end\n\
end\n\
-- copy data into message\n\
ffi.copy(C.zmq_msg_data(this), data, data_len);\n\
\n\
-- check for error.\n\
local err_err\n\
if (0 ~= err) then\n\
err = false\n\
err_err = error_code__ZMQ_Error__push(err)\n\
else\n\
err = true\n\
end\n\
return err, err_err\n\
end\n\
\n\
-- method: data\n\
function zmq_msg_t_meth.data(self)\n\
local this = obj_type_zmq_msg_t_check(self)\n\
local rc_zmq_msg_data\n\
rc_zmq_msg_data = C.zmq_msg_data(this)\n\
rc_zmq_msg_data = rc_zmq_msg_data\n\
return rc_zmq_msg_data\n\
end\n\
\n\
-- method: set_size\n\
function zmq_msg_t_meth.set_size(self, size)\n\
local this = obj_type_zmq_msg_t_check(self)\n\
\n\
local err\n\
-- check message data size.\n\
if (C.zmq_msg_size(this) ~= size) then\n\
-- need to resize message.\n\
C.zmq_msg_close(this); -- close old message, to free old data.\n\
err = C.zmq_msg_init_size(this, size); -- re-initialize message.\n\
if (0 ~= err) then\n\
error(\"set_size() failed: \" .. get_zmq_strerror());\n\
end\n\
end\n\
\n\
-- check for error.\n\
local err_err\n\
if (0 ~= err) then\n\
err = false\n\
err_err = error_code__ZMQ_Error__push(err)\n\
else\n\
err = true\n\
end\n\
return err, err_err\n\
end\n\
\n\
-- method: size\n\
function zmq_msg_t_meth.size(self)\n\
local this = obj_type_zmq_msg_t_check(self)\n\
local rc_zmq_msg_size\n\
rc_zmq_msg_size = C.zmq_msg_size(this)\n\
rc_zmq_msg_size = rc_zmq_msg_size\n\
return rc_zmq_msg_size\n\
end\n\
\n\
-- method: __tostring\n\
function zmq_msg_t_mt.__tostring(self)\n\
local this = obj_type_zmq_msg_t_check(self)\n\
local data_len = 0\n\
local data\n\
data = zmq_msg_data(this);\n\
data_len = zmq_msg_size(this);\n\
\n\
data = ((nil ~= data) and ffi.string(data,data_len))\n\
return data\n\
end\n\
\n\
-- End \"zmq_msg_t\" FFI interface\n\
\n\
\n\
-- Start \"ZMQ_Socket\" FFI interface\n\
-- method: close\n\
function ZMQ_Socket_meth.close(self)\n\
local this,this_flags = obj_type_ZMQ_Socket_delete(self)\n\
if(band(this_flags,OBJ_UDATA_FLAG_OWN) == 0) then return end\n\
local rc_zmq_close\n\
rc_zmq_close = C.zmq_close(this)\n\
-- check for error.\n\
local rc_zmq_close_err\n\
if (0 ~= rc_zmq_close) then\n\
rc_zmq_close = false\n\
rc_zmq_close_err = error_code__ZMQ_Error__push(rc_zmq_close)\n\
else\n\
rc_zmq_close = true\n\
end\n\
return rc_zmq_close, rc_zmq_close_err\n\
end\n\
\n\
-- method: bind\n\
function ZMQ_Socket_meth.bind(self, addr)\n\
local this = obj_type_ZMQ_Socket_check(self)\n\
local addr_len = #addr\n\
local rc_zmq_bind\n\
rc_zmq_bind = C.zmq_bind(this, addr)\n\
-- check for error.\n\
local rc_zmq_bind_err\n\
if (0 ~= rc_zmq_bind) then\n\
rc_zmq_bind = false\n\
rc_zmq_bind_err = error_code__ZMQ_Error__push(rc_zmq_bind)\n\
else\n\
rc_zmq_bind = true\n\
end\n\
return rc_zmq_bind, rc_zmq_bind_err\n\
end\n\
\n\
-- method: connect\n\
function ZMQ_Socket_meth.connect(self, addr)\n\
local this = obj_type_ZMQ_Socket_check(self)\n\
local addr_len = #addr\n\
local rc_zmq_connect\n\
rc_zmq_connect = C.zmq_connect(this, addr)\n\
-- check for error.\n\
local rc_zmq_connect_err\n\
if (0 ~= rc_zmq_connect) then\n\
rc_zmq_connect = false\n\
rc_zmq_connect_err = error_code__ZMQ_Error__push(rc_zmq_connect)\n\
else\n\
rc_zmq_connect = true\n\
end\n\
return rc_zmq_connect, rc_zmq_connect_err\n\
end\n\
\n\
-- temp. values for 'events' function.\n\
local events_tmp = ffi.new('uint32_t[1]', 0)\n\
local events_tmp_size = ffi.sizeof('uint32_t')\n\
local events_tmp_len = ffi.new('size_t[1]', events_tmp_size)\n\
local ZMQ_EVENTS = _M.EVENTS\n\
\n\
-- method: events\n\
function ZMQ_Socket_meth.events(self)\n\
local this = obj_type_ZMQ_Socket_check(self)\n\
local events\n\
local err\n\
events_tmp_len[0] = events_tmp_size\n\
err = C.zmq_getsockopt(this, ZMQ_EVENTS, events_tmp, events_tmp_len);\n\
events = events_tmp[0]\n\
\n\
if not (0 ~= err) then\n\
events = events\n\
else\n\
events = nil\n\
end\n\
err = error_code__ZMQ_Error__push(err)\n\
return events, err\n\
end\n\
\n\
-- method: send_msg\n\
function ZMQ_Socket_meth.send_msg(self, msg, flags)\n\
local this = obj_type_ZMQ_Socket_check(self)\n\
msg = obj_type_zmq_msg_t_check(msg)\n\
flags = flags or 0\n\
local rc_zmq_send\n\
rc_zmq_send = C.zmq_send(this, msg, flags)\n\
-- check for error.\n\
local rc_zmq_send_err\n\
if (0 ~= rc_zmq_send) then\n\
rc_zmq_send = false\n\
rc_zmq_send_err = error_code__ZMQ_Error__push(rc_zmq_send)\n\
else\n\
rc_zmq_send = true\n\
end\n\
return rc_zmq_send, rc_zmq_send_err\n\
end\n\
\n\
local simple_zmq_send = ffi.new(\"simple_zmq_send_func\", _priv[\"simple_zmq_send\"])\n\
\n\
-- method: send\n\
function ZMQ_Socket_meth.send(self, data, flags)\n\
local this = obj_type_ZMQ_Socket_check(self)\n\
local data_len = #data\n\
flags = flags or 0\n\
local err\n\
err = simple_zmq_send(this, data, data_len, flags);\n\
\n\
-- check for error.\n\
local err_err\n\
if (0 ~= err) then\n\
err = false\n\
err_err = error_code__ZMQ_Error__push(err)\n\
else\n\
err = true\n\
end\n\
return err, err_err\n\
end\n\
\n\
-- method: recv_msg\n\
function ZMQ_Socket_meth.recv_msg(self, msg, flags)\n\
local this = obj_type_ZMQ_Socket_check(self)\n\
msg = obj_type_zmq_msg_t_check(msg)\n\
flags = flags or 0\n\
local rc_zmq_recv\n\
rc_zmq_recv = C.zmq_recv(this, msg, flags)\n\
-- check for error.\n\
local rc_zmq_recv_err\n\
if (0 ~= rc_zmq_recv) then\n\
rc_zmq_recv = false\n\
rc_zmq_recv_err = error_code__ZMQ_Error__push(rc_zmq_recv)\n\
else\n\
rc_zmq_recv = true\n\
end\n\
return rc_zmq_recv, rc_zmq_recv_err\n\
end\n\
\n\
local tmp_msg = ffi.new('zmq_msg_t')\n\
\n\
-- method: recv\n\
function ZMQ_Socket_meth.recv(self, flags)\n\
local this = obj_type_ZMQ_Socket_check(self)\n\
flags = flags or 0\n\
local data_len = 0\n\
local data\n\
local err\n\
local msg = tmp_msg\n\
-- initialize blank message.\n\
if C.zmq_msg_init(msg) < 0 then\n\
return nil, get_zmq_strerror()\n\
end\n\
\n\
-- receive message\n\
err = C.zmq_recv(this, msg, flags)\n\
if 0 == err then\n\
local data = ffi.string(C.zmq_msg_data(msg), C.zmq_msg_size(msg))\n\
-- close message\n\
C.zmq_msg_close(msg)\n\
return data\n\
end\n\
\n\
if not (0 ~= err) then\n\
data = ((nil ~= data) and ffi.string(data,data_len))\n\
else\n\
data = nil\n\
end\n\
err = error_code__ZMQ_Error__push(err)\n\
-- close message\n\
C.zmq_msg_close(msg)\n\
\n\
return data, err\n\
end\n\
\n\
-- End \"ZMQ_Socket\" FFI interface\n\
\n\
\n\
-- Start \"ZMQ_Ctx\" FFI interface\n\
-- method: term\n\
function ZMQ_Ctx_meth.term(self)\n\
local this = obj_type_ZMQ_Ctx_check(self)\n\
local rc_zmq_term\n\
rc_zmq_term = C.zmq_term(this)\n\
-- check for error.\n\
local rc_zmq_term_err\n\
if (0 ~= rc_zmq_term) then\n\
rc_zmq_term = false\n\
rc_zmq_term_err = error_code__ZMQ_Error__push(rc_zmq_term)\n\
else\n\
rc_zmq_term = true\n\
end\n\
return rc_zmq_term, rc_zmq_term_err\n\
end\n\
\n\
-- method: socket\n\
function ZMQ_Ctx_meth.socket(self, type)\n\
local this = obj_type_ZMQ_Ctx_check(self)\n\
\n\
local rc_zmq_socket_flags = OBJ_UDATA_FLAG_OWN\n\
local rc_zmq_socket\n\
rc_zmq_socket = C.zmq_socket(this, type)\n\
local rc_zmq_socket_err\n\
if (nil == rc_zmq_socket) then\n\
rc_zmq_socket_err = get_zmq_strerror()\n\
else\n\
rc_zmq_socket = obj_type_ZMQ_Socket_push(rc_zmq_socket, rc_zmq_socket_flags)\n\
end\n\
return rc_zmq_socket, rc_zmq_socket_err\n\
end\n\
\n\
-- End \"ZMQ_Ctx\" FFI interface\n\
\n\
-- method: init\n\
function zmq_meth.init(io_threads)\n\
\n\
local rc_zmq_init_flags = OBJ_UDATA_FLAG_OWN\n\
local rc_zmq_init\n\
rc_zmq_init = C.zmq_init(io_threads)\n\
local rc_zmq_init_err\n\
if (nil == rc_zmq_init) then\n\
rc_zmq_init_err = get_zmq_strerror()\n\
else\n\
rc_zmq_init = obj_type_ZMQ_Ctx_push(rc_zmq_init, rc_zmq_init_flags)\n\
end\n\
return rc_zmq_init, rc_zmq_init_err\n\
end\n\
\n\
-- method: device\n\
function zmq_meth.device(device, insock, outsock)\n\
\n\
insock = obj_type_ZMQ_Socket_check(insock)\n\
outsock = obj_type_ZMQ_Socket_check(outsock)\n\
local rc_zmq_device\n\
rc_zmq_device = C.zmq_device(device, insock, outsock)\n\
-- check for error.\n\
local rc_zmq_device_err\n\
if (0 ~= rc_zmq_device) then\n\
rc_zmq_device = false\n\
rc_zmq_device_err = error_code__ZMQ_Error__push(rc_zmq_device)\n\
else\n\
rc_zmq_device = true\n\
end\n\
return rc_zmq_device, rc_zmq_device_err\n\
end\n\
\n\
";
/* detect zmq version >= 2.1.0 */
#define VERSION_2_1 0
#if defined(ZMQ_VERSION)
#if (ZMQ_VERSION >= ZMQ_MAKE_VERSION(2,1,0))
#undef VERSION_2_1
#define VERSION_2_1 1
#endif
#endif
typedef void * ZMQ_Socket;
#if VERSION_2_1
#ifdef _WIN32
#include <winsock2.h>
typedef SOCKET socket_t;
#else
typedef int socket_t;
#endif
#endif
/* socket option types. */
#define OPT_TYPE_NONE 0
#define OPT_TYPE_INT 1
#define OPT_TYPE_UINT32 2
#define OPT_TYPE_UINT64 3
#define OPT_TYPE_INT64 4
#define OPT_TYPE_STR 5
#define OPT_TYPE_FD 6
static const int opt_types[] = {
OPT_TYPE_NONE, /* unused */
OPT_TYPE_UINT64, /* ZMQ_HWM */
OPT_TYPE_INT64, /* ZMQ_SWAP */
OPT_TYPE_UINT64, /* ZMQ_AFFINITY */
OPT_TYPE_STR, /* ZMQ_IDENTITY */
OPT_TYPE_STR, /* ZMQ_SUBSCRIBE */
OPT_TYPE_STR, /* ZMQ_UNSUBSCRIBE */
OPT_TYPE_INT64, /* ZMQ_RATE */
OPT_TYPE_INT64, /* ZMQ_RECOVERY_IVL */
OPT_TYPE_INT64, /* ZMQ_MCAST_LOOP */
OPT_TYPE_UINT64, /* ZMQ_SNDBUF */
OPT_TYPE_UINT64, /* ZMQ_RCVBUF */
OPT_TYPE_INT64, /* ZMQ_RCVMORE */
#if VERSION_2_1
OPT_TYPE_FD, /* ZMQ_FD */
OPT_TYPE_UINT32, /* ZMQ_EVENTS */
OPT_TYPE_INT, /* ZMQ_TYPE */
OPT_TYPE_INT, /* ZMQ_LINGER */
OPT_TYPE_INT, /* ZMQ_RECONNECT_IVL */
OPT_TYPE_INT, /* ZMQ_BACKLOG */
#endif
};
#define MAX_OPTS ZMQ_BACKLOG
static ZMQ_Error simple_zmq_send(ZMQ_Socket sock, const char *data, size_t data_len, int flags) {
ZMQ_Error err;
zmq_msg_t msg;
/* initialize message */
err = zmq_msg_init_size(&msg, data_len);
if(0 == err) {
/* fill message */
memcpy(zmq_msg_data(&msg), data, data_len);
/* send message */
err = zmq_send(sock, &msg, flags);
/* close message */
zmq_msg_close(&msg);
}
return err;
}
typedef void * ZMQ_Ctx;
#define OBJ_UDATA_CTX_SHOULD_FREE (OBJ_UDATA_LAST_FLAG << 1)
/*
* This wrapper function is to make the EAGAIN/ETERM error messages more like
* what is returned by LuaSocket.
*/
static const char *get_zmq_strerror() {
int err = zmq_errno();
switch(err) {
case EAGAIN:
return "timeout";
break;
case ETERM:
return "closed";
break;
default:
break;
}
return zmq_strerror(err);
}
static void error_code__ZMQ_Error__push(lua_State *L, ZMQ_Error err) {
const char *err_str = NULL;
if(err != 0) {
err_str = get_zmq_strerror();
}
if(err_str) {
lua_pushstring(L, err_str);
} else {
lua_pushnil(L);
}
}
/* method: init */
static int zmq_msg_t__init__meth(lua_State *L) {
int this_flags = OBJ_UDATA_FLAG_OWN;
zmq_msg_t * this;
ZMQ_Error err = 0;
zmq_msg_t tmp;
this = &tmp;
err = zmq_msg_init(this);
if(!(0 != err)) {
obj_type_zmq_msg_t_push(L, this, this_flags);
} else {
lua_pushnil(L);
}
error_code__ZMQ_Error__push(L, err);
return 2;
}
/* method: init_size */
static int zmq_msg_t__init_size__meth(lua_State *L) {
size_t size = luaL_checkinteger(L,1);
int this_flags = OBJ_UDATA_FLAG_OWN;
zmq_msg_t * this;
ZMQ_Error err = 0;
zmq_msg_t tmp;
this = &tmp;
err = zmq_msg_init_size(this, size);
if(!(0 != err)) {
obj_type_zmq_msg_t_push(L, this, this_flags);
} else {
lua_pushnil(L);
}
error_code__ZMQ_Error__push(L, err);
return 2;
}
/* method: init_data */
static int zmq_msg_t__init_data__meth(lua_State *L) {
size_t data_len;
const char * data = luaL_checklstring(L,1,&(data_len));
int this_flags = OBJ_UDATA_FLAG_OWN;
zmq_msg_t * this;
ZMQ_Error err = 0;
zmq_msg_t tmp;
this = &tmp;
err = zmq_msg_init_size(this, data_len);
if(0 == err) {
/* fill message */
memcpy(zmq_msg_data(this), data, data_len);
}
if(!(0 != err)) {
obj_type_zmq_msg_t_push(L, this, this_flags);
} else {
lua_pushnil(L);
}
error_code__ZMQ_Error__push(L, err);
return 2;
}
/* method: delete */
static int zmq_msg_t__delete__meth(lua_State *L) {
int this_flags = 0;
zmq_msg_t * this = obj_type_zmq_msg_t_delete(L,1,&(this_flags));
if(!(this_flags & OBJ_UDATA_FLAG_OWN)) { return 0; }
ZMQ_Error rc_zmq_msg_close = 0;
rc_zmq_msg_close = zmq_msg_close(this);
/* check for error. */
if((0 != rc_zmq_msg_close)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_msg_close);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: close */
static int zmq_msg_t__close__meth(lua_State *L) {
zmq_msg_t * this = obj_type_zmq_msg_t_check(L,1);
ZMQ_Error rc_zmq_msg_close = 0;
rc_zmq_msg_close = zmq_msg_close(this);
/* check for error. */
if((0 != rc_zmq_msg_close)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_msg_close);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: move */
static int zmq_msg_t__move__meth(lua_State *L) {
zmq_msg_t * this = obj_type_zmq_msg_t_check(L,1);
zmq_msg_t * src = obj_type_zmq_msg_t_check(L,2);
ZMQ_Error rc_zmq_msg_move = 0;
rc_zmq_msg_move = zmq_msg_move(this, src);
/* check for error. */
if((0 != rc_zmq_msg_move)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_msg_move);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: copy */
static int zmq_msg_t__copy__meth(lua_State *L) {
zmq_msg_t * this = obj_type_zmq_msg_t_check(L,1);
zmq_msg_t * src = obj_type_zmq_msg_t_check(L,2);
ZMQ_Error rc_zmq_msg_copy = 0;
rc_zmq_msg_copy = zmq_msg_copy(this, src);
/* check for error. */
if((0 != rc_zmq_msg_copy)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_msg_copy);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: set_data */
static int zmq_msg_t__set_data__meth(lua_State *L) {
zmq_msg_t * this = obj_type_zmq_msg_t_check(L,1);
size_t data_len;
const char * data = luaL_checklstring(L,2,&(data_len));
ZMQ_Error err = 0;
/* check message data size. */
if(zmq_msg_size(this) != data_len) {
/* need to resize message. */
zmq_msg_close(this); /* close old message, to free old data. */
err = zmq_msg_init_size(this, data_len); /* re-initialize message. */
if(0 != err) {
luaL_error(L, "set_data() failed: %s", get_zmq_strerror());
}
}
/* copy data into message */
memcpy(zmq_msg_data(this), data, data_len);
/* check for error. */
if((0 != err)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, err);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: data */
static int zmq_msg_t__data__meth(lua_State *L) {
zmq_msg_t * this = obj_type_zmq_msg_t_check(L,1);
void * rc_zmq_msg_data = NULL;
rc_zmq_msg_data = zmq_msg_data(this);
lua_pushlightuserdata(L, rc_zmq_msg_data);
return 1;
}
/* method: set_size */
static int zmq_msg_t__set_size__meth(lua_State *L) {
zmq_msg_t * this = obj_type_zmq_msg_t_check(L,1);
size_t size = luaL_checkinteger(L,2);
ZMQ_Error err = 0;
/* check message data size. */
if(zmq_msg_size(this) != size) {
/* need to resize message. */
zmq_msg_close(this); /* close old message, to free old data. */
err = zmq_msg_init_size(this, size); /* re-initialize message. */
if(0 != err) {
luaL_error(L, "set_size() failed: %s", get_zmq_strerror());
}
}
/* check for error. */
if((0 != err)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, err);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: size */
static int zmq_msg_t__size__meth(lua_State *L) {
zmq_msg_t * this = obj_type_zmq_msg_t_check(L,1);
size_t rc_zmq_msg_size = 0;
rc_zmq_msg_size = zmq_msg_size(this);
lua_pushinteger(L, rc_zmq_msg_size);
return 1;
}
/* method: __tostring */
static int zmq_msg_t____tostring__meth(lua_State *L) {
zmq_msg_t * this = obj_type_zmq_msg_t_check(L,1);
size_t data_len = 0;
const char * data = NULL;
data = zmq_msg_data(this);
data_len = zmq_msg_size(this);
if(data == NULL) lua_pushnil(L); else lua_pushlstring(L, data,data_len);
return 1;
}
/* method: close */
static int ZMQ_Socket__close__meth(lua_State *L) {
int this_flags = 0;
ZMQ_Socket * this = obj_type_ZMQ_Socket_delete(L,1,&(this_flags));
if(!(this_flags & OBJ_UDATA_FLAG_OWN)) { return 0; }
ZMQ_Error rc_zmq_close = 0;
rc_zmq_close = zmq_close(this);
/* check for error. */
if((0 != rc_zmq_close)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_close);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: bind */
static int ZMQ_Socket__bind__meth(lua_State *L) {
ZMQ_Socket * this = obj_type_ZMQ_Socket_check(L,1);
size_t addr_len;
const char * addr = luaL_checklstring(L,2,&(addr_len));
ZMQ_Error rc_zmq_bind = 0;
rc_zmq_bind = zmq_bind(this, addr);
/* check for error. */
if((0 != rc_zmq_bind)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_bind);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: connect */
static int ZMQ_Socket__connect__meth(lua_State *L) {
ZMQ_Socket * this = obj_type_ZMQ_Socket_check(L,1);
size_t addr_len;
const char * addr = luaL_checklstring(L,2,&(addr_len));
ZMQ_Error rc_zmq_connect = 0;
rc_zmq_connect = zmq_connect(this, addr);
/* check for error. */
if((0 != rc_zmq_connect)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_connect);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: setopt */
static int ZMQ_Socket__setopt__meth(lua_State *L) {
ZMQ_Socket * this = obj_type_ZMQ_Socket_check(L,1);
uint32_t opt = luaL_checkinteger(L,2);
ZMQ_Error err = 0;
size_t val_len;
const void *val;
socket_t fd_val;
int int_val;
uint32_t uint32_val;
uint64_t uint64_val;
int64_t int64_val;
if(opt > MAX_OPTS) {
return luaL_argerror(L, 2, "Invalid socket option.");
}
switch(opt_types[opt]) {
case OPT_TYPE_FD:
fd_val = luaL_checklong(L, 3);
val = &fd_val;
val_len = sizeof(fd_val);
break;
case OPT_TYPE_INT:
int_val = luaL_checklong(L, 3);
val = &int_val;
val_len = sizeof(int_val);
break;
case OPT_TYPE_UINT32:
uint32_val = luaL_checklong(L, 3);
val = &uint32_val;
val_len = sizeof(uint32_val);
break;
case OPT_TYPE_UINT64:
uint64_val = luaL_checklong(L, 3);
val = &uint64_val;
val_len = sizeof(uint64_val);
break;
case OPT_TYPE_INT64:
int64_val = luaL_checklong(L, 3);
val = &int64_val;
val_len = sizeof(int64_val);
break;
case OPT_TYPE_STR:
val = luaL_checklstring(L, 3, &(val_len));
break;
default:
printf("Invalid socket option type, this shouldn't happen.\n");
abort();
break;
}
err = zmq_setsockopt(this, opt, val, val_len);
/* check for error. */
if((0 != err)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, err);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: getopt */
static int ZMQ_Socket__getopt__meth(lua_State *L) {
ZMQ_Socket * this = obj_type_ZMQ_Socket_check(L,1);
uint32_t opt = luaL_checkinteger(L,2);
ZMQ_Error err = 0;
size_t val_len;
socket_t fd_val;
int int_val;
uint32_t uint32_val;
uint64_t uint64_val;
int64_t int64_val;
#define STR_MAX 255
char str_val[STR_MAX];
if(opt > MAX_OPTS) {
lua_pushnil(L);
lua_pushliteral(L, "Invalid socket option.");
return 2;
}
switch(opt_types[opt]) {
case OPT_TYPE_FD:
val_len = sizeof(fd_val);
err = zmq_getsockopt(this, opt, &fd_val, &val_len);
if(0 == err) {
lua_pushinteger(L, (lua_Integer)fd_val);
return 1;
}
break;
case OPT_TYPE_INT:
val_len = sizeof(int_val);
err = zmq_getsockopt(this, opt, &int_val, &val_len);
if(0 == err) {
lua_pushinteger(L, (lua_Integer)int_val);
return 1;
}
break;
case OPT_TYPE_UINT32:
val_len = sizeof(uint32_val);
err = zmq_getsockopt(this, opt, &uint32_val, &val_len);
if(0 == err) {
lua_pushinteger(L, (lua_Integer)uint32_val);
return 1;
}
break;
case OPT_TYPE_UINT64:
val_len = sizeof(uint64_val);
err = zmq_getsockopt(this, opt, &uint64_val, &val_len);
if(0 == err) {
lua_pushinteger(L, (lua_Integer)uint64_val);
return 1;
}
break;
case OPT_TYPE_INT64:
val_len = sizeof(int64_val);
err = zmq_getsockopt(this, opt, &int64_val, &val_len);
if(0 == err) {
lua_pushinteger(L, (lua_Integer)int64_val);
return 1;
}
break;
case OPT_TYPE_STR:
val_len = STR_MAX;
err = zmq_getsockopt(this, opt, str_val, &val_len);
if(0 == err) {
lua_pushlstring(L, str_val, val_len);
return 1;
}
#undef STR_MAX
break;
default:
printf("Invalid socket option type, this shouldn't happen.\n");
abort();
break;
}
lua_pushnil(L);
error_code__ZMQ_Error__push(L, err);
return 2;
}
/* method: events */
static int ZMQ_Socket__events__meth(lua_State *L) {
ZMQ_Socket * this = obj_type_ZMQ_Socket_check(L,1);
uint32_t events = 0;
ZMQ_Error err = 0;
size_t val_len = sizeof(events);
err = zmq_getsockopt(this, ZMQ_EVENTS, &(events), &val_len);
if(!(0 != err)) {
lua_pushinteger(L, events);
} else {
lua_pushnil(L);
}
error_code__ZMQ_Error__push(L, err);
return 2;
}
/* method: send_msg */
static int ZMQ_Socket__send_msg__meth(lua_State *L) {
ZMQ_Socket * this = obj_type_ZMQ_Socket_check(L,1);
zmq_msg_t * msg = obj_type_zmq_msg_t_check(L,2);
int flags = luaL_optinteger(L,3,0);
ZMQ_Error rc_zmq_send = 0;
rc_zmq_send = zmq_send(this, msg, flags);
/* check for error. */
if((0 != rc_zmq_send)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_send);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: send */
static int ZMQ_Socket__send__meth(lua_State *L) {
ZMQ_Socket * this = obj_type_ZMQ_Socket_check(L,1);
size_t data_len;
const char * data = luaL_checklstring(L,2,&(data_len));
int flags = luaL_optinteger(L,3,0);
ZMQ_Error err = 0;
err = simple_zmq_send(this, data, data_len, flags);
/* check for error. */
if((0 != err)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, err);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: recv_msg */
static int ZMQ_Socket__recv_msg__meth(lua_State *L) {
ZMQ_Socket * this = obj_type_ZMQ_Socket_check(L,1);
zmq_msg_t * msg = obj_type_zmq_msg_t_check(L,2);
int flags = luaL_optinteger(L,3,0);
ZMQ_Error rc_zmq_recv = 0;
rc_zmq_recv = zmq_recv(this, msg, flags);
/* check for error. */
if((0 != rc_zmq_recv)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_recv);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: recv */
static int ZMQ_Socket__recv__meth(lua_State *L) {
ZMQ_Socket * this = obj_type_ZMQ_Socket_check(L,1);
int flags = luaL_optinteger(L,2,0);
size_t data_len = 0;
const char * data = NULL;
ZMQ_Error err = 0;
zmq_msg_t msg;
/* initialize message */
err = zmq_msg_init(&msg);
if(0 == err) {
/* receive message */
err = zmq_recv(this, &msg, flags);
if(0 == err) {
data = zmq_msg_data(&msg);
data_len = zmq_msg_size(&msg);
}
}
if(!(0 != err)) {
if(data == NULL) lua_pushnil(L); else lua_pushlstring(L, data,data_len);
} else {
lua_pushnil(L);
}
error_code__ZMQ_Error__push(L, err);
/* close message */
zmq_msg_close(&msg);
return 2;
}
/* method: delete */
static int ZMQ_Ctx__delete__meth(lua_State *L) {
int this_flags = 0;
ZMQ_Ctx * this = obj_type_ZMQ_Ctx_delete(L,1,&(this_flags));
if(!(this_flags & OBJ_UDATA_FLAG_OWN)) { return 0; }
if(this_flags & OBJ_UDATA_CTX_SHOULD_FREE) {
zmq_term(this);
}
return 0;
}
/* method: term */
static int ZMQ_Ctx__term__meth(lua_State *L) {
ZMQ_Ctx * this = obj_type_ZMQ_Ctx_check(L,1);
ZMQ_Error rc_zmq_term = 0;
rc_zmq_term = zmq_term(this);
/* check for error. */
if((0 != rc_zmq_term)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_term);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: lightuserdata */
static int ZMQ_Ctx__lightuserdata__meth(lua_State *L) {
ZMQ_Ctx * this = obj_type_ZMQ_Ctx_check(L,1);
void * ptr = NULL;
ptr = this;
lua_pushlightuserdata(L, ptr);
return 1;
}
/* method: socket */
static int ZMQ_Ctx__socket__meth(lua_State *L) {
ZMQ_Ctx * this = obj_type_ZMQ_Ctx_check(L,1);
int type = luaL_checkinteger(L,2);
int rc_zmq_socket_flags = OBJ_UDATA_FLAG_OWN;
ZMQ_Socket rc_zmq_socket;
rc_zmq_socket = zmq_socket(this, type);
if((NULL == rc_zmq_socket)) {
lua_pushnil(L);
lua_pushstring(L, get_zmq_strerror());
} else {
obj_type_ZMQ_Socket_push(L, rc_zmq_socket, rc_zmq_socket_flags);
}
return 1;
}
/* method: version */
static int zmq__version__func(lua_State *L) {
int major, minor, patch;
zmq_version(&(major), &(minor), &(patch));
/* return version as a table: { major, minor, patch } */
lua_createtable(L, 3, 0);
lua_pushinteger(L, major);
lua_rawseti(L, -2, 1);
lua_pushinteger(L, minor);
lua_rawseti(L, -2, 2);
lua_pushinteger(L, patch);
lua_rawseti(L, -2, 3);
return 1;
}
/* method: init */
static int zmq__init__func(lua_State *L) {
int io_threads = luaL_checkinteger(L,1);
int rc_zmq_init_flags = OBJ_UDATA_FLAG_OWN;
ZMQ_Ctx rc_zmq_init;
rc_zmq_init = zmq_init(io_threads);
if((NULL == rc_zmq_init)) {
lua_pushnil(L);
lua_pushstring(L, get_zmq_strerror());
} else {
obj_type_ZMQ_Ctx_push(L, rc_zmq_init, rc_zmq_init_flags);
}
return 1;
}
/* method: init_ctx */
static int zmq__init_ctx__func(lua_State *L) {
int ctx_flags = OBJ_UDATA_FLAG_OWN;
ZMQ_Ctx ctx;
if(lua_isuserdata(L, 1)) {
ctx = lua_touserdata(L, 1);
} else {
/* check if value is a LuaJIT 'cdata' */
int type = lua_type(L, 1);
const char *typename = lua_typename(L, type);
if(strncmp(typename, "cdata", sizeof("cdata")) == 0) {
ctx = (void *)lua_topointer(L, 1);
} else {
return luaL_argerror(L, 1, "(expected userdata)");
}
}
if((NULL == ctx)) {
lua_pushnil(L);
lua_pushstring(L, get_zmq_strerror());
} else {
obj_type_ZMQ_Ctx_push(L, ctx, ctx_flags);
}
return 1;
}
/* method: device */
static int zmq__device__func(lua_State *L) {
int device = luaL_checkinteger(L,1);
ZMQ_Socket insock = obj_type_ZMQ_Socket_check(L,2);
ZMQ_Socket outsock = obj_type_ZMQ_Socket_check(L,3);
ZMQ_Error rc_zmq_device = 0;
rc_zmq_device = zmq_device(device, insock, outsock);
/* check for error. */
if((0 != rc_zmq_device)) {
lua_pushboolean(L, 0);
error_code__ZMQ_Error__push(L, rc_zmq_device);
} else {
lua_pushboolean(L, 1);
}
return 2;
}
/* method: dump_ffi */
static int zmq__dump_ffi__func(lua_State *L) {
size_t ffi_code_len = 0;
const char * ffi_code = NULL;
ffi_code = zmq_ffi_lua_code;
ffi_code_len = sizeof(zmq_ffi_lua_code) - 1;
if(ffi_code == NULL) lua_pushnil(L); else lua_pushlstring(L, ffi_code,ffi_code_len);
return 1;
}
static const luaL_reg obj_zmq_msg_t_pub_funcs[] = {
{"init", zmq_msg_t__init__meth},
{"init_size", zmq_msg_t__init_size__meth},
{"init_data", zmq_msg_t__init_data__meth},
{NULL, NULL}
};
static const luaL_reg obj_zmq_msg_t_methods[] = {
{"close", zmq_msg_t__close__meth},
{"move", zmq_msg_t__move__meth},
{"copy", zmq_msg_t__copy__meth},
{"set_data", zmq_msg_t__set_data__meth},
{"data", zmq_msg_t__data__meth},
{"set_size", zmq_msg_t__set_size__meth},
{"size", zmq_msg_t__size__meth},
{NULL, NULL}
};
static const luaL_reg obj_zmq_msg_t_metas[] = {
{"__gc", zmq_msg_t__delete__meth},
{"__tostring", zmq_msg_t____tostring__meth},
{"__eq", obj_simple_udata_default_equal},
{NULL, NULL}
};
static const obj_base obj_zmq_msg_t_bases[] = {
{-1, NULL}
};
static const obj_field obj_zmq_msg_t_fields[] = {
{NULL, 0, 0, 0}
};
static const obj_const obj_zmq_msg_t_constants[] = {
{NULL, NULL, 0.0 , 0}
};
static const luaL_reg obj_ZMQ_Socket_pub_funcs[] = {
{NULL, NULL}
};
static const luaL_reg obj_ZMQ_Socket_methods[] = {
{"close", ZMQ_Socket__close__meth},
{"bind", ZMQ_Socket__bind__meth},
{"connect", ZMQ_Socket__connect__meth},
{"setopt", ZMQ_Socket__setopt__meth},
{"getopt", ZMQ_Socket__getopt__meth},
{"events", ZMQ_Socket__events__meth},
{"send_msg", ZMQ_Socket__send_msg__meth},
{"send", ZMQ_Socket__send__meth},
{"recv_msg", ZMQ_Socket__recv_msg__meth},
{"recv", ZMQ_Socket__recv__meth},
{NULL, NULL}
};
static const luaL_reg obj_ZMQ_Socket_metas[] = {
{"__gc", ZMQ_Socket__close__meth},
{"__tostring", obj_udata_default_tostring},
{"__eq", obj_udata_default_equal},
{NULL, NULL}
};
static const obj_base obj_ZMQ_Socket_bases[] = {
{-1, NULL}
};
static const obj_field obj_ZMQ_Socket_fields[] = {
{NULL, 0, 0, 0}
};
static const obj_const obj_ZMQ_Socket_constants[] = {
{NULL, NULL, 0.0 , 0}
};
static const luaL_reg obj_ZMQ_Ctx_pub_funcs[] = {
{NULL, NULL}
};
static const luaL_reg obj_ZMQ_Ctx_methods[] = {
{"term", ZMQ_Ctx__term__meth},
{"lightuserdata", ZMQ_Ctx__lightuserdata__meth},
{"socket", ZMQ_Ctx__socket__meth},
{NULL, NULL}
};
static const luaL_reg obj_ZMQ_Ctx_metas[] = {
{"__gc", ZMQ_Ctx__delete__meth},
{"__tostring", obj_udata_default_tostring},
{"__eq", obj_udata_default_equal},
{NULL, NULL}
};
static const obj_base obj_ZMQ_Ctx_bases[] = {
{-1, NULL}
};
static const obj_field obj_ZMQ_Ctx_fields[] = {
{NULL, 0, 0, 0}
};
static const obj_const obj_ZMQ_Ctx_constants[] = {
{NULL, NULL, 0.0 , 0}
};
static const luaL_reg zmq_function[] = {
{"version", zmq__version__func},
{"init", zmq__init__func},
{"init_ctx", zmq__init_ctx__func},
{"device", zmq__device__func},
{"dump_ffi", zmq__dump_ffi__func},
{NULL, NULL}
};
static const obj_const zmq_constants[] = {
{"TYPE", NULL, 16, CONST_NUMBER},
{"RCVMORE", NULL, 13, CONST_NUMBER},
{"LINGER", NULL, 17, CONST_NUMBER},
{"SWAP", NULL, 3, CONST_NUMBER},
{"MSG_SHARED", NULL, 128, CONST_NUMBER},
{"SNDBUF", NULL, 11, CONST_NUMBER},
{"STREAMER", NULL, 1, CONST_NUMBER},
{"NOBLOCK", NULL, 1, CONST_NUMBER},
{"RCVBUF", NULL, 12, CONST_NUMBER},
{"FORWARDER", NULL, 2, CONST_NUMBER},
{"RATE", NULL, 8, CONST_NUMBER},
{"IDENTITY", NULL, 5, CONST_NUMBER},
{"SUB", NULL, 2, CONST_NUMBER},
{"FD", NULL, 14, CONST_NUMBER},
{"PUB", NULL, 1, CONST_NUMBER},
{"DELIMITER", NULL, 31, CONST_NUMBER},
{"BACKLOG", NULL, 19, CONST_NUMBER},
{"SNDMORE", NULL, 2, CONST_NUMBER},
{"POLLIN", NULL, 1, CONST_NUMBER},
{"REP", NULL, 4, CONST_NUMBER},
{"POLLERR", NULL, 4, CONST_NUMBER},
{"MAX_VSM_SIZE", NULL, 30, CONST_NUMBER},
{"PUSH", NULL, 8, CONST_NUMBER},
{"HWM", NULL, 1, CONST_NUMBER},
{"MSG_MORE", NULL, 1, CONST_NUMBER},
{"REQ", NULL, 3, CONST_NUMBER},
{"UNSUBSCRIBE", NULL, 7, CONST_NUMBER},
{"PULL", NULL, 7, CONST_NUMBER},
{"PAIR", NULL, 0, CONST_NUMBER},
{"QUEUE", NULL, 3, CONST_NUMBER},
{"EVENTS", NULL, 15, CONST_NUMBER},
{"XREQ", NULL, 5, CONST_NUMBER},
{"XREP", NULL, 6, CONST_NUMBER},
{"SUBSCRIBE", NULL, 6, CONST_NUMBER},
{"MCAST_LOOP", NULL, 10, CONST_NUMBER},
{"VSM", NULL, 32, CONST_NUMBER},
{"RECOVERY_IVL", NULL, 9, CONST_NUMBER},
{"RECONNECT_IVL", NULL, 18, CONST_NUMBER},
{"POLLOUT", NULL, 2, CONST_NUMBER},
{"AFFINITY", NULL, 4, CONST_NUMBER},
{NULL, NULL, 0.0 , 0}
};
static const ffi_export_symbol zmq_ffi_export[] = {
{ "get_zmq_strerror", get_zmq_strerror },
{ "simple_zmq_send", simple_zmq_send },
{NULL, NULL}
};
static const reg_sub_module reg_sub_modules[] = {
{ &(obj_type_zmq_msg_t), 0, obj_zmq_msg_t_pub_funcs, obj_zmq_msg_t_methods, obj_zmq_msg_t_metas, obj_zmq_msg_t_bases, obj_zmq_msg_t_fields, obj_zmq_msg_t_constants},
{ &(obj_type_ZMQ_Socket), 0, obj_ZMQ_Socket_pub_funcs, obj_ZMQ_Socket_methods, obj_ZMQ_Socket_metas, obj_ZMQ_Socket_bases, obj_ZMQ_Socket_fields, obj_ZMQ_Socket_constants},
{ &(obj_type_ZMQ_Ctx), 0, obj_ZMQ_Ctx_pub_funcs, obj_ZMQ_Ctx_methods, obj_ZMQ_Ctx_metas, obj_ZMQ_Ctx_bases, obj_ZMQ_Ctx_fields, obj_ZMQ_Ctx_constants},
{NULL, 0, NULL, NULL, NULL, NULL, NULL, NULL}
};
static const luaL_Reg submodule_libs[] = {
{NULL, NULL}
};
static void create_object_instance_cache(lua_State *L) {
lua_pushlightuserdata(L, obj_udata_weak_ref_key); /* key for weak table. */
lua_rawget(L, LUA_REGISTRYINDEX); /* check if weak table exists already. */
if(!lua_isnil(L, -1)) {
lua_pop(L, 1); /* pop weak table. */
return;
}
lua_pop(L, 1); /* pop nil. */
/* create weak table for object instance references. */
lua_pushlightuserdata(L, obj_udata_weak_ref_key); /* key for weak table. */
lua_newtable(L); /* weak table. */
lua_newtable(L); /* metatable for weak table. */
lua_pushliteral(L, "__mode");
lua_pushliteral(L, "v");
lua_rawset(L, -3); /* metatable.__mode = 'v' weak values. */
lua_setmetatable(L, -2); /* add metatable to weak table. */
lua_rawset(L, LUA_REGISTRYINDEX); /* create reference to weak table. */
}
int luaopen_zmq(lua_State *L) {
const reg_sub_module *reg = reg_sub_modules;
const luaL_Reg *submodules = submodule_libs;
int priv_table = -1;
#if LUAJIT_FFI
/* private table to hold reference to object metatables. */
lua_newtable(L);
priv_table = lua_gettop(L);
#endif
/* create object cache. */
create_object_instance_cache(L);
/* module table. */
luaL_register(L, "zmq", zmq_function);
/* register module constants. */
obj_type_register_constants(L, zmq_constants, -1);
for(; submodules->func != NULL ; submodules++) {
lua_pushcfunction(L, submodules->func);
lua_pushstring(L, submodules->name);
lua_call(L, 1, 0);
}
/* register objects */
for(; reg->type != NULL ; reg++) {
lua_newtable(L); /* create public API table for object. */
lua_pushvalue(L, -1); /* dup. object's public API table. */
lua_setfield(L, -3, reg->type->name); /* module["<object_name>"] = <object public API> */
#if REG_OBJECTS_AS_GLOBALS
lua_pushvalue(L, -1); /* dup value. */
lua_setglobal(L, reg->type->name); /* global: <object_name> = <object public API> */
#endif
obj_type_register(L, reg, priv_table);
}
#if LUAJIT_FFI
nobj_try_loading_ffi(L, "zmq", zmq_ffi_lua_code,
zmq_ffi_export, priv_table);
#endif
return 1;
}