static int term_test(IC_Env *env) { ETERM *ti, *to, *tr; ti = erl_format("[{hej, 1, 23}, \"string\", {1.23, 45}]"); fprintf(stdout, "\n======== m_i_term test ======\n\n"); tr = m_i_term_test(NULL, ti, &to, env); CHECK_EXCEPTION(env); RETURN_IF_OK(erl_match(ti, to) && erl_match(ti, tr)); if (!erl_match(ti, to)) { fprintf(stdout, " out parameter error, sent:\n"); print_term(ti); fprintf(stdout, "got:\n"); print_term(to); } if (!erl_match(ti, tr)) { fprintf(stdout, " result error, sent:\n"); print_term(ti); fprintf(stdout, "got:\n"); print_term(tr); } erl_free_term(ti); erl_free_term(to); erl_free_term(tr); return -1; }
static int typedef_test(IC_Env *env) { m_banan mbi, mbo; /* erlang_port */ m_apa mai; /* ETERM* */ m_apa mao = NULL; long tl; strcpy(mbi.node,"node"); mbi.id = 15; mbi.creation = 1; fprintf(stdout, "\n======== m_i_typedef test ======\n\n"); mai = erl_format("[{hej, 1, 23}, \"string\", {1.23, 45}]"); tl = m_i_typedef_test(NULL, mai, &mbi, &mao, &mbo, env); CHECK_EXCEPTION(env); RETURN_IF_OK(erl_match(mai, mao) && cmp_port(&mbi, &mbo) && tl == 4711); if (!erl_match(mai, mao)) { fprintf(stdout, " out parameter error (term), sent:\n"); print_term(mai); fprintf(stdout, "got:\n"); print_term(mao); } if (!cmp_port(&mbi, &mbo)) { fprintf(stdout, " out parameter error (port), sent:\n"); print_port(&mbi); fprintf(stdout, "got:\n"); print_port(&mbo); } if (tl != 4711) { fprintf(stdout, " result error, sent: 4711, got %ld\n", tl); } erl_free_term(mai); erl_free_term(mao); return -1; }
static int hello_getattr(const char *path, struct stat *stbuf) { ETERM * response = erl_rpc(FERL_DATA->erlang_fd,"gen_server","call",erl_format("[nefs,{get_attr,~s}]",path)); ETERM * pattern = erl_format("{directory,Mode,Nlink}"); ETERM * pattern2 = erl_format("{file,Mode,Nlink,Size}"); int res = 0; memset(stbuf, 0, sizeof(struct stat)); if(erl_match(pattern, response)) { //directory ETERM * Mode = erl_var_content(pattern, "Mode"); ETERM * Nlink = erl_var_content(pattern, "Nlink"); if(ERL_IS_INTEGER(Nlink) && ERL_IS_INTEGER(Mode)){ stbuf->st_mode = S_IFDIR | ERL_INT_VALUE(Mode); //permissions stbuf->st_nlink = ERL_INT_VALUE(Nlink); // directories have the number of files in them }else{ res = -ENOENT; } }else if(erl_match(pattern2, response)){ //file ETERM * Mode = erl_var_content(pattern2, "Mode"); ETERM * Nlink = erl_var_content(pattern2, "Nlink"); ETERM * Size = erl_var_content(pattern2, "Size"); if(ERL_IS_INTEGER(Nlink) && ERL_IS_INTEGER(Mode) && ERL_IS_INTEGER(Size)){ stbuf->st_mode = S_IFREG | ERL_INT_VALUE(Mode); //permissions stbuf->st_nlink = ERL_INT_VALUE(Nlink); //files only have 1 stbuf->st_size = ERL_INT_VALUE(Size); // length of the file }else{ res = -ENOENT; } }else{ res = -ENOENT; } return res; }
static int process_command(byte *buf) { int retval = 0; ETERM *pattern, *tuple, *cmd, *port, *data; pattern = erl_format("{Cmd, Port, Data}"); tuple = erl_decode(buf); if (erl_match(pattern, tuple)) { cmd = erl_var_content(pattern, "Cmd"); port = erl_var_content(pattern, "Port"); data = erl_var_content(pattern, "Data"); switch (ERL_INT_VALUE(cmd)) { case CMD_AUTH: retval = process_auth(port, data); break; case CMD_ACCT: retval = process_acct(port, data); break; }; erl_free_term(cmd); erl_free_term(port); erl_free_term(data); } erl_free_term(pattern); erl_free_term(tuple); return retval; }
static int hello_readdir(const char *path, void *buf, fuse_fill_dir_t filler, off_t offset, struct fuse_file_info *fi) { int res = 0; ETERM * response = erl_rpc(FERL_DATA->erlang_fd,"gen_server","call",erl_format("[nefs,{read_dir,~s}]",path)); ETERM * pattern = erl_format("{ok,Listing}"); if(erl_match(pattern, response)) { //directory ETERM * Tail = erl_var_content(pattern, "Listing"); if(ERL_IS_LIST(Tail)){ while(!ERL_IS_EMPTY_LIST(Tail)){ ETERM * elem = ERL_CONS_HEAD(Tail); // add in the links to the previous folders filler(buf, ".", NULL, 0); filler(buf, "..", NULL, 0); // add in the folders contents if(ERL_IS_LIST(elem)){ filler(buf,(char *)ERL_BIN_PTR(elem),NULL,0); }else{ res = -ENOENT; break; } Tail = ERL_CONS_TAIL(Tail); } }else{ res = -ENOENT; } }else{ res = -ENOENT; } return res; }
static int process_command(unsigned char *buf) { int retval = 0; ETERM *pattern, *tuple, *cmd, *port, *data; pattern = erl_format("{Cmd, Port, Data}"); tuple = erl_decode(buf); if (erl_match(pattern, tuple)) { cmd = erl_var_content(pattern, "Cmd"); port = erl_var_content(pattern, "Port"); data = erl_var_content(pattern, "Data"); switch (ERL_INT_VALUE(cmd)) { case CMD_SALT: retval = process_encode_salt(port, data); break; case CMD_HASHPW: retval = process_hashpw(port, data); break; }; erl_free_term(cmd); erl_free_term(port); erl_free_term(data); } erl_free_term(pattern); erl_free_term(tuple); return retval; }
static int process_encode_salt(ETERM *pid, ETERM *data) { int retval = 0; ETERM *pattern, *cslt, *lr; byte *csalt = NULL; long log_rounds = -1; int csaltlen = -1; char ret[64]; pattern = erl_format("{Csalt, LogRounds}"); if (erl_match(pattern, data)) { cslt = erl_var_content(pattern, "Csalt"); csaltlen = ERL_BIN_SIZE(cslt); csalt = ERL_BIN_PTR(cslt); lr = erl_var_content(pattern, "LogRounds"); log_rounds = ERL_INT_UVALUE(lr); if (16 != csaltlen) { retval = process_reply(pid, CMD_SALT, "Invalid salt length"); } else if (log_rounds < 4 || log_rounds > 31) { retval = process_reply(pid, CMD_SALT, "Invalid number of rounds"); } else { encode_salt(ret, (u_int8_t*)csalt, csaltlen, log_rounds); retval = process_reply(pid, CMD_SALT, ret); } erl_free_term(cslt); erl_free_term(lr); }; erl_free_term(pattern); return retval; }
static int process_hashpw(ETERM *pid, ETERM *data) { int retval = 0; ETERM *pattern, *pwd, *slt; char *password, *salt; char *ret = NULL; pattern = erl_format("{Pass, Salt}"); if (erl_match(pattern, data)) { pwd = erl_var_content(pattern, "Pass"); password = erl_iolist_to_string(pwd); slt = erl_var_content(pattern, "Salt"); salt = erl_iolist_to_string(slt); if (NULL == (ret = bcrypt(password, salt)) || 0 == strcmp(ret, ":")) { retval = process_reply(pid, CMD_HASHPW, "Invalid salt"); } else { retval = process_reply(pid, CMD_HASHPW, ret); } erl_free_term(pwd); erl_free_term(slt); erl_free(password); erl_free(salt); }; erl_free_term(pattern); return retval; }
static int process_auth(ETERM *pid, ETERM *data) { int retval = 0; ETERM *pattern, *srv, *user, *pass; char *service, *username, *password; pattern = erl_format("{Srv, User, Pass}"); if (erl_match(pattern, data)) { srv = erl_var_content(pattern, "Srv"); service = erl_iolist_to_string(srv); user = erl_var_content(pattern, "User"); username = erl_iolist_to_string(user); pass = erl_var_content(pattern, "Pass"); password = erl_iolist_to_string(pass); retval = process_reply(pid, CMD_AUTH, auth(service, username, password)); erl_free_term(srv); erl_free_term(user); erl_free_term(pass); erl_free(service); erl_free(username); erl_free(password); }; erl_free_term(pattern); return retval; }
static int cmp_etseq(m_etseq *b1, m_etseq *b2) { int i; if (b1->_length != b2->_length) return 0; for (i = 0; i < b1->_length; i++) if (!erl_match(b1->_buffer[i], b2->_buffer[i])) return 0; return 1; }
static int hello_open(const char *path, struct fuse_file_info *fi) { int res = 0; ETERM * response = erl_rpc(FERL_DATA->erlang_fd,"gen_server","call",erl_format("[nefs,{open,~s,~i}]",path,fi->flags)); ETERM * pattern = erl_format("{ok,Fd}"); ETERM * pattern2 = erl_format("{error,access}"); if(erl_match(pattern, response)) { ETERM * Fd_Pid = erl_var_content(pattern, "Fd"); if(ERL_IS_PID(Fd_Pid)){ fi->fh = Fd_Pid; //store off the file handle pid to be used in subsequent functions }else{ res= -ENOENT; } }else if(erl_match(pattern2, response)){ res = -EACCES; }else{ res = -ENOENT; } return res; }
static int hello_read(const char *path, char *buf, size_t size, off_t offset, struct fuse_file_info *fi) { int ret_bytes = 0; ETERM * response = erl_rpc(FERL_DATA->erlang_fd,"file","pread",erl_format("[~s,{bof,~i},~i]",offset,size)); ETERM * pattern = erl_format("{ok,Data}"); if(erl_match(pattern, response)) { ETERM * Data = erl_var_content(pattern, "Data"); if(ERL_IS_BINARY(Data)){ ret_bytes = ERL_BIN_SIZE(Data); char * data = ERL_BIN_PTR(Data); memcpy(buf,data,size); //copy the data over into the buffer } } return ret_bytes; }
void process_send(ErlMessage* emsg, int erl_fd) { ETERM* master_pattern = erl_format("{call, Pid, Cmd}"); if (erl_match(master_pattern, emsg->msg)) { TRACE(("matched master pattern")); process_call(master_pattern, erl_fd); } else { erl_err_msg("could not match the master pattern."); } TRACE(("leaving process_send")); erl_free_term(master_pattern); }
static int process_acct(ETERM *pid, ETERM *data) { int retval = 0; ETERM *pattern, *srv, *user; char *service, *username; pattern = erl_format("{Srv, User}"); if (erl_match(pattern, data)) { srv = erl_var_content(pattern, "Srv"); service = erl_iolist_to_string(srv); user = erl_var_content(pattern, "User"); username = erl_iolist_to_string(user); retval = process_reply(pid, CMD_ACCT, acct_mgmt(service, username)); erl_free_term(srv); erl_free_term(user); erl_free(service); erl_free(username); } erl_free_term(pattern); return retval; }
static int process_hashpw(ETERM *pid, ETERM *data) { int retval = 0; ETERM *pattern, *pwd, *slt, *pwd_bin, *slt_bin; char password[1024]; char salt[1024]; char encrypted[1024] = { 0 }; (void)memset(&password, '\0', sizeof(password)); (void)memset(&salt, '\0', sizeof(salt)); pattern = erl_format("{Pass, Salt}"); if (erl_match(pattern, data)) { pwd = erl_var_content(pattern, "Pass"); pwd_bin = erl_iolist_to_binary(pwd); slt = erl_var_content(pattern, "Salt"); slt_bin = erl_iolist_to_binary(slt); if (ERL_BIN_SIZE(pwd_bin) > sizeof(password)) { retval = process_reply(pid, CMD_HASHPW, "Password too long"); } else if (ERL_BIN_SIZE(slt_bin) > sizeof(salt)) { retval = process_reply(pid, CMD_HASHPW, "Salt too long"); } else { memcpy(password, ERL_BIN_PTR(pwd_bin), ERL_BIN_SIZE(pwd_bin)); memcpy(salt, ERL_BIN_PTR(slt_bin), ERL_BIN_SIZE(slt_bin)); if (bcrypt(encrypted, password, salt)) { retval = process_reply(pid, CMD_HASHPW, "Invalid salt"); } else { retval = process_reply(pid, CMD_HASHPW, encrypted); } } erl_free_term(pwd); erl_free_term(slt); erl_free_term(pwd_bin); erl_free_term(slt_bin); }; erl_free_term(pattern); return retval; }
void process_call(ETERM* master_pattern, int erl_fd) { TRACE(("cnode called")); ETERM* msg_frompid = erl_var_content(master_pattern, "Pid"); ETERM* msg_tuple = erl_var_content(master_pattern, "Cmd"); ETERM* response; if (msg_frompid == NULL || msg_tuple == NULL) { erl_err_msg("could not get Pid or Cmd vars"); fprintf(stderr, "how do i erl_var_content lol\n"); return; } ETERM* init_cmd_pattern = erl_format("{init, Arg}"); if (erl_match(init_cmd_pattern, msg_tuple)) { TRACE(("matched init command")); process_init_cmd(init_cmd_pattern, erl_fd, msg_frompid); } else { erl_err_msg("got unknown function call."); response = erl_format("{ecap_node, {error, {function_clause, ~w}}}", msg_tuple); erl_send(erl_fd, msg_frompid, response); } TRACE(("cleaning up process call")); erl_free_term(response); erl_free_term(init_cmd_pattern); //erl_free_term(msg_frompid); //this needs to be freed by the watcher, I think erl_free_term(msg_tuple); TRACE(("leaving process_call")); }
static int cmp_et(m_et* b1, m_et *b2) { return erl_match(b1->e, b2->e) && b1->l == b2->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; }