int pv_get_ht_cell_expire(struct sip_msg *msg, pv_param_t *param, pv_value_t *res) { str htname; ht_pv_t *hpv; unsigned int now; hpv = (ht_pv_t*)param->pvn.u.dname; if(hpv->ht==NULL) { hpv->ht = ht_get_table(&hpv->htname); if(hpv->ht==NULL) return pv_get_null(msg, param, res); } if(pv_printf_s(msg, hpv->pve, &htname)!=0) { LM_ERR("cannot get $ht name\n"); return -1; } if(ht_get_cell_expire(hpv->ht, &htname, &now)!=0) return pv_get_null(msg, param, res); /* integer */ return pv_get_uintval(msg, param, res, now); }
static int ht_rm_value_re(struct sip_msg* msg, char* key, char* foo) { ht_pv_t *hpv; str sre; pv_spec_t *sp; sp = (pv_spec_t*)key; int_str isval; hpv = (ht_pv_t*)sp->pvp.pvn.u.dname; if(hpv->ht==NULL) { hpv->ht = ht_get_table(&hpv->htname); if(hpv->ht==NULL) return 1; } if(pv_printf_s(msg, hpv->pve, &sre)!=0) { LM_ERR("cannot get $sht expression\n"); return -1; } if (hpv->ht->dmqreplicate>0) { isval.s = sre; if (ht_dmq_replicate_action(HT_DMQ_RM_CELL_RE, &hpv->htname, NULL, AVP_VAL_STR, &isval, 1)!=0) { LM_ERR("dmq relication failed\n"); } } if(ht_rm_cell_re(&sre, hpv->ht, 1)<0) return -1; return 1; }
static int ki_ht_slot_xlock(sip_msg_t *msg, str *htname, str *skey, int lmode) { ht_t *ht; unsigned int hid; unsigned int idx; ht = ht_get_table(htname); if(ht==NULL) { LM_ERR("cannot get hash table by name [%.*s] (%d)\n", htname->len, htname->s, lmode); return -1; } hid = ht_compute_hash(skey); idx = ht_get_entry(hid, ht->htsize); if(lmode==0) { LM_DBG("locking slot %.*s[%u] for key %.*s\n", htname->len, htname->s, idx, skey->len, skey->s); ht_slot_lock(ht, idx); } else { LM_DBG("unlocking slot %.*s[%u] for key %.*s\n", htname->len, htname->s, idx, skey->len, skey->s); ht_slot_unlock(ht, idx); } return 1; }
/*! \brief RPC htable.seti command to set one item to integer value */ static void htable_rpc_seti(rpc_t* rpc, void* c) { str htname, keyname; int_str keyvalue; ht_t *ht; if (rpc->scan(c, "SS.d", &htname, &keyname, &keyvalue.n) < 3) { rpc->fault(c, 500, "Not enough parameters (htable name, key name and value)"); return; } /* Find the htable */ ht = ht_get_table(&htname); if (!ht) { rpc->fault(c, 500, "No such htable"); return; } if (ht->dmqreplicate>0 && ht_dmq_replicate_action(HT_DMQ_SET_CELL, &ht->name, &keyname, 0, &keyvalue, 1)!=0) { LM_ERR("dmq relication failed\n"); } if(ht_set_cell(ht, &keyname, 0, &keyvalue, 1)!=0) { LM_ERR("cannot set $sht(%.*s=>%.*s)\n", htname.len, htname.s, keyname.len, keyname.s); rpc->fault(c, 500, "Failed to set the item"); return; } return; }
int pv_get_ht_cv(struct sip_msg *msg, pv_param_t *param, pv_value_t *res) { str htname; ht_pv_t *hpv; int cnt = 0; hpv = (ht_pv_t*)param->pvn.u.dname; if(hpv->ht==NULL) { hpv->ht = ht_get_table(&hpv->htname); if(hpv->ht==NULL) return pv_get_null(msg, param, res); } if(pv_printf_s(msg, hpv->pve, &htname)!=0) { LM_ERR("cannot get $ht name\n"); return -1; } cnt = ht_count_cells_re(&htname, hpv->ht, 1); /* integer */ return pv_get_sintval(msg, param, res, cnt); }
int ht_api_del_cell(str *hname, str *name) { ht_t* ht; ht = ht_get_table(hname); if(ht==NULL) return -1; return ht_del_cell(ht, name); }
/*! \brief RPC htable.get command to get one item */ static void htable_rpc_get(rpc_t* rpc, void* c) { str htname, keyname; ht_t *ht; ht_cell_t *htc; /*!< One HT cell */ void* th; void* vh; if (rpc->scan(c, "SS", &htname, &keyname) < 2) { rpc->fault(c, 500, "Not enough parameters (htable name and key name)"); return; } /* Find the htable */ ht = ht_get_table(&htname); if (!ht) { rpc->fault(c, 500, "No such htable"); return; } /* Find the cell */ htc = ht_cell_pkg_copy(ht, &keyname, NULL); if(htc == NULL) { /* Print error message */ rpc->fault(c, 500, "Key name doesn't exist in htable."); return; } /* add entry node */ if (rpc->add(c, "{", &th) < 0) { rpc->fault(c, 500, "Internal error creating rpc"); goto error; } if(rpc->struct_add(th, "{", "item", &vh)<0) { rpc->fault(c, 500, "Internal error creating rpc"); goto error; } if(htc->flags&AVP_VAL_STR) { if(rpc->struct_add(vh, "SS", "name", &htc->name.s, "value", &htc->value.s)<0) { rpc->fault(c, 500, "Internal error adding item"); goto error; } } else { if(rpc->struct_add(vh, "Sd", "name", &htc->name.s, "value", (int)htc->value.n)) { rpc->fault(c, 500, "Internal error adding item"); goto error; } } error: /* Release the allocated memory */ ht_cell_pkg_free(htc); return; }
int ht_api_set_cell_expire(str *hname, str *name, int type, int_str *val) { ht_t* ht; ht = ht_get_table(hname); if(ht==NULL) return -1; return ht_set_cell_expire(ht, name, type, val); }
int ht_api_get_cell_expire(str *hname, str *name, unsigned int *val) { ht_t* ht; ht = ht_get_table(hname); if(ht==NULL) return -1; return ht_get_cell_expire(ht, name, val); }
int ht_api_set_cell(str *hname, str *name, int type, int_str *val, int mode) { ht_t* ht; ht = ht_get_table(hname); if(ht==NULL) return -1; return ht_set_cell(ht, name, type, val, mode); }
int ht_iterator_start(str *iname, str *hname) { int i; int k; k = -1; for(i=0; i<HT_ITERATOR_SIZE; i++) { if(_ht_iterators[i].name.len>0) { if(_ht_iterators[i].name.len==iname->len && strncmp(_ht_iterators[i].name.s, iname->s, iname->len)==0) { k = i; break; } } else { if(k==-1) k = i; } } if(k==-1) { LM_ERR("no iterator available - max number is %d\n", HT_ITERATOR_SIZE); return -1; } if(_ht_iterators[k].name.len>0) { if(_ht_iterators[k].ht!=NULL && _ht_iterators[k].it!=NULL) { if(_ht_iterators[k].slot>=0 && _ht_iterators[k].slot<_ht_iterators[k].ht->htsize) { ht_slot_unlock(_ht_iterators[k].ht, _ht_iterators[k].slot); } } } else { if(iname->len>=HT_ITERATOR_NAME_SIZE) { LM_ERR("iterator name is too big [%.*s] (max %d)\n", iname->len, iname->s, HT_ITERATOR_NAME_SIZE); return -1; } strncpy(_ht_iterators[k].bname, iname->s, iname->len); _ht_iterators[k].bname[iname->len] = '\0'; _ht_iterators[k].name.len = iname->len; _ht_iterators[k].name.s = _ht_iterators[k].bname; } _ht_iterators[k].it = NULL; _ht_iterators[k].slot = 0; _ht_iterators[k].ht = ht_get_table(hname); if(_ht_iterators[k].ht==NULL) { LM_ERR("cannot get hash table [%.*s]\n", hname->len, hname->s); return -1; } return 0; }
int ht_api_count_cells_re(str *hname, str *sre, int mode) { ht_t* ht; ht = ht_get_table(hname); if(ht==NULL) return -1; if(ht_count_cells_re(sre, ht, mode /* 0 - name; 1 - value */)<0) return -1; return 0; }
int pv_set_ht_cell(struct sip_msg* msg, pv_param_t *param, int op, pv_value_t *val) { str htname; int_str isval; ht_pv_t *hpv; hpv = (ht_pv_t*)param->pvn.u.dname; if(hpv->ht==NULL) hpv->ht = ht_get_table(&hpv->htname); if(hpv->ht==NULL) return -1; if(pv_printf_s(msg, hpv->pve, &htname)!=0) { LM_ERR("cannot get $ht name\n"); return -1; } LM_DBG("set value for $ht(%.*s=>%.*s)\n", hpv->htname.len, hpv->htname.s, htname.len, htname.s); if((val==NULL) || (val->flags&PV_VAL_NULL)) { /* delete it */ if (hpv->ht->dmqreplicate>0 && ht_dmq_replicate_action(HT_DMQ_DEL_CELL, &hpv->htname, &htname, 0, NULL, 0)!=0) { LM_ERR("dmq relication failed\n"); } ht_del_cell(hpv->ht, &htname); return 0; } if(val->flags&PV_TYPE_INT) { isval.n = val->ri; if (hpv->ht->dmqreplicate>0 && ht_dmq_replicate_action(HT_DMQ_SET_CELL, &hpv->htname, &htname, 0, &isval, 1)!=0) { LM_ERR("dmq relication failed\n"); } if(ht_set_cell(hpv->ht, &htname, 0, &isval, 1)!=0) { LM_ERR("cannot set $ht(%.*s)\n", htname.len, htname.s); return -1; } } else { isval.s = val->rs; if (hpv->ht->dmqreplicate>0 && ht_dmq_replicate_action(HT_DMQ_SET_CELL, &hpv->htname, &htname, AVP_VAL_STR, &isval, 1)!=0) { LM_ERR("dmq relication failed\n"); } if(ht_set_cell(hpv->ht, &htname, AVP_VAL_STR, &isval, 1)!=0) { LM_ERR("cannot set $ht(%.*s)\n", htname.len, htname.s); return -1; } } return 0; }
static int ht_reset_by_name(str *hname) { ht_t *ht; ht = ht_get_table(hname); if(ht==NULL) { LM_ERR("cannot get hash table [%.*s]\n", hname->len, hname->s); return -1; } if(ht_reset_content(ht)<0) return -1; return 0; }
int pv_get_ht_add(struct sip_msg *msg, pv_param_t *param, pv_value_t *res, int val) { str htname; ht_cell_t *htc=NULL; ht_pv_t *hpv; hpv = (ht_pv_t*)param->pvn.u.dname; if(hpv->ht==NULL) { hpv->ht = ht_get_table(&hpv->htname); if(hpv->ht==NULL) return pv_get_null(msg, param, res); } if(pv_printf_s(msg, hpv->pve, &htname)!=0) { LM_ERR("cannot get $ht name\n"); return -1; } htc = ht_cell_value_add(hpv->ht, &htname, val, 1, _htc_local); if(htc==NULL) { return pv_get_null(msg, param, res); } if(_htc_local!=htc) { ht_cell_pkg_free(_htc_local); _htc_local=htc; } if(htc->flags&AVP_VAL_STR) return pv_get_null(msg, param, res); /* integer */ if (hpv->ht->dmqreplicate>0) { if (ht_dmq_replicate_action(HT_DMQ_SET_CELL, &hpv->htname, &htname, 0, &htc->value, 1)!=0) { LM_ERR("dmq relication failed\n"); } } return pv_get_sintval(msg, param, res, htc->value.n); }
static int ht_reset(struct sip_msg* msg, char* htname, char* foo) { ht_t *ht; str sname; if(fixup_get_svalue(msg, (gparam_t*)htname, &sname)<0 || sname.len<=0) { LM_ERR("cannot get hash table name\n"); return -1; } ht = ht_get_table(&sname); if(ht==NULL) { LM_ERR("cannot get hash table [%.*s]\n", sname.len, sname.s); return -1; } if(ht_reset_content(ht)<0) return -1; return 1; }
static void htable_rpc_delete(rpc_t* rpc, void* c) { str htname, keyname; ht_t *ht; if (rpc->scan(c, "SS", &htname, &keyname) < 2) { rpc->fault(c, 500, "Not enough parameters (htable name & key name"); return; } ht = ht_get_table(&htname); if (!ht) { rpc->fault(c, 500, "No such htable"); return; } if (ht->dmqreplicate>0 && ht_dmq_replicate_action(HT_DMQ_DEL_CELL, &ht->name, &keyname, 0, NULL, 0)!=0) { LM_ERR("dmq relication failed\n"); } ht_del_cell(ht, &keyname); }
int pv_get_ht_cell(struct sip_msg *msg, pv_param_t *param, pv_value_t *res) { str htname; ht_cell_t *htc=NULL; ht_pv_t *hpv; hpv = (ht_pv_t*)param->pvn.u.dname; if(hpv->ht==NULL) { hpv->ht = ht_get_table(&hpv->htname); if(hpv->ht==NULL) return pv_get_null(msg, param, res); } if(pv_printf_s(msg, hpv->pve, &htname)!=0) { LM_ERR("cannot get $ht name\n"); return -1; } htc = ht_cell_pkg_copy(hpv->ht, &htname, _htc_local); if(htc==NULL) { if(hpv->ht->flags==PV_VAL_INT) return pv_get_sintval(msg, param, res, hpv->ht->initval.n); return pv_get_null(msg, param, res); } if(_htc_local!=htc) { ht_cell_pkg_free(_htc_local); _htc_local=htc; } if(htc->flags&AVP_VAL_STR) return pv_get_strval(msg, param, res, &htc->value.s); /* integer */ return pv_get_sintval(msg, param, res, htc->value.n); }
static struct mi_root* ht_mi_delete(struct mi_root* cmd_tree, void* param) { struct mi_node *node; str *htname, *key; ht_t *ht; node = cmd_tree->node.kids; if (!node) goto param_err; htname = &node->value; if (!htname->len) goto param_err; node = node->next; if (!node) goto param_err; key = &node->value; if (!key->len) goto param_err; ht = ht_get_table(htname); if (!ht) return init_mi_tree(404, MI_BAD_PARM_S, MI_BAD_PARM_LEN); if (ht->dmqreplicate>0 && ht_dmq_replicate_action(HT_DMQ_DEL_CELL, &ht->name, key, 0, NULL, 0)!=0) { LM_ERR("dmq relication failed\n"); } LM_DBG("deleting key [%.*s] from [%.*s]\n", key->len, key->s, htname->len, htname->s); ht_del_cell(ht, key); return init_mi_tree(200, MI_OK_S, MI_OK_LEN); param_err: return init_mi_tree(400, MI_MISSING_PARM_S, MI_MISSING_PARM_LEN); }
int pv_set_ht_cell_expire(struct sip_msg* msg, pv_param_t *param, int op, pv_value_t *val) { str htname; int_str isval; ht_pv_t *hpv; hpv = (ht_pv_t*)param->pvn.u.dname; if(hpv->ht==NULL) hpv->ht = ht_get_table(&hpv->htname); if(hpv->ht==NULL) return -1; if(pv_printf_s(msg, hpv->pve, &htname)!=0) { LM_ERR("cannot get $ht name\n"); return -1; } LM_DBG("set expire value for $ht(%.*s=>%.*s)\n", hpv->htname.len, hpv->htname.s, htname.len, htname.s); isval.n = 0; if(val!=NULL) { if(val->flags&PV_TYPE_INT) isval.n = val->ri; } if (hpv->ht->dmqreplicate>0 && ht_dmq_replicate_action(HT_DMQ_SET_CELL_EXPIRE, &hpv->htname, &htname, 0, &isval, 0)!=0) { LM_ERR("dmq relication failed\n"); } if(ht_set_cell_expire(hpv->ht, &htname, 0, &isval)!=0) { LM_ERR("cannot set $ht(%.*s)\n", htname.len, htname.s); return -1; } return 0; }
/** * unlock the slot for a given key in a hash table */ static int w_ht_slot_unlock(struct sip_msg* msg, char* key, char* foo) { ht_pv_t *hpv; str skey; pv_spec_t *sp; unsigned int hid; unsigned int idx; sp = (pv_spec_t*)key; hpv = (ht_pv_t*)sp->pvp.pvn.u.dname; if(hpv->ht==NULL) { hpv->ht = ht_get_table(&hpv->htname); if(hpv->ht==NULL) { LM_ERR("cannot get $sht root\n"); return -11; } } if(pv_printf_s(msg, hpv->pve, &skey)!=0) { LM_ERR("cannot get $sht key\n"); return -1; } hid = ht_compute_hash(&skey); idx = ht_get_entry(hid, hpv->ht->htsize); LM_DBG("unlocking slot %.*s[%u] for key %.*s\n", hpv->htname.len, hpv->htname.s, idx, skey.len, skey.s); ht_slot_unlock(hpv->ht, idx); return 1; }
static int ht_rm_items(sip_msg_t* msg, str* hname, str* op, str *val, int mkey) { ht_t *ht; int_str isval; ht = ht_get_table(hname); if(ht==NULL) { LM_ERR("cannot get hash table [%.*s]\n", hname->len, hname->s); return -1; } switch(op->len) { case 2: if(strncmp(op->s, "re", 2)==0) { isval.s = *val; if (ht_dmq_replicate_action(HT_DMQ_RM_CELL_RE, &ht->name, NULL, AVP_VAL_STR, &isval, mkey)!=0) { LM_ERR("dmq relication failed (op %d)\n", mkey); } if(ht_rm_cell_re(val, ht, mkey)<0) { return -1; } return 1; } else if(strncmp(op->s, "sw", 2)==0) { if(ht_rm_cell_op(val, ht, mkey, HT_RM_OP_SW)<0) { return -1; } } LM_WARN("unsupported match operator: %.*s\n", op->len, op->s); break; default: LM_WARN("unsupported match operator: %.*s\n", op->len, op->s); } return -1; }
int ht_dmq_replay_action(ht_dmq_action_t action, str* htname, str* cname, int type, int_str* val, int mode) { ht_t* ht; ht = ht_get_table(htname); if(ht==NULL) { LM_ERR("unable to get table\n"); return -1; } LM_DBG("replaying action %d on %.*s=>%.*s...\n", action, htname->len, htname->s, cname->len, cname->s); if (action==HT_DMQ_SET_CELL) { return ht_set_cell(ht, cname, type, val, mode); } else if (action==HT_DMQ_SET_CELL_EXPIRE) { return ht_set_cell_expire(ht, cname, 0, val); } else if (action==HT_DMQ_DEL_CELL) { return ht_del_cell(ht, cname); } else if (action==HT_DMQ_RM_CELL_RE) { return ht_rm_cell_re(&val->s, ht, mode); } else { LM_ERR("unrecognized action"); return -1; } }
/*! \brief RPC htable.get command to get one item */ static void htable_rpc_get(rpc_t* rpc, void* c) { str htname, keyname; ht_t *ht; ht_cell_t *htc; /*!< One HT cell */ void* th; void* vh; struct tm *_expire_t; char expire_buf[RPC_DATE_BUF_LEN]="NEVER"; if (rpc->scan(c, "SS", &htname, &keyname) < 2) { rpc->fault(c, 500, "Not enough parameters (htable name and key name)"); return; } /* Find the htable */ ht = ht_get_table(&htname); if (!ht) { rpc->fault(c, 500, "No such htable"); return; } /* Find the cell */ htc = ht_cell_pkg_copy(ht, &keyname, NULL); if(htc == NULL) { /* Print error message */ rpc->fault(c, 500, "Key name doesn't exist in htable."); return; } /* add entry node */ if (rpc->add(c, "{", &th) < 0) { rpc->fault(c, 500, "Internal error creating rpc"); goto error; } if(rpc->struct_add(th, "{", "item", &vh)<0) { rpc->fault(c, 500, "Internal error creating rpc"); goto error; } if (htc->expire) { _expire_t = localtime(&htc->expire); strftime(expire_buf, RPC_DATE_BUF_LEN - 1, "%Y-%m-%d %H:%M:%S", _expire_t); } if(htc->flags&AVP_VAL_STR) { if(rpc->struct_add(vh, "SSds", "name", &htc->name.s, "value", &htc->value.s, "flags", htc->flags, "expire", expire_buf)<0) { rpc->fault(c, 500, "Internal error adding item"); goto error; } } else { if(rpc->struct_add(vh, "Sdds", "name", &htc->name.s, "value", (int)htc->value.n, "flags", htc->flags, "expire", expire_buf)<0) { rpc->fault(c, 500, "Internal error adding item"); goto error; } } error: /* Release the allocated memory */ ht_cell_pkg_free(htc); return; }
/*! \brief RPC htable.reload command to reload content of a hash table */ static void htable_rpc_reload(rpc_t* rpc, void* c) { str htname; ht_t *ht; ht_t nht; ht_cell_t *first; ht_cell_t *it; int i; if(ht_db_url.len<=0) { rpc->fault(c, 500, "No htable db_url"); return; } if(ht_db_init_con()!=0) { rpc->fault(c, 500, "Failed to init htable db connection"); return; } if(ht_db_open_con()!=0) { rpc->fault(c, 500, "Failed to open htable db connection"); return; } if (rpc->scan(c, "S", &htname) < 1) { rpc->fault(c, 500, "No htable name given"); return; } ht = ht_get_table(&htname); if(ht==NULL) { rpc->fault(c, 500, "No such htable"); return; } memcpy(&nht, ht, sizeof(ht_t)); /* it's temporary operation - use system malloc */ nht.entries = (ht_entry_t*)malloc(nht.htsize*sizeof(ht_entry_t)); if(nht.entries == NULL) { ht_db_close_con(); rpc->fault(c, 500, "Mtree reload failed"); return; } memset(nht.entries, 0, nht.htsize*sizeof(ht_entry_t)); if(ht_db_load_table(&nht, &ht->dbtable, 0)<0) { /* free any entry set if it was a partial load */ for(i=0; i<nht.htsize; i++) { first = nht.entries[i].first; while(first) { it = first; first = first->next; ht_cell_free(it); } } free(nht.entries); ht_db_close_con(); rpc->fault(c, 500, "Mtree reload failed"); return; } /* replace old entries */ for(i=0; i<nht.htsize; i++) { ht_slot_lock(ht, i); first = ht->entries[i].first; ht->entries[i].first = nht.entries[i].first; ht->entries[i].esize = nht.entries[i].esize; ht_slot_unlock(ht, i); nht.entries[i].first = first; } /* free old entries */ for(i=0; i<nht.htsize; i++) { first = nht.entries[i].first; while(first) { it = first; first = first->next; ht_cell_free(it); } } free(nht.entries); ht_db_close_con(); return; }
static struct mi_root* ht_mi_reload(struct mi_root* cmd_tree, void* param) { struct mi_node* node; str htname; ht_t *ht; ht_t nht; ht_cell_t *first; ht_cell_t *it; int i; if(ht_db_url.len<=0) return init_mi_tree(500, MI_ERR_RELOAD, MI_ERR_RELOAD_LEN); if(ht_db_init_con()!=0) return init_mi_tree(500, MI_ERR_RELOAD, MI_ERR_RELOAD_LEN); if(ht_db_open_con()!=0) return init_mi_tree(500, MI_ERR_RELOAD, MI_ERR_RELOAD_LEN); node = cmd_tree->node.kids; if(node == NULL) { ht_db_close_con(); return init_mi_tree( 400, MI_MISSING_PARM_S, MI_MISSING_PARM_LEN); } htname = node->value; if(htname.len<=0 || htname.s==NULL) { LM_ERR("bad hash table name\n"); ht_db_close_con(); return init_mi_tree( 500, "bad hash table name", 19); } ht = ht_get_table(&htname); if(ht==NULL || ht->dbtable.len<=0) { LM_ERR("bad hash table name\n"); ht_db_close_con(); return init_mi_tree( 500, "no such hash table", 18); } memcpy(&nht, ht, sizeof(ht_t)); /* it's temporary operation - use system malloc */ nht.entries = (ht_entry_t*)malloc(nht.htsize*sizeof(ht_entry_t)); if(nht.entries == NULL) { ht_db_close_con(); return init_mi_tree(500, MI_ERR_RELOAD, MI_ERR_RELOAD_LEN); } memset(nht.entries, 0, nht.htsize*sizeof(ht_entry_t)); if(ht_db_load_table(&nht, &ht->dbtable, 0)<0) { /* free any entry set if it was a partial load */ for(i=0; i<nht.htsize; i++) { first = nht.entries[i].first; while(first) { it = first; first = first->next; ht_cell_free(it); } } free(nht.entries); ht_db_close_con(); return init_mi_tree(500, MI_ERR_RELOAD, MI_ERR_RELOAD_LEN); } /* replace old entries */ for(i=0; i<nht.htsize; i++) { ht_slot_lock(ht, i); first = ht->entries[i].first; ht->entries[i].first = nht.entries[i].first; ht->entries[i].esize = nht.entries[i].esize; ht_slot_unlock(ht, i); nht.entries[i].first = first; } /* free old entries */ for(i=0; i<nht.htsize; i++) { first = nht.entries[i].first; while(first) { it = first; first = first->next; ht_cell_free(it); } } free(nht.entries); ht_db_close_con(); return init_mi_tree( 200, MI_OK_S, MI_OK_LEN); }
static struct mi_root* ht_mi_dump(struct mi_root* cmd_tree, void* param) { struct mi_node* node; struct mi_node* node2; struct mi_root *rpl_tree; struct mi_node *rpl; str htname; ht_t *ht; ht_cell_t *it; int i; int len; char *p; node = cmd_tree->node.kids; if(node == NULL) return init_mi_tree( 400, MI_MISSING_PARM_S, MI_MISSING_PARM_LEN); htname = node->value; if(htname.len<=0 || htname.s==NULL) { LM_ERR("bad hash table name\n"); return init_mi_tree( 500, "bad hash table name", 19); } ht = ht_get_table(&htname); if(ht==NULL) { LM_ERR("bad hash table name\n"); return init_mi_tree( 500, "no such hash table", 18); } rpl_tree = init_mi_tree( 200, MI_OK_S, MI_OK_LEN); if (rpl_tree==NULL) return 0; rpl = &rpl_tree->node; for(i=0; i<ht->htsize; i++) { ht_slot_lock(ht, i); it = ht->entries[i].first; if(it) { /* add entry node */ p = int2str((unsigned long)i, &len); node = add_mi_node_child(rpl, MI_DUP_VALUE, "Entry", 5, p, len); if (node==0) goto error; while(it) { if(it->flags&AVP_VAL_STR) { node2 = add_mi_node_child(node, MI_DUP_VALUE, it->name.s, it->name.len, it->value.s.s, it->value.s.len); } else { p = sint2str((long)it->value.n, &len); node2 = add_mi_node_child(node, MI_DUP_VALUE, it->name.s, it->name.len, p, len); } if (node2==0) goto error; it = it->next; } } ht_slot_unlock(ht, i); } return rpl_tree; error: free_mi_tree(rpl_tree); return 0; }
/*! \brief RPC htable.dump command to print content of a hash table */ static void htable_rpc_dump(rpc_t* rpc, void* c) { str htname; ht_t *ht; ht_cell_t *it; int i; void* th; void* ih; void* vh; if (rpc->scan(c, "S", &htname) < 1) { rpc->fault(c, 500, "No htable name given"); return; } ht = ht_get_table(&htname); if(ht==NULL) { rpc->fault(c, 500, "No such htable"); return; } for(i=0; i<ht->htsize; i++) { ht_slot_lock(ht, i); it = ht->entries[i].first; if(it) { /* add entry node */ if (rpc->add(c, "{", &th) < 0) { rpc->fault(c, 500, "Internal error creating rpc"); goto error; } if(rpc->struct_add(th, "dd{", "entry", i, "size", (int)ht->entries[i].esize, "slot", &ih)<0) { rpc->fault(c, 500, "Internal error creating rpc"); goto error; } while(it) { if(rpc->struct_add(ih, "{", "item", &vh)<0) { rpc->fault(c, 500, "Internal error creating rpc"); goto error; } if(it->flags&AVP_VAL_STR) { if(rpc->struct_add(vh, "SSs", "name", &it->name.s, "value", &it->value.s, "type", "str")<0) { rpc->fault(c, 500, "Internal error adding item"); goto error; } } else { if(rpc->struct_add(vh, "Sds", "name", &it->name.s, "value", (int)it->value.n, "type", "int")<0) { rpc->fault(c, 500, "Internal error adding item"); goto error; } } it = it->next; } } ht_slot_unlock(ht, i); } return; error: ht_slot_unlock(ht, i); }
int pv_parse_ht_name(pv_spec_p sp, str *in) { ht_pv_t *hpv=NULL; char *p; str pvs; if(in->s==NULL || in->len<=0) return -1; hpv = (ht_pv_t*)pkg_malloc(sizeof(ht_pv_t)); if(hpv==NULL) return -1; memset(hpv, 0, sizeof(ht_pv_t)); p = in->s; while(p<in->s+in->len && (*p==' ' || *p=='\t' || *p=='\n' || *p=='\r')) p++; if(p>in->s+in->len || *p=='\0') goto error; hpv->htname.s = p; while(p < in->s + in->len) { if(*p=='=' || *p==' ' || *p=='\t' || *p=='\n' || *p=='\r') break; p++; } if(p>in->s+in->len || *p=='\0') goto error; hpv->htname.len = p - hpv->htname.s; if(*p!='=') { while(p<in->s+in->len && (*p==' ' || *p=='\t' || *p=='\n' || *p=='\r')) p++; if(p>in->s+in->len || *p=='\0' || *p!='=') goto error; } p++; if(*p!='>') goto error; p++; pvs.len = in->len - (int)(p - in->s); pvs.s = p; LM_DBG("htable [%.*s] - key [%.*s]\n", hpv->htname.len, hpv->htname.s, pvs.len, pvs.s); if(pv_parse_format(&pvs, &hpv->pve)<0 || hpv->pve==NULL) { LM_ERR("wrong format[%.*s]\n", in->len, in->s); goto error; } hpv->ht = ht_get_table(&hpv->htname); sp->pvp.pvn.u.dname = (void*)hpv; sp->pvp.pvn.type = PV_NAME_OTHER; return 0; error: if(hpv!=NULL) pkg_free(hpv); return -1; }