int erl_print_term(FILE *fp, const ETERM *ep) { int j,i,doquote; int ch_written = 0; /* counter of written chars */ if ((!fp) || (!ep)) return 0; /* ASSERT(ep != NULL); */ j = i = doquote = 0; switch(ERL_TYPE(ep)) { case ERL_ATOM: { char* adata = ERL_ATOM_PTR(ep); /* FIXME: what if some weird locale is in use? */ if (!islower(adata[0])) doquote = 1; for (i = 0; !doquote && i < ERL_ATOM_SIZE(ep); i++) { doquote = !(isalnum(adata[i]) || (adata[i] == '_')); } if (doquote) { putc('\'', fp); ch_written++; } fputs(adata, fp); ch_written += ERL_ATOM_SIZE(ep); if (doquote) { putc('\'', fp); ch_written++; } break; } case ERL_VARIABLE: if (!isupper((int)ERL_VAR_NAME(ep)[0])) { doquote = 1; putc('\'', fp); ch_written++; } fputs(ERL_VAR_NAME(ep), fp); ch_written += ERL_VAR_LEN(ep); if (doquote) { putc('\'', fp); ch_written++; } break; case ERL_PID: ch_written += fprintf(fp, "<%s.%d.%d>", ERL_PID_NODE(ep), ERL_PID_NUMBER(ep), ERL_PID_SERIAL(ep)); break; case ERL_PORT: ch_written += fprintf(fp, "#Port"); break; case ERL_REF: ch_written += fprintf(fp, "#Ref"); break; case ERL_EMPTY_LIST: ch_written += fprintf(fp, "[]"); break; case ERL_LIST: if (is_printable_list(ep)) { ch_written += print_string(fp, ep); } else { putc('[', fp); ch_written++; while (ERL_IS_CONS(ep)) { ch_written += erl_print_term(fp, HEAD(ep)); ep = TAIL(ep); if (ERL_IS_CONS(ep)) { putc(',', fp); ch_written++; } } if (!ERL_IS_EMPTY_LIST(ep)) { putc('|', fp); ch_written++; ch_written += erl_print_term(fp, ep); } putc(']', fp); ch_written++; } break; case ERL_TUPLE: putc('{', fp); ch_written++; for (i=0; i < ERL_TUPLE_SIZE(ep); i++) { ch_written += erl_print_term(fp, ERL_TUPLE_ELEMENT(ep, j++) ); if (i != ERL_TUPLE_SIZE(ep)-1) { putc(',', fp); ch_written++; } } putc('}', fp); ch_written++; break; case ERL_BINARY: { int sz = (ERL_BIN_SIZE(ep) > 20) ? 20 : ERL_BIN_SIZE(ep); unsigned char *ptr = ERL_BIN_PTR(ep); ch_written += fprintf(fp, "#Bin<"); for (i = 0; i < sz; i++) { putc(ptr[i], fp); ch_written++; } if (sz == 20) ch_written += fprintf(fp, "(%d)....>", ERL_BIN_SIZE(ep)-20); else ch_written += fprintf(fp, ">"); break; } case ERL_INTEGER: case ERL_SMALL_BIG: ch_written += fprintf(fp, "%d", ERL_INT_VALUE(ep)); break; case ERL_U_INTEGER: case ERL_U_SMALL_BIG: ch_written += fprintf(fp, "%d", ERL_INT_UVALUE(ep)); break; case ERL_LONGLONG: case ERL_U_LONGLONG: ch_written += fprintf(fp, "%lld", ERL_LL_UVALUE(ep)); break; case ERL_FLOAT: ch_written += fprintf(fp, "%f", ERL_FLOAT_VALUE(ep)); break; case ERL_FUNCTION: ch_written += fprintf(fp, "#Fun<"); ch_written += erl_print_term(fp, ERL_FUN_MODULE(ep)); putc('.', fp); ch_written++; ch_written += erl_print_term(fp, ERL_FUN_INDEX(ep)); putc('.', fp); ch_written++; ch_written += erl_print_term(fp, ERL_FUN_UNIQ(ep)); putc('>', fp); ch_written++; break; default: ch_written = -10000; erl_err_msg("<ERROR> erl_print_term: Bad type of term !"); } return ch_written; }
int erl_sprint_term(char *buf, const ETERM *ep) { int j,i,doquote; int ch_written = 0; /* counter of written chars */ if ((!buf) || (!ep)) return 0; /* ASSERT(ep != NULL); */ j = i = doquote = 0; switch(ERL_TYPE(ep)) { case ERL_ATOM: /* FIXME: what if some weird locale is in use? */ if (!islower((int)ERL_ATOM_PTR(ep)[0])) doquote = 1; for (i = 0; !doquote && i < ERL_ATOM_SIZE(ep); i++) { doquote = !(isalnum((int)ERL_ATOM_PTR(ep)[i]) || (ERL_ATOM_PTR(ep)[i] == '_')); } if (doquote) { *buf++ = '\''; ch_written++; } { int len = ERL_ATOM_SIZE(ep); strncpy(buf, ERL_ATOM_PTR(ep), len); buf += len; ch_written += len; } if (doquote) { *buf++ = '\''; ch_written++; } break; case ERL_VARIABLE: if (!isupper((int)ERL_VAR_NAME(ep)[0])) { doquote = 1; *buf++ = '\''; ch_written++; } len = ERL_VAR_LEN(ep); strncpy(buf, ERL_VAR_NAME(ep), len); buf += len; ch_written += len; if (doquote) { *buf++ = '\''; ch_written++; } break; case ERL_PID: len = sprintf(buf, "<%s.%d.%d>", ERL_PID_NODE(ep), ERL_PID_NUMBER(ep), ERL_PID_SERIAL(ep)); buf += len; ch_written += len; break; case ERL_PORT: len = sprintf(buf , "#Port"); buf += len; ch_written += len; break; case ERL_REF: len = sprintf(buf , "#Ref"); buf += len; ch_written += len; break; case ERL_EMPTY_LIST: len = sprintf(buf , "[]"); buf += len; ch_written += len; break; case ERL_LIST: if (is_printable_list(ep)) { ch_written += print_string(fp, ep); } else { putc('[', fp); ch_written++; while (ERL_IS_CONS(ep)) { ch_written += erl_sprint_term(fp, HEAD(ep)); ep = TAIL(ep); if (ERL_IS_CONS(ep)) { putc(',', fp); ch_written++; } } if (!ERL_IS_EMPTY_LIST(ep)) { putc('|', fp); ch_written++; ch_written += erl_sprint_term(fp, ep); } putc(']', fp); ch_written++; } break; case ERL_TUPLE: putc('{', fp); ch_written++; for (i=0; i < ERL_TUPLE_SIZE(ep); i++) { ch_written += erl_sprint_term(fp, ERL_TUPLE_ELEMENT(ep, j++) ); if (i != ERL_TUPLE_SIZE(ep)-1) { putc(',', fp); ch_written++; } } putc('}', fp); ch_written++; break; case ERL_BINARY: len = sprintf(buf , "#Bin"); buf += len; ch_written += len; break; case ERL_INTEGER: case ERL_SMALL_BIG: len = sprintf(buf , "%d", ERL_INT_VALUE(ep)); buf += len; ch_written += len; break; case ERL_U_INTEGER: case ERL_U_SMALL_BIG: len = sprintf(buf , "%d", ERL_INT_UVALUE(ep)); buf += len; ch_written += len; break; case ERL_FLOAT: len = sprintf(buf , "%f", ERL_FLOAT_VALUE(ep)); buf += len; ch_written += len; break; case ERL_FUNCTION: len = sprintf(buf , "#Fun<"); buf += len; ch_written += len; ch_written += erl_sprint_term(fp, ERL_FUN_MODULE(ep)); putc('.', fp); ch_written++; ch_written += erl_sprint_term(fp, ERL_FUN_INDEX(ep)); putc('.', fp); ch_written++; ch_written += erl_sprint_term(fp, ERL_FUN_UNIQ(ep)); putc('>', fp); ch_written++; break; default: ch_written = -10000; erl_err_msg("<ERROR> erl_sprint_term: Bad type of term !"); } return ch_written; }
VALUE erlix_atom_size(VALUE self){ ErlixTerm *atom; Data_Get_Struct(self,ErlixTerm,atom); int l=ERL_ATOM_SIZE(atom->term); return INT2FIX(l); }
int main(void) #endif { ei_x_buff eix; int index = 0; ETERM **etermpp = NULL, *etermp = NULL; char *charp = NULL; unsigned char uchar, **ucharpp = NULL, *ucharp = NULL; void *voidp = NULL; Erl_Heap *erl_heapp = NULL; int intx = 0; int *intp = NULL; unsigned int uintx, *uintp; unsigned long *ulongp = NULL; long longx = 0; double doublex = 0.0; short shortx = 42; FILE *filep = NULL; Erl_IpAddr erl_ipaddr = NULL; ErlMessage *erlmessagep = NULL; ErlConnect *erlconnectp = NULL; struct hostent *hostp = NULL; struct in_addr *inaddrp = NULL; /* Converion to erl_interface format is in liberl_interface */ intx = erl_errno; ei_encode_term(charp, &index, voidp); ei_x_encode_term(&eix, voidp); ei_decode_term(charp, &index, voidp); erl_init(voidp, longx); erl_connect_init(intx, charp,shortx); erl_connect_xinit(charp,charp,charp,erl_ipaddr,charp,shortx); erl_connect(charp); erl_xconnect(erl_ipaddr,charp); erl_close_connection(intx); erl_receive(intx, ucharp, intx); erl_receive_msg(intx, ucharp, intx, erlmessagep); erl_xreceive_msg(intx, ucharpp, intp, erlmessagep); erl_send(intx, etermp, etermp); erl_reg_send(intx, charp, etermp); erl_rpc(intx,charp,charp,etermp); erl_rpc_to(intx,charp,charp,etermp); erl_rpc_from(intx,intx,erlmessagep); erl_publish(intx); erl_accept(intx,erlconnectp); erl_thiscookie(); erl_thisnodename(); erl_thishostname(); erl_thisalivename(); erl_thiscreation(); erl_unpublish(charp); erl_err_msg(charp); erl_err_quit(charp); erl_err_ret(charp); erl_err_sys(charp); erl_cons(etermp,etermp); erl_copy_term(etermp); erl_element(intx,etermp); erl_hd(etermp); erl_iolist_to_binary(etermp); erl_iolist_to_string(etermp); erl_iolist_length(etermp); erl_length(etermp); erl_mk_atom(charp); erl_mk_binary(charp,intx); erl_mk_empty_list(); erl_mk_estring(charp, intx); erl_mk_float(doublex); erl_mk_int(intx); erl_mk_list(etermpp,intx); erl_mk_pid(charp,uintx,uintx,uchar); erl_mk_port(charp,uintx,uchar); erl_mk_ref(charp,uintx,uchar); erl_mk_long_ref(charp,uintx,uintx,uintx,uchar); erl_mk_string(charp); erl_mk_tuple(etermpp,intx); erl_mk_uint(uintx); erl_mk_var(charp); erl_print_term(filep,etermp); /* erl_sprint_term(charp,etermp); */ erl_size(etermp); erl_tl(etermp); erl_var_content(etermp, charp); erl_format(charp); erl_match(etermp, etermp); erl_global_names(intx, intp); erl_global_register(intx, charp, etermp); erl_global_unregister(intx, charp); erl_global_whereis(intx, charp, charp); erl_init_malloc(erl_heapp,longx); erl_alloc_eterm(uchar); erl_eterm_release(); erl_eterm_statistics(ulongp,ulongp); erl_free_array(etermpp,intx); erl_free_term(etermp); erl_free_compound(etermp); erl_malloc(longx); erl_free(voidp); erl_compare_ext(ucharp, ucharp); erl_decode(ucharp); erl_decode_buf(ucharpp); erl_encode(etermp,ucharp); erl_encode_buf(etermp,ucharpp); erl_ext_size(ucharp); erl_ext_type(ucharp); erl_peek_ext(ucharp,intx); erl_term_len(etermp); erl_gethostbyname(charp); erl_gethostbyaddr(charp, intx, intx); erl_gethostbyname_r(charp, hostp, charp, intx, intp); erl_gethostbyaddr_r(charp, intx, intx, hostp, charp, intx, intp); erl_init_resolve(); erl_distversion(intx); erl_epmd_connect(inaddrp); erl_epmd_port(inaddrp, charp, intp); charp = ERL_ATOM_PTR(etermp); intx = ERL_ATOM_SIZE(etermp); ucharp = ERL_BIN_PTR(etermp); intx = ERL_BIN_SIZE(etermp); etermp = ERL_CONS_HEAD(etermp); etermp = ERL_CONS_TAIL(etermp); intx = ERL_COUNT(etermp); doublex= ERL_FLOAT_VALUE(etermp); uintx = ERL_INT_UVALUE(etermp); intx = ERL_INT_VALUE(etermp); intx = ERL_IS_ATOM(etermp); intx = ERL_IS_BINARY(etermp); intx = ERL_IS_CONS(etermp); intx = ERL_IS_EMPTY_LIST(etermp); intx = ERL_IS_FLOAT(etermp); intx = ERL_IS_INTEGER(etermp); intx = ERL_IS_LIST(etermp); intx = ERL_IS_PID(etermp); intx = ERL_IS_PORT(etermp); intx = ERL_IS_REF(etermp); intx = ERL_IS_TUPLE(etermp); intx = ERL_IS_UNSIGNED_INTEGER(etermp); uchar = ERL_PID_CREATION(etermp); charp = ERL_PID_NODE(etermp); uintx = ERL_PID_NUMBER(etermp); uintx = ERL_PID_SERIAL(etermp); uchar = ERL_PORT_CREATION(etermp); charp = ERL_PORT_NODE(etermp); uintx = ERL_PORT_NUMBER(etermp); uchar = ERL_REF_CREATION(etermp); intx = ERL_REF_LEN(etermp); charp = ERL_REF_NODE(etermp); uintx = ERL_REF_NUMBER(etermp); uintp = ERL_REF_NUMBERS(etermp); etermp = ERL_TUPLE_ELEMENT(etermp,intx); intx = ERL_TUPLE_SIZE(etermp); return BUFSIZ + EAGAIN + EHOSTUNREACH + EINVAL + EIO + EMSGSIZE + ENOMEM + ERL_ATOM + ERL_BINARY + ERL_ERROR + ERL_EXIT + ERL_FLOAT + ERL_INTEGER + ERL_LINK + ERL_LIST + ERL_MSG + ERL_NO_TIMEOUT + ERL_PID + ERL_PORT + ERL_REF + ERL_REG_SEND + ERL_SEND + ERL_SMALL_BIG + ERL_TICK + ERL_TIMEOUT + ERL_TUPLE + ERL_UNLINK + ERL_U_INTEGER + ERL_U_SMALL_BIG + ERL_VARIABLE + ETIMEDOUT + MAXNODELEN + MAXREGLEN; }
PyObject *eterm_to_py(ETERM * obj) { int i; int count; ETERM *obj2; PyObject *eobj = NULL; if (obj == NULL) { Py_INCREF(Py_None); return Py_None; } switch (ERL_TYPE(obj)) { case ERL_CONS: case ERL_NIL: count = erl_length(obj); eobj = PyList_New(0); for (i = 0; i < count; i++) { obj2 = erl_hd(obj); PyList_Append(eobj, eterm_to_py(obj2)); obj = erl_tl(obj); } break; case ERL_TUPLE: eobj = PyTuple_New(erl_size(obj)); for (i = 1; i <= erl_size(obj); i++) { obj2 = erl_element(i, obj); PyTuple_SetItem(eobj, i - 1, eterm_to_py(obj2)); } break; case ERL_ATOM: eobj = PyString_FromStringAndSize(ERL_ATOM_PTR(obj), ERL_ATOM_SIZE(obj)); break; case ERL_INTEGER: eobj = PyInt_FromLong(ERL_INT_VALUE(obj)); break; case ERL_BINARY: fprintf(stderr, "FOUND A BINARY %.*s\n", ERL_BIN_SIZE(obj), ERL_BIN_PTR(obj)); break; case ERL_PID: eobj = PyDict_New(); if (PyDict_SetItemString(eobj, "node", PyString_FromString(ERL_PID_NODE(obj)))) { PyErr_Print(); break; } if (PyDict_SetItemString(eobj, "number", PyInt_FromLong(ERL_PID_NUMBER(obj)))) { PyErr_Print(); break; } if (PyDict_SetItemString(eobj, "serial", PyInt_FromLong(ERL_PID_SERIAL(obj)))) { PyErr_Print(); break; } if (PyDict_SetItemString(eobj, "creation", PyInt_FromLong(ERL_PID_CREATION(obj)))) { PyErr_Print(); break; } default: fprintf(stderr, "UNMANAGED ETERM TYPE: %d\n", ERL_TYPE(obj)); break; } if (eobj == NULL) { Py_INCREF(Py_None); return Py_None; } return eobj; }
PyObject *py_erlang_rpc(PyObject * self, PyObject * args) { int fd, timeout = uwsgi.shared->options[UWSGI_OPTION_SOCKET_TIMEOUT]; char *emod, *efun; PyObject *eargs, *pyer = NULL; ETERM *pyargs, *rex; ErlMessage emsg; int eret; if (!PyArg_ParseTuple(args, "issO|i:erlang_rpc", &fd, &emod, &efun, &eargs, &timeout)) { return NULL; } if (fd < 0) { goto clear; } pyargs = py_to_eterm(eargs); if (!pyargs) { goto clear; } if (erl_rpc_to(fd, emod, efun, pyargs)) { erl_err_msg("erl_rpc_to()"); goto clear2; } cycle: memset(&emsg, 0, sizeof(ErlMessage)); UWSGI_SET_BLOCKING; eret = erl_rpc_from(fd, timeout * 1000, &emsg); if (eret == ERL_TICK) { goto cycle; } else if (eret == ERL_MSG) { if (emsg.msg) { if (ERL_IS_TUPLE(emsg.msg)) { rex = erl_element(1, emsg.msg); if (!rex) { goto clear2; } if (!strncmp("rex", ERL_ATOM_PTR(rex), ERL_ATOM_SIZE(rex))) { erl_free_term(rex); rex = erl_element(2, emsg.msg); if (!rex) { goto clear2; } pyer = eterm_to_py(rex); erl_free_term(rex); } else { erl_free_term(rex); } } } if (emsg.msg) { erl_free_compound(emsg.msg); } if (emsg.to) { erl_free_compound(emsg.to); } if (emsg.from) { erl_free_compound(emsg.from); } if (!pyer) { goto clear2; } erl_free_compound(pyargs); UWSGI_UNSET_BLOCKING; return pyer; } else { erl_err_msg("erl_rpc_from()"); } clear2: UWSGI_UNSET_BLOCKING; erl_free_compound(pyargs); clear: Py_INCREF(Py_None); return Py_None; }