From 4d6996c27ad2cc1e0055b06b18522a44036c4f5c Mon Sep 17 00:00:00 2001 From: murf Date: Tue, 7 Nov 2006 21:47:49 +0000 Subject: A fair number of changes for the sake of bug 7506 git-svn-id: http://svn.digium.com/svn/asterisk/trunk@47290 f38db490-d61c-443f-a65b-d21fe96a405b --- apps/app_voicemail.c | 12 +++---- channels/chan_agent.c | 10 +++--- channels/chan_alsa.c | 4 +-- channels/chan_features.c | 24 ++++++++----- channels/chan_gtalk.c | 19 ++++++----- channels/chan_h323.c | 32 +++++++++--------- channels/chan_iax2.c | 10 ++---- channels/chan_jingle.c | 19 ++++++----- channels/chan_local.c | 9 ++--- channels/chan_mgcp.c | 5 ++- channels/chan_misdn.c | 20 ++++++++--- channels/chan_nbs.c | 4 +-- channels/chan_oss.c | 10 +++--- channels/chan_phone.c | 5 ++- channels/chan_sip.c | 37 ++++++++++----------- channels/chan_skinny.c | 6 ++-- channels/chan_vpb.cc | 5 +-- channels/chan_zap.c | 47 ++++++++++++++------------ include/asterisk/channel.h | 8 ++++- include/asterisk/stringfields.h | 39 ++++++++++++++++++++++ main/channel.c | 74 +++++++++++++++++++++++++++++++---------- main/pbx.c | 9 ++--- main/utils.c | 21 ++++++++---- res/res_features.c | 10 ++---- 24 files changed, 266 insertions(+), 173 deletions(-) diff --git a/apps/app_voicemail.c b/apps/app_voicemail.c index 2468f751a..b29381362 100644 --- a/apps/app_voicemail.c +++ b/apps/app_voicemail.c @@ -1882,7 +1882,7 @@ static void make_email_file(FILE *p, char *srcemail, struct ast_vm_user *vmu, in if (*fromstring) { struct ast_channel *ast; - if ((ast = ast_channel_alloc(0))) { + if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, 0))) { char *passdata; int vmlen = strlen(fromstring)*3 + 200; if ((passdata = alloca(vmlen))) { @@ -1900,7 +1900,7 @@ static void make_email_file(FILE *p, char *srcemail, struct ast_vm_user *vmu, in fprintf(p, "To: %s <%s>\r\n", vmu->fullname, vmu->email); if (emailsubject) { struct ast_channel *ast; - if ((ast = ast_channel_alloc(0))) { + if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, 0))) { char *passdata; int vmlen = strlen(emailsubject)*3 + 200; if ((passdata = alloca(vmlen))) { @@ -1954,7 +1954,7 @@ static void make_email_file(FILE *p, char *srcemail, struct ast_vm_user *vmu, in fprintf(p, "Content-Type: text/plain; charset=%s\r\nContent-Transfer-Encoding: 8bit\r\n\r\n", charset); if (emailbody) { struct ast_channel *ast; - if ((ast = ast_channel_alloc(0))) { + if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, 0))) { char *passdata; int vmlen = strlen(emailbody)*3 + 200; if ((passdata = alloca(vmlen))) { @@ -2069,7 +2069,7 @@ static int sendpage(char *srcemail, char *pager, int msgnum, char *context, char if (*pagerfromstring) { struct ast_channel *ast; - if ((ast = ast_channel_alloc(0))) { + if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, 0))) { char *passdata; int vmlen = strlen(fromstring)*3 + 200; if ((passdata = alloca(vmlen))) { @@ -2086,7 +2086,7 @@ static int sendpage(char *srcemail, char *pager, int msgnum, char *context, char fprintf(p, "To: %s\n", pager); if (pagersubject) { struct ast_channel *ast; - if ((ast = ast_channel_alloc(0))) { + if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, 0))) { char *passdata; int vmlen = strlen(pagersubject) * 3 + 200; if ((passdata = alloca(vmlen))) { @@ -2102,7 +2102,7 @@ static int sendpage(char *srcemail, char *pager, int msgnum, char *context, char strftime(date, sizeof(date), "%A, %B %d, %Y at %r", &tm); if (pagerbody) { struct ast_channel *ast; - if ((ast = ast_channel_alloc(0))) { + if ((ast = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, 0))) { char *passdata; int vmlen = strlen(pagerbody)*3 + 200; if ((passdata = alloca(vmlen))) { diff --git a/channels/chan_agent.c b/channels/chan_agent.c index 4eff85fdb..40909b21d 100644 --- a/channels/chan_agent.c +++ b/channels/chan_agent.c @@ -905,7 +905,10 @@ static struct ast_channel *agent_new(struct agent_pvt *p, int state) return NULL; } #endif - tmp = ast_channel_alloc(0); + if (p->pending) + tmp = ast_channel_alloc(0, state, 0, 0, "Agent/P%s-%d", p->agent, ast_random() & 0xffff); + else + tmp = ast_channel_alloc(0, state, 0, 0, "Agent/%s", p->agent); if (!tmp) { ast_log(LOG_WARNING, "Unable to allocate agent channel structure\n"); return NULL; @@ -929,12 +932,7 @@ static struct ast_channel *agent_new(struct agent_pvt *p, int state) tmp->readformat = AST_FORMAT_SLINEAR; tmp->rawreadformat = AST_FORMAT_SLINEAR; } - if (p->pending) - ast_string_field_build(tmp, name, "Agent/P%s-%d", p->agent, ast_random() & 0xffff); - else - ast_string_field_build(tmp, name, "Agent/%s", p->agent); /* Safe, agentlock already held */ - ast_setstate(tmp, state); tmp->tech_pvt = p; p->owner = tmp; tmp->priority = 1; diff --git a/channels/chan_alsa.c b/channels/chan_alsa.c index 07d5038ca..965cb18e0 100644 --- a/channels/chan_alsa.c +++ b/channels/chan_alsa.c @@ -788,11 +788,10 @@ static struct ast_channel *alsa_new(struct chan_alsa_pvt *p, int state) { struct ast_channel *tmp = NULL; - if (!(tmp = ast_channel_alloc(1))) + if (!(tmp = ast_channel_alloc(1, state, 0, 0, "ALSA/%s", indevname))) return NULL; tmp->tech = &alsa_tech; - ast_string_field_build(tmp, name, "ALSA/%s", indevname); tmp->fds[0] = readdev; tmp->nativeformats = AST_FORMAT_SLINEAR; tmp->readformat = AST_FORMAT_SLINEAR; @@ -805,7 +804,6 @@ static struct ast_channel *alsa_new(struct chan_alsa_pvt *p, int state) if (!ast_strlen_zero(language)) ast_string_field_set(tmp, language, language); p->owner = tmp; - ast_setstate(tmp, state); ast_jb_configure(tmp, &global_jbconf); if (state != AST_STATE_DOWN) { if (ast_pbx_start(tmp)) { diff --git a/channels/chan_features.c b/channels/chan_features.c index bf5ef8d5b..8a5846d27 100644 --- a/channels/chan_features.c +++ b/channels/chan_features.c @@ -449,6 +449,7 @@ static struct ast_channel *features_new(struct feature_pvt *p, int state, int in { struct ast_channel *tmp; int x,y; + char *b2 = 0; if (!p->subchan) { ast_log(LOG_WARNING, "Called upon channel with no subchan:(\n"); return NULL; @@ -457,24 +458,29 @@ static struct ast_channel *features_new(struct feature_pvt *p, int state, int in ast_log(LOG_WARNING, "Called to put index %d already there!\n", index); return NULL; } - tmp = ast_channel_alloc(0); - if (!tmp) { - ast_log(LOG_WARNING, "Unable to allocate channel structure\n"); - return NULL; - } - tmp->tech = &features_tech; + /* figure out what you want the name to be */ for (x=1;x<4;x++) { - ast_string_field_build(tmp, name, "Feature/%s/%s-%d", p->tech, p->dest, x); + if (b2) + free(b2); + b2 = ast_safe_string_alloc("Feature/%s/%s-%d", p->tech, p->dest, x); for (y=0;y<3;y++) { if (y == index) continue; - if (p->subs[y].owner && !strcasecmp(p->subs[y].owner->name, tmp->name)) + if (p->subs[y].owner && !strcasecmp(p->subs[y].owner->name, b2)) break; } if (y >= 3) break; } - ast_setstate(tmp, state); + tmp = ast_channel_alloc(0, state, 0,0, b2); + /* free up the name, it was copied into the channel name */ + if (b2) + free(b2); + if (!tmp) { + ast_log(LOG_WARNING, "Unable to allocate channel structure\n"); + return NULL; + } + tmp->tech = &features_tech; tmp->writeformat = p->subchan->writeformat; tmp->rawwriteformat = p->subchan->rawwriteformat; tmp->readformat = p->subchan->readformat; diff --git a/channels/chan_gtalk.c b/channels/chan_gtalk.c index 7094e94a8..e3a71c624 100644 --- a/channels/chan_gtalk.c +++ b/channels/chan_gtalk.c @@ -895,8 +895,13 @@ static struct ast_channel *gtalk_new(struct gtalk *client, struct gtalk_pvt *i, struct ast_channel *tmp; int fmt; int what; + char *n2; - tmp = ast_channel_alloc(1); + if (title) + n2 = title; + else + n2 = i->us; + tmp = ast_channel_alloc(1, state, i->cid_num, i->cid_name, "Gtalk/%s-%04lx", n2, ast_random() & 0xffff); if (!tmp) { ast_log(LOG_WARNING, "Unable to allocate Gtalk channel structure!\n"); return NULL; @@ -915,11 +920,6 @@ static struct ast_channel *gtalk_new(struct gtalk *client, struct gtalk_pvt *i, tmp->nativeformats = ast_codec_choose(&i->prefs, what, 1) | (i->jointcapability & AST_FORMAT_VIDEO_MASK); fmt = ast_best_codec(tmp->nativeformats); - if (title) - ast_string_field_build(tmp, name, "Gtalk/%s-%04lx", title, ast_random() & 0xffff); - else - ast_string_field_build(tmp, name, "Gtalk/%s-%04lx", i->us, ast_random() & 0xffff); - if (i->rtp) { tmp->fds[0] = ast_rtp_fd(i->rtp); tmp->fds[1] = ast_rtcp_fd(i->rtp); @@ -951,11 +951,14 @@ static struct ast_channel *gtalk_new(struct gtalk *client, struct gtalk_pvt *i, i->owner = tmp; ast_copy_string(tmp->context, client->context, sizeof(tmp->context)); ast_copy_string(tmp->exten, i->exten, sizeof(tmp->exten)); - ast_set_callerid(tmp, i->cid_num, i->cid_name, i->cid_num); + /* Don't use ast_set_callerid() here because it will + * generate a needless NewCallerID event */ + tmp->cid.cid_num = ast_strdup(l->cid_num); + tmp->cid.cid_ani = ast_strdup(l->cid_num); + tmp->cid.cid_name = ast_strdup(l->cid_name); if (!ast_strlen_zero(i->exten) && strcmp(i->exten, "s")) tmp->cid.cid_dnid = ast_strdup(i->exten); tmp->priority = 1; - ast_setstate(tmp, state); if (i->rtp) ast_jb_configure(tmp, &global_jbconf); if (state != AST_STATE_DOWN && ast_pbx_start(tmp)) { diff --git a/channels/chan_h323.c b/channels/chan_h323.c index 3bb49d39b..663d48142 100644 --- a/channels/chan_h323.c +++ b/channels/chan_h323.c @@ -1006,17 +1006,27 @@ static int __oh323_rtp_create(struct oh323_pvt *pvt) static struct ast_channel *__oh323_new(struct oh323_pvt *pvt, int state, const char *host) { struct ast_channel *ch; + char *cid_num, *cid_name; int fmt; + if (!ast_strlen_zero(pvt->options.cid_num)) + cid_num = pvt->options.cid_num; + else + cid_num = pvt->cd.call_source_e164; + + if (!ast_strlen_zero(pvt->options.cid_name)) + cid_name = pvt->options.cid_name; + else + cid_name = pvt->cd.call_source_name; + /* Don't hold a oh323_pvt lock while we allocate a chanel */ ast_mutex_unlock(&pvt->lock); - ch = ast_channel_alloc(1); + ch = ast_channel_alloc(1, state, cid_num, cid_name, "H323/%s", host); /* Update usage counter */ ast_module_ref(ast_module_info->self); ast_mutex_lock(&pvt->lock); if (ch) { ch->tech = &oh323_tech; - ast_string_field_build(ch, name, "H323/%s", host); if (!(fmt = pvt->jointcapability) && !(fmt = pvt->options.capability)) fmt = global_options.capability; ch->nativeformats = ast_codec_choose(&pvt->options.prefs, fmt, 1)/* | (pvt->jointcapability & AST_FORMAT_VIDEO_MASK)*/; @@ -1065,18 +1075,11 @@ static struct ast_channel *__oh323_new(struct oh323_pvt *pvt, int state, const c } /* Don't use ast_set_callerid() here because it will - * generate a NewCallerID event before the NewChannel event */ - if (!ast_strlen_zero(pvt->options.cid_num)) { - ch->cid.cid_num = ast_strdup(pvt->options.cid_num); - ch->cid.cid_ani = ast_strdup(pvt->options.cid_num); - } else { - ch->cid.cid_num = ast_strdup(pvt->cd.call_source_e164); - ch->cid.cid_ani = ast_strdup(pvt->cd.call_source_e164); - } - if (!ast_strlen_zero(pvt->options.cid_name)) - ch->cid.cid_name = ast_strdup(pvt->options.cid_name); - else - ch->cid.cid_name = ast_strdup(pvt->cd.call_source_name); + * generate a needless NewCallerID event */ + ch->cid.cid_num = ast_strdup(cid_num); + ch->cid.cid_ani = ast_strdup(cid_num); + ch->cid.cid_name = ast_strdup(cid_name); + if (pvt->cd.redirect_reason >= 0) { ch->cid.cid_rdnis = ast_strdup(pvt->cd.redirect_number); pbx_builtin_setvar_helper(ch, "PRIREDIRECTREASON", redirectingreason2str(pvt->cd.redirect_reason)); @@ -1089,7 +1092,6 @@ static struct ast_channel *__oh323_new(struct oh323_pvt *pvt, int state, const c } if (pvt->cd.transfer_capability >= 0) ch->transfercapability = pvt->cd.transfer_capability; - ast_setstate(ch, state); if (state != AST_STATE_DOWN) { if (ast_pbx_start(ch)) { ast_log(LOG_WARNING, "Unable to start PBX on %s\n", ch->name); diff --git a/channels/chan_iax2.c b/channels/chan_iax2.c index 95c333766..d3ce281f9 100644 --- a/channels/chan_iax2.c +++ b/channels/chan_iax2.c @@ -3265,12 +3265,11 @@ static struct ast_channel *ast_iax2_new(int callno, int state, int capability) /* Don't hold call lock */ ast_mutex_unlock(&iaxsl[callno]); - tmp = ast_channel_alloc(1); + tmp = ast_channel_alloc(1, state, i->cid_num, i->cid_name, "IAX2/%s-%d", i->host, i->callno); ast_mutex_lock(&iaxsl[callno]); if (!tmp) return NULL; tmp->tech = &iax2_tech; - ast_string_field_build(tmp, name, "IAX2/%s-%d", i->host, i->callno); /* We can support any format by default, until we get restricted */ tmp->nativeformats = capability; tmp->readformat = ast_best_codec(capability); @@ -3304,7 +3303,6 @@ static struct ast_channel *ast_iax2_new(int callno, int state, int capability) tmp->adsicpe = AST_ADSI_UNAVAILABLE; i->owner = tmp; i->capability = capability; - ast_setstate(tmp, state); if (state != AST_STATE_DOWN) { if (ast_pbx_start(tmp)) { ast_log(LOG_WARNING, "Unable to start PBX on %s\n", tmp->name); @@ -6112,10 +6110,9 @@ static int iax_park(struct ast_channel *chan1, struct ast_channel *chan2) struct iax_dual *d; struct ast_channel *chan1m, *chan2m; pthread_t th; - chan1m = ast_channel_alloc(0); - chan2m = ast_channel_alloc(0); + chan1m = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "Parking/%s", chan1->name); + chan2m = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "IAXPeer/%s",chan2->name); if (chan2m && chan1m) { - ast_string_field_build(chan1m, name, "Parking/%s", chan1->name); /* Make formats okay */ chan1m->readformat = chan1->readformat; chan1m->writeformat = chan1->writeformat; @@ -6127,7 +6124,6 @@ static int iax_park(struct ast_channel *chan1, struct ast_channel *chan2) /* We make a clone of the peer channel too, so we can play back the announcement */ - ast_string_field_build(chan2m, name, "IAXPeer/%s",chan2->name); /* Make formats okay */ chan2m->readformat = chan2->readformat; chan2m->writeformat = chan2->writeformat; diff --git a/channels/chan_jingle.c b/channels/chan_jingle.c index f366cdd6b..732199b75 100644 --- a/channels/chan_jingle.c +++ b/channels/chan_jingle.c @@ -754,8 +754,13 @@ static struct ast_channel *jingle_new(struct jingle *client, struct jingle_pvt * struct ast_channel *tmp; int fmt; int what; + char *str; - tmp = ast_channel_alloc(1); + if (title) + str = title; + else + str = i->from; + tmp = ast_channel_alloc(1, state, i->cid_num, i->cid_name, "Jingle/%s-%04lx", str, ast_random() & 0xffff); if (!tmp) { ast_log(LOG_WARNING, "Unable to allocate Jingle channel structure!\n"); return NULL; @@ -773,11 +778,6 @@ static struct ast_channel *jingle_new(struct jingle *client, struct jingle_pvt * tmp->nativeformats = ast_codec_choose(&i->prefs, what, 1) | (i->jointcapability & AST_FORMAT_VIDEO_MASK); fmt = ast_best_codec(tmp->nativeformats); - if (title) - ast_string_field_build(tmp, name, "Jingle/%s-%04lx", title, ast_random() & 0xffff); - else - ast_string_field_build(tmp, name, "Jingle/%s-%04lx", i->from, ast_random() & 0xffff); - if (i->rtp) { tmp->fds[0] = ast_rtp_fd(i->rtp); tmp->fds[1] = ast_rtcp_fd(i->rtp); @@ -809,11 +809,14 @@ static struct ast_channel *jingle_new(struct jingle *client, struct jingle_pvt * i->owner = tmp; ast_copy_string(tmp->context, client->context, sizeof(tmp->context)); ast_copy_string(tmp->exten, i->exten, sizeof(tmp->exten)); - ast_set_callerid(tmp, i->cid_num, i->cid_name, i->cid_num); + /* Don't use ast_set_callerid() here because it will + * generate an unnecessary NewCallerID event */ + tmp->cid.cid_num = ast_strdup(i->cid_num); + tmp->cid.cid_ani = ast_strdup(i->cid_num); + tmp->cid.cid_name = ast_strdup(i->cid_name); if (!ast_strlen_zero(i->exten) && strcmp(i->exten, "s")) tmp->cid.cid_dnid = ast_strdup(i->exten); tmp->priority = 1; - ast_setstate(tmp, state); if (i->rtp) ast_jb_configure(tmp, &global_jbconf); if (state != AST_STATE_DOWN && ast_pbx_start(tmp)) { diff --git a/channels/chan_local.c b/channels/chan_local.c index db6081a53..fe821363d 100644 --- a/channels/chan_local.c +++ b/channels/chan_local.c @@ -549,7 +549,8 @@ static struct ast_channel *local_new(struct local_pvt *p, int state) int randnum = ast_random() & 0xffff, fmt = 0; /* Allocate two new Asterisk channels */ - if (!(tmp = ast_channel_alloc(1)) || !(tmp2 = ast_channel_alloc(1))) { + if (!(tmp = ast_channel_alloc(1, state, 0, 0, "Local/%s@%s-%04x,1", p->exten, p->context, randnum)) + || !(tmp2 = ast_channel_alloc(1, AST_STATE_RING, 0, 0, "Local/%s@%s-%04x,2", p->exten, p->context, randnum))) { if (tmp) ast_channel_free(tmp); if (tmp2) @@ -563,12 +564,6 @@ static struct ast_channel *local_new(struct local_pvt *p, int state) tmp->nativeformats = p->reqformat; tmp2->nativeformats = p->reqformat; - ast_string_field_build(tmp, name, "Local/%s@%s-%04x,1", p->exten, p->context, randnum); - ast_string_field_build(tmp2, name, "Local/%s@%s-%04x,2", p->exten, p->context, randnum); - - ast_setstate(tmp, state); - ast_setstate(tmp2, AST_STATE_RING); - /* Determine our read/write format and set it on each channel */ fmt = ast_best_codec(p->reqformat); tmp->writeformat = fmt; diff --git a/channels/chan_mgcp.c b/channels/chan_mgcp.c index 02a7600df..2e8011acc 100644 --- a/channels/chan_mgcp.c +++ b/channels/chan_mgcp.c @@ -1433,7 +1433,7 @@ static struct ast_channel *mgcp_new(struct mgcp_subchannel *sub, int state) struct mgcp_endpoint *i = sub->parent; int fmt; - tmp = ast_channel_alloc(1); + tmp = ast_channel_alloc(1, state, i->cid_num, i->cid_name, "MGCP/%s@%s-%d", i->name, i->parent->name, sub->id); if (tmp) { tmp->tech = &mgcp_tech; tmp->nativeformats = i->capability; @@ -1451,7 +1451,6 @@ static struct ast_channel *mgcp_new(struct mgcp_subchannel *sub, int state) } else { i->dsp = NULL; } - ast_setstate(tmp, state); if (state == AST_STATE_RING) tmp->rings = 1; tmp->writeformat = fmt; @@ -1474,7 +1473,7 @@ static struct ast_channel *mgcp_new(struct mgcp_subchannel *sub, int state) ast_copy_string(tmp->exten, i->exten, sizeof(tmp->exten)); /* Don't use ast_set_callerid() here because it will - * generate a NewCallerID event before the NewChannel event */ + * generate a needless NewCallerID event */ tmp->cid.cid_num = ast_strdup(i->cid_num); tmp->cid.cid_ani = ast_strdup(i->cid_num); tmp->cid.cid_name = ast_strdup(i->cid_name); diff --git a/channels/chan_misdn.c b/channels/chan_misdn.c index e318bd267..74a6ce4e8 100644 --- a/channels/chan_misdn.c +++ b/channels/chan_misdn.c @@ -3103,14 +3103,25 @@ static void update_name(struct ast_channel *tmp, int port, int c) static struct ast_channel *misdn_new(struct chan_list *chlist, int state, char *exten, char *callerid, int format, int port, int c) { struct ast_channel *tmp; + char *cid_name = 0, *cid_num = 0; + int chan_offset=0; + int tmp_port = misdn_cfg_get_next_port(0); + + for (; tmp_port > 0; tmp_port=misdn_cfg_get_next_port(tmp_port)) { + if (tmp_port == port) break; + chan_offset+=misdn_lib_port_is_pri(tmp_port)?30:2; + } + if (c<0) c=0; + - tmp = ast_channel_alloc(1); + if (callerid) + ast_callerid_parse(callerid, &cid_name, &cid_num); + + tmp = ast_channel_alloc(1, state, cid_num, cid_name, "%s/%d-u%d", misdn_type, chan_offset + c, glob_channel++); if (tmp) { chan_misdn_log(2, 0, " --> * NEW CHANNEL dad:%s oad:%s\n",exten,callerid); - update_name(tmp,port,c); - tmp->nativeformats = prefformat; tmp->readformat = format; @@ -3141,7 +3152,7 @@ static struct ast_channel *misdn_new(struct chan_list *chlist, int state, char ast_callerid_parse(callerid, &cid_name, &cid_num); /* Don't use ast_set_callerid() here because it will - * generate a NewCallerID event before the NewChannel event */ + * generate a needless NewCallerID event */ tmp->cid.cid_num = ast_strdup(cid_num); tmp->cid.cid_ani = ast_strdup(cid_num); tmp->cid.cid_name = ast_strdup(cid_name); @@ -3155,7 +3166,6 @@ static struct ast_channel *misdn_new(struct chan_list *chlist, int state, char } - ast_setstate(tmp, state); if (state == AST_STATE_RING) tmp->rings = 1; else diff --git a/channels/chan_nbs.c b/channels/chan_nbs.c index 8cf72fb43..0e9a32950 100644 --- a/channels/chan_nbs.c +++ b/channels/chan_nbs.c @@ -233,17 +233,15 @@ static int nbs_xwrite(struct ast_channel *ast, struct ast_frame *frame) static struct ast_channel *nbs_new(struct nbs_pvt *i, int state) { struct ast_channel *tmp; - tmp = ast_channel_alloc(1); + tmp = ast_channel_alloc(1, state, 0, 0, "NBS/%s", i->stream); if (tmp) { tmp->tech = &nbs_tech; - ast_string_field_build(tmp, name, "NBS/%s", i->stream); tmp->fds[0] = nbs_fd(i->nbs); tmp->nativeformats = prefformat; tmp->rawreadformat = prefformat; tmp->rawwriteformat = prefformat; tmp->writeformat = prefformat; tmp->readformat = prefformat; - ast_setstate(tmp, state); if (state == AST_STATE_RING) tmp->rings = 1; tmp->tech_pvt = i; diff --git a/channels/chan_oss.c b/channels/chan_oss.c index cba7356e3..2e13f269d 100644 --- a/channels/chan_oss.c +++ b/channels/chan_oss.c @@ -990,11 +990,10 @@ static struct ast_channel *oss_new(struct chan_oss_pvt *o, char *ext, char *ctx, { struct ast_channel *c; - c = ast_channel_alloc(1); + c = ast_channel_alloc(1, state, o->cid_num, o->cid_name, "OSS/%s", o->device + 5); if (c == NULL) return NULL; c->tech = &oss_tech; - ast_string_field_build(c, name, "OSS/%s", o->device + 5); if (o->sounddev < 0) setformat(o, O_RDWR); c->fds[0] = o->sounddev; /* -1 if device closed, override later */ @@ -1009,12 +1008,15 @@ static struct ast_channel *oss_new(struct chan_oss_pvt *o, char *ext, char *ctx, ast_copy_string(c->exten, ext, sizeof(c->exten)); if (!ast_strlen_zero(o->language)) ast_string_field_set(c, language, o->language); - ast_set_callerid(c, o->cid_num, o->cid_name, o->cid_num); + /* Don't use ast_set_callerid() here because it will + * generate a needless NewCallerID event */ + c->cid.cid_num = ast_strdup(o->cid_num); + c->cid.cid_ani = ast_strdup(o->cid_num); + c->cid.cid_name = ast_strdup(o->cid_name); if (!ast_strlen_zero(ext)) c->cid.cid_dnid = ast_strdup(ext); o->owner = c; - ast_setstate(c, state); ast_jb_configure(c, &global_jbconf); if (state != AST_STATE_DOWN) { if (ast_pbx_start(c)) { diff --git a/channels/chan_phone.c b/channels/chan_phone.c index 853668043..244326cd8 100644 --- a/channels/chan_phone.c +++ b/channels/chan_phone.c @@ -835,10 +835,9 @@ static struct ast_channel *phone_new(struct phone_pvt *i, int state, char *conte { struct ast_channel *tmp; struct phone_codec_data codec; - tmp = ast_channel_alloc(1); + tmp = ast_channel_alloc(1, state, i->cid_num, i->cid_name, "Phone/%s", i->dev + 5); if (tmp) { tmp->tech = cur_tech; - ast_string_field_build(tmp, name, "Phone/%s", i->dev + 5); tmp->fds[0] = i->fd; /* XXX Switching formats silently causes kernel panics XXX */ if (i->mode == MODE_FXS && @@ -860,7 +859,7 @@ static struct ast_channel *phone_new(struct phone_pvt *i, int state, char *conte tmp->rawreadformat = prefformat; tmp->rawwriteformat = prefformat; } - ast_setstate(tmp, state); + /* no need to call ast_setstate: the channel_alloc already did its job */ if (state == AST_STATE_RING) tmp->rings = 1; tmp->tech_pvt = i; diff --git a/channels/chan_sip.c b/channels/chan_sip.c index fa9902e56..727ab43e8 100644 --- a/channels/chan_sip.c +++ b/channels/chan_sip.c @@ -3775,10 +3775,22 @@ static struct ast_channel *sip_new(struct sip_pvt *i, int state, const char *tit int fmt; int what; int needvideo = 0; + { + const char *my_name; /* pick a good name */ - sip_pvt_unlock(i); - /* Don't hold a sip pvt lock while we allocate a channel */ - tmp = ast_channel_alloc(1); + if (title) + my_name = title; + else if ( (my_name = strchr(i->fromdomain,':')) ) + my_name++; /* skip ':' */ + else + my_name = i->fromdomain; + + sip_pvt_unlock(i); + /* Don't hold a sip pvt lock while we allocate a channel */ + + tmp = ast_channel_alloc(1, state, i->cid_num, i->cid_name, "SIP/%s-%08x", my_name, (int)(long) i); + + } sip_pvt_lock(i); if (!tmp) { ast_log(LOG_WARNING, "Unable to allocate AST channel structure for SIP channel\n"); @@ -3829,16 +3841,6 @@ static struct ast_channel *sip_new(struct sip_pvt *i, int state, const char *tit } - { - const char *my_name; /* pick a good name */ - if (title) - my_name = title; - else if ( (my_name = strchr(i->fromdomain,':')) ) - my_name++; /* skip ':' */ - else - my_name = i->fromdomain; - ast_string_field_build(tmp, name, "SIP/%s-%08x", my_name, (int)(long) i); - } if (ast_test_flag(&i->flags[0], SIP_DTMF) == SIP_DTMF_INBAND) { i->vad = ast_dsp_new(); @@ -3880,7 +3882,7 @@ static struct ast_channel *sip_new(struct sip_pvt *i, int state, const char *tit ast_copy_string(tmp->exten, i->exten, sizeof(tmp->exten)); /* Don't use ast_set_callerid() here because it will - * generate a NewCallerID event before the NewChannel event */ + * generate an unnecessary NewCallerID event */ tmp->cid.cid_num = ast_strdup(i->cid_num); tmp->cid.cid_ani = ast_strdup(i->cid_num); tmp->cid.cid_name = ast_strdup(i->cid_name); @@ -3897,7 +3899,6 @@ static struct ast_channel *sip_new(struct sip_pvt *i, int state, const char *tit pbx_builtin_setvar_helper(tmp, "SIPDOMAIN", i->domain); if (!ast_strlen_zero(i->callid)) pbx_builtin_setvar_helper(tmp, "SIPCALLID", i->callid); - ast_setstate(tmp, state); if (i->rtp) ast_jb_configure(tmp, &global_jbconf); if (state != AST_STATE_DOWN && ast_pbx_start(tmp)) { @@ -12517,8 +12518,8 @@ static int sip_park(struct ast_channel *chan1, struct ast_channel *chan2, struct /* Chan2m: The transferer, chan1m: The transferee */ pthread_t th; - transferee = ast_channel_alloc(0); - transferer = ast_channel_alloc(0); + transferee = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "Parking/%s", chan1->name); + transferer = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "SIPPeer/%s", chan2->name); if ((!transferer) || (!transferee)) { if (transferee) { transferee->hangupcause = AST_CAUSE_SWITCH_CONGESTION; @@ -12530,7 +12531,6 @@ static int sip_park(struct ast_channel *chan1, struct ast_channel *chan2, struct } return -1; } - ast_string_field_build(transferee, name, "Parking/%s", chan1->name); /* Make formats okay */ transferee->readformat = chan1->readformat; @@ -12546,7 +12546,6 @@ static int sip_park(struct ast_channel *chan1, struct ast_channel *chan2, struct /* We make a clone of the peer channel too, so we can play back the announcement */ - ast_string_field_build(transferer, name, "SIPPeer/%s", chan2->name); /* Make formats okay */ transferer->readformat = chan2->readformat; diff --git a/channels/chan_skinny.c b/channels/chan_skinny.c index bda495a82..cc086b0bf 100644 --- a/channels/chan_skinny.c +++ b/channels/chan_skinny.c @@ -2699,7 +2699,7 @@ static struct ast_channel *skinny_new(struct skinny_line *l, int state) struct skinny_device *d = l->parent; int fmt; - tmp = ast_channel_alloc(1); + tmp = ast_channel_alloc(1, state, l->cid_num, l->cid_name, "Skinny/%s@%s-%d", l->name, d->name, callnums); if (!tmp) { ast_log(LOG_WARNING, "Unable to allocate channel structure\n"); return NULL; @@ -2731,11 +2731,9 @@ static struct ast_channel *skinny_new(struct skinny_line *l, int state) fmt = ast_best_codec(tmp->nativeformats); if (skinnydebug) ast_verbose("skinny_new: tmp->nativeformats=%d fmt=%d\n", tmp->nativeformats, fmt); - ast_string_field_build(tmp, name, "Skinny/%s@%s-%d", l->name, d->name, sub->callid); if (sub->rtp) { tmp->fds[0] = ast_rtp_fd(sub->rtp); } - ast_setstate(tmp, state); if (state == AST_STATE_RING) { tmp->rings = 1; } @@ -2757,7 +2755,7 @@ static struct ast_channel *skinny_new(struct skinny_line *l, int state) ast_copy_string(tmp->exten, l->exten, sizeof(tmp->exten)); /* Don't use ast_set_callerid() here because it will - * generate a NewCallerID event before the NewChannel event */ + * generate a needless NewCallerID event */ tmp->cid.cid_num = ast_strdup(l->cid_num); tmp->cid.cid_ani = ast_strdup(l->cid_num); tmp->cid.cid_name = ast_strdup(l->cid_name); diff --git a/channels/chan_vpb.cc b/channels/chan_vpb.cc index 06832cb5c..e85500b93 100644 --- a/channels/chan_vpb.cc +++ b/channels/chan_vpb.cc @@ -2626,7 +2626,7 @@ static struct ast_channel *vpb_new(struct vpb_pvt *me, enum ast_channel_state st if (option_verbose > 3) ast_verbose("%s: New call for context [%s]\n",me->dev,context); - tmp = ast_channel_alloc(1); + tmp = ast_channel_alloc(1, state, 0, 0, me->dev); if (tmp) { if (use_ast_ind == 1){ tmp->tech = &vpb_tech_indicate; @@ -2635,8 +2635,6 @@ static struct ast_channel *vpb_new(struct vpb_pvt *me, enum ast_channel_state st tmp->tech = &vpb_tech; } - ast_string_field_set(tmp, name, me->dev); - tmp->callgroup = me->callgroup; tmp->pickupgroup = me->pickupgroup; @@ -2647,7 +2645,6 @@ static struct ast_channel *vpb_new(struct vpb_pvt *me, enum ast_channel_state st tmp->nativeformats = prefformat; tmp->rawreadformat = AST_FORMAT_SLINEAR; tmp->rawwriteformat = AST_FORMAT_SLINEAR; - ast_setstate(tmp, state); if (state == AST_STATE_RING) { tmp->rings = 1; cid_name[0] = '\0'; diff --git a/channels/chan_zap.c b/channels/chan_zap.c index 0a2bfc3dd..6d0c9ccd2 100644 --- a/channels/chan_zap.c +++ b/channels/chan_zap.c @@ -5482,12 +5482,35 @@ static struct ast_channel *zt_new(struct zt_pvt *i, int state, int startpbx, int int res; int x,y; int features; + char *b2 = 0; ZT_PARAMS ps; if (i->subs[index].owner) { ast_log(LOG_WARNING, "Channel %d already has a %s call\n", i->channel,subnames[index]); return NULL; } - if (!(tmp = ast_channel_alloc(0))) + y = 1; + do { + if (b2) + free(b2); +#ifdef HAVE_PRI + if (i->bearer || (i->pri && (i->sig == SIG_FXSKS))) + b2 = ast_safe_string_alloc("Zap/%d:%d-%d", i->pri->trunkgroup, i->channel, y); + else +#endif + if (i->channel == CHAN_PSEUDO) + b2 = ast_safe_string_alloc("Zap/pseudo-%d", ast_random()); + else + b2 = ast_safe_string_alloc("Zap/%d-%d", i->channel, y); + for (x = 0; x < 3; x++) { + if ((index != x) && i->subs[x].owner && !strcasecmp(b2, i->subs[x].owner->name)) + break; + } + y++; + } while (x < 3); + tmp = ast_channel_alloc(0, state, 0, 0, b2); + if (b2) /*!> b2 can be freed now, it's been copied into the channel structure */ + free(b2); + if (!tmp) return NULL; tmp->tech = &zap_tech; ps.channo = i->channel; @@ -5506,23 +5529,6 @@ static struct ast_channel *zt_new(struct zt_pvt *i, int state, int startpbx, int else deflaw = AST_FORMAT_ULAW; } - y = 1; - do { -#ifdef HAVE_PRI - if (i->bearer || (i->pri && (i->sig == SIG_FXSKS))) - ast_string_field_build(tmp, name, "Zap/%d:%d-%d", i->pri->trunkgroup, i->channel, y); - else -#endif - if (i->channel == CHAN_PSEUDO) - ast_string_field_build(tmp, name, "Zap/pseudo-%d", ast_random()); - else - ast_string_field_build(tmp, name, "Zap/%d-%d", i->channel, y); - for (x = 0; x < 3; x++) { - if ((index != x) && i->subs[x].owner && !strcasecmp(tmp->name, i->subs[x].owner->name)) - break; - } - y++; - } while (x < 3); tmp->fds[0] = i->subs[index].zfd; tmp->nativeformats = AST_FORMAT_SLINEAR | deflaw; /* Start out assuming ulaw since it's smaller :) */ @@ -5613,9 +5619,9 @@ static struct ast_channel *zt_new(struct zt_pvt *i, int state, int startpbx, int if (!ast_strlen_zero(i->dnid)) tmp->cid.cid_dnid = ast_strdup(i->dnid); -#ifdef PRI_ANI /* Don't use ast_set_callerid() here because it will - * generate a NewCallerID event before the NewChannel event */ + * generate a needless NewCallerID event */ +#ifdef PRI_ANI tmp->cid.cid_num = ast_strdup(i->cid_num); tmp->cid.cid_name = ast_strdup(i->cid_name); if (!ast_strlen_zero(i->cid_ani)) @@ -5642,7 +5648,6 @@ static struct ast_channel *zt_new(struct zt_pvt *i, int state, int startpbx, int i->fake_event = 0; /* Assure there is no confmute on this channel */ zt_confmute(i, 0); - ast_setstate(tmp, state); /* Configure the new channel jb */ ast_jb_configure(tmp, &global_jbconf); if (startpbx) { diff --git a/include/asterisk/channel.h b/include/asterisk/channel.h index 26412b3fe..10491a041 100644 --- a/include/asterisk/channel.h +++ b/include/asterisk/channel.h @@ -579,7 +579,7 @@ int ast_setstate(struct ast_channel *chan, enum ast_channel_state); by default set to the "default" context and extension "s" */ -struct ast_channel *ast_channel_alloc(int needalertpipe); +struct ast_channel *ast_channel_alloc(int needalertpipe, int state, const char *cid_num, const char *cid_name, const char *name_fmt, ...); /*! \brief Queue an outgoing frame */ int ast_queue_frame(struct ast_channel *chan, struct ast_frame *f); @@ -1106,6 +1106,12 @@ void ast_deactivate_generator(struct ast_channel *chan); void ast_set_callerid(struct ast_channel *chan, const char *cidnum, const char *cidname, const char *ani); + +/*! return a mallocd string with the result of sprintf of the fmt and following args */ +char *ast_safe_string_alloc(const char *fmt, ...); + + + /*! Start a tone going */ int ast_tonepair_start(struct ast_channel *chan, int freq1, int freq2, int duration, int vol); /*! Stop a tone from playing */ diff --git a/include/asterisk/stringfields.h b/include/asterisk/stringfields.h index bf4c0a055..d35ef7d8e 100644 --- a/include/asterisk/stringfields.h +++ b/include/asterisk/stringfields.h @@ -167,6 +167,22 @@ void __ast_string_field_index_build(struct ast_string_field_mgr *mgr, ast_string_field *fields, int num_fields, int index, const char *format, ...); +/*! + \internal + \brief Set a field to a complex (built) value + \param mgr Pointer to the pool manager structure + \param fields Pointer to the first entry of the field array + \param num_fields Number of fields in the array + \param index Index position of the field within the structure + \param format printf-style format string + \param args va_list of the args for the format_string + \param args_again a copy of the first va_list for the sake of bsd not having a copy routine + \return nothing +*/ +void __ast_string_field_index_build_va(struct ast_string_field_mgr *mgr, + ast_string_field *fields, int num_fields, + int index, const char *format, va_list a1, va_list a2); + /*! \brief Declare a string field \param name The field name @@ -275,6 +291,18 @@ void __ast_string_field_index_build(struct ast_string_field_mgr *mgr, #define ast_string_field_index_build(x, index, fmt, args...) \ __ast_string_field_index_build(&(x)->__field_mgr, &(x)->__begin_field[0], ast_string_field_count(x), index, fmt, args) +/*! + \brief Set a field to a complex (built) value with prebuilt va_lists. + \param x Pointer to a structure containing fields + \param index Index position of the field within the structure + \param fmt printf-style format string + \param args1 Arguments for format string in va_list format + \param args2 a second copy of the va_list for the sake of bsd, with no va_list copy operation + \return nothing +*/ +#define ast_string_field_index_build_va(x, index, fmt, args1, args2) \ + __ast_string_field_index_build_va(&(x)->__field_mgr, &(x)->__begin_field[0], ast_string_field_count(x), index, fmt, args1, args2) + /*! \brief Set a field to a complex (built) value \param x Pointer to a structure containing fields @@ -286,6 +314,17 @@ void __ast_string_field_index_build(struct ast_string_field_mgr *mgr, #define ast_string_field_build(x, field, fmt, args...) \ ast_string_field_index_build(x, ast_string_field_index(x, field), fmt, args) +/*! + \brief Set a field to a complex (built) value + \param x Pointer to a structure containing fields + \param field Name of the field to set + \param fmt printf-style format string + \param argslist a va_list of the args + \return nothing +*/ +#define ast_string_field_build_va(x, field, fmt, args1, args2) \ + ast_string_field_index_build_va(x, ast_string_field_index(x, field), fmt, args1, args2) + /*! \brief Free a field's value. \param x Pointer to a structure containing fields diff --git a/main/channel.c b/main/channel.c index 17d368372..ed369b9ec 100644 --- a/main/channel.c +++ b/main/channel.c @@ -29,6 +29,7 @@ ASTERISK_FILE_VERSION(__FILE__, "$Revision$") #include #include +#include #include #include #include @@ -330,6 +331,21 @@ static int ast_check_hangup_locked(struct ast_channel *chan) return res; } +/*! \brief printf the string into a correctly sized mallocd buffer, and return the buffer */ +char *ast_safe_string_alloc(const char *fmt, ...) +{ + char *b2,buf[1]; + int len; + + va_list args; + va_start(args, fmt); + len = vsnprintf(buf, 1, fmt, args); + b2 = ast_malloc(len+1); + vsnprintf(b2, len+1, fmt, args); + va_end(args); + return b2; +} + /*! \brief Initiate system shutdown */ void ast_begin_shutdown(int hangup) { @@ -608,12 +624,13 @@ static const struct ast_channel_tech null_tech = { }; /*! \brief Create a new channel structure */ -struct ast_channel *ast_channel_alloc(int needqueue) +struct ast_channel *ast_channel_alloc(int needqueue, int state, const char *cid_num, const char *cid_name, const char *name_fmt, ...) { struct ast_channel *tmp; int x; int flags; struct varshead *headp; + va_list ap1, ap2; /* If shutting down, don't allocate any new channels */ if (shutting_down) { @@ -671,10 +688,10 @@ struct ast_channel *ast_channel_alloc(int needqueue) /* And timing pipe */ tmp->fds[AST_TIMING_FD] = tmp->timingfd; ast_string_field_set(tmp, name, "**Unknown**"); - + /* Initial state */ - tmp->_state = AST_STATE_DOWN; - + tmp->_state = state; + tmp->streamid = -1; tmp->fin = global_fin; @@ -688,6 +705,37 @@ struct ast_channel *ast_channel_alloc(int needqueue) (long) time(NULL), ast_atomic_fetchadd_int(&uniqueint, 1)); } + if (!ast_strlen_zero(name_fmt)) { + /* Almost every channel is calling this function, and setting the name via the ast_string_field_build() call. + * And they all use slightly different formats for their name string. + * This means, to set the name here, we have to accept variable args, and call the string_field_build from here. + * This means, that the stringfields must have a routine that takes the va_lists directly, and + * uses them to build the string, instead of forming the va_lists internally from the vararg ... list. + * This new function was written so this can be accomplished. + */ + va_start(ap1, name_fmt); + va_start(ap2, name_fmt); + ast_string_field_build_va(tmp, name, name_fmt, ap1, ap2); + va_end(ap1); + va_end(ap2); + + /* and now, since the channel structure is built, and has its name, let's call the + * manager event generator with this Newchannel event. This is the proper and correct + * place to make this call, but you sure do have to pass a lot of data into this func + * to do it here! + */ + manager_event(EVENT_FLAG_CALL, "Newchannel", + "Channel: %s\r\n" + "State: %s\r\n" + "CallerIDNum: %s\r\n" + "CallerIDName: %s\r\n" + "Uniqueid: %s\r\n", + tmp->name, ast_state2str(state), + S_OR(cid_num, ""), + S_OR(cid_name, ""), + tmp->uniqueid); + } + headp = &tmp->varshead; AST_LIST_HEAD_INIT_NOLOCK(headp); @@ -2858,19 +2906,8 @@ struct ast_channel *ast_request(const char *type, int format, void *data, int *c if (!(c = chan->tech->requester(type, capabilities | videoformat, data, cause))) return NULL; - - if (c->_state == AST_STATE_DOWN) { - manager_event(EVENT_FLAG_CALL, "Newchannel", - "Channel: %s\r\n" - "State: %s\r\n" - "CallerIDNum: %s\r\n" - "CallerIDName: %s\r\n" - "Uniqueid: %s\r\n", - c->name, ast_state2str(c->_state), - S_OR(c->cid.cid_num, ""), - S_OR(c->cid.cid_name, ""), - c->uniqueid); - } + + /* no need to generate a Newchannel event here; it is done in the channel_alloc call */ return c; } @@ -3518,8 +3555,9 @@ int ast_setstate(struct ast_channel *chan, enum ast_channel_state state) chan->_state = state; ast_device_state_changed_literal(chan->name); + /* setstate used to conditionally report Newchannel; this is no more */ manager_event(EVENT_FLAG_CALL, - (oldstate == AST_STATE_DOWN) ? "Newchannel" : "Newstate", + "Newstate", "Channel: %s\r\n" "State: %s\r\n" "CallerIDNum: %s\r\n" diff --git a/main/pbx.c b/main/pbx.c index 991d93f1b..ee905976f 100644 --- a/main/pbx.c +++ b/main/pbx.c @@ -4501,12 +4501,10 @@ int ast_async_goto(struct ast_channel *chan, const char *context, const char *ex /* In order to do it when the channel doesn't really exist within the PBX, we have to make a new channel, masquerade, and start the PBX at the new location */ - struct ast_channel *tmpchan = ast_channel_alloc(0); + struct ast_channel *tmpchan = ast_channel_alloc(0, chan->_state, 0, 0, "AsyncGoto/%s", chan->name); if (!tmpchan) res = -1; else { - ast_string_field_build(tmpchan, name, "AsyncGoto/%s", chan->name); - ast_setstate(tmpchan, chan->_state); /* Make formats okay */ tmpchan->readformat = chan->readformat; tmpchan->writeformat = chan->writeformat; @@ -4863,7 +4861,7 @@ static void *async_wait(void *data) static int ast_pbx_outgoing_cdr_failed(void) { /* allocate a channel */ - struct ast_channel *chan = ast_channel_alloc(0); + struct ast_channel *chan = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, 0); if (!chan) return -1; /* failure */ @@ -4976,9 +4974,8 @@ int ast_pbx_outgoing_exten(const char *type, int format, void *data, int timeout /* create a fake channel and execute the "failed" extension (if it exists) within the requested context */ /* check if "failed" exists */ if (ast_exists_extension(chan, context, "failed", 1, NULL)) { - chan = ast_channel_alloc(0); + chan = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "OutgoingSpoolFailed"); if (chan) { - ast_string_field_set(chan, name, "OutgoingSpoolFailed"); if (!ast_strlen_zero(context)) ast_copy_string(chan->context, context, sizeof(chan->context)); set_ext_pri(chan, "failed", 1); diff --git a/main/utils.c b/main/utils.c index f930f74c6..aa621704a 100644 --- a/main/utils.c +++ b/main/utils.c @@ -892,15 +892,11 @@ ast_string_field __ast_string_field_alloc_space(struct ast_string_field_mgr *mgr return result; } -void __ast_string_field_index_build(struct ast_string_field_mgr *mgr, +void __ast_string_field_index_build_va(struct ast_string_field_mgr *mgr, ast_string_field *fields, int num_fields, - int index, const char *format, ...) + int index, const char *format, va_list ap1, va_list ap2) { size_t needed; - va_list ap1, ap2; - - va_start(ap1, format); - va_start(ap2, format); /* va_copy does not exist on FreeBSD */ needed = vsnprintf(mgr->pool->base + mgr->used, mgr->space, format, ap1) + 1; @@ -921,7 +917,20 @@ void __ast_string_field_index_build(struct ast_string_field_mgr *mgr, fields[index] = mgr->pool->base + mgr->used; mgr->used += needed; mgr->space -= needed; +} + +void __ast_string_field_index_build(struct ast_string_field_mgr *mgr, + ast_string_field *fields, int num_fields, + int index, const char *format, ...) +{ + va_list ap1, ap2; + va_start(ap1, format); + va_start(ap2, format); /* va_copy does not exist on FreeBSD */ + + __ast_string_field_index_build_va(mgr, fields, num_fields, index, format, ap1, ap2); + + va_end(ap1); va_end(ap2); } diff --git a/res/res_features.c b/res/res_features.c index f8a1168e1..5494d5a09 100644 --- a/res/res_features.c +++ b/res/res_features.c @@ -190,14 +190,13 @@ static void check_goto_on_transfer(struct ast_channel *chan) goto_on_transfer = ast_strdupa(val); - if (!(xferchan = ast_channel_alloc(0))) + if (!(xferchan = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, chan->name))) return; for (x = goto_on_transfer; x && *x; x++) { if (*x == '^') *x = '|'; } - ast_string_field_set(xferchan, name, chan->name); /* Make formats okay */ xferchan->readformat = chan->readformat; xferchan->writeformat = chan->writeformat; @@ -442,12 +441,10 @@ int ast_masq_park_call(struct ast_channel *rchan, struct ast_channel *peer, int struct ast_frame *f; /* Make a new, fake channel that we'll use to masquerade in the real one */ - if (!(chan = ast_channel_alloc(0))) { + if (!(chan = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "Parked/%s",rchan->name))) { ast_log(LOG_WARNING, "Unable to create parked channel\n"); return -1; } - /* Let us keep track of the channel name */ - ast_string_field_build(chan, name, "Parked/%s",rchan->name); /* Make formats okay */ chan->readformat = rchan->readformat; @@ -828,12 +825,11 @@ static int builtin_atxfer(struct ast_channel *chan, struct ast_channel *peer, st return -1; } - xferchan = ast_channel_alloc(0); + xferchan = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, "Transfered/%s", transferee->name); if (!xferchan) { ast_hangup(newchan); return -1; } - ast_string_field_build(xferchan, name, "Transfered/%s", transferee->name); /* Make formats okay */ xferchan->readformat = transferee->readformat; xferchan->writeformat = transferee->writeformat; -- cgit v1.2.3