static void rpc_set_pipe(rpc_t *rpc, void *c) { int pipe_no = MAX_PIPES, algo_id, limit = 0; str algo_str; if (rpc->scan(c, "dSd", &pipe_no, &algo_str, &limit) < 3) return; if (str_map_str(algo_names, &algo_str, &algo_id)) { LM_ERR("unknown algorithm: '%.*s'\n", algo_str.len, algo_str.s); rpc->fault(c, 400, "Unknown algorithm"); return; } LM_DBG("set_pipe: %d:%d:%d\n", pipe_no, algo_id, limit); if (pipe_no >= MAX_PIPES || pipe_no < 0) { LM_ERR("wrong pipe_no: %d\n", pipe_no); rpc->fault(c, 400, "Unknown pipe"); return; } LOCK_GET(rl_lock); *pipes[pipe_no].algo = algo_id; *pipes[pipe_no].limit = limit; if (check_feedback_setpoints(0)) { LM_ERR("feedback limits don't match\n"); rpc->fault(c, 400, "Feedback limits don't match"); } else { *pid_setpoint = 0.01 * (double)cfg_setpoint; } LOCK_RELEASE(rl_lock); }
void rpc_pl_set_pipe(rpc_t *rpc, void *c) { unsigned int algo_id, limit = 0; pl_pipe_t *it; str pipeid, algo_str; if (rpc->scan(c, "SSd", &pipeid, &algo_str, &limit) < 3) return; if (str_map_str(algo_names, &algo_str, (int*)&algo_id)) { LM_ERR("unknown algorithm: '%.*s'\n", algo_str.len, algo_str.s); rpc->fault(c, 400, "Unknown algorithm"); return; } LM_DBG("set_pipe: %.*s:%d:%d\n", pipeid.len, pipeid.s, algo_id, limit); it = pl_pipe_get(&pipeid, 1); if (it==NULL) { LM_ERR("no pipe: %.*s\n", pipeid.len, pipeid.s); rpc->fault(c, 400, "Unknown pipe id %.*s", pipeid.len, pipeid.s); return; } it->algo = algo_id; it->limit = limit; pl_pipe_release(&pipeid); if (check_feedback_setpoints(0)) { LM_ERR("feedback limits don't match\n"); rpc->fault(c, 400, "Feedback limits don't match"); return; } else { *_pl_pid_setpoint = 0.01 * (double)_pl_cfg_setpoint; } }
struct mi_root* mi_set_pipe(struct mi_root* cmd_tree, void* param) { struct mi_node *node; unsigned int algo_id, limit = 0; pl_pipe_t *it; str pipeid; node = cmd_tree->node.kids; if (node == NULL) return init_mi_tree( 400, MI_MISSING_PARM_S, MI_MISSING_PARM_LEN); if ( !node->value.s || !node->value.len) goto error; pipeid = node->value; node = node->next; if ( !node->value.s || !node->value.len) goto error; if (str_map_str(algo_names, &(node->value), (int*)&algo_id)) { LM_ERR("unknown algorithm: '%.*s'\n", node->value.len, node->value.s); goto error; } node = node->next; if ( !node->value.s || !node->value.len || strno2int(&node->value,&limit)<0) goto error; LM_DBG("set_pipe: %.*s:%d:%d\n", pipeid.len, pipeid.s, algo_id, limit); it = pl_pipe_get(&pipeid, 1); if (it==NULL) { LM_ERR("no pipe: %.*s\n", pipeid.len, pipeid.s); goto error; } it->algo = algo_id; it->limit = limit; if (check_feedback_setpoints(0)) { pl_pipe_release(&pipeid); LM_ERR("feedback limits don't match\n"); goto error; } else { *_pl_pid_setpoint = 0.01 * (double)_pl_cfg_setpoint; } pl_pipe_release(&pipeid); return init_mi_tree( 200, MI_OK_S, MI_OK_LEN); error: return init_mi_tree( 400, MI_BAD_PARM_S, MI_BAD_PARM_LEN); }
struct mi_root* mi_set_pipe(struct mi_root* cmd_tree, void* param) { struct mi_node *node; unsigned int pipe_no = MAX_PIPES, algo_id, limit = 0; //str algo; node = cmd_tree->node.kids; if (node == NULL) return init_mi_tree( 400, MI_MISSING_PARM_S, MI_MISSING_PARM_LEN); if ( !node->value.s || !node->value.len || strno2int(&node->value,&pipe_no)<0) goto bad_syntax; node = node->next; if ( !node->value.s || !node->value.len) goto bad_syntax; if (str_map_str(algo_names, &(node->value), (int*)&algo_id)) { LM_ERR("unknown algorithm: '%.*s'\n", node->value.len, node->value.s); goto bad_syntax; } node = node->next; if ( !node->value.s || !node->value.len || strno2int(&node->value,&limit)<0) goto bad_syntax; LM_DBG("set pipe: %d:%d:%d\n", pipe_no, algo_id, limit); if (pipe_no >= MAX_PIPES) { LM_ERR("wrong pipe_no: %d\n", pipe_no); goto bad_syntax; } LOCK_GET(rl_lock); *pipes[pipe_no].algo = algo_id; *pipes[pipe_no].limit = limit; if (check_feedback_setpoints(0)) { LM_ERR("feedback limits don't match\n"); goto error; } else { *pid_setpoint = 0.01 * (double)cfg_setpoint; } set_check_network_load(); LOCK_RELEASE(rl_lock); return init_mi_tree( 200, MI_OK_S, MI_OK_LEN); error: LOCK_RELEASE(rl_lock); bad_syntax: return init_mi_tree( 400, MI_BAD_PARM_S, MI_BAD_PARM_LEN); }
/** * parses a "pipe_no:algorithm:bandwidth" line * \return 0 on success */ static int parse_pipe_params(char * line, pipe_params_t * params) { regmatch_t m[4]; str algo_str; if (! params_inited && init_params()) return -1; if (regexec(&pipe_params_regex, line, 4, m, 0)) { LM_ERR("invalid param tuple: %s\n", line); return -1; } LM_DBG("pipe: [%.*s|%.*s|%.*s]\n", RXLS(m, line, 1), RXLS(m, line, 2), RXLS(m, line, 3)); params->no = atoi(RXS(m, line, 1)); params->limit = atoi(RXS(m, line, 3)); algo_str.s = RXS(m, line, 2); algo_str.len = RXL(m, line, 2); if (str_map_str(algo_names, &algo_str, ¶ms->algo)) return -1; return 0; }
int pl_pipe_add(str *pipeid, str *algorithm, int limit) { unsigned int cellid; unsigned int idx; pl_pipe_t *it, *prev, *cell; if(_pl_pipes_ht==NULL) return -1; cellid = pl_compute_hash(pipeid); idx = pl_get_entry(cellid, _pl_pipes_ht->htsize); lock_get(&_pl_pipes_ht->slots[idx].lock); it = _pl_pipes_ht->slots[idx].first; prev = NULL; while(it!=NULL && it->cellid < cellid) { prev = it; it = it->next; } while(it!=NULL && it->cellid == cellid) { if(pipeid->len==it->name.len && strncmp(pipeid->s, it->name.s, pipeid->len)==0) { lock_release(&_pl_pipes_ht->slots[idx].lock); return 1; } prev = it; it = it->next; } cell = (pl_pipe_t*)shm_malloc(sizeof(pl_pipe_t)+(1+pipeid->len)*sizeof(char)); if(cell == NULL) { LM_ERR("cannot create new cell.\n"); lock_release(&_pl_pipes_ht->slots[idx].lock); return -1; } memset(cell, 0, sizeof(pl_pipe_t)+(1+pipeid->len)*sizeof(char)); cell->name.s = (char*)cell + sizeof(pl_pipe_t); strncpy(cell->name.s, pipeid->s, pipeid->len); cell->name.len = pipeid->len; cell->name.s[cell->name.len] = '\0'; cell->cellid = cellid; cell->limit = limit; if (str_map_str(algo_names, algorithm, &cell->algo)) { LM_ERR("cannot find algorithm [%.*s].\n", algorithm->len, algorithm->s); lock_release(&_pl_pipes_ht->slots[idx].lock); return -1; } if(prev==NULL) { if(_pl_pipes_ht->slots[idx].first!=NULL) { cell->next = _pl_pipes_ht->slots[idx].first; _pl_pipes_ht->slots[idx].first->prev = cell; } _pl_pipes_ht->slots[idx].first = cell; } else { cell->next = prev->next; cell->prev = prev; if(prev->next) prev->next->prev = cell; prev->next = cell; } _pl_pipes_ht->slots[idx].ssize++; lock_release(&_pl_pipes_ht->slots[idx].lock); return 0; }