Asterisk - The Open Source Telephony Project  18.5.0
Functions
pjsip_session_caps.c File Reference
#include "asterisk.h"
#include "asterisk/astobj2.h"
#include "asterisk/channel.h"
#include "asterisk/format.h"
#include "asterisk/format_cap.h"
#include "asterisk/logger.h"
#include "asterisk/sorcery.h"
#include "asterisk/stream.h"
#include "asterisk/res_pjsip.h"
#include "asterisk/res_pjsip_session.h"
#include "asterisk/res_pjsip_session_caps.h"
Include dependency graph for pjsip_session_caps.c:

Go to the source code of this file.

Functions

struct ast_format_capast_sip_create_joint_call_cap (const struct ast_format_cap *remote, struct ast_format_cap *local, enum ast_media_type media_type, struct ast_flags codec_pref)
 Create joint capabilities. More...
 
struct ast_format_capast_sip_session_create_joint_call_cap (const struct ast_sip_session *session, enum ast_media_type media_type, const struct ast_format_cap *remote)
 Create joint capabilities. More...
 
struct ast_streamast_sip_session_create_joint_call_stream (const struct ast_sip_session *session, struct ast_stream *remote_stream)
 Create a new stream of joint capabilities. More...
 
static void log_caps (int level, const char *file, int line, const char *function, const struct ast_sip_session *session, enum ast_media_type media_type, const struct ast_format_cap *local, const struct ast_format_cap *remote, const struct ast_format_cap *joint)
 

Function Documentation

◆ ast_sip_create_joint_call_cap()

struct ast_format_cap* ast_sip_create_joint_call_cap ( const struct ast_format_cap remote,
struct ast_format_cap local,
enum ast_media_type  media_type,
struct ast_flags  codec_pref 
)

Create joint capabilities.

Since
18.0.0

Creates a list of joint capabilities between the given remote capabilities, and local ones. "local" and "remote" reference the values in ast_sip_call_codec_pref.

Parameters
remoteThe "remote" capabilities
localThe "local" capabilities
media_typeThe media type
codec_prefsOne or more of enum ast_sip_call_codec_pref
Return values
Apointer to the joint capabilities (which may be empty). NULL will be returned only if no memory was available to allocate the structure.
Note
Returned object's reference must be released at some point,

Definition at line 65 of file pjsip_session_caps.c.

References ao2_cleanup, ao2_ref, ast_codec_media_type2str(), ast_format_cap_alloc, ast_format_cap_append, ast_format_cap_append_from_cap(), ast_format_cap_empty(), AST_FORMAT_CAP_FLAG_DEFAULT, ast_format_cap_get_compatible(), ast_format_cap_get_format(), ast_format_cap_remove_by_type(), ast_log, AST_MEDIA_TYPE_UNKNOWN, LOG_ERROR, and NULL.

Referenced by ast_sip_session_create_joint_call_cap(), ast_sip_session_create_joint_call_stream(), and test_create_joint().

