Skip to content

Commit cb30c5c

Browse files
authored
Add support to send a command to an RTPEngine specified by the sock_var (#3617)
* Add support to send a command to an RTPEngine specified by the sock_var * Removed some logging problems that the linter complained about. * Updates to support memory corruption edge case * Fixed casting typo * Update some comments * Implement developer suggestions 1. If the set variable is passed in, use it. Otherwise use the existing logic. 2. Move setting of the socket STR outside of the loop. * Update README * Update rtpengine_admin.xml documentation
1 parent 953a2f6 commit cb30c5c

3 files changed

Lines changed: 55 additions & 9 deletions

File tree

modules/rtpengine/README

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -442,6 +442,15 @@ modparam("rtpengine", "ping_enabled", yes)
442442

443443
1.5. Exported Functions
444444

445+
Many rtpengine_* functions accept a "sock_var" parameter that
446+
will be populated with the socket of the RTPEngine chosen for
447+
the particular operation. The format of the data stored in
448+
"sock_var" is: "proto:ip:port". If the "sock_var" has
449+
been specified and it is non-NULL then it will be used to
450+
determine the specific RTPEngine to use. Note that the socket
451+
specified by "sock_var" must be a member of the current RTPEngine
452+
Set context.
453+
445454
1.5.1. rtpengine_use_set(setid)
446455

447456
Sets the ID of the RTP proxy set to be used for the next

modules/rtpengine/doc/rtpengine_admin.xml

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,16 @@
7878
You can use the <xref linkend="param_extra_failover_error"/> parameter
7979
to extend the above list.
8080
</para>
81+
<para>
82+
Many rtpengine_* functions accept a "sock_var" parameter that
83+
will be populated with the socket of the RTPEngine chosen for
84+
the particular operation. The format of the data stored in
85+
"sock_var" is: "proto:ip:port". If the "sock_var" has
86+
been specified and it is non-NULL then it will be used to
87+
determine the specific RTPEngine to use. Note that the socket
88+
specified by "sock_var" must be a member of the current RTPEngine
89+
Set context.
90+
</para>
8191
</section>
8292

8393
<section id="dependencies" xreflabel="Dependencies">

modules/rtpengine/rtpengine.c

Lines changed: 36 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -344,6 +344,7 @@ static int add_rtpengine_socks(struct rtpe_set * rtpe_list, char * rtpengine);
344344
static int fixup_set_id(void ** param);
345345
static int fixup_free_set_id(void ** param);
346346
static int set_rtpengine_set_f(struct sip_msg * msg, rtpe_set_link_t *set_param);
347+
static int set_rtpengine_set_from_avp(struct sip_msg *msg);
347348
static struct rtpe_set * select_rtpe_set(int id_set);
348349
static struct rtpe_node *select_rtpe_node(str, struct rtpe_set *, struct rtpe_ignore_node *);
349350
static struct rtpe_node *lookup_rtpe_node(struct rtpe_set * rtpe_list, str *rtpe_url);
@@ -1865,7 +1866,6 @@ static int connect_rtpengines(int force_test)
18651866
return 0;
18661867
LM_DBG("[Re]connecting sockets (%d > %d)\n", *rtpe_no, rtpe_number);
18671868

1868-
18691869
if (*rtpe_no > rtpe_number) {
18701870
rtpe_socks = (int*)pkg_realloc(rtpe_socks, *rtpe_no * sizeof(int));
18711871
if (rtpe_socks==NULL) {
@@ -2827,30 +2827,56 @@ static bencode_item_t *rtpe_function_call(bencode_buffer_t *bencbuf, struct sip_
28272827
pv_value_t val;
28282828
struct rtpe_ignore_node *ignore_list = NULL;
28292829
int ret;
2830-
28312830
memset(&ng_flags, 0, sizeof(ng_flags));
28322831
error.len = 0;
28332832
error.s = "";
2833+
pv_value_t socket_val;
28342834

28352835
/*** get & init basic stuff needed ***/
28362836
if (rtpe_function_call_prepare(bencbuf, msg, op, &ng_flags, flags_str, body_in, extra_dict,&err) < 0)
28372837
goto error;
28382838

2839-
/*** send it out ***/
2840-
if (!set && (set=rtpe_ctx_set_get())==NULL )
2841-
set = *default_rtpe_set;
2839+
/*** set can be passed into this routine. If it is NULL, then attempt to determine it. ***/
2840+
if (!set) {
2841+
if ((set=rtpe_ctx_set_get())==NULL)
2842+
set = *default_rtpe_set;
2843+
}
2844+
2845+
/*** If the spvar "sock_var" has been specified, parse it into a (socket_val) STR variable ***/
2846+
if (spvar) {
2847+
memset(&socket_val, 0, sizeof(pv_value_t));
2848+
pv_get_spec_value(msg, spvar, &socket_val);
2849+
}
28422850

28432851
failed_node = NULL;
28442852

28452853
RTPE_START_READ();
28462854
do {
2847-
if (snode && snode->s) {
2855+
/*
2856+
* Many rtpengine_* commands allow a "sock_var" to be specified by the script writer.
2857+
* The "sock_var" will be populated by the rtpengine_* command with the RTPEngine that
2858+
* was chosen for the operation.
2859+
*
2860+
* The "sock_var" can be used by subsequent rtpengine_* commands to direct the command
2861+
* toward a specific RTPEngine instance.
2862+
*/
2863+
if (spvar && (socket_val.rs.len > 0)) {
2864+
LM_DBG("Sending command [%d] to RTPEngine socket: [%.*s] set id: [%d]\n", op, (int)(socket_val.rs.len), (char *)(socket_val.rs.s), set->id_set);
2865+
node = lookup_rtpe_node(set, &socket_val.rs);
2866+
if (node == NULL) {
2867+
RTPE_STOP_READ();
2868+
goto error;
2869+
}
2870+
2871+
} else if (snode && snode->s) {
28482872
if ((node = get_rtpe_node(snode, set)) == NULL && op == OP_OFFER)
28492873
node = select_rtpe_node(ng_flags.call_id, set, ignore_list);
28502874
snode = NULL;
2875+
28512876
} else {
28522877
node = select_rtpe_node(ng_flags.call_id, set, ignore_list);
28532878
}
2879+
28542880
if (!node) {
28552881
if (!err && !error.len)
28562882
err = "no available proxies";
@@ -3026,6 +3052,7 @@ rtpe_test(struct rtpe_node *node, int isdisabled, int force)
30263052
{
30273053
bencode_buffer_t bencbuf;
30283054
bencode_item_t *dict;
3055+
bencode_item_t *resp;
30293056
char *cp;
30303057
int ret;
30313058

@@ -3055,14 +3082,14 @@ rtpe_test(struct rtpe_node *node, int isdisabled, int force)
30553082
goto error;
30563083
}
30573084

3058-
dict = bencode_decode_expect(&bencbuf, cp, ret, BENCODE_DICTIONARY);
3059-
if (!dict || bencode_dictionary_get_strcmp(dict, "result", "pong")) {
3085+
resp = bencode_decode_expect(&bencbuf, cp, ret, BENCODE_DICTIONARY);
3086+
if (!resp || bencode_dictionary_get_strcmp(resp, "result", "pong")) {
30603087
LM_ERR("proxy responded with invalid response\n");
30613088
goto error;
30623089
}
30633090

30643091
if (isdisabled)
3065-
LM_INFO("rtp proxy <%s> found, support for it %senabled\n",
3092+
LM_DBG("rtpengine <%s> found, support for it %senabled\n",
30663093
node->rn_url.s, force == 0 ? "re-" : "");
30673094

30683095
bencode_buffer_free(&bencbuf);

0 commit comments

Comments
 (0)