Exemplo n.º 1
0
static term nif_erlang_concat_2(Context *ctx, int argc, term argv[])
{
    if (UNLIKELY(argc != 2)) {
        fprintf(stderr, "++: wrong args count\n");
        abort();
    }

    term prepend_list = argv[0];

    if (UNLIKELY(!term_is_nonempty_list(prepend_list))) {
        if (term_is_nil(prepend_list)) {
            return argv[1];

        } else {
            fprintf(stderr, "Argument error\n");
            abort();
        }
    }

    int len = term_list_length(prepend_list);
    memory_ensure_free(ctx, len * 2);

    // GC might have changed all pointers
    prepend_list = argv[0];
    term append_list = argv[1];

    term t = prepend_list;
    term list_begin = term_nil();
    term *prev_term = NULL;

    // TODO: handle impropers list
    while (!term_is_nil(t)) {
        term head = term_get_list_head(t);

        term *new_list_item = term_list_alloc(ctx);

        if (prev_term) {
            prev_term[0] = term_list_from_list_ptr(new_list_item);
        } else {
            list_begin = term_list_from_list_ptr(new_list_item);
        }

        prev_term = new_list_item;
        new_list_item[1] = head;

        t = term_get_list_tail(t);
    }

    if (prev_term) {
        prev_term[0] = append_list;
    }

    return list_begin;
}
Exemplo n.º 2
0
Arquivo: parse.c Projeto: GJDuck/SMCHR
/*
 * Initialise the parser.
 */
extern void parse_init(void)
{
    name_t entry;
    entry = name_lookup("false");
    entry->val = term_boolean(make_boolean(false));
    entry = name_lookup("inf");
    entry->val = term_num(make_num(1.0/0.0));
    entry = name_lookup("nil");
    entry->val = term_nil(make_nil());
    entry = name_lookup("true");
    entry->val = term_boolean(make_boolean(true));
}
Exemplo n.º 3
0
static term nif_erlang_display_1(Context *ctx, int argc, term argv[])
{
    UNUSED(ctx);

    if (argc != 1) {
        fprintf(stderr, "display: wrong args count\n");
        abort();
    }

    display_term(argv[0], ctx);
    printf("\n");

    return term_nil();
}
Exemplo n.º 4
0
static term nif_erlang_register_2(Context *ctx, int argc, term argv[])
{
    if (UNLIKELY((argc != 2) || !term_is_atom(argv[0]) || !term_is_pid(argv[1]))) {
        fprintf(stderr, "bad match\n");
        abort();
    }

    int atom_index = term_to_atom_index(argv[0]);
    int pid = term_to_local_process_id(argv[1]);

    globalcontext_register_process(ctx->global, atom_index, pid);

    return term_nil();
}
Exemplo n.º 5
0
static term binary_to_atom(Context *ctx, int argc, term argv[], int create_new)
{
    if (argc != 2) {
        fprintf(stderr, "binary_to_atom: wrong args count\n");
        abort();
    }

    if (UNLIKELY(argv[1] != term_from_atom_string(ctx->global, latin1_atom))) {
        fprintf(stderr, "binary_to_atom: only latin1 is supported.\n");
        abort();
    }

    char *atom_string = interop_binary_to_string(argv[0]);
    if (IS_NULL_PTR(atom_string)) {
        fprintf(stderr, "Failed to alloc temporary string\n");
        abort();
    }
    int atom_string_len = strlen(atom_string);
    if (UNLIKELY(atom_string_len > 255)) {
        fprintf(stderr, "Too long atom.\n");
        free(atom_string);
        abort();
    }

    AtomString atom = malloc(atom_string_len + 1);
    ((uint8_t *) atom)[0] = atom_string_len;
    memcpy(((char *) atom) + 1, atom_string, atom_string_len);

    unsigned long global_atom_index = atomshashtable_get_value(ctx->global->atoms_table, atom, ULONG_MAX);
    int has_atom = (global_atom_index != ULONG_MAX);

    if (create_new || has_atom) {
        if (!has_atom) {
            global_atom_index = globalcontext_insert_atom(ctx->global, atom);
        } else {
            free((void *) atom);
        }
        return term_from_atom_index(global_atom_index);

    } else {
        free((void *) atom);
        //TODO: error here
        return term_nil();
    }
}
Exemplo n.º 6
0
static term nif_erlang_tuple_to_list_1(Context *ctx, int argc, term argv[])
{
    if (argc != 1) {
        fprintf(stderr, "tuple_to_list: wrong args count\n");
        abort();
    }

    int tuple_size = term_get_tuple_arity(argv[0]);

    memory_ensure_free(ctx, tuple_size * 2);

    term tuple = argv[0];
    term prev = term_nil();

    for (int i = tuple_size - 1; i >= 0; i--) {
        prev = term_list_prepend(term_get_tuple_element(tuple, i), prev, ctx);
    }

    return prev;
}
Exemplo n.º 7
0
static term nif_erlang_integer_to_list_1(Context *ctx, int argc, term argv[])
{
    if (argc != 1) {
        fprintf(stderr, "integer_to_list: wrong args count\n");
        abort();
    }

    int32_t int_value = term_to_int32(argv[0]);
    char integer_string[24];

    snprintf(integer_string, 24, "%i", int_value);
    int integer_string_len = strlen(integer_string);

    memory_ensure_free(ctx, integer_string_len * 2);

    term prev = term_nil();
    for (int i = integer_string_len - 1; i >= 0; i--) {
        prev = term_list_prepend(term_from_int11(integer_string[i]), prev, ctx);
    }

    return prev;
}
Exemplo n.º 8
0
static term nif_erlang_atom_to_list_1(Context *ctx, int argc, term argv[])
{
    if (argc != 1) {
        fprintf(stderr, "list_to_atom: wrong args count\n");
        abort();
    }

    int atom_index = term_to_atom_index(argv[0]);
    AtomString atom_string = (AtomString) valueshashtable_get_value(ctx->global->atoms_ids_table, atom_index, (unsigned long) NULL);

    int atom_len = atom_string_len(atom_string);

    memory_ensure_free(ctx, atom_len * 2);

    term prev = term_nil();
    for (int i = atom_len - 1; i >= 0; i--) {
        char c = ((const char *) atom_string_data(atom_string))[i];
        prev = term_list_prepend(term_from_int11(c), prev, ctx);
    }

    return prev;
}