diff --git a/chan_capi_chat.c b/chan_capi_chat.c index 4c50ab6..e21db15 100644 --- a/chan_capi_chat.c +++ b/chan_capi_chat.c @@ -286,7 +286,8 @@ int pbx_capi_chat(struct ast_channel *c, char *param) struct capi_pvt *i = NULL; char *roomname, *controller, *options; struct capichat_s *room; - unsigned int contr = 1; + ast_group_t tmpcntr; + unsigned long contr = 0; roomname = strsep(¶m, "|"); controller = strsep(¶m, "|"); @@ -302,7 +303,8 @@ int pbx_capi_chat(struct ast_channel *c, char *param) c->name, roomname, controller, options); if (controller) { - contr = (unsigned int)strtoul(controller, NULL, 0); + tmpcntr = ast_get_group(controller); + contr = (unsigned long)(tmpcntr >> 1); } if (c->tech == &capi_tech) { diff --git a/chan_capi_utils.c b/chan_capi_utils.c index 1f896d4..60fa4d9 100644 --- a/chan_capi_utils.c +++ b/chan_capi_utils.c @@ -38,6 +38,7 @@ AST_MUTEX_DEFINE_STATIC(nullif_lock); static _cword capi_MessageNumber; static struct capi_pvt *nulliflist = NULL; +static int controller_nullplcis[CAPI_MAX_CONTROLLERS]; #define CAPI_MAX_PEERLINKCHANNELS 32 static struct peerlink_s { @@ -117,6 +118,7 @@ void capi_remove_nullif(struct capi_pvt *i) ast_smoother_free(i->smoother); cc_mutex_destroy(&i->lock); ast_cond_destroy(&i->event_trigger); + controller_nullplcis[i->controller - 1]--; free(i); break; } @@ -129,9 +131,22 @@ void capi_remove_nullif(struct capi_pvt *i) /* * create new null-interface */ -struct capi_pvt *capi_mknullif(struct ast_channel *c, unsigned int controller) +struct capi_pvt *capi_mknullif(struct ast_channel *c, unsigned long controllermask) { struct capi_pvt *tmp; + unsigned int controller = 1; + int contrcount; + int channelcount = 0xffff; + + /* find the next controller of mask with least plcis used */ + for (contrcount = 0; contrcount < CAPI_MAX_CONTROLLERS; contrcount++) { + if ((controllermask & (1 << contrcount))) { + if (controller_nullplcis[contrcount] < channelcount) { + channelcount = controller_nullplcis[contrcount]; + controller = contrcount + 1; + } + } + } tmp = malloc(sizeof(struct capi_pvt)); if (!tmp) { @@ -178,6 +193,7 @@ struct capi_pvt *capi_mknullif(struct ast_channel *c, unsigned int controller) cc_mutex_lock(&nullif_lock); tmp->next = nulliflist; /* prepend */ nulliflist = tmp; + controller_nullplcis[tmp->controller - 1]++; cc_mutex_unlock(&nullif_lock); /* connect to driver */ @@ -189,8 +205,8 @@ struct capi_pvt *capi_mknullif(struct ast_channel *c, unsigned int controller) "w()()()()(www()()()())()()()((wwbbb)()()())", 0, 1,1,0, 3,0,0,0,0); - cc_verbose(3, 1, VERBOSE_PREFIX_4 "%s: created null-interface.\n", - tmp->vname); + cc_verbose(3, 1, VERBOSE_PREFIX_4 "%s: created null-interface on controller %d.\n", + tmp->vname, tmp->controller); return tmp; } diff --git a/chan_capi_utils.h b/chan_capi_utils.h index 606bfb5..702496e 100644 --- a/chan_capi_utils.h +++ b/chan_capi_utils.h @@ -34,7 +34,7 @@ extern char *capi_number_func(unsigned char *data, unsigned int strip, char *buf extern int cc_add_peer_link_id(struct ast_channel *c); extern struct ast_channel *cc_get_peer_link_id(const char *p); extern void capi_remove_nullif(struct capi_pvt *i); -extern struct capi_pvt *capi_mknullif(struct ast_channel *c, unsigned int controller); +extern struct capi_pvt *capi_mknullif(struct ast_channel *c, unsigned long controllermask); extern int capi_create_reader_writer_pipe(struct capi_pvt *i); extern struct ast_frame *capi_read_pipeframe(struct capi_pvt *i); extern int capi_write_frame(struct capi_pvt *i, struct ast_frame *f);