Beispiel #1
0
int16_t corto_value_field(
    corto_value *val,
    const char* field_expr,
    corto_value *out)
{
    corto_type t = corto_value_typeof(val);
    corto_object o = corto_value_objectof(val);
    void *ptr = corto_value_ptrof(val);

    corto_field field = {0};

    ut_try(corto_field_lookup(field_expr, t, ptr, &field), NULL);

    if (field.index != -1) {
        *out = corto_value_element(o, field.type, field.index, field.ptr);
    } else if (!field.member && !field.is_super) {
        if (o == ptr) {
            *out = corto_value_base(field.ptr, field.type);
        } else {
            /* super member of a nested sub-struct */
            *out = corto_value_pointer(field.ptr, field.type);
        }
    } else {
        if (field.is_super) {
            *out = corto_value_base(field.ptr, field.type);
        } else {
            *out = corto_value_member(o, field.member, field.ptr);
        }
    }

    return 0;
error:
    return -1;
}
Beispiel #2
0
corto_int16 corto_value_memberExpr(corto_value *val, corto_string member, corto_value *out) {
    corto_type t = corto_value_typeof(val);
    corto_object o = corto_value_objectof(val);
    void *ptr = corto_value_ptrof(val);

    corto_id tokens;
    strncpy(tokens, member, sizeof(corto_id));

    char *cur = tokens, *prev = tokens;
    do {
        if (cur && (cur = strchr(cur + 1, '.'))) *cur = '\0';

        if (!corto_instanceof(corto_interface_o, t)) {
            corto_seterr(
                "cannot get member from a non-composite value (type is '%s')",
                corto_fullpath(NULL, t));
            goto error;
        }

        if (!strcmp(prev, "super")) {
            if (!(t = (corto_type)corto_interface(t)->base)) {
                corto_seterr("super unpexpected: interface '%s' does not have a base",
                    corto_fullpath(NULL, t));
                goto error;
            } else {
                *out = corto_value_base(ptr, t);
            }
        } else {
            corto_member m = corto_interface_resolveMember(t, prev);
            if (!m) {
                corto_seterr(
                    "unresolved member '%s' in type '%s'",
                    prev,
                    corto_fullpath(NULL, t));
                goto error;
            }

            ptr = CORTO_OFFSET(ptr, m->offset);
            t = m->type;

            *out = corto_value_member(o, m, ptr);
        }

        prev = cur + 1;
    } while (cur);

    return 0;
error:
    return -1;
}