void* cb_http_args(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { http_args_t* args = (http_args_t*)enif_alloc(sizeof(http_args_t)); unsigned int len; if (!enif_get_list_length(env, argv[0], &len)) goto error0; len += 1; args->path = (char *)enif_alloc(len * sizeof(char)); if (!enif_get_string(env, argv[0], args->path, len, ERL_NIF_LATIN1)) goto error1; if (!enif_get_list_length(env, argv[1], &len)) goto error1; len += 1; args->body = (char *)enif_alloc(len * sizeof(char)); if (!enif_get_string(env, argv[1], args->body, len, ERL_NIF_LATIN1)) goto error2; if (!enif_get_list_length(env, argv[2], &len)) goto error2; len += 1; args->content_type = (char *)enif_alloc(len * sizeof(char)); if (!enif_get_string(env, argv[2], args->content_type, len, ERL_NIF_LATIN1)) goto error3; if (!enif_get_int(env, argv[3], (int*)&args->method)) goto error3; if (!enif_get_int(env, argv[4], (int*)&args->type)) goto error3; return (void*)args; error3: enif_free(args->content_type); error2: enif_free(args->path); error1: enif_free(args->body); error0: return NULL; }
static int x509_parse_subject(ErlNifEnv* env, ERL_NIF_TERM subject_tuple, int *num_subject_entries, x509_subject_entry **subject_entries){ int num_subject_tuple; unsigned num_subject_terms; ERL_NIF_TERM head, tail; int pair_arity; char *name; char *value; char *subject_string = NULL; const ERL_NIF_TERM* pair; int idx; x509_subject_entry* se; unsigned value_len; const ERL_NIF_TERM* subject_terms; *subject_entries = NULL; *num_subject_entries = 0; /* make sure this is a tuple with first term 'subject' */ if(!enif_get_tuple(env, subject_tuple, &num_subject_tuple, &subject_terms) || !atom_to_string(env, subject_terms[0], &subject_string) || strncmp(subject_string, SUBJECT_STR, subject_strlen)) { if(subject_string) free(subject_string); return 0; } free(subject_string); /* create room for the x509_subject_entry structs */ if(!enif_get_list_length(env, subject_terms[1], &num_subject_terms) || (NULL == (se = (x509_subject_entry*)malloc(num_subject_terms * sizeof(x509_subject_entry))))) return 0; /* get the first entry and prime the pump for walking the rest */ if(!enif_get_list_cell(env, subject_terms[1], &head, &tail) || !enif_get_tuple(env, head, &pair_arity, &pair) || pair_arity!=2) { return 0; } for(idx=0; idx<num_subject_terms; idx++){ atom_to_string(env, pair[0], &name); enif_get_list_length(env, pair[1], &value_len); value = (char*)malloc(value_len+1); enif_get_string(env, pair[1], value, value_len+1, ERL_NIF_LATIN1); (se+idx)->name = name; (se+idx)->value = value; if(!enif_get_list_cell(env, tail, &head, &tail) || !enif_get_tuple(env, head, &pair_arity, &pair) || pair_arity!=2) { break; } } *num_subject_entries = num_subject_terms; *subject_entries = se; return 1; }
static ERL_NIF_TERM list_to_cstr(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { int err, written, tmp; unsigned int l; char* cstr; err = enif_get_list_length(env, argv[0], &l); if (!err) { goto error; } l+=1; // Null Termination cstr = enif_alloc(sizeof(char)*l); if (!cstr) { goto error; } written = 0; while (written<(l)) { tmp = enif_get_string(env, argv[0], cstr+written, l-written, ERL_NIF_LATIN1); if (tmp<=0) { enif_free(cstr); goto error; } written += tmp; } return enif_make_tuple2(env, enif_make_int64(env, (ptr_t)cstr), enif_make_string(env, "nifty.char *", ERL_NIF_LATIN1)); error: return enif_make_badarg(env); }
int init_parser(Parser* parser, ErlNifEnv* env, ERL_NIF_TERM arg, ErlNifBinary* buffer, ERL_NIF_TERM columns) { parser->env = env; parser->atoms = enif_priv_data(env); parser->raw = arg; parser->buffer = buffer->data; if(!enif_get_list_length(env, columns, &parser->table_width)) return 0; ERL_NIF_TERM list, head, tail; int val, index = 0; parser->columns = (int *) enif_alloc(parser->table_width * sizeof(int)); list = columns; while(enif_get_list_cell(env, list, &head, &tail)) { if (!enif_get_int(env, head, &val)) return 0; parser->columns[index] = val; index++; list = tail; } parser->frame_start = 0; parser->frame_size = 0; parser->buffer_size = buffer->size; return 1; }
static ERL_NIF_TERM do_bind(ErlNifEnv *env, sqlite3 *db, sqlite3_stmt *stmt, const ERL_NIF_TERM arg) { int parameter_count = sqlite3_bind_parameter_count(stmt); int i, is_list, r; ERL_NIF_TERM list, head, tail; unsigned int list_length; is_list = enif_get_list_length(env, arg, &list_length); if(!is_list) return make_error_tuple(env, "bad_arg_list"); if(parameter_count != list_length) return make_error_tuple(env, "args_wrong_length"); sqlite3_reset(stmt); list = arg; for(i=0; i < list_length; i++) { enif_get_list_cell(env, list, &head, &tail); r = bind_cell(env, head, stmt, i+1); if(r == -1) return make_error_tuple(env, "wrong_type"); if(r != SQLITE_OK) return make_sqlite3_error_tuple(env, r, db); list = tail; } return make_atom(env, "ok"); }
GEOSGeometry* eterm_to_geom_polygon(ErlNifEnv *env, const ERL_NIF_TERM *eterm) { ERL_NIF_TERM outer_eterm, inner_eterm, tail; unsigned int rings_num, i; GEOSCoordSequence *outer_seq, *inner_seq; GEOSGeometry *outer_geom, *geom; GEOSGeometry **geoms; enif_get_list_length(env, *eterm, &rings_num); enif_get_list_cell(env, *eterm, &outer_eterm, &inner_eterm); outer_seq = eterm_to_geom_linestring_coords(env, &outer_eterm); outer_geom = GEOSGeom_createLinearRing(outer_seq); // if there are holes geoms = malloc(sizeof(GEOSGeometry*)*rings_num-1); for (i=0; enif_get_list_cell(env, inner_eterm, &inner_eterm, &tail); i++) { inner_seq = eterm_to_geom_linestring_coords(env, &inner_eterm); geoms[i] = GEOSGeom_createLinearRing(inner_seq); inner_eterm = tail; } geom = GEOSGeom_createPolygon(outer_geom, geoms, rings_num-1); free(geoms); return geom; }
inline static ERL_NIF_TERM do_offset(ErlNifEnv* env, UCalendar* cal, date_fun_ptr fun, const ERL_NIF_TERM in) { UCalendarDateFields field; UErrorCode status = U_ZERO_ERROR; ERL_NIF_TERM head, tail; ERL_NIF_TERM* tuple; unsigned int count, i; int32_t len, offset; char value[ATOM_LEN]; int parsed_value; i = 0; if (!enif_get_list_length(env, in, &count)) return enif_make_badarg(env); tail = in; while (enif_get_list_cell(env, tail, &head, &tail)) { if (enif_get_tuple(env, head, &len, (const ERL_NIF_TERM**) &tuple) && (len == 2)) { /* Set an attribute start */ if (!(enif_get_atom(env, tuple[0], (char*) value, ATOM_LEN, ERL_NIF_LATIN1) && enif_get_int(env, tuple[1], &offset))) goto bad_elem; parsed_value = parseCalendarDateField(value); if ((parsed_value == -1)) goto bad_elem; field = (UCalendarDateFields) parsed_value; fun(cal, field, offset, &status); if (U_FAILURE(status)) goto bad_elem; /* Set an attribute end */ } else goto bad_elem; } return calendar_to_double(env, (const UCalendar*) cal); bad_elem: return list_element_error(env, in, i); }
ERL_NIF_TERM date_clear(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { UErrorCode status = U_ZERO_ERROR; UCalendar* cal; cloner* ptr; double date; UCalendarDateFields field; ERL_NIF_TERM head, tail; unsigned int count, i = 0; char value[ATOM_LEN]; int parsed_value; if(!((argc == 3) && enif_get_resource(env, argv[0], calendar_type, (void**) &ptr) && enif_get_double(env, argv[1], &date) && enif_get_list_length(env, argv[2], &count))) { return enif_make_badarg(env); } cal = (UCalendar*) cloner_get(ptr); CHECK_RES(env, cal); ucal_setMillis(cal, (UDate) date, &status); CHECK(env, status); tail = argv[2]; while (enif_get_list_cell(env, tail, &head, &tail)) { /* Set an attribute start */ if (!enif_get_atom(env, head, (char*) value, ATOM_LEN, ERL_NIF_LATIN1)) goto bad_elem; parsed_value = parseCalendarDateField(value); if ((parsed_value == -1)) goto bad_elem; field = (UCalendarDateFields) parsed_value; ucal_clearField(cal, field); if (U_FAILURE(status)) goto bad_elem; /* Set an attribute end */ } return calendar_to_double(env, (const UCalendar*) cal); bad_elem: return list_element_error(env, argv[2], i); }
static char* alloc_str(ErlNifEnv* env, const ERL_NIF_TERM list, unsigned* len) { unsigned list_len; if (!enif_get_list_length(env, list, &list_len)) return NULL; list_len++; *len = list_len; return (char*)enif_alloc(list_len); }
//////////////////// Matrix buffer ERL_NIF_TERM pteracuda_nifs_new_matrix_int_buffer(ErlNifEnv *env, int argc, const ERL_NIF_TERM argv[]) { unsigned int rows; unsigned int cols; bool from_matrix = false; MatrixOrientation orientation = ROW_MAJOR; unsigned int mo; if (argc == 2) { ERL_NIF_TERM head; ERL_NIF_TERM tail; if(!enif_get_list_length(env, argv[0], &rows) || !enif_get_list_cell(env, argv[0], &head, &tail) || !enif_get_list_length(env, head, &cols) || !enif_get_uint(env, argv[1], &mo)) return enif_make_badarg(env); from_matrix = true; }else if (argc !=3 || !enif_get_uint(env, argv[0], &rows) || !enif_get_uint(env, argv[1], &cols) || !enif_get_uint(env, argv[2], &mo)) { return enif_make_badarg(env); } PCudaBufferRef *ref = (PCudaBufferRef *) enif_alloc_resource(pteracuda_buffer_resource, sizeof(PCudaBufferRef)); if (!ref) { return OOM_ERROR; } if(mo == ROW_MAJOR){ orientation = ROW_MAJOR; }else if (mo == COLUMN_MAJOR){ orientation = COLUMN_MAJOR; }else return enif_make_badarg(env); ref->buffer = new PCudaMatrixIntBuffer(rows, cols, orientation); ref->destroyed = false; if (from_matrix) ref->buffer->write(env, argv[0]); ERL_NIF_TERM res = enif_make_resource(env, ref); enif_release_resource(ref); return enif_make_tuple2(env, ATOM_OK, res); }
static ERL_NIF_TERM create_worker_data(ErlNifEnv *env, int32_t argc, const ERL_NIF_TERM *argv) { BundlePaths *bundle_paths; ERL_NIF_TERM list, head, tail, result; unsigned int index, length, string_length; char *new_path; WorkerData *worker_data; (void)(argc); list = argv[0]; if (!enif_is_list(env, list)) return enif_make_badarg(env); enif_get_list_length(env, list, &length); bundle_paths = bundle_paths_new(length); index = 0; tail = list; while (enif_get_list_cell(env, tail, &head, &tail)) { if (!enif_is_list(env, head)) return enif_make_badarg(env); enif_get_list_length(env, head, &string_length); new_path = malloc(sizeof(char) * string_length + 1); if (!enif_get_string(env, head, new_path, string_length + 1, ERL_NIF_LATIN1)) return enif_make_badarg(env); bundle_paths->paths[index] = new_path; index += 1; } worker_data = enif_alloc_resource(WORKER_DATA, sizeof(WorkerData)); worker_data_initialize(worker_data, length); worker_data_read(bundle_paths, worker_data); result = enif_make_resource(env, worker_data); enif_release_resource(&worker_data); bundle_paths_free(&bundle_paths); return result; }
static ERL_NIF_TERM do_write(ErlNifEnv *env, int argc, const ERL_NIF_TERM argv[]) { static PortMidiStream ** stream; ErlNifResourceType* streamType = (ErlNifResourceType*)enif_priv_data(env); if(!enif_get_resource(env, argv[0], streamType, (PortMidiStream **) &stream)) { return enif_make_badarg(env); } ERL_NIF_TERM erlMessages = argv[1]; const ERL_NIF_TERM * erlEvent; const ERL_NIF_TERM * erlMessage; ERL_NIF_TERM erlTuple; unsigned int numOfMessages; int tupleSize; enif_get_list_length(env, erlMessages, &numOfMessages); PmEvent events[numOfMessages]; long int status, note, velocity, timestamp; for(unsigned int i = 0; i < numOfMessages; i++) { enif_get_list_cell(env, erlMessages, &erlTuple, &erlMessages); enif_get_tuple(env, erlTuple, &tupleSize, &erlEvent); enif_get_tuple(env, erlEvent[0], &tupleSize, &erlMessage); enif_get_long(env, erlMessage[0], &status); enif_get_long(env, erlMessage[1], ¬e); enif_get_long(env, erlMessage[2], &velocity); enif_get_long(env, erlEvent[1], ×tamp); PmEvent event; event.message = Pm_Message(status, note, velocity); event.timestamp = timestamp; events[i] = event; } PmError writeError; writeError = Pm_Write(*stream, events, numOfMessages); if (writeError == pmNoError) { return enif_make_atom(env, "ok"); } const char * writeErrorMsg; writeErrorMsg = Pm_GetErrorText(writeError); return enif_make_tuple2( env, enif_make_atom(env, "error"), enif_make_string(env, writeErrorMsg, ERL_NIF_LATIN1) ); }
/* * argv[0] atom with length of 6 * argv[1] list with length of 6 * argv[2] empty list * argv[3] not an atom * argv[4] not a list */ static ERL_NIF_TERM length_test(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { unsigned len; if (!enif_get_atom_length(env, argv[0], &len, ERL_NIF_LATIN1) || len != 6) return enif_make_badarg(env); if (!enif_get_list_length(env, argv[1], &len) || len != 6) return enif_make_badarg(env); if (!enif_get_list_length(env, argv[2], &len) || len != 0) return enif_make_badarg(env); if (enif_get_atom_length(env, argv[3], &len, ERL_NIF_LATIN1)) return enif_make_badarg(env); if (enif_get_list_length(env, argv[4], &len)) return enif_make_badarg(env); return enif_make_atom(env, "ok"); }
/* OGRDataSourceH CPL_DLL OGROpen(const char *, int, OGRSFDriverH *) CPL_WARN_UNUSED_RESULT; {ok, DataSource} = lgeo_ogr:open("test/polygon.shp"). {ok, DataSource} = lgeo_ogr:open("test/polygon.shp", 1). */ static ERL_NIF_TERM open(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { int update = 0; // read-only (default) OGRDataSourceH datasource; ERL_NIF_TERM eterm; /* OGRSFDriverH *pahDriver; ERL_NIF_TERM eterm1, eterm2; */ unsigned len; if (argc > 0 && !enif_get_list_length(env, argv[0], &len)) { return enif_make_badarg(env); } char * filename = enif_alloc(sizeof(char)*(len+1)); if(!enif_get_string(env, argv[0], filename, len+1, ERL_NIF_LATIN1)) { return enif_make_badarg(env); } if (argc == 2 && !enif_get_int(env, argv[1], &update)) { return enif_make_badarg(env); } datasource = OGROpen(filename, update, NULL); //datasource = OGROpen(filename, upadate, pahDriver); enif_free(filename); if(datasource == NULL) { return enif_make_atom(env, "undefined"); } OGRDataSourceH **hDS = \ enif_alloc_resource(OGR_DS_RESOURCE, sizeof(OGRDataSourceH*)); *hDS = datasource; /* OGRSFDriverH **hDriver = \ enif_alloc_resource(OGR_D_RESOURCE, sizeof(OGRSFDriverH*)); *hDriver = *pahDriver; */ eterm = enif_make_resource(env, hDS); enif_release_resource(hDS); return enif_make_tuple2(env, enif_make_atom(env, "ok"), eterm); /* eterm2 = enif_make_resource(env, hDriver); enif_release_resource(hDriver); return enif_make_tuple2(env, eterm1, eterm1); */ }
static int do_iterator_options(ErlNifEnv* env, UCollator* col, const ERL_NIF_TERM in, unsigned int& i) { ERL_NIF_TERM out, list; ERL_NIF_TERM* tuple; unsigned int count; UErrorCode status = U_ZERO_ERROR; int32_t len; char value[ATOM_LEN], key[ATOM_LEN]; int parsed_value, parsed_key; i = 0; if (!enif_get_list_length(env, in, &count)) return 0; list = in; while (enif_get_list_cell(env, list, &out, &list)) { if (enif_get_tuple(env, out, &len, (const ERL_NIF_TERM**) &tuple) && (len == 2)) { /* Set an attribute start */ if (!(enif_get_atom(env, tuple[0], (char*) key, ATOM_LEN, ERL_NIF_LATIN1) && enif_get_atom(env, tuple[1], (char*) value, ATOM_LEN, ERL_NIF_LATIN1))) return 0; parsed_key = parseAttrKey(key); parsed_value = parseAttrValue(value); if ((parsed_value == -1) || (parsed_key == -1)) return 0; ucol_setAttribute(col, (UColAttribute) parsed_key, (UColAttributeValue) parsed_value, &status); if (U_FAILURE(status)) return 0; /* Set an attribute end */ } else return 0; } return 1; }
static ERL_NIF_TERM helloworld (ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { unsigned int length = 0; enif_get_list_length(env, argv[0], &length); char *name = (char *)enif_alloc(++length); enif_get_string(env, argv[0], name, length, ERL_NIF_LATIN1); printf("Hello, %s!\n", name); enif_free(name); return enif_make_atom(env, "ok"); }
static ERL_NIF_TERM eval2(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { ErlNifBinary script_binary; if (!enif_inspect_binary(env, argv[0], &script_binary)){ return enif_make_badarg(env); } if (!enif_is_list(env, argv[1])) { enif_release_binary(&script_binary); return enif_make_badarg(env); } mrb_state *mrb; mrbc_context *cxt; mrb = mrb_open(); if (mrb == NULL) { return enif_make_atom(env, "error"); } unsigned int mrb_argv_len; enif_get_list_length(env, argv[1], &mrb_argv_len); mrb_value mrb_argv = mrb_ary_new(mrb); ERL_NIF_TERM cur; for(cur = argv[1]; !enif_is_empty_list(env, cur); ) { ERL_NIF_TERM head, tail; enif_get_list_cell(env, cur, &head, &tail); mrb_ary_push(mrb, mrb_argv, erl2mruby(env, mrb, head)); cur = tail; } mrb_define_global_const(mrb, "ARGV", mrb_argv); char *script = malloc(script_binary.size+1); strncpy(script, (const char *)script_binary.data, (int)script_binary.size); script[script_binary.size] = '\0'; cxt = mrbc_context_new(mrb); struct mrb_parser_state* st = mrb_parse_string(mrb, (const char *)script, cxt); int n = mrb_generate_code(mrb, st); mrb_pool_close(st->pool); mrb_value result = mrb_run(mrb, mrb_proc_new(mrb, mrb->irep[n]), mrb_nil_value()); ERL_NIF_TERM erl_result = mruby2erl(env, mrb, result); free(script); mrbc_context_free(mrb, cxt); mrb_close(mrb); enif_release_binary(&script_binary); return erl_result; }
static ERL_NIF_TERM exec_nif(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { unsigned path_length, args_count, arg_length; ERL_NIF_TERM head, tail; int i = 0; enif_get_list_length(env, argv[0], &path_length); enif_get_list_length(env, argv[1], &args_count); char* exec_argv[args_count + 2]; char path[path_length + 1]; if (!enif_get_string(env, argv[0], path, path_length + 1, ERL_NIF_LATIN1) || !enif_is_list(env, argv[1])) { return enif_make_badarg(env); } tail = argv[1]; while(enif_get_list_cell(env, tail, &head, &tail) != 0) { enif_get_list_length(env, head, &arg_length); char* arg = (char*) malloc(sizeof(char) * (arg_length + 1)); if (!enif_get_string(env, head, arg, arg_length + 1, ERL_NIF_LATIN1)) { return enif_make_badarg(env); } exec_argv[i + 1] = arg; i++; } exec_argv[0] = path; exec_argv[args_count + 1] = NULL; execv(path, exec_argv); return enif_make_atom(env, "ok"); }
void* cb_mtouch_args(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { mtouch_args_t* args = (mtouch_args_t*)enif_alloc(sizeof(mtouch_args_t)); ERL_NIF_TERM* currKey; ERL_NIF_TERM tail; ErlNifBinary key_binary; if (!enif_get_list_length(env, argv[0], &args->numkeys)) goto error0; args->keys = malloc(sizeof(char*) * args->numkeys); args->nkeys = malloc(sizeof(size_t) * args->numkeys); currKey = malloc(sizeof(ERL_NIF_TERM)); tail = argv[0]; int i = 0; while(0 != enif_get_list_cell(env, tail, currKey, &tail)) { if (!enif_inspect_iolist_as_binary(env, *currKey, &key_binary)) goto error1; args->keys[i] = malloc(sizeof(char) * key_binary.size); memcpy(args->keys[i], key_binary.data, key_binary.size); args->nkeys[i] = key_binary.size; i++; } args->exp = malloc(sizeof(int64_t) * args->numkeys); tail = argv[1]; int i2 = 0; while(0 != enif_get_list_cell(env, tail, currKey, &tail)) { if (!enif_get_long(env, *currKey, &args->exp[i2])) goto error2; i2++; } free(currKey); return (void*)args; int f = 0; error2: free(args->exp); error1: for(f = 0; f < i; f++) { free(args->keys[f]); } free(args->keys); free(args->nkeys); error0: enif_free(args); return NULL; }
void *cb_connect_args(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { connect_args_t* args = (connect_args_t*)enif_alloc(sizeof(connect_args_t)); unsigned arg_length; if (!enif_get_list_length(env, argv[0], &arg_length)) goto error0; args->host = (char *) malloc(arg_length + 1); if (!enif_get_string(env, argv[0], args->host, arg_length + 1, ERL_NIF_LATIN1)) goto error1; if (!enif_get_list_length(env, argv[1], &arg_length)) goto error1; args->user = (char *) malloc(arg_length + 1); if (!enif_get_string(env, argv[1], args->user, arg_length + 1, ERL_NIF_LATIN1)) goto error2; if (!enif_get_list_length(env, argv[2], &arg_length)) goto error2; args->pass = (char *) malloc(arg_length + 1); if (!enif_get_string(env, argv[2], args->pass, arg_length + 1, ERL_NIF_LATIN1)) goto error3; if (!enif_get_list_length(env, argv[3], &arg_length)) goto error3; args->bucket = (char *) malloc(arg_length + 1); if (!enif_get_string(env, argv[3], args->bucket, arg_length + 1, ERL_NIF_LATIN1)) goto error4; return (void*)args; error4: free(args->bucket); error3: free(args->pass); error2: free(args->user); error1: free(args->host); error0: enif_free(args); return NULL; }
static ERL_NIF_TERM slog(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { int priority = LOG_DEBUG; enif_get_int(env, argv[0], &priority); unsigned int length = 0; enif_get_list_length(env, argv[1], &length); char *buf = (char *)enif_alloc(++length); enif_get_string(env,argv[1], buf, length, ERL_NIF_LATIN1); syslog(priority,"%s",buf); enif_free(buf); return enif_make_atom(env, ENIF_OK); }
static ERL_NIF_TERM nif_scheduler_reconcileTasks(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { unsigned int length ; state_ptr state = (state_ptr) enif_priv_data(env); if(state->initilised == 0 ) { return enif_make_tuple2(env, enif_make_atom(env, "state_error"), enif_make_atom(env, "scheduler_not_inited")); } if(!enif_is_list(env, argv[0])) { return enif_make_tuple3(env, enif_make_atom(env, "argument_error"), enif_make_atom(env, "invalid_or_corrupted_parameter"), enif_make_atom(env, "task_status_array")); }; if(!enif_get_list_length(env, argv[0], &length)) { return enif_make_tuple3(env, enif_make_atom(env, "argument_error"), enif_make_atom(env, "invalid_or_corrupted_parameter"), enif_make_atom(env, "task_status_array")); } ErlNifBinary binary_arr[length]; if(!inspect_array_of_binary_objects(env, argv[0], &binary_arr )) { return enif_make_tuple3(env, enif_make_atom(env, "argument_error"), enif_make_atom(env, "invalid_or_corrupted_parameter"), enif_make_atom(env, "task_status_array")); } BinaryNifArray binaryNifArrayHolder ; binaryNifArrayHolder.length = length; binaryNifArrayHolder.obj = &binary_arr[0]; SchedulerDriverStatus status = scheduler_reconcileTasks( state->scheduler_state, &binaryNifArrayHolder); return get_return_value_from_status(env, status); }
static ERL_NIF_TERM open_1(ErlNifEnv *env, int argc, const ERL_NIF_TERM argv[]) { char *device; unsigned int length; uint8_t tmp8; uint32_t tmp32; state.env = env; state.fd = -1; state.mode = 0; state.bits_per_word = 0; state.max_speed_hz = 0; if (argc != 1 || !enif_is_list(env, argv[0])) return enif_make_badarg(env); if (!enif_get_list_length(env, argv[0], &length)) return enif_make_badarg(env); device = (char *) enif_alloc(length + 1); enif_get_string(env, argv[0], device, length + 1, ERL_NIF_LATIN1); if ((state.fd = open(device, O_RDWR, 0)) == -1) { return enif_make_badarg(env); } if (ioctl(state.fd, SPI_IOC_RD_MODE, &tmp8) == -1) { close(state.fd); enif_free(device); return enif_make_tuple2(env, enif_make_atom(env, "error"), enif_make_string(env, "read mode", ERL_NIF_LATIN1)); } state.mode = tmp8; if (ioctl(state.fd, SPI_IOC_RD_BITS_PER_WORD, &tmp8) == -1) { close(state.fd); enif_free(device); return enif_make_tuple2(env, enif_make_atom(env, "error"), enif_make_string(env, "read bits per word", ERL_NIF_LATIN1)); } state.bits_per_word = tmp8; if (ioctl(state.fd, SPI_IOC_RD_MAX_SPEED_HZ, &tmp32) == -1) { close(state.fd); enif_free(device); return enif_make_tuple2(env, enif_make_atom(env, "error"), enif_make_string(env, "read max speed hz", ERL_NIF_LATIN1)); } state.max_speed_hz = tmp32; enif_free(device); return enif_make_atom(env, "ok"); }
static ERL_NIF_TERM xfer2_1(ErlNifEnv *env, int argc, const ERL_NIF_TERM argv[]) { int status, val, i; struct spi_ioc_transfer xfer; uint8_t *txbuf, *rxbuf; unsigned int length; ERL_NIF_TERM cell, head, tail, res, list; if (state.fd == -1) return enif_make_tuple2(env, enif_make_atom(env, "error"), enif_make_string(env, "device closed", ERL_NIF_LATIN1)); if (argc != 1 || !enif_is_list(env, argv[0])) return enif_make_badarg(env); if (!enif_get_list_length(env, argv[0], &length)) return enif_make_badarg(env); txbuf = (uint8_t *) enif_alloc(sizeof(uint8_t) * length); rxbuf = (uint8_t *) enif_alloc(sizeof(uint8_t) * length); list = argv[0]; for (i = 0; enif_get_list_cell(env, list, &head, &tail); ++i, list = tail) { if (!enif_get_int(env, head, &val)) { return enif_make_badarg(env); } txbuf[i] = val; } xfer.tx_buf = (unsigned long) txbuf; xfer.rx_buf = (unsigned long) rxbuf; xfer.len = length; status = ioctl(state.fd, SPI_IOC_MESSAGE(1), &xfer); if (status < 0) { enif_free(txbuf); enif_free(rxbuf); return enif_make_tuple2(env, enif_make_atom(env, "error"), enif_make_string(env, "spi ioc message", ERL_NIF_LATIN1)); } list = enif_make_list(env, 0); for (i = length - 1; i >= 0; --i) { cell = enif_make_uint(env, (unsigned int) rxbuf[i]); list = enif_make_list_cell(env, cell, list); } res = enif_make_tuple2(env, enif_make_atom(env, "ok"), list); enif_free(txbuf); enif_free(rxbuf); return res; }
static ERL_NIF_TERM mem_write_list(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { unsigned int i, l, data, err; int ar; char* ptr; ERL_NIF_TERM head, tail, list, *tpl; err = enif_get_list_length(env, argv[0], &l); if (!err) { goto error; } err = enif_get_tuple(env, argv[1], &ar, (const ERL_NIF_TERM**)(&tpl)); if (err) { err = nifty_get_ptr(env, tpl[0], (ptr_t*)&ptr); } if (!err) { goto error; } list = argv[0]; i = 0; while (!enif_is_empty_list(env, list)) { err = enif_get_list_cell(env, list, &head, &tail); list = tail; if (!err) { goto error; } err = enif_get_uint(env, head, &data); if (!err) { goto error; } *(ptr+i++) = (char)data; } return argv[1]; error: return enif_make_badarg(env); }
ERL_NIF_TERM date_get_fields(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) { UErrorCode status = U_ZERO_ERROR; UCalendar* cal; cloner* ptr; double date; ERL_NIF_TERM res; ERL_NIF_TERM head, tail, out; unsigned int count; if(!((argc == 3) && enif_get_resource(env, argv[0], calendar_type, (void**) &ptr) && enif_get_double(env, argv[1], &date) && enif_get_list_length(env, argv[2], &count))) { return enif_make_badarg(env); } cal = (UCalendar*) cloner_get(ptr); CHECK_RES(env, cal); ucal_setMillis(cal, (UDate) date, &status); CHECK(env, status); tail = argv[2]; out = enif_make_list(env, 0); while (enif_get_list_cell(env, tail, &head, &tail)) { /* Set an attribute start */ res = do_date_get_field(env, cal, head, status); CHECK(env, status); out = enif_make_list_cell(env, enif_make_tuple2(env, head, res), out); /* Set an attribute end */ } return out; }
GEOSGeometry* eterm_to_geom_multi(ErlNifEnv *env, ERL_NIF_TERM eterm, int type, GEOSGeometry*(*eterm_to_geom)(ErlNifEnv *env, const ERL_NIF_TERM *eterm)) { unsigned int i, geoms_num; GEOSGeometry *geom; GEOSGeometry **geoms; ERL_NIF_TERM tail; enif_get_list_length(env, eterm, &geoms_num); geoms = malloc(sizeof(GEOSGeometry*)*geoms_num); for (i=0; enif_get_list_cell(env, eterm , &eterm, &tail); i++) { geoms[i] = (*eterm_to_geom)(env, &eterm); eterm = tail; } geom = GEOSGeom_createCollection(type, geoms, geoms_num); free(geoms); return geom; }
GEOSCoordSeq eterm_to_geom_linestring_coords(ErlNifEnv *env, const ERL_NIF_TERM *coords_list) { unsigned int i=0, len; GEOSCoordSequence *coords_seq; ERL_NIF_TERM head, tail; enif_get_list_length(env, *coords_list, &len); coords_seq = GEOSCoordSeq_create(len, DIMENSION); while (enif_get_list_cell(env, *coords_list, &head, &tail)) { if (!set_GEOSCoordSeq_from_eterm_list(coords_seq, i, env, &head)) { return NULL; } i++; coords_list = &tail; } return coords_seq; }
/* 0: fd, 1: list of buffers */ static ERL_NIF_TERM nif_writev(ErlNifEnv *env, int argc, const ERL_NIF_TERM argv[]) { ERL_NIF_TERM head = {0}; ERL_NIF_TERM tail = {0}; struct iovec iovs[IOVMAX]; int fd = -1; unsigned iovcnt; ssize_t n = 0; if (!enif_get_int(env, argv[0], &fd)) return enif_make_badarg(env); tail = argv[1]; if (!enif_get_list_length(env, tail, &iovcnt)) return enif_make_badarg(env); if (!iovcnt || iovcnt > IOVMAX) return enif_make_badarg(env); iovcnt = 0; while (enif_get_list_cell(env, tail, &head, &tail)) { struct iovec *iov = &iovs[iovcnt++]; ErlNifBinary buf = {0}; if (!enif_inspect_binary(env, head, &buf)) return enif_make_badarg(env); iov->iov_base = buf.data; iov->iov_len = buf.size; } n = writev(fd, iovs, iovcnt); if (n < 0) return error_tuple(env, errno); return enif_make_tuple2(env, atom_ok, enif_make_int64(env, n)); }
static inline int match_proplist(ErlNifEnv* env, ERL_NIF_TERM term, State *st){ ERL_NIF_TERM list, head, tail; unsigned len, i; if(!enif_get_list_length(env, term, &len)){ return 0; } b_putc('{', st); list = term; for(i = 0; i < len; i++){ enif_get_list_cell(env, list, &head, &tail); if(i > 0){ b_putc(',', st); } if(!match_pair(env, head, st)){ return 0; } list = tail; } b_putc('}', st); return 1; }