From cb8c35cd518bba3caedd16a923464a956e3eb4f4 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Tue, 10 Aug 2010 20:24:24 +0800 Subject: mgcp: Speculative mgcp fix... We really have 32 channels per multiplex... so use the right number... or at least it seems we do have 32. --- openbsc/include/openbsc/mgcp.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'openbsc') diff --git a/openbsc/include/openbsc/mgcp.h b/openbsc/include/openbsc/mgcp.h index 38fe50482..02abeea39 100644 --- a/openbsc/include/openbsc/mgcp.h +++ b/openbsc/include/openbsc/mgcp.h @@ -147,7 +147,7 @@ static inline int mgcp_timeslot_to_endpoint(int multiplex, int timeslot) { if (timeslot == 0) timeslot = 1; - return timeslot + (31 * multiplex); + return timeslot + (32 * multiplex); } -- cgit v1.2.3 From 82049d81413c23f08e7a5418f30676001e1a4588 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Sat, 28 Aug 2010 17:59:15 +0800 Subject: mgcp: Add method to go back from endpoint to multiplex/timeslot --- openbsc/include/openbsc/mgcp.h | 9 +++++++++ 1 file changed, 9 insertions(+) (limited to 'openbsc') diff --git a/openbsc/include/openbsc/mgcp.h b/openbsc/include/openbsc/mgcp.h index 02abeea39..ed070cdbc 100644 --- a/openbsc/include/openbsc/mgcp.h +++ b/openbsc/include/openbsc/mgcp.h @@ -150,5 +150,14 @@ static inline int mgcp_timeslot_to_endpoint(int multiplex, int timeslot) return timeslot + (32 * multiplex); } +static inline void mgcp_endpoint_to_timeslot(int endpoint, int *multiplex, int *timeslot) +{ + *multiplex = endpoint / 32; + *timeslot = endpoint % 32; + + if (*timeslot == 1) + *timeslot = 0; +} + #endif -- cgit v1.2.3 From 591003328dac804592c8a5dc749d93d5e0be4347 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Sat, 28 Aug 2010 14:56:00 +0800 Subject: nat: Use the bsc_timeslot when talking to the BSC downstream --- openbsc/src/nat/bsc_mgcp_utils.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) (limited to 'openbsc') diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index 067df0eda..e3258f02f 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -156,9 +156,10 @@ void bsc_mgcp_dlcx(struct sccp_connections *con) { /* send a DLCX down the stream */ if (con->bsc_timeslot != -1 && con->crcx) { - int endp = mgcp_timeslot_to_endpoint(0, con->msc_timeslot); - bsc_mgcp_send_dlcx(con->bsc, endp); - bsc_mgcp_free_endpoint(con->bsc->nat, endp); + int bsc_endp = mgcp_timeslot_to_endpoint(0, con->bsc_timeslot); + int msc_endp = mgcp_timeslot_to_endpoint(0, con->msc_timeslot); + bsc_mgcp_send_dlcx(con->bsc, bsc_endp); + bsc_mgcp_free_endpoint(con->bsc->nat, msc_endp); } bsc_mgcp_init(con); -- cgit v1.2.3 From f4b343920668280b39ddb95209f6ab0ceccab630 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Sat, 28 Aug 2010 16:08:39 +0800 Subject: nat: Make the code work in terms of endpoints instead of timeslot/multiplex We are going to have more than one trunk, so all code hardcoding the multiplex to zero must go. Avoid this kind of problem by saving the MGCP endpoint number and comparing that. --- openbsc/include/openbsc/bsc_nat_sccp.h | 9 ++++++--- openbsc/src/nat/bsc_mgcp_utils.c | 30 ++++++++++++++---------------- openbsc/src/nat/bsc_nat_vty.c | 2 +- openbsc/tests/bsc-nat/bsc_nat_test.c | 17 +++++------------ 4 files changed, 26 insertions(+), 32 deletions(-) (limited to 'openbsc') diff --git a/openbsc/include/openbsc/bsc_nat_sccp.h b/openbsc/include/openbsc/bsc_nat_sccp.h index 73e9c690c..fcfd23beb 100644 --- a/openbsc/include/openbsc/bsc_nat_sccp.h +++ b/openbsc/include/openbsc/bsc_nat_sccp.h @@ -79,10 +79,13 @@ struct sccp_connections { int con_type; int con_local; - /* GSM audio handling. That is 32 * multiplex + ts */ + /* + * audio handling. Remember if we have ever send a CRCX, + * remember the endpoint used by the MSC and BSC. + */ int crcx; - int msc_timeslot; - int bsc_timeslot; + int msc_endp; + int bsc_endp; /* timeout handling */ struct timespec creation_time; diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index e3258f02f..4983c352c 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -45,7 +45,7 @@ int bsc_mgcp_assign(struct sccp_connections *con, struct msgb *msg) uint16_t cic; uint8_t timeslot; uint8_t multiplex; - int combined; + int endp; if (!msg->l3h) { LOGP(DNAT, LOGL_ERROR, "Assignment message should have l3h pointer.\n"); @@ -68,22 +68,22 @@ int bsc_mgcp_assign(struct sccp_connections *con, struct msgb *msg) multiplex = (cic & ~0x1f) >> 5; - combined = (32 * multiplex) + timeslot; + endp = mgcp_timeslot_to_endpoint(multiplex, timeslot); /* find stale connections using that endpoint */ llist_for_each_entry(mcon, &con->bsc->nat->sccp_connections, list_entry) { - if (mcon->msc_timeslot == combined) { + if (mcon->msc_endp == endp) { LOGP(DNAT, LOGL_ERROR, - "Timeslot %d was assigned to 0x%x and now 0x%x\n", - combined, + "Endpoint %d was assigned to 0x%x and now 0x%x\n", + endp, sccp_src_ref_to_int(&mcon->patched_ref), sccp_src_ref_to_int(&con->patched_ref)); bsc_mgcp_dlcx(mcon); } } - con->msc_timeslot = combined; - con->bsc_timeslot = con->msc_timeslot; + con->msc_endp = endp; + con->bsc_endp = endp; return 0; } @@ -147,19 +147,17 @@ static void bsc_mgcp_send_dlcx(struct bsc_connection *bsc, int endpoint) void bsc_mgcp_init(struct sccp_connections *con) { - con->msc_timeslot = -1; - con->bsc_timeslot = -1; + con->msc_endp = -1; + con->bsc_endp = -1; con->crcx = 0; } void bsc_mgcp_dlcx(struct sccp_connections *con) { /* send a DLCX down the stream */ - if (con->bsc_timeslot != -1 && con->crcx) { - int bsc_endp = mgcp_timeslot_to_endpoint(0, con->bsc_timeslot); - int msc_endp = mgcp_timeslot_to_endpoint(0, con->msc_timeslot); - bsc_mgcp_send_dlcx(con->bsc, bsc_endp); - bsc_mgcp_free_endpoint(con->bsc->nat, msc_endp); + if (con->bsc_endp != -1 && con->crcx) { + bsc_mgcp_send_dlcx(con->bsc, con->bsc_endp); + bsc_mgcp_free_endpoint(con->bsc->nat, con->msc_endp); } bsc_mgcp_init(con); @@ -172,9 +170,9 @@ struct sccp_connections *bsc_mgcp_find_con(struct bsc_nat *nat, int endpoint) struct sccp_connections *sccp; llist_for_each_entry(sccp, &nat->sccp_connections, list_entry) { - if (sccp->msc_timeslot == -1) + if (sccp->msc_endp == -1) continue; - if (mgcp_timeslot_to_endpoint(0, sccp->msc_timeslot) != endpoint) + if (sccp->msc_endp != endpoint) continue; con = sccp; diff --git a/openbsc/src/nat/bsc_nat_vty.c b/openbsc/src/nat/bsc_nat_vty.c index d8af1c23f..b72eb4e26 100644 --- a/openbsc/src/nat/bsc_nat_vty.c +++ b/openbsc/src/nat/bsc_nat_vty.c @@ -121,7 +121,7 @@ DEFUN(show_sccp, show_sccp_cmd, "show sccp connections", sccp_src_ref_to_int(&con->patched_ref), con->has_remote_ref, sccp_src_ref_to_int(&con->remote_ref), - con->msc_timeslot, con->bsc_timeslot, + con->msc_endp, con->bsc_endp, bsc_con_type_to_string(con->con_type), VTY_NEWLINE); } diff --git a/openbsc/tests/bsc-nat/bsc_nat_test.c b/openbsc/tests/bsc-nat/bsc_nat_test.c index c5234aa24..b7a89c5b7 100644 --- a/openbsc/tests/bsc-nat/bsc_nat_test.c +++ b/openbsc/tests/bsc-nat/bsc_nat_test.c @@ -449,19 +449,19 @@ static void test_mgcp_ass_tracking(void) abort(); } - if (con.msc_timeslot != 21) { + if (con.msc_endp != 21) { fprintf(stderr, "Timeslot should be 21.\n"); abort(); } - if (con.bsc_timeslot != 21) { + if (con.bsc_endp != 21) { fprintf(stderr, "Assigned timeslot should have been 21.\n"); abort(); } talloc_free(parsed); bsc_mgcp_dlcx(&con); - if (con.bsc_timeslot != -1 || con.msc_timeslot != -1) { + if (con.bsc_endp != -1 || con.msc_endp != -1) { fprintf(stderr, "Clearing should remove the mapping.\n"); abort(); } @@ -483,8 +483,8 @@ static void test_mgcp_find(void) llist_add(&con->list_entry, &nat->bsc_connections); sccp_con = talloc_zero(con, struct sccp_connections); - sccp_con->msc_timeslot = 12; - sccp_con->bsc_timeslot = 12; + sccp_con->msc_endp = 12; + sccp_con->bsc_endp = 12; sccp_con->bsc = con; llist_add(&sccp_con->list_entry, &nat->sccp_connections); @@ -498,13 +498,6 @@ static void test_mgcp_find(void) abort(); } - sccp_con->msc_timeslot = 0; - sccp_con->bsc_timeslot = 0; - if (bsc_mgcp_find_con(nat, 1) != sccp_con) { - fprintf(stderr, "Didn't find the connection\n"); - abort(); - } - /* free everything */ talloc_free(nat); } -- cgit v1.2.3 From c021fbe603c69c2ca79f6c91b1af109fd7e1613f Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Sat, 28 Aug 2010 16:46:27 +0800 Subject: nat: Reindent the code, no functional change --- openbsc/src/nat/bsc_mgcp_utils.c | 40 ++++++++++++++++++++-------------------- 1 file changed, 20 insertions(+), 20 deletions(-) (limited to 'openbsc') diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index 4983c352c..567c325b1 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -274,30 +274,30 @@ int bsc_mgcp_policy_cb(struct mgcp_config *cfg, int endpoint, int state, const c static void free_chan_downstream(struct mgcp_endpoint *endp, struct bsc_endpoint *bsc_endp, struct bsc_connection *bsc) { - LOGP(DMGCP, LOGL_ERROR, "No CI, freeing endpoint 0x%x in state %d\n", - ENDPOINT_NUMBER(endp), bsc_endp->transaction_state); - - /* if a CRCX failed... send a DLCX down the stream */ - if (bsc_endp->transaction_state == MGCP_ENDP_CRCX) { - struct sccp_connections *con; - con = bsc_mgcp_find_con(bsc->nat, ENDPOINT_NUMBER(endp)); - if (!con) { - LOGP(DMGCP, LOGL_ERROR, - "No SCCP connection for endp 0x%x\n", - ENDPOINT_NUMBER(endp)); + LOGP(DMGCP, LOGL_ERROR, "No CI, freeing endpoint 0x%x in state %d\n", + ENDPOINT_NUMBER(endp), bsc_endp->transaction_state); + + /* if a CRCX failed... send a DLCX down the stream */ + if (bsc_endp->transaction_state == MGCP_ENDP_CRCX) { + struct sccp_connections *con; + con = bsc_mgcp_find_con(bsc->nat, ENDPOINT_NUMBER(endp)); + if (!con) { + LOGP(DMGCP, LOGL_ERROR, + "No SCCP connection for endp 0x%x\n", + ENDPOINT_NUMBER(endp)); + } else { + if (con->bsc == bsc) { + bsc_mgcp_send_dlcx(bsc, ENDPOINT_NUMBER(endp)); + con->crcx = 0; } else { - if (con->bsc == bsc) { - bsc_mgcp_send_dlcx(bsc, ENDPOINT_NUMBER(endp)); - con->crcx = 0; - } else { - LOGP(DMGCP, LOGL_ERROR, - "Endpoint belongs to a different BSC\n"); - } + LOGP(DMGCP, LOGL_ERROR, + "Endpoint belongs to a different BSC\n"); } } + } - bsc_mgcp_free_endpoint(bsc->nat, ENDPOINT_NUMBER(endp)); - mgcp_free_endp(endp); + bsc_mgcp_free_endpoint(bsc->nat, ENDPOINT_NUMBER(endp)); + mgcp_free_endp(endp); } /* -- cgit v1.2.3 From 39cd32e650d490ba2d5e74f2df90a3f12514d618 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Sat, 28 Aug 2010 18:11:07 +0800 Subject: nat: Remove the CRCX value from the nat Assume that if the MSC has assigned a timeslot/multiplex it will also be used for the MGCP. So we just assume that it was allocated on the BSC as well... in the worse case we will send a DLCX downstream but it should be fine. --- openbsc/include/openbsc/bsc_nat_sccp.h | 1 - openbsc/src/nat/bsc_mgcp_utils.c | 5 +---- 2 files changed, 1 insertion(+), 5 deletions(-) (limited to 'openbsc') diff --git a/openbsc/include/openbsc/bsc_nat_sccp.h b/openbsc/include/openbsc/bsc_nat_sccp.h index fcfd23beb..4f1afcb2b 100644 --- a/openbsc/include/openbsc/bsc_nat_sccp.h +++ b/openbsc/include/openbsc/bsc_nat_sccp.h @@ -83,7 +83,6 @@ struct sccp_connections { * audio handling. Remember if we have ever send a CRCX, * remember the endpoint used by the MSC and BSC. */ - int crcx; int msc_endp; int bsc_endp; diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index 567c325b1..8ed930145 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -149,13 +149,12 @@ void bsc_mgcp_init(struct sccp_connections *con) { con->msc_endp = -1; con->bsc_endp = -1; - con->crcx = 0; } void bsc_mgcp_dlcx(struct sccp_connections *con) { /* send a DLCX down the stream */ - if (con->bsc_endp != -1 && con->crcx) { + if (con->bsc_endp != -1) { bsc_mgcp_send_dlcx(con->bsc, con->bsc_endp); bsc_mgcp_free_endpoint(con->bsc->nat, con->msc_endp); } @@ -253,7 +252,6 @@ int bsc_mgcp_policy_cb(struct mgcp_config *cfg, int endpoint, int state, const c } /* send the message and a fake MDCX to force sending of a dummy packet */ - sccp->crcx = 1; bsc_write(sccp->bsc, bsc_msg, NAT_IPAC_PROTO_MGCP); bsc_mgcp_send_mdcx(sccp->bsc, mgcp_endp); return MGCP_POLICY_DEFER; @@ -288,7 +286,6 @@ static void free_chan_downstream(struct mgcp_endpoint *endp, struct bsc_endpoint } else { if (con->bsc == bsc) { bsc_mgcp_send_dlcx(bsc, ENDPOINT_NUMBER(endp)); - con->crcx = 0; } else { LOGP(DMGCP, LOGL_ERROR, "Endpoint belongs to a different BSC\n"); -- cgit v1.2.3 From 45fd07dc33b5dd845e2b266adda5d24a4d500f96 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Sat, 28 Aug 2010 18:22:14 +0800 Subject: nat: Attempt to assign the BSC Timeslot based on a free list Do attempt to not reassign an endpoint immediately but go to the next free one. --- openbsc/include/openbsc/bsc_nat.h | 6 ++++- openbsc/src/nat/bsc_mgcp_utils.c | 52 ++++++++++++++++++++++++++++++++++-- openbsc/src/nat/bsc_nat.c | 2 +- openbsc/tests/bsc-nat/bsc_nat_test.c | 13 ++++++--- 4 files changed, 65 insertions(+), 8 deletions(-) (limited to 'openbsc') diff --git a/openbsc/include/openbsc/bsc_nat.h b/openbsc/include/openbsc/bsc_nat.h index 5f746f237..11c24dc60 100644 --- a/openbsc/include/openbsc/bsc_nat.h +++ b/openbsc/include/openbsc/bsc_nat.h @@ -75,6 +75,10 @@ struct bsc_connection { struct timer_list ping_timeout; struct timer_list pong_timeout; + /* mgcp related code */ + int endpoint_status[33]; + int last_endpoint; + /* a back pointer */ struct bsc_nat *nat; }; @@ -253,7 +257,7 @@ struct sccp_connections *patch_sccp_src_ref_to_msc(struct msgb *, struct bsc_nat * MGCP/Audio handling */ int bsc_write_mgcp(struct bsc_connection *bsc, const uint8_t *data, unsigned int length); -int bsc_mgcp_assign(struct sccp_connections *, struct msgb *msg); +int bsc_mgcp_assign_patch(struct sccp_connections *, struct msgb *msg); void bsc_mgcp_init(struct sccp_connections *); void bsc_mgcp_dlcx(struct sccp_connections *); void bsc_mgcp_free_endpoints(struct bsc_nat *nat); diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index 8ed930145..475e04cc2 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -38,7 +38,36 @@ #include #include -int bsc_mgcp_assign(struct sccp_connections *con, struct msgb *msg) +static int bsc_assign_endpoint(struct bsc_connection *bsc, struct sccp_connections *con) +{ + const int number_endpoints = ARRAY_SIZE(bsc->endpoint_status); + int i; + + for (i = 1; i < number_endpoints; ++i) { + int endpoint = (bsc->last_endpoint + i) % number_endpoints; + if (endpoint == 0) + endpoint = 1; + + if (bsc->endpoint_status[endpoint] == 0) { + bsc->endpoint_status[endpoint] = 1; + con->bsc_endp = endpoint; + bsc->last_endpoint = endpoint; + return 0; + } + } + + return -1; +} + +static uint16_t create_cic(int endpoint) +{ + int timeslot, multiplex; + + mgcp_endpoint_to_timeslot(endpoint, &multiplex, ×lot); + return (multiplex << 5) | (timeslot & 0x1f); +} + +int bsc_mgcp_assign_patch(struct sccp_connections *con, struct msgb *msg) { struct sccp_connections *mcon; struct tlv_parsed tp; @@ -83,7 +112,17 @@ int bsc_mgcp_assign(struct sccp_connections *con, struct msgb *msg) } con->msc_endp = endp; - con->bsc_endp = endp; + if (bsc_assign_endpoint(con->bsc, con) != 0) + return -1; + + /* + * now patch the message for the new CIC... + * still assumed to be one multiplex only + */ + cic = htons(create_cic(con->bsc_endp)); + memcpy((uint8_t *) TLVP_VAL(&tp, GSM0808_IE_CIRCUIT_IDENTITY_CODE), + &cic, sizeof(cic)); + return 0; } @@ -94,6 +133,15 @@ static void bsc_mgcp_free_endpoint(struct bsc_nat *nat, int i) nat->bsc_endpoints[i].transaction_id = NULL; } + /* Free the endpoint status, so we can allocate it again */ + if (nat->bsc_endpoints[i].bsc) { + struct bsc_connection *bsc = nat->bsc_endpoints[i].bsc; + if (bsc->endpoint_status[i] != 1) + LOGP(DNAT, LOGL_ERROR, "Endpoint %d should be allocated\n", i); + + bsc->endpoint_status[i] = 0; + } + nat->bsc_endpoints[i].transaction_state = 0; nat->bsc_endpoints[i].bsc = NULL; } diff --git a/openbsc/src/nat/bsc_nat.c b/openbsc/src/nat/bsc_nat.c index 997a57f44..a380a61fb 100644 --- a/openbsc/src/nat/bsc_nat.c +++ b/openbsc/src/nat/bsc_nat.c @@ -422,7 +422,7 @@ static int forward_sccp_to_bts(struct bsc_msc_connection *msc_con, struct msgb * struct rate_ctr_group *ctrg; ctrg = con->bsc->cfg->stats.ctrg; rate_ctr_inc(&ctrg->ctr[BCFG_CTR_SCCP_CALLS]); - if (bsc_mgcp_assign(con, msg) != 0) + if (bsc_mgcp_assign_patch(con, msg) != 0) LOGP(DNAT, LOGL_ERROR, "Failed to assign...\n"); } else LOGP(DNAT, LOGL_ERROR, "Assignment command but no BSC.\n"); diff --git a/openbsc/tests/bsc-nat/bsc_nat_test.c b/openbsc/tests/bsc-nat/bsc_nat_test.c index b7a89c5b7..acc5de343 100644 --- a/openbsc/tests/bsc-nat/bsc_nat_test.c +++ b/openbsc/tests/bsc-nat/bsc_nat_test.c @@ -444,7 +444,7 @@ static void test_mgcp_ass_tracking(void) msg = msgb_alloc(4096, "foo"); copy_to_msg(msg, ass_cmd, sizeof(ass_cmd)); parsed = bsc_nat_parse(msg); - if (bsc_mgcp_assign(&con, msg) != 0) { + if (bsc_mgcp_assign_patch(&con, msg) != 0) { fprintf(stderr, "Failed to handle assignment.\n"); abort(); } @@ -454,14 +454,19 @@ static void test_mgcp_ass_tracking(void) abort(); } - if (con.bsc_endp != 21) { - fprintf(stderr, "Assigned timeslot should have been 21.\n"); + if (con.bsc_endp != 1) { + fprintf(stderr, "Assigned timeslot should have been 1.\n"); abort(); } + if (con.bsc->endpoint_status[1] != 1) { + fprintf(stderr, "The status on the BSC is wrong.\n"); + abort(); + } + talloc_free(parsed); bsc_mgcp_dlcx(&con); - if (con.bsc_endp != -1 || con.msc_endp != -1) { + if (con.bsc_endp != -1 || con.msc_endp != -1 || con.bsc->endpoint_status[1] != 0) { fprintf(stderr, "Clearing should remove the mapping.\n"); abort(); } -- cgit v1.2.3 From 0d8330c8cc066ce6609286fe58de3f7962ef7736 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Sat, 28 Aug 2010 18:33:34 +0800 Subject: nat: Add vty command to show the endpoint allocation status --- openbsc/src/nat/bsc_nat_vty.c | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) (limited to 'openbsc') diff --git a/openbsc/src/nat/bsc_nat_vty.c b/openbsc/src/nat/bsc_nat_vty.c index b72eb4e26..0bbd313a9 100644 --- a/openbsc/src/nat/bsc_nat_vty.c +++ b/openbsc/src/nat/bsc_nat_vty.c @@ -29,6 +29,7 @@ #include #include +#include #include @@ -148,6 +149,30 @@ DEFUN(show_bsc, show_bsc_cmd, "show bsc connections", return CMD_SUCCESS; } +DEFUN(show_bsc_mgcp, show_bsc_mgcp_cmd, "show bsc mgcp NR", + SHOW_STR "Display the MGCP status for a given BSC") +{ + struct bsc_connection *con; + int nr = atoi(argv[0]); + int i; + + llist_for_each_entry(con, &_nat->bsc_connections, list_entry) { + if (!con->cfg) + continue; + if (con->cfg->nr != nr) + continue; + + vty_out(vty, "MGCP Status for %d%s", con->cfg->nr, VTY_NEWLINE); + for (i = 1; i < ARRAY_SIZE(con->endpoint_status); ++i) + vty_out(vty, " Endpoint 0x%x %s%s", i, + con->endpoint_status[i] == 0 ? "free" : "allocated", + VTY_NEWLINE); + break; + } + + return CMD_SUCCESS; +} + DEFUN(show_bsc_cfg, show_bsc_cfg_cmd, "show bsc config", SHOW_STR "Display information about known BSC configs") { @@ -564,6 +589,7 @@ int bsc_nat_vty_init(struct bsc_nat *nat) install_element_ve(&close_bsc_cmd); install_element_ve(&show_msc_cmd); install_element_ve(&test_regex_cmd); + install_element_ve(&show_bsc_mgcp_cmd); /* nat group */ install_element(CONFIG_NODE, &cfg_nat_cmd); -- cgit v1.2.3 From 8574dcf9da046daaff5703342e376f9f82cc8734 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Sun, 29 Aug 2010 22:39:07 +0800 Subject: nat: Close the right endpoint down the stream. --- openbsc/src/nat/bsc_mgcp_utils.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'openbsc') diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index 475e04cc2..2dcd25022 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -333,7 +333,7 @@ static void free_chan_downstream(struct mgcp_endpoint *endp, struct bsc_endpoint ENDPOINT_NUMBER(endp)); } else { if (con->bsc == bsc) { - bsc_mgcp_send_dlcx(bsc, ENDPOINT_NUMBER(endp)); + bsc_mgcp_send_dlcx(bsc, con->bsc_endp); } else { LOGP(DMGCP, LOGL_ERROR, "Endpoint belongs to a different BSC\n"); -- cgit v1.2.3 From 7d5bb26fdcb402e46fc301468ed903e4c4023bf0 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Sun, 29 Aug 2010 22:44:10 +0800 Subject: nat: Remove the code that is wrongly placed.. i refers to the MSC side of endpoints and not the BSC.. --- openbsc/src/nat/bsc_mgcp_utils.c | 9 --------- 1 file changed, 9 deletions(-) (limited to 'openbsc') diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index 2dcd25022..12124aff2 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -133,15 +133,6 @@ static void bsc_mgcp_free_endpoint(struct bsc_nat *nat, int i) nat->bsc_endpoints[i].transaction_id = NULL; } - /* Free the endpoint status, so we can allocate it again */ - if (nat->bsc_endpoints[i].bsc) { - struct bsc_connection *bsc = nat->bsc_endpoints[i].bsc; - if (bsc->endpoint_status[i] != 1) - LOGP(DNAT, LOGL_ERROR, "Endpoint %d should be allocated\n", i); - - bsc->endpoint_status[i] = 0; - } - nat->bsc_endpoints[i].transaction_state = 0; nat->bsc_endpoints[i].bsc = NULL; } -- cgit v1.2.3 From 601180f2d93e56757a02a2b2161a73ce6a99e8b8 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Sun, 29 Aug 2010 23:40:33 +0800 Subject: nat: Send the right MDCX down the stream --- openbsc/src/nat/bsc_mgcp_utils.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'openbsc') diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index 12124aff2..b71ec9482 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -148,7 +148,7 @@ void bsc_mgcp_free_endpoints(struct bsc_nat *nat) } /* send a MDCX where we do not want a response */ -static void bsc_mgcp_send_mdcx(struct bsc_connection *bsc, struct mgcp_endpoint *endp) +static void bsc_mgcp_send_mdcx(struct bsc_connection *bsc, int port, struct mgcp_endpoint *endp) { char buf[2096]; int len; @@ -159,7 +159,7 @@ static void bsc_mgcp_send_mdcx(struct bsc_connection *bsc, struct mgcp_endpoint "\r\n" "c=IN IP4 %s\r\n" "m=audio %d RTP/AVP 255\r\n", - ENDPOINT_NUMBER(endp), + port, bsc->nat->mgcp_cfg->source_addr, endp->bts_end.local_port); if (len < 0) { @@ -292,7 +292,7 @@ int bsc_mgcp_policy_cb(struct mgcp_config *cfg, int endpoint, int state, const c /* send the message and a fake MDCX to force sending of a dummy packet */ bsc_write(sccp->bsc, bsc_msg, NAT_IPAC_PROTO_MGCP); - bsc_mgcp_send_mdcx(sccp->bsc, mgcp_endp); + bsc_mgcp_send_mdcx(sccp->bsc, sccp->bsc_endp, mgcp_endp); return MGCP_POLICY_DEFER; } else if (state == MGCP_ENDP_DLCX) { /* we will free the endpoint now and send a DLCX to the BSC */ -- cgit v1.2.3 From d38aa450d758cebbbb78194bdc35df6462ffe501 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Mon, 30 Aug 2010 11:58:49 +0800 Subject: nat: Document that the MDCX message is not implemented --- openbsc/src/nat/bsc_mgcp_utils.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'openbsc') diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index b71ec9482..e68b6479b 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -166,6 +166,8 @@ static void bsc_mgcp_send_mdcx(struct bsc_connection *bsc, int port, struct mgcp LOGP(DMGCP, LOGL_ERROR, "snprintf for DLCX failed.\n"); return; } + + #warning "The MDCX is not send to the BSC. It should" } static void bsc_mgcp_send_dlcx(struct bsc_connection *bsc, int endpoint) -- cgit v1.2.3 From bf812fa83cfff25540e29166246ca71d8ddf0de9 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Mon, 30 Aug 2010 12:01:36 +0800 Subject: nat: Use different static transaction numbers for the DLCX/MDCX message --- openbsc/src/nat/bsc_mgcp_utils.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'openbsc') diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index e68b6479b..d8ec29869 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -176,7 +176,7 @@ static void bsc_mgcp_send_dlcx(struct bsc_connection *bsc, int endpoint) int len; len = snprintf(buf, sizeof(buf), - "DLCX 23 %x@mgw MGCP 1.0\r\n" + "DLCX 26 %x@mgw MGCP 1.0\r\n" "Z: noanswer\r\n", endpoint); if (len < 0) { LOGP(DMGCP, LOGL_ERROR, "snprintf for DLCX failed.\n"); -- cgit v1.2.3 From f7c86c5b4d8f7d909595c0f01fcfaf5da4c4e7c4 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Mon, 30 Aug 2010 13:44:32 +0800 Subject: nat: Replace the MGCP Endpoint if that is required Add code to replace the Endpoint number for the mgcp. --- openbsc/include/openbsc/bsc_nat.h | 2 +- openbsc/src/nat/bsc_mgcp_utils.c | 37 ++++++++++++++++++++++++++++++++---- openbsc/tests/bsc-nat/bsc_data.c | 6 +++--- openbsc/tests/bsc-nat/bsc_nat_test.c | 2 +- 4 files changed, 38 insertions(+), 9 deletions(-) (limited to 'openbsc') diff --git a/openbsc/include/openbsc/bsc_nat.h b/openbsc/include/openbsc/bsc_nat.h index 11c24dc60..25b6429c4 100644 --- a/openbsc/include/openbsc/bsc_nat.h +++ b/openbsc/include/openbsc/bsc_nat.h @@ -264,7 +264,7 @@ void bsc_mgcp_free_endpoints(struct bsc_nat *nat); int bsc_mgcp_nat_init(struct bsc_nat *nat); struct sccp_connections *bsc_mgcp_find_con(struct bsc_nat *, int endpoint_number); -struct msgb *bsc_mgcp_rewrite(char *input, int length, const char *ip, int port); +struct msgb *bsc_mgcp_rewrite(char *input, int length, int endp, const char *ip, int port); void bsc_mgcp_forward(struct bsc_connection *bsc, struct msgb *msg); void bsc_mgcp_clear_endpoints_for(struct bsc_connection *bsc); diff --git a/openbsc/src/nat/bsc_mgcp_utils.c b/openbsc/src/nat/bsc_mgcp_utils.c index d8ec29869..1728a41e7 100644 --- a/openbsc/src/nat/bsc_mgcp_utils.c +++ b/openbsc/src/nat/bsc_mgcp_utils.c @@ -196,6 +196,9 @@ void bsc_mgcp_dlcx(struct sccp_connections *con) { /* send a DLCX down the stream */ if (con->bsc_endp != -1) { + if (con->bsc->endpoint_status[con->bsc_endp] != 1) + LOGP(DNAT, LOGL_ERROR, "Endpoint 0x%x was not in use\n", con->bsc_endp); + con->bsc->endpoint_status[con->bsc_endp] = 0; bsc_mgcp_send_dlcx(con->bsc, con->bsc_endp); bsc_mgcp_free_endpoint(con->bsc->nat, con->msc_endp); } @@ -269,7 +272,7 @@ int bsc_mgcp_policy_cb(struct mgcp_config *cfg, int endpoint, int state, const c } /* we need to generate a new and patched message */ - bsc_msg = bsc_mgcp_rewrite((char *) nat->mgcp_msg, nat->mgcp_length, + bsc_msg = bsc_mgcp_rewrite((char *) nat->mgcp_msg, nat->mgcp_length, sccp->bsc_endp, nat->mgcp_cfg->source_addr, mgcp_endp->bts_end.local_port); if (!bsc_msg) { LOGP(DMGCP, LOGL_ERROR, "Failed to patch the msg.\n"); @@ -401,7 +404,7 @@ void bsc_mgcp_forward(struct bsc_connection *bsc, struct msgb *msg) * there should be nothing for us to rewrite so putting endp->rtp_port * with the value of 0 should be no problem. */ - output = bsc_mgcp_rewrite((char * ) msg->l2h, msgb_l2len(msg), + output = bsc_mgcp_rewrite((char * ) msg->l2h, msgb_l2len(msg), -1, bsc->nat->mgcp_cfg->source_addr, endp->net_end.local_port); if (!output) { @@ -438,9 +441,28 @@ uint32_t bsc_mgcp_extract_ci(const char *str) return ci; } +static void patch_mgcp(struct msgb *output, const char *op, const char *tok, + int endp, int len, int cr) +{ + int slen; + int ret; + char buf[40]; + + buf[0] = buf[39] = '\0'; + ret = sscanf(tok, "%*s %s", buf); + + slen = sprintf((char *) output->l3h, "%s %s %x@mgw MGCP 1.0%s", + op, buf, endp, cr ? "\r\n" : "\n"); + output->l3h = msgb_put(output, slen); +} + /* we need to replace some strings... */ -struct msgb *bsc_mgcp_rewrite(char *input, int length, const char *ip, int port) +struct msgb *bsc_mgcp_rewrite(char *input, int length, int endpoint, const char *ip, int port) { + static const char *crcx_str = "CRCX "; + static const char *dlcx_str = "DLCX "; + static const char *mdcx_str = "MDCX "; + static const char *ip_str = "c=IN IP4 "; static const char *aud_str = "m=audio "; @@ -461,11 +483,18 @@ struct msgb *bsc_mgcp_rewrite(char *input, int length, const char *ip, int port) running = input; output->l2h = output->data; + output->l3h = output->l2h; for (token = strsep(&running, "\n"); running; token = strsep(&running, "\n")) { int len = strlen(token); int cr = len > 0 && token[len - 1] == '\r'; - if (strncmp(ip_str, token, (sizeof ip_str) - 1) == 0) { + if (strncmp(crcx_str, token, (sizeof crcx_str) - 1) == 0) { + patch_mgcp(output, "CRCX", token, endpoint, len, cr); + } else if (strncmp(dlcx_str, token, (sizeof dlcx_str) - 1) == 0) { + patch_mgcp(output, "DLCX", token, endpoint, len, cr); + } else if (strncmp(mdcx_str, token, (sizeof mdcx_str) - 1) == 0) { + patch_mgcp(output, "MDCX", token, endpoint, len, cr); + } else if (strncmp(ip_str, token, (sizeof ip_str) - 1) == 0) { output->l3h = msgb_put(output, strlen(ip_str)); memcpy(output->l3h, ip_str, strlen(ip_str)); output->l3h = msgb_put(output, strlen(ip)); diff --git a/openbsc/tests/bsc-nat/bsc_data.c b/openbsc/tests/bsc-nat/bsc_data.c index 6700b0ca2..a3239799c 100644 --- a/openbsc/tests/bsc-nat/bsc_data.c +++ b/openbsc/tests/bsc-nat/bsc_data.c @@ -94,7 +94,7 @@ static const uint8_t ass_cmd[] = { /* nothing to patch */ static const char crcx[] = "CRCX 23265295 8@mgw MGCP 1.0\r\nC: 394b0439fb\r\nL: p:20, a:AMR, nt:IN\r\nM: recvonly\r\n"; -static const char crcx_patched[] = "CRCX 23265295 8@mgw MGCP 1.0\r\nC: 394b0439fb\r\nL: p:20, a:AMR, nt:IN\r\nM: recvonly\r\n"; +static const char crcx_patched[] = "CRCX 23265295 1e@mgw MGCP 1.0\r\nC: 394b0439fb\r\nL: p:20, a:AMR, nt:IN\r\nM: recvonly\r\n"; /* patch the ip and port */ @@ -102,8 +102,8 @@ static const char crcx_resp[] = "200 23265295\r\nI: 1\r\n\r\nv=0\r\nc=IN IP4 172 static const char crcx_resp_patched[] = "200 23265295\r\nI: 1\r\n\r\nv=0\r\nc=IN IP4 10.0.0.1\r\nm=audio 999 RTP/AVP 98\r\na=rtpmap:98 AMR/8000\r\n"; /* patch the ip and port */ -static const char mdcx[] = " MDCX 23330829 8@mgw MGCP 1.0\r\nC: 394b0439fb\r\nI: 1\r\nL: p:20, a:AMR, nt:IN\r\nM: recvonly\r\n\r\nv=0\r\no=- 1049380491 0 IN IP4 172.16.18.2\r\ns=-\r\nc=IN IP4 172.16.18.2\r\nt=0 0\r\nm=audio 4410 RTP/AVP 126\r\na=rtpmap:126 AMR/8000/1\r\na=fmtp:126 mode-set=2;start-mode=0\r\na=ptime:20\r\na=recvonly\r\nm=image 4412 udptl t38\r\na=T38FaxVersion:0\r\na=T38MaxBitRate:14400\r\n"; -static const char mdcx_patched[] = " MDCX 23330829 8@mgw MGCP 1.0\r\nC: 394b0439fb\r\nI: 1\r\nL: p:20, a:AMR, nt:IN\r\nM: recvonly\r\n\r\nv=0\r\no=- 1049380491 0 IN IP4 172.16.18.2\r\ns=-\r\nc=IN IP4 10.0.0.23\r\nt=0 0\r\nm=audio 6666 RTP/AVP 126\r\na=rtpmap:126 AMR/8000/1\r\na=fmtp:126 mode-set=2;start-mode=0\r\na=ptime:20\r\na=recvonly\r\nm=image 4412 udptl t38\r\na=T38FaxVersion:0\r\na=T38MaxBitRate:14400\r\n"; +static const char mdcx[] = "MDCX 23330829 8@mgw MGCP 1.0\r\nC: 394b0439fb\r\nI: 1\r\nL: p:20, a:AMR, nt:IN\r\nM: recvonly\r\n\r\nv=0\r\no=- 1049380491 0 IN IP4 172.16.18.2\r\ns=-\r\nc=IN IP4 172.16.18.2\r\nt=0 0\r\nm=audio 4410 RTP/AVP 126\r\na=rtpmap:126 AMR/8000/1\r\na=fmtp:126 mode-set=2;start-mode=0\r\na=ptime:20\r\na=recvonly\r\nm=image 4412 udptl t38\r\na=T38FaxVersion:0\r\na=T38MaxBitRate:14400\r\n"; +static const char mdcx_patched[] = "MDCX 23330829 1e@mgw MGCP 1.0\r\nC: 394b0439fb\r\nI: 1\r\nL: p:20, a:AMR, nt:IN\r\nM: recvonly\r\n\r\nv=0\r\no=- 1049380491 0 IN IP4 172.16.18.2\r\ns=-\r\nc=IN IP4 10.0.0.23\r\nt=0 0\r\nm=audio 6666 RTP/AVP 126\r\na=rtpmap:126 AMR/8000/1\r\na=fmtp:126 mode-set=2;start-mode=0\r\na=ptime:20\r\na=recvonly\r\nm=image 4412 udptl t38\r\na=T38FaxVersion:0\r\na=T38MaxBitRate:14400\r\n"; static const char mdcx_resp[] = "200 23330829\r\n\r\nv=0\r\nc=IN IP4 172.16.18.2\r\nm=audio 4002 RTP/AVP 98\r\na=rtpmap:98 AMR/8000\r\n"; diff --git a/openbsc/tests/bsc-nat/bsc_nat_test.c b/openbsc/tests/bsc-nat/bsc_nat_test.c index acc5de343..8f4e2d152 100644 --- a/openbsc/tests/bsc-nat/bsc_nat_test.c +++ b/openbsc/tests/bsc-nat/bsc_nat_test.c @@ -521,7 +521,7 @@ static void test_mgcp_rewrite(void) char *input = strdup(orig); - output = bsc_mgcp_rewrite(input, strlen(input), ip, port); + output = bsc_mgcp_rewrite(input, strlen(input), 0x1e, ip, port); if (msgb_l2len(output) != strlen(patc)) { fprintf(stderr, "Wrong sizes for test: %d %d != %d != %d\n", i, msgb_l2len(output), strlen(patc), strlen(orig)); fprintf(stderr, "String '%s' vs '%s'\n", (const char *) output->l2h, patc); -- cgit v1.2.3 From 85902a4d4a53094e8ab4cb242e8de1f6ce431f9e Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Wed, 1 Sep 2010 09:31:46 +0800 Subject: nat: We have 1 to 31 available to the BSC. --- openbsc/include/openbsc/bsc_nat.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'openbsc') diff --git a/openbsc/include/openbsc/bsc_nat.h b/openbsc/include/openbsc/bsc_nat.h index 25b6429c4..0c9af9184 100644 --- a/openbsc/include/openbsc/bsc_nat.h +++ b/openbsc/include/openbsc/bsc_nat.h @@ -76,7 +76,7 @@ struct bsc_connection { struct timer_list pong_timeout; /* mgcp related code */ - int endpoint_status[33]; + int endpoint_status[32]; int last_endpoint; /* a back pointer */ -- cgit v1.2.3