summaryrefslogtreecommitdiffstats
path: root/src/router/call.c
diff options
context:
space:
mode:
authorAndreas Eversberg <jolly@eversberg.eu>2021-08-25 15:35:09 +0200
committerAndreas Eversberg <jolly@eversberg.eu>2021-09-17 16:33:29 +0200
commit42f4d661a999215166672fba9d3a182ae58babcc (patch)
tree5bd3c1a94501bd516782f3a7547b01d43f44f55e /src/router/call.c
parent80d911e5a649b4c9cf3bb506c766b1611a8e95aa (diff)
Support for two endpoints. Useful for multi stack setups.
Diffstat (limited to 'src/router/call.c')
-rw-r--r--src/router/call.c134
1 files changed, 73 insertions, 61 deletions
diff --git a/src/router/call.c b/src/router/call.c
index eca0f75..945c2ac 100644
--- a/src/router/call.c
+++ b/src/router/call.c
@@ -78,7 +78,7 @@
call_t *call_list = NULL;
struct timer status_timer;
-static osmo_cc_endpoint_t *cc_ep;
+static osmo_cc_endpoint_t *cc_ep_list[3];
static const char *routing_script, *routing_shell;
static struct osmo_cc_helper_audio_codecs codecs_def[] = {
@@ -95,31 +95,34 @@ static void refresh_status(void)
int from_count, to_count;
call_t *call;
call_relation_t *relation;
+ int e;
display_status_start();
- for (cc_call = cc_ep->call_list; cc_call; cc_call = cc_call->next) {
- if (cc_call->state != OSMO_CC_STATE_ATTACH_IN)
- continue;
- if (!cc_call->attached_name)
- continue;
- from_count = 0;
- for (call = call_list; call; call = call->next) {
- if (!call->relation_list)
+ for (e = 0; cc_ep_list[e]; e++) {
+ for (cc_call = cc_ep_list[e]->call_list; cc_call; cc_call = cc_call->next) {
+ if (cc_call->state != OSMO_CC_STATE_ATTACH_IN)
continue;
- if (!!strcmp(cc_call->attached_name, call->relation_list->interface))
+ if (!cc_call->attached_name)
continue;
- to_count = 0;
- for (relation = call->relation_list->next; relation; relation = relation->next) {
- display_status_line(cc_call->attached_name, from_count, call->relation_list->id, to_count, relation->interface, relation->id, relation->state);
- to_count++;
+ from_count = 0;
+ for (call = call_list; call; call = call->next) {
+ if (!call->relation_list)
+ continue;
+ if (!!strcmp(cc_call->attached_name, call->relation_list->interface))
+ continue;
+ to_count = 0;
+ for (relation = call->relation_list->next; relation; relation = relation->next) {
+ display_status_line(cc_call->attached_name, from_count, call->relation_list->id, to_count, relation->interface, relation->id, relation->state);
+ to_count++;
+ }
+ if (!to_count)
+ display_status_line(cc_call->attached_name, from_count, call->relation_list->id, 0, NULL, NULL, 0);
+ from_count++;
}
- if (!to_count)
- display_status_line(cc_call->attached_name, from_count, call->relation_list->id, 0, NULL, NULL, 0);
- from_count++;
+ if (!from_count)
+ display_status_line(cc_call->attached_name, 0, NULL, 0, NULL, NULL, 0);
}
- if (!from_count)
- display_status_line(cc_call->attached_name, 0, NULL, 0, NULL, NULL, 0);
}
display_status_end();
@@ -132,11 +135,14 @@ static void status_timeout(struct timer *timer)
static int last_interfaces = -1;
osmo_cc_call_t *cc_call;
int interfaces = 0;
+ int e;
- for (cc_call = cc_ep->call_list; cc_call; cc_call = cc_call->next) {
- if (cc_call->state != OSMO_CC_STATE_ATTACH_IN)
- continue;
- interfaces++;
+ for (e = 0; cc_ep_list[e]; e++) {
+ for (cc_call = cc_ep_list[e]->call_list; cc_call; cc_call = cc_call->next) {
+ if (cc_call->state != OSMO_CC_STATE_ATTACH_IN)
+ continue;
+ interfaces++;
+ }
}
if (interfaces != last_interfaces) {
@@ -314,9 +320,11 @@ static void relation_destroy(call_relation_t *relation)
status_needs_update = 1;
}
-int call_init(osmo_cc_endpoint_t *ep, const char *_routing_script, const char *_routing_shell)
+int call_init(osmo_cc_endpoint_t *cc_ep1, osmo_cc_endpoint_t *cc_ep2, const char *_routing_script, const char *_routing_shell)
{
- cc_ep = ep;
+ cc_ep_list[0] = cc_ep1;
+ cc_ep_list[1] = cc_ep2;
+ cc_ep_list[2] = NULL;
routing_script = _routing_script;
routing_shell = _routing_shell;
timer_init(&status_timer, status_timeout, NULL);
@@ -405,7 +413,7 @@ static void proxy_send_sdp_answer(call_relation_t *relation, osmo_cc_msg_t *msg)
*/
/* a new call is received */
-static void orig_setup(uint32_t callref, osmo_cc_msg_t *old_msg)
+static void orig_setup(osmo_cc_endpoint_t *cc_ep, uint32_t callref, osmo_cc_msg_t *old_msg)
{
call_t *call;
call_relation_t *relation;
@@ -421,7 +429,9 @@ static void orig_setup(uint32_t callref, osmo_cc_msg_t *old_msg)
abort();
}
relation = relation_create(call);
+
/* link with cc */
+ relation->cc_ep = cc_ep;
relation->cc_callref = callref;
PDEBUG(DROUTER, DEBUG_DEBUG, "%s CC-SETUP-REQ from originator.\n", relation_name(relation));
@@ -517,7 +527,7 @@ static void orig_info(call_t *call, osmo_cc_msg_t *old_msg)
strcat(call->relation_list->next->id, number);
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_INFO_IND;
- osmo_cc_ll_msg(cc_ep, call->relation_list->next->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->next->cc_ep, call->relation_list->next->cc_callref, new_msg);
return;
}
@@ -571,7 +581,7 @@ static void orig_disc(call_t *call, osmo_cc_msg_t *old_msg)
if (!call->relation_list->next) {
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_IND;
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
/* destroy call */
call_destroy(call);
return;
@@ -585,7 +595,7 @@ static void orig_disc(call_t *call, osmo_cc_msg_t *old_msg)
/* forward disc message */
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_DISC_IND;
- osmo_cc_ll_msg(cc_ep, call->relation_list->next->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->next->cc_ep, call->relation_list->next->cc_callref, new_msg);
new_state(call, CALL_STATE_DISC_FROM_ORIG);
return;
}
@@ -594,11 +604,11 @@ static void orig_disc(call_t *call, osmo_cc_msg_t *old_msg)
for (relation = call->relation_list->next; relation; relation = relation->next) {
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_IND;
- osmo_cc_ll_msg(cc_ep, relation->cc_callref, new_msg);
+ osmo_cc_ll_msg(relation->cc_ep, relation->cc_callref, new_msg);
}
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_IND;
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
/* destroy call */
call_destroy(call);
}
@@ -620,11 +630,11 @@ static void orig_rel(call_t *call, osmo_cc_msg_t *old_msg)
for (relation = call->relation_list->next; relation; relation = relation->next) {
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_IND;
- osmo_cc_ll_msg(cc_ep, relation->cc_callref, new_msg);
+ osmo_cc_ll_msg(relation->cc_ep, relation->cc_callref, new_msg);
}
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_CNF;
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
/* destroy call */
call_destroy(call);
}
@@ -640,7 +650,7 @@ static void orig_other(call_t *call, osmo_cc_msg_t *old_msg)
if (call->relation_list->next && !call->forking) {
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = old_msg->type | 1; /* convert REQ->IND, RSP->CNF */
- osmo_cc_ll_msg(cc_ep, call->relation_list->next->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->next->cc_ep, call->relation_list->next->cc_callref, new_msg);
return;
}
}
@@ -663,7 +673,7 @@ static void term_progress(call_t *call, call_relation_t *relation, osmo_cc_msg_t
new_msg->type = OSMO_CC_MSG_PROGRESS_IND;
/* send SDP answer */
proxy_send_sdp_answer(call->relation_list, new_msg);
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
}
}
@@ -699,7 +709,7 @@ static void term_overlap(call_t *call, call_relation_t *relation, osmo_cc_msg_t
}
/* send SDP answer */
proxy_send_sdp_answer(call->relation_list, new_msg);
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
}
/* proceeding is received from terminating side */
@@ -735,7 +745,7 @@ static void term_proc(call_t *call, call_relation_t *relation, osmo_cc_msg_t *ol
}
/* send SDP answer */
proxy_send_sdp_answer(call->relation_list, new_msg);
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
}
/* alerting is received from terminating side */
@@ -772,7 +782,7 @@ static void term_alert(call_t *call, call_relation_t *relation, osmo_cc_msg_t *o
}
/* send SDP answer */
proxy_send_sdp_answer(call->relation_list, new_msg);
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
}
/* connect is received from terminating side */
@@ -815,8 +825,8 @@ static void term_connect(call_t *call, call_relation_t *relation, osmo_cc_msg_t
PDEBUG(DROUTER, DEBUG_DEBUG, "Sending 'non-selected user clearing' to other terminator.\n");
/* send release message */
new_msg = osmo_cc_new_msg(OSMO_CC_MSG_REL_IND);
- osmo_cc_add_ie_cause(new_msg, cc_ep->serving_location, OSMO_CC_ISDN_CAUSE_NONSE_USER_CLR, 0, 0);
- osmo_cc_ll_msg(cc_ep, other->cc_callref, new_msg);
+ osmo_cc_add_ie_cause(new_msg, other->cc_ep->serving_location, OSMO_CC_ISDN_CAUSE_NONSE_USER_CLR, 0, 0);
+ osmo_cc_ll_msg(other->cc_ep, other->cc_callref, new_msg);
/* destroy terminating relation */
relation_destroy(other);
}
@@ -839,7 +849,7 @@ static void term_connect(call_t *call, call_relation_t *relation, osmo_cc_msg_t
/* use earlier SDP if not included */
if (!sdp[0] && relation->sdp)
osmo_cc_add_ie_sdp(new_msg, relation->sdp);
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
}
/* disconnect is received from terminating side */
@@ -876,7 +886,7 @@ static void term_disc(call_t *call, call_relation_t *relation, osmo_cc_msg_t *ol
new_msg->type = OSMO_CC_MSG_DISC_IND;
/* send SDP answer */
proxy_send_sdp_answer(call->relation_list, new_msg);
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
return;
}
@@ -889,7 +899,7 @@ static void term_disc(call_t *call, call_relation_t *relation, osmo_cc_msg_t *ol
/* release the terminator */
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_IND;
- osmo_cc_ll_msg(cc_ep, relation->cc_callref, new_msg);
+ osmo_cc_ll_msg(relation->cc_ep, relation->cc_callref, new_msg);
/* remove relation */
relation_destroy(relation);
@@ -898,8 +908,8 @@ static void term_disc(call_t *call, call_relation_t *relation, osmo_cc_msg_t *ol
if (!call->relation_list->next) {
PDEBUG(DROUTER, DEBUG_DEBUG, "All terminators have disconnected, so we forward a release with the collected cause.\n");
new_msg = osmo_cc_new_msg(OSMO_CC_MSG_REL_IND);
- osmo_cc_add_ie_cause(new_msg, cc_ep->serving_location, call->collect_cause, 0, 0);
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_add_ie_cause(new_msg, call->relation_list->cc_ep->serving_location, call->collect_cause, 0, 0);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
/* destroy call */
call_destroy(call);
}
@@ -912,10 +922,10 @@ static void term_disc(call_t *call, call_relation_t *relation, osmo_cc_msg_t *ol
PDEBUG(DROUTER, DEBUG_DEBUG, "Got a disconnect after connect, so we directly forward this disconnect.\n");
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_IND;
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_IND;
- osmo_cc_ll_msg(cc_ep, relation->cc_callref, new_msg);
+ osmo_cc_ll_msg(relation->cc_ep, relation->cc_callref, new_msg);
/* destroy call */
call_destroy(call);
return;
@@ -947,11 +957,11 @@ static void term_rel(call_t *call, call_relation_t *relation, osmo_cc_msg_t *old
/* forward message to originator */
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_IND;
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
/* confirm to terminator */
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_CNF;
- osmo_cc_ll_msg(cc_ep, relation->cc_callref, new_msg);
+ osmo_cc_ll_msg(relation->cc_ep, relation->cc_callref, new_msg);
/* destroy call */
call_destroy(call);
return;
@@ -966,7 +976,7 @@ static void term_rel(call_t *call, call_relation_t *relation, osmo_cc_msg_t *old
/* confirm the terminator */
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_CNF;
- osmo_cc_ll_msg(cc_ep, relation->cc_callref, new_msg);
+ osmo_cc_ll_msg(relation->cc_ep, relation->cc_callref, new_msg);
/* remove relation */
relation_destroy(relation);
@@ -975,8 +985,8 @@ static void term_rel(call_t *call, call_relation_t *relation, osmo_cc_msg_t *old
if (!call->relation_list->next) {
PDEBUG(DROUTER, DEBUG_DEBUG, "All terminators have released, so we forward it with the collected cause.\n");
new_msg = osmo_cc_new_msg(OSMO_CC_MSG_REL_IND);
- osmo_cc_add_ie_cause(new_msg, cc_ep->serving_location, call->collect_cause, 0, 0);
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_add_ie_cause(new_msg, call->relation_list->cc_ep->serving_location, call->collect_cause, 0, 0);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
/* destroy call */
call_destroy(call);
}
@@ -989,10 +999,10 @@ static void term_rel(call_t *call, call_relation_t *relation, osmo_cc_msg_t *old
PDEBUG(DROUTER, DEBUG_DEBUG, "Got a release after connect, so we directly forward this release.\n");
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_IND;
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = OSMO_CC_MSG_REL_CNF;
- osmo_cc_ll_msg(cc_ep, relation->cc_callref, new_msg);
+ osmo_cc_ll_msg(relation->cc_ep, relation->cc_callref, new_msg);
/* destroy call */
call_destroy(call);
return;
@@ -1012,13 +1022,13 @@ static void term_other(call_t *call, call_relation_t *relation, osmo_cc_msg_t *o
if (!call->relation_list->next->next) {
new_msg = osmo_cc_clone_msg(old_msg);
new_msg->type = old_msg->type | 1; /* convert REQ->IND, RSP->CNF */
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
return;
}
}
/* handle message from upper layer */
-void cc_message(osmo_cc_endpoint_t __attribute__((unused)) *ep, uint32_t callref, osmo_cc_msg_t *msg)
+void cc_message(osmo_cc_endpoint_t *cc_ep, uint32_t callref, osmo_cc_msg_t *msg)
{
call_t *call;
call_relation_t *relation;
@@ -1045,7 +1055,7 @@ void cc_message(osmo_cc_endpoint_t __attribute__((unused)) *ep, uint32_t callref
PDEBUG(DROUTER, DEBUG_ERROR, "Received message without call instance, please fix!\n");
return;
}
- orig_setup(callref, msg);
+ orig_setup(cc_ep, callref, msg);
osmo_cc_free_msg(msg);
return;
}
@@ -1447,11 +1457,13 @@ next_call:
if (calls > 1)
call->forking = 1;
+
/* create endpoint */
- osmo_cc_call_t *cc_call = osmo_cc_call_new(cc_ep);
+ osmo_cc_call_t *cc_call = osmo_cc_call_new(att->ep);
call_relation_t *relation = relation_create(call);
/* link with cc */
+ relation->cc_ep = att->ep;
relation->cc_callref = cc_call->callref;
PDEBUG(DROUTER, DEBUG_DEBUG, "%s CC-SETUP-IND to terminator.\n", relation_name(relation));
@@ -1942,7 +1954,7 @@ void routing_close(routing_t *routing)
new_state(call, CALL_STATE_OVERLAP);
/* forward message to originator */
new_msg = osmo_cc_new_msg(OSMO_CC_MSG_SETUP_ACK_IND);
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
return;
}
@@ -1953,8 +1965,8 @@ void routing_close(routing_t *routing)
/* there is no way to dial more digits, so we release the call */
new_msg = osmo_cc_new_msg(OSMO_CC_MSG_REL_IND);
- osmo_cc_add_ie_cause(new_msg, cc_ep->serving_location, OSMO_CC_ISDN_CAUSE_NO_ROUTE, 0, 0);
- osmo_cc_ll_msg(cc_ep, call->relation_list->cc_callref, new_msg);
+ osmo_cc_add_ie_cause(new_msg, call->relation_list->cc_ep->serving_location, OSMO_CC_ISDN_CAUSE_NO_ROUTE, 0, 0);
+ osmo_cc_ll_msg(call->relation_list->cc_ep, call->relation_list->cc_callref, new_msg);
/* destroy call */
call_destroy(call);