68 {
72 
73  if (!joint || !local_filtered || !remote_filtered) {
74  ast_log(LOG_ERROR, "Failed to allocate %s call offer capabilities\n",
76  ao2_cleanup(joint);
77  ao2_cleanup(local_filtered);
78  ao2_cleanup(remote_filtered);
79  return NULL;
80  }
81 
82  ast_format_cap_append_from_cap(local_filtered, local, media_type);
83 
84  /* Remote should always be a subset of local, as local is what defines the underlying
85  * permitted formats.
86  */
87  ast_format_cap_get_compatible(remote, local_filtered, remote_filtered);
88 
89  if (ast_sip_call_codec_pref_test(codec_pref, LOCAL)) {
90  if (ast_sip_call_codec_pref_test(codec_pref, INTERSECT)) {
91  ast_format_cap_get_compatible(local_filtered, remote_filtered, joint); /* Get common, prefer local */
92  } else {
93  ast_format_cap_append_from_cap(joint, local_filtered, media_type); /* Add local */
94  ast_format_cap_append_from_cap(joint, remote_filtered, media_type); /* Then remote */
95  }
96  } else {
97  if (ast_sip_call_codec_pref_test(codec_pref, INTERSECT)) {
98  joint = remote_filtered; /* Get common, prefer remote - as was done when filtering initially */
99  remote_filtered = NULL;
100  } else {
101  ast_format_cap_append_from_cap(joint, remote_filtered, media_type); /* Add remote */
102  ast_format_cap_append_from_cap(joint, local_filtered, media_type); /* Then local */
103  }
104  }
105 
106  ao2_ref(local_filtered, -1);
107  ao2_cleanup(remote_filtered);
108 
109  if (ast_format_cap_empty(joint)) {
110  return joint;
111  }
112 
113  if (ast_sip_call_codec_pref_test(codec_pref, FIRST)) {
114  /*
115  * Save the most preferred one. Session capabilities are per stream and
116  * a stream only carries a single media type, so no reason to worry with
117  * the type here (i.e different or multiple types)
118  */
119  struct ast_format *single = ast_format_cap_get_format(joint, 0);
120  /* Remove all formats */
122  /* Put the most preferred one back */
123  ast_format_cap_append(joint, single, 0);
124  ao2_ref(single, -1);
125  }
126 
127  return joint;
128 }
media_type
Media types generate different "dummy answers" for not accepting the offer of a media stream...
Definition: sip.h:489
const char * ast_codec_media_type2str(enum ast_media_type type)
Conversion function to take a media type and turn it into a string.
Definition: codec.c:347
Definition of a media format.
Definition: format.c:43
#define NULL
Definition: resample.c:96
#define ast_log
Definition: astobj2.c:42
#define ao2_ref(o, delta)
Definition: astobj2.h:464
#define ast_format_cap_append(cap, format, framing)
Definition: format_cap.h:103
#define ast_format_cap_alloc(flags)
Definition: format_cap.h:52
void ast_format_cap_remove_by_type(struct ast_format_cap *cap, enum ast_media_type type)
Remove all formats matching a specific format type.
Definition: format_cap.c:525
#define LOG_ERROR
Definition: logger.h:285
Format capabilities structure, holds formats + preference order + etc.
Definition: format_cap.c:54
#define ao2_cleanup(obj)
Definition: astobj2.h:1958
int ast_format_cap_empty(const struct ast_format_cap *cap)
Determine if a format cap has no formats in it.
Definition: format_cap.c:746
int ast_format_cap_append_from_cap(struct ast_format_cap *dst, const struct ast_format_cap *src, enum ast_media_type type)
Append the formats of provided type in src to dst.
Definition: format_cap.c:269
struct ast_format * ast_format_cap_get_format(const struct ast_format_cap *cap, int position)
Get the format at a specific index.
Definition: format_cap.c:400
int ast_format_cap_get_compatible(const struct ast_format_cap *cap1, const struct ast_format_cap *cap2, struct ast_format_cap *result)
Find the compatible formats between two capabilities structures.
Definition: format_cap.c:630

◆ ast_sip_session_create_joint_call_cap()

struct ast_format_cap* ast_sip_session_create_joint_call_cap ( const struct ast_sip_session session,
enum ast_media_type  media_type,
const struct ast_format_cap remote 
)

Create joint capabilities.

Since
18.0.0

Creates a list of joint capabilities between the given session's local capabilities, and the remote capabilities. Codec selection is based on the session->endpoint's codecs, the session->endpoint's codec call preferences, and the "remote" capabilities passed by the core (for outgoing calls) or created by the incoming SDP (for incoming calls).

Parameters
sessionThe session
media_typeThe media type
remoteCapabilities received in an SDP offer or from the core
Return values
Apointer to the joint capabilities (which may be empty). NULL will be returned only if no memory was available to allocate the structure.
Note
Returned object's reference must be released at some point,

Definition at line 151 of file pjsip_session_caps.c.

References ast_sip_create_joint_call_cap(), AST_SIP_SESSION_OUTGOING_CALL, ast_sip_session::call_direction, ast_sip_endpoint_media_configuration::codecs, ast_sip_session::endpoint, ast_sip_endpoint_media_configuration::incoming_call_offer_pref, log_caps(), LOG_DEBUG, ast_sip_endpoint::media, and ast_sip_endpoint_media_configuration::outgoing_call_offer_pref.

Referenced by set_incoming_call_offer_cap().

154 {
155  struct ast_format_cap *joint = ast_sip_create_joint_call_cap(remote,
156  session->endpoint->media.codecs, media_type,
160 
161  log_caps(LOG_DEBUG, session, media_type, session->endpoint->media.codecs, remote, joint);
162 
163  return joint;
164 }
static void log_caps(int level, const char *file, int line, const char *function, const struct ast_sip_session *session, enum ast_media_type media_type, const struct ast_format_cap *local, const struct ast_format_cap *remote, const struct ast_format_cap *joint)
struct ast_sip_endpoint * endpoint
struct ast_flags outgoing_call_offer_pref
Definition: res_pjsip.h:798
media_type
Media types generate different "dummy answers" for not accepting the offer of a media stream...
Definition: sip.h:489
struct ast_format_cap * codecs
Definition: res_pjsip.h:770
#define LOG_DEBUG
Definition: logger.h:241
struct ast_sip_endpoint_media_configuration media
Definition: res_pjsip.h:841
Format capabilities structure, holds formats + preference order + etc.
Definition: format_cap.c:54
struct ast_format_cap * ast_sip_create_joint_call_cap(const struct ast_format_cap *remote, struct ast_format_cap *local, enum ast_media_type media_type, struct ast_flags codec_pref)
Create joint capabilities.
enum ast_sip_session_call_direction call_direction
struct ast_flags incoming_call_offer_pref
Definition: res_pjsip.h:796

◆ ast_sip_session_create_joint_call_stream()

struct ast_stream* ast_sip_session_create_joint_call_stream ( const struct ast_sip_session session,
struct ast_stream remote 
)

Create a new stream of joint capabilities.

Since
18.0.0

Creates a new stream with capabilities between the given session's local capabilities, and the remote stream's. Codec selection is based on the session->endpoint's codecs, the session->endpoint's codec call preferences, and the stream passed by the core (for outgoing calls) or created by the incoming SDP (for incoming calls).

Parameters
sessionThe session
remoteThe remote stream
Return values
Apointer to a new stream with the joint capabilities (which may be empty), NULL will be returned only if no memory was available to allocate the structure.

Definition at line 130 of file pjsip_session_caps.c.

References ao2_cleanup, ast_sip_create_joint_call_cap(), AST_SIP_SESSION_OUTGOING_CALL, ast_stream_clone(), ast_stream_get_formats(), ast_stream_get_type(), ast_stream_set_formats(), ast_sip_session::call_direction, ast_sip_endpoint_media_configuration::codecs, ast_sip_session::endpoint, ast_sip_endpoint_media_configuration::incoming_call_offer_pref, log_caps(), LOG_DEBUG, ast_sip_endpoint::media, NULL, and ast_sip_endpoint_media_configuration::outgoing_call_offer_pref.

Referenced by ast_sip_session_create_outgoing().

132 {
133  struct ast_stream *joint_stream = ast_stream_clone(remote_stream, NULL);
134  const struct ast_format_cap *remote = ast_stream_get_formats(remote_stream);
135  enum ast_media_type media_type = ast_stream_get_type(remote_stream);
136 
137  struct ast_format_cap *joint = ast_sip_create_joint_call_cap(remote,
138  session->endpoint->media.codecs, media_type,
142 
143  ast_stream_set_formats(joint_stream, joint);
144  ao2_cleanup(joint);
145 
146  log_caps(LOG_DEBUG, session, media_type, session->endpoint->media.codecs, remote, joint);
147 
148  return joint_stream;
149 }
static void log_caps(int level, const char *file, int line, const char *function, const struct ast_sip_session *session, enum ast_media_type media_type, const struct ast_format_cap *local, const struct ast_format_cap *remote, const struct ast_format_cap *joint)
struct ast_sip_endpoint * endpoint
struct ast_flags outgoing_call_offer_pref
Definition: res_pjsip.h:798
media_type
Media types generate different "dummy answers" for not accepting the offer of a media stream...
Definition: sip.h:489
enum ast_media_type ast_stream_get_type(const struct ast_stream *stream)
Get the media type of a stream.
Definition: stream.c:316
struct ast_format_cap * codecs
Definition: res_pjsip.h:770
#define NULL
Definition: resample.c:96
#define LOG_DEBUG
Definition: logger.h:241
void ast_stream_set_formats(struct ast_stream *stream, struct ast_format_cap *caps)
Set the current negotiated formats of a stream.
Definition: stream.c:365
struct ast_sip_endpoint_media_configuration media
Definition: res_pjsip.h:841
const struct ast_format_cap * ast_stream_get_formats(const struct ast_stream *stream)
Get the current negotiated formats of a stream.
Definition: stream.c:330
Format capabilities structure, holds formats + preference order + etc.
Definition: format_cap.c:54
struct ast_format_cap * ast_sip_create_joint_call_cap(const struct ast_format_cap *remote, struct ast_format_cap *local, enum ast_media_type media_type, struct ast_flags codec_pref)
Create joint capabilities.
#define ao2_cleanup(obj)
Definition: astobj2.h:1958
struct ast_stream * ast_stream_clone(const struct ast_stream *stream, const char *name)
Create a deep clone of an existing stream.
Definition: stream.c:257
enum ast_sip_session_call_direction call_direction
ast_media_type
Types of media.
Definition: codec.h:30
struct ast_flags incoming_call_offer_pref
Definition: res_pjsip.h:796

◆ log_caps()

static void log_caps ( int  level,
const char *  file,
int  line,
const char *  function,
const struct ast_sip_session session,
enum ast_media_type  media_type,
const struct ast_format_cap local,
const struct ast_format_cap remote,
const struct ast_format_cap joint 
)
static

Definition at line 32 of file pjsip_session_caps.c.

References __LOG_DEBUG, ast_channel_name(), ast_codec_media_type2str(), ast_format_cap_get_names(), AST_FORMAT_CAP_NAMES_LEN, ast_log, ast_sip_call_codec_pref_to_str(), AST_SIP_SESSION_OUTGOING_CALL, ast_sorcery_object_get_id(), ast_str_alloca, ast_sip_session::call_direction, ast_sip_session::channel, DEBUG_ATLEAST, ast_sip_session::endpoint, ast_sip_endpoint_media_configuration::incoming_call_offer_pref, ast_sip_endpoint::media, NULL, and ast_sip_endpoint_media_configuration::outgoing_call_offer_pref.

Referenced by ast_sip_session_create_joint_call_cap(), and ast_sip_session_create_joint_call_stream().

36 {
37  struct ast_str *s1;
38  struct ast_str *s2;
39  struct ast_str *s3;
41  struct ast_flags pref =
42  outgoing
45 
46  if (level == __LOG_DEBUG && !DEBUG_ATLEAST(3)) {
47  return;
48  }
49 
53 
54  ast_log(level, file, line, function, "'%s' Caps for %s %s call with pref '%s' - remote: %s local: %s joint: %s\n",
55  session->channel ? ast_channel_name(session->channel) :
57  outgoing? "outgoing" : "incoming",
60  s2 ? ast_format_cap_get_names(remote, &s2) : "(NONE)",
61  s1 ? ast_format_cap_get_names(local, &s1) : "(NONE)",
62  s3 ? ast_format_cap_get_names(joint, &s3) : "(NONE)");
63 }
struct ast_sip_endpoint * endpoint
struct ast_flags outgoing_call_offer_pref
Definition: res_pjsip.h:798
#define __LOG_DEBUG
Definition: logger.h:240
media_type
Media types generate different "dummy answers" for not accepting the offer of a media stream...
Definition: sip.h:489
#define AST_FORMAT_CAP_NAMES_LEN
Definition: format_cap.h:326
const char * ast_codec_media_type2str(enum ast_media_type type)
Conversion function to take a media type and turn it into a string.
Definition: codec.c:347
#define ast_str_alloca(init_len)
Definition: strings.h:800
#define NULL
Definition: resample.c:96
struct ast_sip_endpoint_media_configuration media
Definition: res_pjsip.h:841
#define ast_log
Definition: astobj2.c:42
const char * ast_sip_call_codec_pref_to_str(struct ast_flags pref)
Convert the call codec preference flags to a string.
Definition: res_pjsip.c:5534
const char * ast_sorcery_object_get_id(const void *object)
Get the unique identifier of a sorcery object.
Definition: sorcery.c:2312
struct ast_channel * channel
The descriptor of a dynamic string XXX storage will be optimized later if needed We use the ts field ...
Definition: strings.h:584
const char * ast_format_cap_get_names(const struct ast_format_cap *cap, struct ast_str **buf)
Get the names of codecs of a set of formats.
Definition: format_cap.c:736
Structure used to handle boolean flags.
Definition: utils.h:199
const char * ast_channel_name(const struct ast_channel *chan)
enum ast_sip_session_call_direction call_direction
struct ast_flags incoming_call_offer_pref
Definition: res_pjsip.h:796
#define DEBUG_ATLEAST(level)
Definition: logger.h:441