static int foreach_property(const uint32_t off,
        void (*propfn)(const prop_info *pi, void *cookie), void *cookie)
{
    prop_bt *trie = reinterpret_cast<prop_bt*>(to_prop_obj(off));
    if (!trie)
        return -1;

    if (trie->left) {
        const int err = foreach_property(trie->left, propfn, cookie);
        if (err < 0)
            return -1;
    }
    if (trie->prop) {
        prop_info *info = reinterpret_cast<prop_info*>(to_prop_obj(trie->prop));
        if (!info)
            return -1;
        propfn(info, cookie);
    }
    if (trie->children) {
        const int err = foreach_property(trie->children, propfn, cookie);
        if (err < 0)
            return -1;
    }
    if (trie->right) {
        const int err = foreach_property(trie->right, propfn, cookie);
        if (err < 0)
            return -1;
    }

    return 0;
}
bool prop_area::foreach_property(prop_bt *const trie,
        void (*propfn)(const prop_info *pi, void *cookie), void *cookie)
{
    if (!trie)
        return false;

    uint_least32_t left_offset = atomic_load_explicit(&trie->left, memory_order_relaxed);
    if (left_offset != 0) {
        const int err = foreach_property(to_prop_bt(&trie->left), propfn, cookie);
        if (err < 0)
            return false;
    }
    uint_least32_t prop_offset = atomic_load_explicit(&trie->prop, memory_order_relaxed);
    if (prop_offset != 0) {
        prop_info *info = to_prop_info(&trie->prop);
        if (!info)
            return false;
        propfn(info, cookie);
    }
    uint_least32_t children_offset = atomic_load_explicit(&trie->children, memory_order_relaxed);
    if (children_offset != 0) {
        const int err = foreach_property(to_prop_bt(&trie->children), propfn, cookie);
        if (err < 0)
            return false;
    }
    uint_least32_t right_offset = atomic_load_explicit(&trie->right, memory_order_relaxed);
    if (right_offset != 0) {
        const int err = foreach_property(to_prop_bt(&trie->right), propfn, cookie);
        if (err < 0)
            return false;
    }

    return true;
}
Exemplo n.º 3
0
int property_list(void (*propfn)(const char *key, const char *value, void *cookie),
                  void *cookie)
{
    char name[PROP_NAME_MAX];
    char value[PROP_VALUE_MAX];
    const prop_info *pi;
    unsigned n;

    for(n = 0; (pi = __system_property_find_nth(n)); n++) {
        __system_property_read(pi, name, value);
        propfn(name, value, cookie);
    }
    return 0;
}
Exemplo n.º 4
0
static struct property_vector*
find_all_properties_raw(void)
{
    for (;;) {
        SCOPED_RESLIST(rl);

        struct find_all_properties_context ctx = {
            .pv = property_vector_new(),
            .oom = false,
        };

        if (property_foreach(find_all_properties_propfn, &ctx) == 1)
            continue;

        if (ctx.oom)
            die_oom();
        reslist_xfer(rl->parent, rl);
        property_vector_sort(ctx.pv);
        return ctx.pv;
    }
}

static void
property_vector_swap(struct property_vector* a,
                     struct property_vector* b)
{
    struct property_vector tmp = *a;
    *a = *b;
    *b = tmp;
}

static bool
property_vector_equal(const struct property_vector* a,
                      const struct property_vector* b)
{
    return a->size == b->size &&
        memcmp(a->props, b->props, a->size * sizeof (a->props[0])) == 0;
}

static struct property_vector*
find_all_properties(void)
{
    struct property_vector* pv1 = find_all_properties_raw();
    for (;;) {
        SCOPED_RESLIST(pv);
        struct property_vector* pv2 = find_all_properties_raw();
        if (property_vector_equal(pv1, pv2))
            return pv1;
        property_vector_swap(pv1, pv2);
    }
}

static int
compat_property_foreach(
    void (*propfn)(const prop_info *pi, void *cookie),
    void *cookie)
{
    find_symbol_in_libc("__system_property_find_nth",
                        &property_find_nth);
    if (property_find_nth == NULL)
        die(EINVAL, "no property-enumeration functions available");

    unsigned propno = 0;
    for (;;) {
        const prop_info* pi = property_find_nth(propno++);
        if (pi == NULL)
            break;
        propfn(pi, cookie);
    }
    return 0;
}