mirror of
https://github.com/asterisk/asterisk.git
synced 2026-07-28 00:10:25 -07:00
Introduce a new API call ast_channel_search_locked, which iterates through the
channel list calling a caller-defined callback. The callback returns non-zero if a match is found. This should speed up some of the code that I committed earlier today in chan_sip (which is also updated by this commit). Reviewed by russellb and kpfleming via ReviewBoard: http://reviewboard.digium.com/r/28/ git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@154429 65c4cc65-6c06-0410-ace0-fbb531ad65f3
This commit is contained in:
+13
-11
@@ -10037,19 +10037,21 @@ static int transmit_state_notify(struct sip_pvt *p, int state, int full, int tim
|
||||
callee must be dialing the same extension that is being monitored. Simply dialing
|
||||
the hint'd device is not sufficient. */
|
||||
if (global_notifycid) {
|
||||
struct ast_channel *caller = NULL;
|
||||
auto int find_calling_channel(struct ast_channel *c);
|
||||
int find_calling_channel(struct ast_channel *c) {
|
||||
return (c->pbx &&
|
||||
(!strcasecmp(c->macroexten, p->exten) || !strcasecmp(c->exten, p->exten)) &&
|
||||
!strcasecmp(c->context, p->context));
|
||||
}
|
||||
|
||||
while ((caller = ast_channel_walk_locked(caller))) {
|
||||
if (caller->pbx &&
|
||||
(!strcasecmp(caller->macroexten, p->exten) || !strcasecmp(caller->exten, p->exten)) &&
|
||||
!strcasecmp(caller->context, p->context)) {
|
||||
local_display = ast_strdupa(caller->cid.cid_name);
|
||||
local_target = ast_strdupa(caller->cid.cid_num);
|
||||
ast_channel_unlock(caller);
|
||||
break;
|
||||
}
|
||||
struct ast_channel *caller = ast_channel_search_locked(find_calling_channel);
|
||||
|
||||
if (caller) {
|
||||
local_display = ast_strdupa(caller->cid.cid_name);
|
||||
local_target = ast_strdupa(caller->cid.cid_num);
|
||||
ast_channel_unlock(caller);
|
||||
}
|
||||
caller = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
/* We create a fake call-id which the phone will send back in an INVITE
|
||||
|
||||
@@ -1177,6 +1177,17 @@ struct ast_channel *ast_get_channel_by_exten_locked(const char *exten, const cha
|
||||
struct ast_channel *ast_walk_channel_by_exten_locked(const struct ast_channel *chan, const char *exten,
|
||||
const char *context);
|
||||
|
||||
/*! \brief Search for a channel based on the passed channel matching callback
|
||||
* Search for a channel based on the specified is_match callback, and return the
|
||||
* first channel that we match. When returned, the channel will be locked. Note
|
||||
* that the is_match callback is called with the passed channel locked, and should
|
||||
* return 0 if there is no match, and non-zero if there is.
|
||||
* \param is_match callback executed on each channel until non-zero is returned, or we
|
||||
* run out of channels to search.
|
||||
* \return Returns the matched channel, or NULL if no channel was matched.
|
||||
*/
|
||||
struct ast_channel *ast_channel_search_locked(int (*is_match)(struct ast_channel *));
|
||||
|
||||
/*! ! \brief Waits for a digit
|
||||
* \param c channel to wait for a digit on
|
||||
* \param ms how many milliseconds to wait
|
||||
|
||||
@@ -1226,6 +1226,24 @@ struct ast_channel *ast_walk_channel_by_exten_locked(const struct ast_channel *c
|
||||
return channel_find_locked(chan, NULL, 0, context, exten);
|
||||
}
|
||||
|
||||
/*! \brief Search for a channel based on the passed channel matching callback (first match) and return it, locked */
|
||||
struct ast_channel *ast_channel_search_locked(int (*is_match)(struct ast_channel *))
|
||||
{
|
||||
struct ast_channel *c = NULL;
|
||||
|
||||
AST_RWLIST_RDLOCK(&channels);
|
||||
AST_RWLIST_TRAVERSE(&channels, c, chan_list) {
|
||||
ast_channel_lock(c);
|
||||
if (is_match(c)) {
|
||||
break;
|
||||
}
|
||||
ast_channel_unlock(c);
|
||||
}
|
||||
AST_RWLIST_UNLOCK(&channels);
|
||||
|
||||
return c;
|
||||
}
|
||||
|
||||
/*! \brief Wait, look for hangups and condition arg */
|
||||
int ast_safe_sleep_conditional(struct ast_channel *chan, int ms, int (*cond)(void*), void *data)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user