static void reset_notify_element(const struct dm_table *kw, struct dm_value_table *st, int index, uint32_t mask) { const struct dm_element *elem; if (!kw->table) return; elem = &kw->table[index]; switch(elem->type) { case T_TOKEN: if (DM_TABLE(st->values[index])) reset_notify_table(elem->u.t.table, DM_TABLE(st->values[index]), mask); break; case T_OBJECT: reset_notify_object(elem, DM_INSTANCE(st->values[index]), mask); break; default: break; } st->values[index].notify &= mask; DM_parity_update(st->values[index]); }
/************************************************************ * Initializes the radiusAccClientExtTable module */ void init_radiusAccClientExtTable() { struct dm_instance *clnts; struct dm_instance_node *node; ENTER(); initialize_table_radiusAccClientExtTable(); /** VAR: InternetGatewayDevice.X_TPLINO_NET_SessionControl.RadiusServer.Accounting.Client */ clnts = dm_get_instance_ref_by_selector((dm_selector){ dm__InternetGatewayDevice, dm__IGD_X_TPLINO_NET_SessionControl, dm__IGD_SCG_RadiusServer, dm__IGD_SCG_RS_Accounting, dm__IGD_SCG_RS_Acct_Client, 0}); if (!clnts) { EXIT(); return; } for (node = dm_instance_first(clnts); node != NULL; node = dm_instance_next(clnts, node)) { /** VAR: InternetGatewayDevice.X_TPLINO_NET_SessionControl.RadiusServer.Accounting.Client.{i} */ debug(": adding instance: %d (%p)", node->instance, DM_TABLE(node->table)); add_radiusAccClientExtTable(node->instance, DM_TABLE(node->table)); } EXIT(); }
static void set_notify_slot_element(const struct dm_table *kw, struct dm_value_table *st, int index, int slot, uint32_t ntfy) { const struct dm_element *elem; if (!kw->table) return; elem = &kw->table[index]; switch(elem->type) { case T_TOKEN: if (DM_TABLE(st->values[index])) set_notify_slot_table(elem->u.t.table, DM_TABLE(st->values[index]), slot, ntfy); break; case T_OBJECT: set_notify_slot_object(elem, DM_INSTANCE(st->values[index]), slot, ntfy); break; default: break; } set_notify_single_slot_element(elem, &st->values[index], slot, ntfy); }
DM_RESULT dm_set_notify_by_selector_recursive(const dm_selector sel, int slot, int value) { struct dm_element_ref ref; ENTER(); if (dm_get_element_ref(sel, &ref)) { #if DEBUG debug("(): %s\n", ref.kw_base->name); #endif debug("(): kw elem: %p, type: %d, ref idx: %p, type %d\n", ref.kw_elem, ref.kw_elem->type, ref.st_value, ref.st_type); switch (ref.kw_elem->type) { case T_TOKEN: if (DM_TABLE(*ref.st_value)) set_notify_slot_table(ref.kw_elem->u.t.table, DM_TABLE(*ref.st_value), slot, value); break; case T_OBJECT: if (ref.st_type == T_OBJECT) { /* set notify on instance table */ set_notify_single_slot_element(ref.kw_elem, ref.st_value, slot, value); set_notify_slot_object(ref.kw_elem, DM_INSTANCE(*ref.st_value), slot, value); } else { struct dm_instance_node *node = cast_node_table_ref2node(ref.st_value); /* set notify on a instance */ set_notify_single_slot_element(ref.kw_elem, &node->table, slot, value); set_notify_slot_table(ref.kw_elem->u.t.table, DM_TABLE(node->table), slot, value); } break; default: EXIT(); return DM_INVALID_TYPE; } EXIT(); return DM_OK; } EXIT(); return DM_VALUE_NOT_FOUND; }
static void reset_notify_object(const struct dm_element *elem, struct dm_instance *base, uint32_t mask) { struct dm_instance_node *node; if (!elem || !base) return; debug("(): base: %p, elem: %s\n", base, elem->key); for (node = dm_instance_first(base); node != NULL; node = dm_instance_next(base, node)) reset_notify_table(elem->u.t.table, DM_TABLE(node->table), mask); }
static void set_notify_slot_object(const struct dm_element *elem, struct dm_instance *base, int slot, uint32_t ntfy) { struct dm_instance_node *node; if (!elem || !base) return; debug("(): base: %p, elem: %s\n", base, elem->key); for (node = dm_instance_first(base); node != NULL; node = dm_instance_next(base, node)) { /* set notify on a instance */ set_notify_single_slot_element(elem, &node->table, slot, ntfy); set_notify_slot_table(elem->u.t.table, DM_TABLE(node->table), slot, ntfy); } }
static void XMLCALL startElement(void *userData, const char *name, const char **atts) { const struct dm_element *kw = NULL; DM_VALUE *val = NULL; struct XMLstate **state = userData; const char *base = (*state)->base; int valid = ((*state)->flags & XML_VALID) == XML_VALID; int is_root = ((*state)->flags & XML_ROOT) == XML_ROOT; const struct dm_element *element = (*state)->element; DM_VALUE *value = (*state)->value; int xid = 0; int ntfy = 0; dm_id id; for (int i = 0; atts[i]; i += 2) { if (strcasecmp("instance", atts[i]) == 0) { xml_debug("%s: instance: %s\n", name, atts[i + 1]); xid = atoi(atts[i + 1]); break; } else if (strcasecmp("notify", atts[i]) == 0) { xml_debug("%s: notify: %s\n", name, atts[i + 1]); ntfy = dm_enum2int( ¬ify_attr, atts[i + 1]); } else if (strcasecmp("encoding", atts[i]) == 0) { xml_debug("%s: encoding: %s\n", name, atts[i + 1]); if (strcasecmp(atts[i+1], "escaped") == 0) (*state)->flags |= XML_ESCAPED; } else if (strcasecmp("version", atts[i]) == 0) { xml_debug("%s: config version: %s\n", name, atts[i + 1]); dm_set_cfg_version(atoi(atts[i + 1])); } } (*state)++; if (is_root) { if (flags & DS_VERSIONCHECK && dm_get_cfg_version() != CFG_VERSION) { (*state)->flags |= XML_UPGRADE; lua_pushinteger(lua_environment, CFG_VERSION); lua_pushinteger(lua_environment, dm_get_cfg_version()); if (fp_Lua_function("fncPreVersionCheck", 2)) debug("(): Error during Lua function execution"); } } else { memset(*state, 0, sizeof(struct XMLstate)); if (xid != 0) asprintf(&(*state)->base, "%s.%s.%d", base, name, xid); else asprintf(&(*state)->base, "%s.%s", base, name); if (valid) { const struct dm_table *table = element->u.t.table; id = dm_get_element_id_by_name(name, strlen(name), table); if (id != DM_ERR) { kw = &(table->table[id - 1]); val = dm_get_value_ref_by_id(DM_TABLE(*value), id); (*state)->flags |= XML_VALID; } else { printf("Element '%s' not found in table '%s'\n", name, element->key); valid = 0; } } if (!valid || !((*state)->flags & XML_VALID)) { debug("enter invalid: %s\n", (*state)->base); return; } xml_debug("enter: %s = %p, (%p, %p)\n", name, *state, kw, val); (*state)->element = kw; if (kw->type == T_OBJECT) { struct dm_instance *inst = DM_INSTANCE(*val); struct dm_instance_node *node = NULL; /** FIXME: this should be easier */ if (xid > 0) node = dm_get_instance_node_by_id(inst, xid); if (!node) { dm_selector basesel; dm_selcpy(basesel, DM_TABLE(*value)->id); dm_selcat(basesel, id); node = dm_add_instance(kw, inst, basesel, xid); dm_assert(node); if (flags & DS_USERCONFIG) { val->flags |= DV_UPDATED; DM_parity_update(*val); node->table.flags |= DV_UPDATED; DM_parity_update(node->table); } } val = &node->table; (*state)->inst = inst; (*state)->node = node; } else if (kw->type == T_TOKEN) { if (DM_TABLE(*val) == NULL) { set_DM_TABLE(*val, dm_alloc_table(kw->u.t.table, DM_TABLE(*value)->id, id)); if (flags & DS_USERCONFIG) val->flags |= DV_UPDATED; xml_debug("adding table for token \"%s\" with %d elements: %p\n", name, kw->u.t.table->size, DM_TABLE(*val)); DM_parity_update(*val); } } (*state)->value = val; if (ntfy >= 0) set_notify_single_slot_element(kw, (*state)->value, 0, ntfy); } }