fixeria has submitted this change. (
https://gerrit.osmocom.org/c/osmo-bsc/+/28327 )
Change subject: lchan_select: allow different alloc order for assignment and handover
......................................................................
lchan_select: allow different alloc order for assignment and handover
A follow-up patch implements a special channel allocation mode, which is
only working for assignment (basically TCH selection for a voice call).
This mode cannot be employed for initial CHANNEL REQUEST or handover due
to the absence of an already established lchan.
Adding this mode to the existing VTY command syntax would be confusing:
channel allocator (ascending|desscending|dynamic)
^^^^^^^
so this patch extends the VTY syntax in a way that it becomes possible
to configure different channel allocator modes for different cases:
OsmoBSC(config-net-bts)# channel allocator mode ?
set-all Set a single mode for all variants
chan-req Channel allocation for CHANNEL REQUEST (RACH)
assignment Channel allocation for assignment
handover Channel allocation for handover
The old command syntax, which is basically 'set-all', is kept for
backwards compatibility, but marked as deprecated.
Change-Id: I3ae73b36ee9433cc768376b56f0765e5f416162f
Related: SYS#5460
---
M doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus01-4trx.cfg
M doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus02-4trx.cfg
M doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus02-8trx.cfg
M doc/examples/osmo-bsc/ericsson/osmo-bsc.rbs2308.cfg
M doc/examples/osmo-bsc/osmo-bsc-4trx.cfg
M doc/examples/osmo-bsc/osmo-bsc.cfg
M doc/examples/osmo-bsc/osmo-bsc_custom-sccp.cfg
M doc/manuals/chapters/bts-examples.adoc
M doc/manuals/chapters/chan_alloc.adoc
M include/osmocom/bsc/bts.h
M include/osmocom/bsc/lchan_select.h
M src/osmo-bsc/abis_rsl.c
M src/osmo-bsc/assignment_fsm.c
M src/osmo-bsc/bsc_vty.c
M src/osmo-bsc/bts_vty.c
M src/osmo-bsc/handover_decision_2.c
M src/osmo-bsc/handover_fsm.c
M src/osmo-bsc/lchan_select.c
M tests/ctrl/osmo-bsc-apply-config-file.cfg
M tests/ctrl/osmo-bsc-neigh-test.cfg
M tests/handover/handover_test.c
M tests/handover/test_dyn_ts_favor_static_ts_as_target.ho_vty
M tests/osmo-bsc.vty
23 files changed, 187 insertions(+), 67 deletions(-)
Approvals:
laforge: Looks good to me, but someone else must approve
fixeria: Looks good to me, approved
osmith: Looks good to me, but someone else must approve
Jenkins Builder: Verified
diff --git a/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus01-4trx.cfg
b/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus01-4trx.cfg
index 68837ca..8ef1619 100644
--- a/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus01-4trx.cfg
+++ b/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus01-4trx.cfg
@@ -39,7 +39,7 @@
ms max power 15
cell reselection hysteresis 4
rxlev access min 0
- channel allocator descending
+ channel allocator mode set-all descending
rach tx integer 9
rach max transmission 7
oml e1 line 0 timeslot 1 sub-slot full
diff --git a/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus02-4trx.cfg
b/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus02-4trx.cfg
index ae0b7db..7c9b847 100644
--- a/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus02-4trx.cfg
+++ b/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus02-4trx.cfg
@@ -39,7 +39,7 @@
ms max power 15
cell reselection hysteresis 4
rxlev access min 0
- channel allocator descending
+ channel allocator mode set-all descending
rach tx integer 9
rach max transmission 7
oml e1 line 0 timeslot 1 sub-slot full
diff --git a/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus02-8trx.cfg
b/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus02-8trx.cfg
index ff0b277..6db88b5 100644
--- a/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus02-8trx.cfg
+++ b/doc/examples/osmo-bsc/ericsson/osmo-bsc.dug20-rus02-8trx.cfg
@@ -39,7 +39,7 @@
ms max power 15
cell reselection hysteresis 4
rxlev access min 0
- channel allocator descending
+ channel allocator mode set-all descending
rach tx integer 9
rach max transmission 7
oml e1 line 0 timeslot 1 sub-slot full
diff --git a/doc/examples/osmo-bsc/ericsson/osmo-bsc.rbs2308.cfg
b/doc/examples/osmo-bsc/ericsson/osmo-bsc.rbs2308.cfg
index f79d457..a90cfa1 100644
--- a/doc/examples/osmo-bsc/ericsson/osmo-bsc.rbs2308.cfg
+++ b/doc/examples/osmo-bsc/ericsson/osmo-bsc.rbs2308.cfg
@@ -45,7 +45,7 @@
ms max power 33
cell reselection hysteresis 4
rxlev access min 0
- channel allocator descending
+ channel allocator mode set-all descending
rach tx integer 9
rach max transmission 7
oml e1 line 0 timeslot 1 sub-slot full
diff --git a/doc/examples/osmo-bsc/osmo-bsc-4trx.cfg
b/doc/examples/osmo-bsc/osmo-bsc-4trx.cfg
index 68d6a38..206a3c7 100644
--- a/doc/examples/osmo-bsc/osmo-bsc-4trx.cfg
+++ b/doc/examples/osmo-bsc/osmo-bsc-4trx.cfg
@@ -17,7 +17,7 @@
cell reselection hysteresis 4
rxlev access min 0
radio-link-timeout 32
- channel allocator ascending
+ channel allocator mode set-all ascending
rach tx integer 9
rach max transmission 7
channel-description attach 1
diff --git a/doc/examples/osmo-bsc/osmo-bsc.cfg b/doc/examples/osmo-bsc/osmo-bsc.cfg
index c86a491..22afa07 100644
--- a/doc/examples/osmo-bsc/osmo-bsc.cfg
+++ b/doc/examples/osmo-bsc/osmo-bsc.cfg
@@ -29,7 +29,7 @@
cell reselection hysteresis 4
rxlev access min 0
radio-link-timeout 32
- channel allocator ascending
+ channel allocator mode set-all ascending
rach tx integer 9
rach max transmission 7
channel-description attach 1
diff --git a/doc/examples/osmo-bsc/osmo-bsc_custom-sccp.cfg
b/doc/examples/osmo-bsc/osmo-bsc_custom-sccp.cfg
index e60f39a..21187c7 100644
--- a/doc/examples/osmo-bsc/osmo-bsc_custom-sccp.cfg
+++ b/doc/examples/osmo-bsc/osmo-bsc_custom-sccp.cfg
@@ -28,7 +28,7 @@
cell reselection hysteresis 4
rxlev access min 0
radio-link-timeout 32
- channel allocator ascending
+ channel allocator mode set-all ascending
rach tx integer 9
rach max transmission 7
channel-description attach 1
diff --git a/doc/manuals/chapters/bts-examples.adoc
b/doc/manuals/chapters/bts-examples.adoc
index 836dec0..2afc8ff 100644
--- a/doc/manuals/chapters/bts-examples.adoc
+++ b/doc/manuals/chapters/bts-examples.adoc
@@ -32,7 +32,7 @@
ms max power 15
cell reselection hysteresis 4
rxlev access min 0
- channel allocator ascending
+ channel allocator mode set-all ascending
rach tx integer 9
rach max transmission 7
ipa unit-id 1801 0 <4>
@@ -110,7 +110,7 @@
ms max power 15
cell reselection hysteresis 4
rxlev access min 0
- channel allocator ascending
+ channel allocator mode set-all ascending
rach tx integer 9
rach max transmission 7
ipa unit-id 1800 0 <1>
@@ -203,7 +203,7 @@
ms max power 15
cell reselection hysteresis 4
rxlev access min 0
- channel allocator ascending
+ channel allocator mode set-all ascending
rach tx integer 9
rach max transmission 7
oml e1 line 0 timeslot 1 sub-slot full <3>
diff --git a/doc/manuals/chapters/chan_alloc.adoc b/doc/manuals/chapters/chan_alloc.adoc
index d995124..b6b7b92 100644
--- a/doc/manuals/chapters/chan_alloc.adoc
+++ b/doc/manuals/chapters/chan_alloc.adoc
@@ -19,7 +19,9 @@
----
network
bts 0
- channel allocator ascending
+ channel allocator mode chan-req ascending
+ channel allocator mode assignment ascending
+ channel allocator mode handover ascending
channel allocator avoid-interference 0
channel allocator tch-signalling-policy always
----
@@ -41,10 +43,21 @@
The allocation mode to be used can be configured using the following VTY command:
----
-OsmoBSC(config-net-bts)# channel allocator ?
- ascending Allocate Timeslots and Transceivers in ascending order
- descending Allocate Timeslots and Transceivers in descending order
+OsmoBSC(config-net-bts)# channel allocator mode ? <1>
+ set-all Set a single mode for all variants
+ chan-req Channel allocation for CHANNEL REQUEST (RACH)
+ assignment Channel allocation for assignment
+ handover Channel allocation for handover
+
+OsmoBSC(config-net-bts)# channel allocator mode set-all ? <2>
+ ascending Allocate Timeslots and Transceivers in ascending order
+ descending Allocate Timeslots and Transceivers in descending order
----
+<1> It's optionally possible to configure different allocation modes for
+different allocation causes, e.g. `ascending` for `chan-req` and `descending`
+for both `assignment` and `handover`.
+<2> `set-all` is equivalent to the old (deprecated) command syntax:
+`channel allocator (ascending|descending)`.
==== Interference aware channel allocation
diff --git a/include/osmocom/bsc/bts.h b/include/osmocom/bsc/bts.h
index 8abcf13..76945a1 100644
--- a/include/osmocom/bsc/bts.h
+++ b/include/osmocom/bsc/bts.h
@@ -517,7 +517,9 @@
/* should the channel allocator allocate channels from high TRX to TRX0,
* rather than starting from TRX0 and go upwards? */
- int chan_alloc_reverse;
+ bool chan_alloc_chan_req_reverse;
+ bool chan_alloc_assignment_reverse;
+ bool chan_alloc_handover_reverse;
/* When true, interference measurements from the BTS are used in the channel allocator
to favor lchans with less
* interference reported in RSL Resource Indication. */
diff --git a/include/osmocom/bsc/lchan_select.h b/include/osmocom/bsc/lchan_select.h
index 3bb0d1c..b5eb078 100644
--- a/include/osmocom/bsc/lchan_select.h
+++ b/include/osmocom/bsc/lchan_select.h
@@ -1,9 +1,24 @@
/* Select a suitable lchan from a given cell. */
#pragma once
-struct gsm_lchan *lchan_select_by_type(struct gsm_bts *bts, enum gsm_chan_t type);
+enum lchan_select_reason {
+ SELECT_FOR_MS_CHAN_REQ,
+ SELECT_FOR_ASSIGNMENT,
+ SELECT_FOR_HANDOVER,
+};
+
+extern const struct value_string lchan_select_reason_names[];
+static inline const char *lchan_select_reason_name(enum lchan_select_reason reason)
+{ return get_value_string(lchan_select_reason_names, reason); }
+
+struct gsm_lchan *lchan_select_by_type(struct gsm_bts *bts,
+ enum gsm_chan_t type,
+ enum lchan_select_reason reason);
enum gsm_chan_t chan_mode_to_chan_type(enum gsm48_chan_mode chan_mode, enum channel_rate
chan_rate);
struct gsm_lchan *lchan_select_by_chan_mode(struct gsm_bts *bts,
- enum gsm48_chan_mode chan_mode, enum channel_rate chan_rate);
-struct gsm_lchan *lchan_avail_by_type(struct gsm_bts *bts, enum gsm_chan_t type, bool
log);
+ enum gsm48_chan_mode chan_mode,
+ enum channel_rate chan_rate,
+ enum lchan_select_reason reason);
+struct gsm_lchan *lchan_avail_by_type(struct gsm_bts *bts, enum gsm_chan_t type,
+ enum lchan_select_reason reason, bool log);
void lchan_select_set_type(struct gsm_lchan *lchan, enum gsm_chan_t type);
diff --git a/src/osmo-bsc/abis_rsl.c b/src/osmo-bsc/abis_rsl.c
index f6215d9..7f88096 100644
--- a/src/osmo-bsc/abis_rsl.c
+++ b/src/osmo-bsc/abis_rsl.c
@@ -1978,10 +1978,10 @@
ts_for_n_lchans(lchan, ts, ts->max_primary_lchans) {
if (lchan->type == GSM_LCHAN_TCH_F || lchan->type == GSM_LCHAN_TCH_H) {
if (lchan->fi->state == LCHAN_ST_ESTABLISHED) {
- if (!lchan_est || bts->chan_alloc_reverse)
+ if (!lchan_est || bts->chan_alloc_chan_req_reverse)
lchan_est = lchan;
} else {
- if (!lchan_any || bts->chan_alloc_reverse)
+ if (!lchan_any || bts->chan_alloc_chan_req_reverse)
lchan_any = lchan;
}
}
@@ -2007,12 +2007,12 @@
/* First check the situation on the BTS, if we have TCH/H or TCH/F resources available
for another (EMERGENCY)
* call. If yes, then no (further) action has to be carried out. */
- if (lchan_avail_by_type(rqd->bts, GSM_LCHAN_TCH_F, true)) {
+ if (lchan_avail_by_type(rqd->bts, GSM_LCHAN_TCH_F, SELECT_FOR_MS_CHAN_REQ, true)) {
LOG_BTS(rqd->bts, DRSL, LOGL_NOTICE,
"CHAN RQD/EMERGENCY-PRIORITY: at least one TCH/F is (now) available!\n");
return false;
}
- if (lchan_avail_by_type(rqd->bts, GSM_LCHAN_TCH_H, true)) {
+ if (lchan_avail_by_type(rqd->bts, GSM_LCHAN_TCH_H, SELECT_FOR_MS_CHAN_REQ, true)) {
LOG_BTS(rqd->bts, DRSL, LOGL_NOTICE,
"CHAN RQD/EMERGENCY-PRIORITY: at least one TCH/H is (now) available!\n");
return false;
@@ -2083,7 +2083,7 @@
int free_tchf, free_tchh;
bool needs_dyn_switch;
- lchan = lchan_avail_by_type(bts, GSM_LCHAN_SDCCH, false);
+ lchan = lchan_avail_by_type(bts, GSM_LCHAN_SDCCH, SELECT_FOR_MS_CHAN_REQ, false);
if (!lchan)
return NULL;
@@ -2172,7 +2172,8 @@
if (rqd->reason == GSM_CHREQ_REASON_CALL) {
lchan = _select_sdcch_for_call(bts, rqd, lctype);
} else if (rqd->reason != GSM_CHREQ_REASON_EMERG) {
- lchan = lchan_select_by_type(bts, GSM_LCHAN_SDCCH);
+ lchan = lchan_select_by_type(bts, GSM_LCHAN_SDCCH,
+ SELECT_FOR_MS_CHAN_REQ);
}
/* else: Emergency calls will be put on a free TCH/H or TCH/F directly
* in the code below, all other channel requests will get an SDCCH first
@@ -2187,13 +2188,15 @@
LOG_BTS(bts, DRSL, LOGL_NOTICE, "CHAN RQD[%s]: no resources for %s 0x%x, retrying
with %s\n",
get_value_string(gsm_chreq_descs, rqd->reason), gsm_lchant_name(GSM_LCHAN_SDCCH),
rqd->ref.ra, gsm_lchant_name(GSM_LCHAN_TCH_H));
- lchan = lchan_select_by_type(bts, GSM_LCHAN_TCH_H);
+ lchan = lchan_select_by_type(bts, GSM_LCHAN_TCH_H,
+ SELECT_FOR_MS_CHAN_REQ);
}
if (!lchan) {
LOG_BTS(bts, DRSL, LOGL_NOTICE, "CHAN RQD[%s]: no resources for %s 0x%x, retrying
with %s\n",
get_value_string(gsm_chreq_descs, rqd->reason), gsm_lchant_name(GSM_LCHAN_SDCCH),
rqd->ref.ra, gsm_lchant_name(GSM_LCHAN_TCH_F));
- lchan = lchan_select_by_type(bts, GSM_LCHAN_TCH_F);
+ lchan = lchan_select_by_type(bts, GSM_LCHAN_TCH_F,
+ SELECT_FOR_MS_CHAN_REQ);
}
}
if (!lchan) {
diff --git a/src/osmo-bsc/assignment_fsm.c b/src/osmo-bsc/assignment_fsm.c
index a0d008d..209545f 100644
--- a/src/osmo-bsc/assignment_fsm.c
+++ b/src/osmo-bsc/assignment_fsm.c
@@ -604,7 +604,9 @@
/* Try to allocate a new lchan in order of preference */
for (i = 0; i < req->n_ch_mode_rate; i++) {
conn->assignment.new_lchan = lchan_select_by_chan_mode(bts,
- req->ch_mode_rate_list[i].chan_mode, req->ch_mode_rate_list[i].chan_rate);
+ req->ch_mode_rate_list[i].chan_mode,
+ req->ch_mode_rate_list[i].chan_rate,
+ SELECT_FOR_ASSIGNMENT);
if (!conn->assignment.new_lchan)
continue;
LOG_ASSIGNMENT(conn, LOGL_DEBUG, "selected new lchan %s for mode[%d] = %s
channel_rate=%d\n",
diff --git a/src/osmo-bsc/bsc_vty.c b/src/osmo-bsc/bsc_vty.c
index 5b46e79..0df5712 100644
--- a/src/osmo-bsc/bsc_vty.c
+++ b/src/osmo-bsc/bsc_vty.c
@@ -770,7 +770,9 @@
{
LOG_LCHAN(from_lchan, LOGL_NOTICE, "Manually triggering Assignment from
VTY\n");
if (!to_lchan) {
- to_lchan = lchan_select_by_type(from_lchan->ts->trx->bts,
from_lchan->type);
+ struct gsm_bts *bts = from_lchan->ts->trx->bts;
+ to_lchan = lchan_select_by_type(bts, from_lchan->type,
+ SELECT_FOR_ASSIGNMENT);
vty_out(vty, "Error: cannot find free lchan of type %s%s",
gsm_lchant_name(from_lchan->type), VTY_NEWLINE);
}
@@ -955,7 +957,8 @@
continue;
llist_for_each_entry(trx, &bts->trx_list, list) {
- struct gsm_lchan *lchan = lchan_select_by_type(bts, free_type);
+ struct gsm_lchan *lchan = lchan_select_by_type(bts, free_type,
+ SELECT_FOR_HANDOVER);
if (!lchan)
continue;
diff --git a/src/osmo-bsc/bts_vty.c b/src/osmo-bsc/bts_vty.c
index c23c14e..1a9b1e3 100644
--- a/src/osmo-bsc/bts_vty.c
+++ b/src/osmo-bsc/bts_vty.c
@@ -533,20 +533,51 @@
"Channel Allocator\n" \
"Channel Allocator\n"
-DEFUN_ATTR(cfg_bts_challoc,
- cfg_bts_challoc_cmd,
- CHAN_ALLOC_CMD " (ascending|descending)",
- CHAN_ALLOC_DESC
- "Allocate Timeslots and Transceivers in ascending order\n"
- "Allocate Timeslots and Transceivers in descending order\n",
- CMD_ATTR_IMMEDIATE)
+#define CHAN_ALLOC_ASC_DSC "(ascending|descending)"
+#define CHAN_ALLOC_ASC_DSC_DESC \
+ "Allocate Timeslots and Transceivers in ascending order\n" \
+ "Allocate Timeslots and Transceivers in descending order\n"
+
+DEFUN_ATTR(cfg_bts_challoc_mode_all,
+ cfg_bts_challoc_mode_all_cmd,
+ CHAN_ALLOC_CMD " " CHAN_ALLOC_ASC_DSC,
+ CHAN_ALLOC_DESC CHAN_ALLOC_ASC_DSC_DESC,
+ CMD_ATTR_IMMEDIATE | CMD_ATTR_DEPRECATED)
{
+ bool reverse = !strcmp(argv[0], "descending");
struct gsm_bts *bts = vty->index;
- if (!strcmp(argv[0], "ascending"))
- bts->chan_alloc_reverse = 0;
- else
- bts->chan_alloc_reverse = 1;
+ bts->chan_alloc_chan_req_reverse = reverse;
+ bts->chan_alloc_assignment_reverse = reverse;
+ bts->chan_alloc_handover_reverse = reverse;
+
+ return CMD_SUCCESS;
+}
+
+DEFUN_ATTR(cfg_bts_challoc_mode,
+ cfg_bts_challoc_mode_cmd,
+ CHAN_ALLOC_CMD
+ " mode (set-all|chan-req|assignment|handover) "
+ CHAN_ALLOC_ASC_DSC,
+ CHAN_ALLOC_DESC
+ "Channel allocation mode\n"
+ "Set a single mode for all variants\n"
+ "Channel allocation for CHANNEL REQUEST (RACH)\n"
+ "Channel allocation for assignment\n"
+ "Channel allocation for handover\n"
+ CHAN_ALLOC_ASC_DSC_DESC,
+ CMD_ATTR_IMMEDIATE)
+{
+ bool reverse = !strcmp(argv[1], "descending");
+ bool set_all = !strcmp(argv[0], "set-all");
+ struct gsm_bts *bts = vty->index;
+
+ if (set_all || !strcmp(argv[0], "chan-req"))
+ bts->chan_alloc_chan_req_reverse = reverse;
+ if (set_all || !strcmp(argv[0], "assignment"))
+ bts->chan_alloc_assignment_reverse = reverse;
+ if (set_all || !strcmp(argv[0], "handover"))
+ bts->chan_alloc_handover_reverse = reverse;
return CMD_SUCCESS;
}
@@ -4212,8 +4243,14 @@
vty_out(vty, " radio-link-timeout %d%s",
gsm_bts_get_radio_link_timeout(bts), VTY_NEWLINE);
- vty_out(vty, " channel allocator %s%s",
- bts->chan_alloc_reverse ? "descending" : "ascending",
+ vty_out(vty, " channel allocator mode chan-req %s%s",
+ bts->chan_alloc_chan_req_reverse ? "descending" : "ascending",
+ VTY_NEWLINE);
+ vty_out(vty, " channel allocator mode assignment %s%s",
+ bts->chan_alloc_assignment_reverse ? "descending" :
"ascending",
+ VTY_NEWLINE);
+ vty_out(vty, " channel allocator mode handover %s%s",
+ bts->chan_alloc_handover_reverse ? "descending" : "ascending",
VTY_NEWLINE);
if (bts->chan_alloc_avoid_interf)
vty_out(vty, " channel allocator avoid-interference 1%s", VTY_NEWLINE);
@@ -4543,7 +4580,8 @@
install_element(BTS_NODE, &cfg_bts_deprecated_stream_id_cmd);
install_element(BTS_NODE, &cfg_bts_oml_e1_cmd);
install_element(BTS_NODE, &cfg_bts_oml_e1_tei_cmd);
- install_element(BTS_NODE, &cfg_bts_challoc_cmd);
+ install_element(BTS_NODE, &cfg_bts_challoc_mode_cmd);
+ install_element(BTS_NODE, &cfg_bts_challoc_mode_all_cmd);
install_element(BTS_NODE, &cfg_bts_chan_alloc_interf_cmd);
install_element(BTS_NODE, &cfg_bts_chan_alloc_tch_signalling_policy_cmd);
install_element(BTS_NODE, &cfg_bts_chan_alloc_allow_tch_for_signalling_cmd);
diff --git a/src/osmo-bsc/handover_decision_2.c b/src/osmo-bsc/handover_decision_2.c
index a1a8ffa..3c4b3ba 100644
--- a/src/osmo-bsc/handover_decision_2.c
+++ b/src/osmo-bsc/handover_decision_2.c
@@ -1050,7 +1050,7 @@
/* Would the next TCH/F lchan occupy a dynamic timeslot that currently counts for free
TCH/H timeslots?
*/
- next_lchan = lchan_avail_by_type(c->target.bts, GSM_LCHAN_TCH_F, false);
+ next_lchan = lchan_avail_by_type(c->target.bts, GSM_LCHAN_TCH_F,
SELECT_FOR_HANDOVER, false);
if (next_lchan && next_lchan->ts->pchan_on_init == GSM_PCHAN_OSMO_DYN)
c->target.next_tchf_reduces_tchh = 2;
else
@@ -1058,7 +1058,7 @@
/* Would the next TCH/H lchan occupy a dynamic timeslot that currently counts for free
TCH/F timeslots?
* Note that a dyn TS already in TCH/H mode (half occupied) would not reduce free
TCH/F. */
- next_lchan = lchan_avail_by_type(c->target.bts, GSM_LCHAN_TCH_H, false);
+ next_lchan = lchan_avail_by_type(c->target.bts, GSM_LCHAN_TCH_H,
SELECT_FOR_HANDOVER, false);
if (next_lchan && next_lchan->ts->pchan_on_init == GSM_PCHAN_OSMO_DYN
&& next_lchan->ts->pchan_is != GSM_PCHAN_TCH_H)
c->target.next_tchh_reduces_tchf = 1;
diff --git a/src/osmo-bsc/handover_fsm.c b/src/osmo-bsc/handover_fsm.c
index a4221c4..0797bf3 100644
--- a/src/osmo-bsc/handover_fsm.c
+++ b/src/osmo-bsc/handover_fsm.c
@@ -379,7 +379,9 @@
ho->async = true;
gsm_bts_cell_id_list(&ho->target_cell_ids, ho->new_bts);
- ho->new_lchan = lchan_select_by_type(ho->new_bts, ho->new_lchan_type);
+ ho->new_lchan = lchan_select_by_type(ho->new_bts,
+ ho->new_lchan_type,
+ SELECT_FOR_HANDOVER);
if (ho->scope & HO_INTRA_CELL) {
ho_count(bts, CTR_INTRA_CELL_HO_ATTEMPTED);
@@ -696,7 +698,10 @@
ch_mode_rate.chan_rate == CH_RATE_FULL ? "full-rate" :
"half-rate",
gsm0808_channel_type_name(&req->ct));
- lchan = lchan_select_by_chan_mode(bts, ch_mode_rate.chan_mode,
ch_mode_rate.chan_rate);
+ lchan = lchan_select_by_chan_mode(bts,
+ ch_mode_rate.chan_mode,
+ ch_mode_rate.chan_rate,
+ SELECT_FOR_HANDOVER);
if (!lchan) {
LOG_HO(conn, LOGL_DEBUG, "BTS %u has no matching free channels\n",
bts->nr);
continue;
diff --git a/src/osmo-bsc/lchan_select.c b/src/osmo-bsc/lchan_select.c
index a322f07..8b6da40 100644
--- a/src/osmo-bsc/lchan_select.c
+++ b/src/osmo-bsc/lchan_select.c
@@ -35,6 +35,13 @@
unsigned int num;
};
+const struct value_string lchan_select_reason_names[] = {
+ OSMO_VALUE_STRING(SELECT_FOR_MS_CHAN_REQ),
+ OSMO_VALUE_STRING(SELECT_FOR_ASSIGNMENT),
+ OSMO_VALUE_STRING(SELECT_FOR_HANDOVER),
+ {0, NULL}
+};
+
static struct gsm_lchan *pick_better_lchan(struct gsm_lchan *a, struct gsm_lchan *b)
{
if (!a)
@@ -190,6 +197,7 @@
static void populate_ts_list(struct lchan_select_ts_list *ts_list,
struct gsm_bts *bts,
+ bool chan_alloc_reverse,
bool log)
{
struct gsm_bts_trx *trx;
@@ -208,7 +216,7 @@
ts_list->num = num;
/* Reverse the timeslot list if required */
- if (bts->chan_alloc_reverse) {
+ if (chan_alloc_reverse) {
for (unsigned int tn = 0; tn < num / 2; tn++) {
struct gsm_bts_trx_ts *temp = ts_list->list[tn];
ts_list->list[tn] = ts_list->list[num - tn - 1];
@@ -218,22 +226,40 @@
}
struct gsm_lchan *lchan_select_by_chan_mode(struct gsm_bts *bts,
- enum gsm48_chan_mode chan_mode, enum channel_rate chan_rate)
+ enum gsm48_chan_mode chan_mode,
+ enum channel_rate chan_rate,
+ enum lchan_select_reason reason)
{
enum gsm_chan_t type = chan_mode_to_chan_type(chan_mode, chan_rate);
if (type == GSM_LCHAN_NONE)
return NULL;
- return lchan_select_by_type(bts, type);
+ return lchan_select_by_type(bts, type, reason);
}
-struct gsm_lchan *lchan_avail_by_type(struct gsm_bts *bts, enum gsm_chan_t type, bool
log)
+struct gsm_lchan *lchan_avail_by_type(struct gsm_bts *bts, enum gsm_chan_t type,
+ enum lchan_select_reason reason, bool log)
{
struct gsm_lchan *lchan = NULL;
enum gsm_phys_chan_config first, first_cbch, second, second_cbch;
struct lchan_select_ts_list ts_list;
+ bool chan_alloc_reverse;
- if (log)
- LOG_BTS(bts, DRLL, LOGL_DEBUG, "lchan_avail_by_type(%s)\n",
gsm_lchant_name(type));
+ if (log) {
+ LOG_BTS(bts, DRLL, LOGL_DEBUG, "lchan_avail_by_type(type=%s, reason=%s)\n",
+ gsm_lchant_name(type), lchan_select_reason_name(reason));
+ }
+
+ switch (reason) {
+ case SELECT_FOR_MS_CHAN_REQ:
+ chan_alloc_reverse = bts->chan_alloc_chan_req_reverse;
+ break;
+ case SELECT_FOR_ASSIGNMENT:
+ chan_alloc_reverse = bts->chan_alloc_assignment_reverse;
+ break;
+ case SELECT_FOR_HANDOVER:
+ chan_alloc_reverse = bts->chan_alloc_handover_reverse;
+ break;
+ }
/* Allocate an array with pointers to all timeslots of a BTS */
ts_list.list = talloc_array_ptrtype(bts, ts_list.list, bts->num_trx * 8);
@@ -241,11 +267,11 @@
return NULL;
/* Populate this array with the actual pointers */
- populate_ts_list(&ts_list, bts, log);
+ populate_ts_list(&ts_list, bts, chan_alloc_reverse, log);
switch (type) {
case GSM_LCHAN_SDCCH:
- if (bts->chan_alloc_reverse) {
+ if (chan_alloc_reverse) {
first = GSM_PCHAN_SDCCH8_SACCH8C;
first_cbch = GSM_PCHAN_SDCCH8_SACCH8C_CBCH;
second = GSM_PCHAN_CCCH_SDCCH4;
@@ -302,17 +328,20 @@
/* Return a matching lchan from a specific BTS that is currently available. The next
logical step is
* lchan_activate() on it, which would possibly cause dynamic timeslot pchan switching,
taken care of by
* the lchan and timeslot FSMs. */
-struct gsm_lchan *lchan_select_by_type(struct gsm_bts *bts, enum gsm_chan_t type)
+struct gsm_lchan *lchan_select_by_type(struct gsm_bts *bts,
+ enum gsm_chan_t type,
+ enum lchan_select_reason reason)
{
struct gsm_lchan *lchan = NULL;
- LOG_BTS(bts, DRLL, LOGL_DEBUG, "lchan_select_by_type(%s)\n",
gsm_lchant_name(type));
+ LOG_BTS(bts, DRLL, LOGL_DEBUG, "lchan_select_by_type(type=%s, reason=%s)\n",
+ gsm_lchant_name(type), lchan_select_reason_name(reason));
- lchan = lchan_avail_by_type(bts, type, true);
+ lchan = lchan_avail_by_type(bts, type, reason, true);
if (!lchan) {
- LOG_BTS(bts, DRLL, LOGL_NOTICE, "Failed to select %s channel\n",
- gsm_lchant_name(type));
+ LOG_BTS(bts, DRLL, LOGL_NOTICE, "Failed to select %s channel (%s)\n",
+ gsm_lchant_name(type), lchan_select_reason_name(reason));
return NULL;
}
diff --git a/tests/ctrl/osmo-bsc-apply-config-file.cfg
b/tests/ctrl/osmo-bsc-apply-config-file.cfg
index 1a069ce..0094cd7 100644
--- a/tests/ctrl/osmo-bsc-apply-config-file.cfg
+++ b/tests/ctrl/osmo-bsc-apply-config-file.cfg
@@ -9,7 +9,7 @@
cell reselection hysteresis 4
rxlev access min 0
radio-link-timeout 32
- channel allocator ascending
+ channel allocator mode set-all ascending
rach tx integer 9
rach max transmission 7
channel-description attach 1
diff --git a/tests/ctrl/osmo-bsc-neigh-test.cfg b/tests/ctrl/osmo-bsc-neigh-test.cfg
index 93d7fca..8c04db6 100644
--- a/tests/ctrl/osmo-bsc-neigh-test.cfg
+++ b/tests/ctrl/osmo-bsc-neigh-test.cfg
@@ -35,7 +35,7 @@
cell reselection hysteresis 4
rxlev access min 0
radio-link-timeout 32
- channel allocator ascending
+ channel allocator mode set-all ascending
rach tx integer 9
rach max transmission 7
channel-description attach 1
@@ -92,7 +92,7 @@
cell reselection hysteresis 4
rxlev access min 0
radio-link-timeout 32
- channel allocator ascending
+ channel allocator mode set-all ascending
rach tx integer 9
rach max transmission 7
channel-description attach 1
diff --git a/tests/handover/handover_test.c b/tests/handover/handover_test.c
index d82ba9f..77fa371 100644
--- a/tests/handover/handover_test.c
+++ b/tests/handover/handover_test.c
@@ -488,7 +488,8 @@
{
struct gsm_lchan *lchan;
- lchan = lchan_select_by_type(bts, (full_rate) ? GSM_LCHAN_TCH_F : GSM_LCHAN_TCH_H);
+ lchan = lchan_select_by_type(bts, (full_rate) ? GSM_LCHAN_TCH_F : GSM_LCHAN_TCH_H,
+ SELECT_FOR_HANDOVER);
if (!lchan) {
fprintf(stderr, "No resource for lchan\n");
exit(EXIT_FAILURE);
diff --git a/tests/handover/test_dyn_ts_favor_static_ts_as_target.ho_vty
b/tests/handover/test_dyn_ts_favor_static_ts_as_target.ho_vty
index c50b007..0c55a2c 100644
--- a/tests/handover/test_dyn_ts_favor_static_ts_as_target.ho_vty
+++ b/tests/handover/test_dyn_ts_favor_static_ts_as_target.ho_vty
@@ -3,7 +3,7 @@
network
bts 0
- channel allocator ascending
+ channel allocator mode set-all ascending
set-ts-use trx 0 0 states * TCH/-H TCH/-H TCH/-H TCH/-H TCH/-H TCH/-H *
diff --git a/tests/osmo-bsc.vty b/tests/osmo-bsc.vty
index f2af32b..e0b9bdc 100644
--- a/tests/osmo-bsc.vty
+++ b/tests/osmo-bsc.vty
@@ -166,11 +166,20 @@
allocator Channel Allocator
OsmoBSC(config-net-bts)# channel allocator ?
- ascending Allocate Timeslots and Transceivers in ascending order
- descending Allocate Timeslots and Transceivers in descending order
+ mode Channel allocation mode
avoid-interference Configure whether reported interference levels from RES IND are
used in channel allocation
tch-signalling-policy Configure when TCH/H or TCH/F channels can be used to serve
signalling if SDCCHs are exhausted
+OsmoBSC(config-net-bts)# channel allocator mode ?
+ set-all Set a single mode for all variants
+ chan-req Channel allocation for CHANNEL REQUEST (RACH)
+ assignment Channel allocation for assignment
+ handover Channel allocation for handover
+
+OsmoBSC(config-net-bts)# channel allocator mode set-all ?
+ ascending Allocate Timeslots and Transceivers in ascending order
+ descending Allocate Timeslots and Transceivers in descending order
+
OsmoBSC(config-net-bts)# channel allocator avoid-interference ?
0 Ignore interference levels (default). Always assign lchans in a deterministic
order.
1 In channel allocation, prefer lchans with less interference.
--
To view, visit
https://gerrit.osmocom.org/c/osmo-bsc/+/28327
To unsubscribe, or for help writing mail filters, visit
https://gerrit.osmocom.org/settings
Gerrit-Project: osmo-bsc
Gerrit-Branch: master
Gerrit-Change-Id: I3ae73b36ee9433cc768376b56f0765e5f416162f
Gerrit-Change-Number: 28327
Gerrit-PatchSet: 3
Gerrit-Owner: fixeria <vyanitskiy(a)sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: fixeria <vyanitskiy(a)sysmocom.de>
Gerrit-Reviewer: laforge <laforge(a)osmocom.org>
Gerrit-Reviewer: osmith <osmith(a)sysmocom.de>
Gerrit-CC: pespin <pespin(a)sysmocom.de>
Gerrit-MessageType: merged