summaryrefslogtreecommitdiff
path: root/res/res_pjsip_session.c
diff options
context:
space:
mode:
authorRichard Mudgett <rmudgett@digium.com>2017-04-21 12:07:39 -0500
committerRichard Mudgett <rmudgett@digium.com>2017-04-21 14:14:08 -0500
commit835c20944512db77f5366c4d9e3002b0dfdbd805 (patch)
tree376f6844ee1504ab910e22b910dd15121ae6eb96 /res/res_pjsip_session.c
parentd373ebc428f23cb37dcbcafac37295f4be1e1a9e (diff)
res_pjsip_session.c: Restructure ast_sip_session_alloc()
* Restructure ast_sip_session_alloc() to need less cleanup on off nominal error paths. * Made ast_sip_session_alloc() and ast_sip_session_create_outgoing() avoid unnecessary ref manipulation to return a session. This is faster than calling a function. That function may do logging of the ref changes with REF_DEBUG enabled. Change-Id: I2a0affc4be51013d3f0485782c96b8fee3ddb00a
Diffstat (limited to 'res/res_pjsip_session.c')
-rw-r--r--res/res_pjsip_session.c82
1 files changed, 45 insertions, 37 deletions
diff --git a/res/res_pjsip_session.c b/res/res_pjsip_session.c
index 560b3903d..a8777415a 100644
--- a/res/res_pjsip_session.c
+++ b/res/res_pjsip_session.c
@@ -1328,9 +1328,7 @@ static void session_destructor(void *obj)
ao2_cleanup(session->req_caps);
ao2_cleanup(session->direct_media_cap);
- if (session->dsp) {
- ast_dsp_free(session->dsp);
- }
+ ast_dsp_free(session->dsp);
if (session->inv_session) {
pjsip_dlg_dec_session(session->inv_session->dlg, &session_module);
@@ -1400,6 +1398,7 @@ struct ast_sip_session *ast_sip_session_alloc(struct ast_sip_endpoint *endpoint,
struct ast_sip_contact *contact, pjsip_inv_session *inv_session, pjsip_rx_data *rdata)
{
RAII_VAR(struct ast_sip_session *, session, NULL, ao2_cleanup);
+ struct ast_sip_session *ret_session;
struct ast_sip_session_supplement *iter;
int dsp_features = 0;
@@ -1407,12 +1406,39 @@ struct ast_sip_session *ast_sip_session_alloc(struct ast_sip_endpoint *endpoint,
if (!session) {
return NULL;
}
+
AST_LIST_HEAD_INIT(&session->supplements);
+ AST_LIST_HEAD_INIT_NOLOCK(&session->delayed_requests);
+ ast_party_id_init(&session->id);
+
+ session->direct_media_cap = ast_format_cap_alloc(AST_FORMAT_CAP_FLAG_DEFAULT);
+ if (!session->direct_media_cap) {
+ return NULL;
+ }
+ session->req_caps = ast_format_cap_alloc(AST_FORMAT_CAP_FLAG_DEFAULT);
+ if (!session->req_caps) {
+ return NULL;
+ }
session->datastores = ao2_container_alloc(DATASTORE_BUCKETS, datastore_hash, datastore_cmp);
if (!session->datastores) {
return NULL;
}
+ if (endpoint->dtmf == AST_SIP_DTMF_INBAND || endpoint->dtmf == AST_SIP_DTMF_AUTO) {
+ dsp_features |= DSP_FEATURE_DIGIT_DETECT;
+ }
+ if (endpoint->faxdetect) {
+ dsp_features |= DSP_FEATURE_FAX_DETECT;
+ }
+ if (dsp_features) {
+ session->dsp = ast_dsp_new();
+ if (!session->dsp) {
+ return NULL;
+ }
+
+ ast_dsp_set_features(session->dsp, dsp_features);
+ }
+
session->endpoint = ao2_bump(endpoint);
session->media = ao2_container_alloc(MEDIA_BUCKETS, session_media_hash, session_media_cmp);
@@ -1449,30 +1475,6 @@ struct ast_sip_session *ast_sip_session_alloc(struct ast_sip_endpoint *endpoint,
inv_session->mod_data[session_module.id] = ao2_bump(session);
session->contact = ao2_bump(contact);
session->inv_session = inv_session;
- session->req_caps = ast_format_cap_alloc(AST_FORMAT_CAP_FLAG_DEFAULT);
- if (!session->req_caps) {
- /* Release the ref held by session->inv_session */
- ao2_ref(session, -1);
- return NULL;
- }
-
- if ((endpoint->dtmf == AST_SIP_DTMF_INBAND) || (endpoint->dtmf == AST_SIP_DTMF_AUTO)) {
- dsp_features |= DSP_FEATURE_DIGIT_DETECT;
- }
-
- if (endpoint->faxdetect) {
- dsp_features |= DSP_FEATURE_FAX_DETECT;
- }
-
- if (dsp_features) {
- if (!(session->dsp = ast_dsp_new())) {
- /* Release the ref held by session->inv_session */
- ao2_ref(session, -1);
- return NULL;
- }
-
- ast_dsp_set_features(session->dsp, dsp_features);
- }
if (add_supplements(session)) {
/* Release the ref held by session->inv_session */
@@ -1484,11 +1486,11 @@ struct ast_sip_session *ast_sip_session_alloc(struct ast_sip_endpoint *endpoint,
iter->session_begin(session);
}
}
- session->direct_media_cap = ast_format_cap_alloc(AST_FORMAT_CAP_FLAG_DEFAULT);
- AST_LIST_HEAD_INIT_NOLOCK(&session->delayed_requests);
- ast_party_id_init(&session->id);
- ao2_ref(session, +1);
- return session;
+
+ /* Avoid unnecessary ref manipulation to return a session */
+ ret_session = session;
+ session = NULL;
+ return ret_session;
}
/*! \brief struct controlling the suspension of the session's serializer. */
@@ -1704,6 +1706,7 @@ struct ast_sip_session *ast_sip_session_create_outgoing(struct ast_sip_endpoint
pjsip_dialog *dlg;
struct pjsip_inv_session *inv_session;
RAII_VAR(struct ast_sip_session *, session, NULL, ao2_cleanup);
+ struct ast_sip_session *ret_session;
/* If no location has been provided use the AOR list from the endpoint itself */
if (location || !contact) {
@@ -1760,14 +1763,17 @@ struct ast_sip_session *ast_sip_session_create_outgoing(struct ast_sip_endpoint
if (ast_format_cap_count(req_caps)) {
/* get joint caps between req_caps and endpoint caps */
struct ast_format_cap *joint_caps = ast_format_cap_alloc(AST_FORMAT_CAP_FLAG_DEFAULT);
- ast_format_cap_get_compatible(req_caps, session->endpoint->media.codecs, joint_caps);
+
+ ast_format_cap_get_compatible(req_caps, endpoint->media.codecs, joint_caps);
/* if joint caps */
if (ast_format_cap_count(joint_caps)) {
/* copy endpoint caps into session->req_caps */
- ast_format_cap_append_from_cap(session->req_caps, session->endpoint->media.codecs, AST_MEDIA_TYPE_UNKNOWN);
+ ast_format_cap_append_from_cap(session->req_caps,
+ endpoint->media.codecs, AST_MEDIA_TYPE_UNKNOWN);
/* replace instances of joint caps equivalents in session->req_caps */
- ast_format_cap_replace_from_cap(session->req_caps, joint_caps, AST_MEDIA_TYPE_UNKNOWN);
+ ast_format_cap_replace_from_cap(session->req_caps, joint_caps,
+ AST_MEDIA_TYPE_UNKNOWN);
}
ao2_cleanup(joint_caps);
}
@@ -1781,8 +1787,10 @@ struct ast_sip_session *ast_sip_session_create_outgoing(struct ast_sip_endpoint
return NULL;
}
- ao2_ref(session, +1);
- return session;
+ /* Avoid unnecessary ref manipulation to return a session */
+ ret_session = session;
+ session = NULL;
+ return ret_session;
}
void ast_sip_session_terminate(struct ast_sip_session *session, int response)