2013-02-05 10:45:28 +00:00
|
|
|
/* Scheduler for OsmoBTS-TRX */
|
|
|
|
|
|
|
|
/* (C) 2013 by Andreas Eversberg <jolly@eversberg.eu>
|
2015-04-05 21:12:02 +00:00
|
|
|
* (C) 2015 by Alexander Chemeris <Alexander.Chemeris@fairwaves.co>
|
2016-01-09 20:33:58 +00:00
|
|
|
* (C) 2015 by Harald Welte <laforge@gnumonks.org>
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
* Contributions by sysmocom - s.f.m.c. GmbH
|
2013-02-05 10:45:28 +00:00
|
|
|
*
|
|
|
|
* All Rights Reserved
|
|
|
|
*
|
|
|
|
* This program is free software; you can redistribute it and/or modify
|
|
|
|
* it under the terms of the GNU Affero General Public License as published by
|
|
|
|
* the Free Software Foundation; either version 3 of the License, or
|
|
|
|
* (at your option) any later version.
|
|
|
|
*
|
|
|
|
* This program is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
* GNU General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU Affero General Public License
|
|
|
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
*
|
|
|
|
*/
|
|
|
|
#include <stdlib.h>
|
|
|
|
#include <unistd.h>
|
|
|
|
#include <errno.h>
|
|
|
|
#include <stdint.h>
|
|
|
|
#include <ctype.h>
|
|
|
|
|
|
|
|
#include <osmocom/core/msgb.h>
|
|
|
|
#include <osmocom/core/talloc.h>
|
|
|
|
#include <osmocom/core/bits.h>
|
2019-10-02 15:53:15 +00:00
|
|
|
#include <osmocom/core/utils.h>
|
2020-06-16 14:02:55 +00:00
|
|
|
#include <osmocom/core/rate_ctr.h>
|
|
|
|
#include <osmocom/core/stats.h>
|
2019-06-01 15:54:15 +00:00
|
|
|
|
|
|
|
#include <osmocom/gsm/protocol/gsm_08_58.h>
|
2023-03-05 22:35:16 +00:00
|
|
|
#include <osmocom/gsm/gsm0502.h>
|
2013-02-21 08:27:52 +00:00
|
|
|
#include <osmocom/gsm/a5.h>
|
2013-02-05 10:45:28 +00:00
|
|
|
|
|
|
|
#include <osmo-bts/gsm_data.h>
|
|
|
|
#include <osmo-bts/logging.h>
|
|
|
|
#include <osmo-bts/rsl.h>
|
|
|
|
#include <osmo-bts/l1sap.h>
|
2016-01-09 22:28:57 +00:00
|
|
|
#include <osmo-bts/scheduler.h>
|
|
|
|
#include <osmo-bts/scheduler_backend.h>
|
2020-07-03 14:43:51 +00:00
|
|
|
#include <osmo-bts/bts.h>
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
extern void *tall_bts_ctx;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
static int rts_data_fn(const struct l1sched_ts *l1ts, const struct trx_dl_burst_req *br);
|
|
|
|
static int rts_tchf_fn(const struct l1sched_ts *l1ts, const struct trx_dl_burst_req *br);
|
|
|
|
static int rts_tchh_fn(const struct l1sched_ts *l1ts, const struct trx_dl_burst_req *br);
|
2020-06-28 03:48:50 +00:00
|
|
|
|
2016-01-09 12:26:14 +00:00
|
|
|
/*! \brief Dummy Burst (TS 05.02 Chapter 5.2.6) */
|
2020-06-28 03:48:50 +00:00
|
|
|
const ubit_t _sched_dummy_burst[GSM_BURST_LEN] = {
|
2013-02-05 10:45:28 +00:00
|
|
|
0,0,0,
|
|
|
|
1,1,1,1,1,0,1,1,0,1,1,1,0,1,1,0,0,0,0,0,1,0,1,0,0,1,0,0,1,1,1,0,
|
|
|
|
0,0,0,0,1,0,0,1,0,0,0,1,0,0,0,0,0,0,0,1,1,1,1,1,0,0,0,1,1,1,0,0,
|
|
|
|
0,1,0,1,1,1,0,0,0,1,0,1,1,1,0,0,0,1,0,1,0,1,1,1,0,1,0,0,1,0,1,0,
|
|
|
|
0,0,1,1,0,0,1,1,0,0,1,1,1,0,0,1,1,1,1,0,1,0,0,1,1,1,1,1,0,0,0,1,
|
|
|
|
0,0,1,0,1,1,1,1,1,0,1,0,1,0,
|
|
|
|
0,0,0,
|
|
|
|
};
|
|
|
|
|
2021-05-20 00:27:47 +00:00
|
|
|
/*! Training Sequences for Normal Burst (see 3GPP TS 45.002, section 5.2.3) */
|
|
|
|
const ubit_t _sched_train_seq_gmsk_nb[4][8][26] = {
|
|
|
|
{ /* TSC set 1, table 5.2.3a */
|
|
|
|
{ 0,0,1,0,0,1,0,1,1,1,0,0,0,0,1,0,0,0,1,0,0,1,0,1,1,1 },
|
|
|
|
{ 0,0,1,0,1,1,0,1,1,1,0,1,1,1,1,0,0,0,1,0,1,1,0,1,1,1 },
|
|
|
|
{ 0,1,0,0,0,0,1,1,1,0,1,1,1,0,1,0,0,1,0,0,0,0,1,1,1,0 },
|
|
|
|
{ 0,1,0,0,0,1,1,1,1,0,1,1,0,1,0,0,0,1,0,0,0,1,1,1,1,0 },
|
|
|
|
{ 0,0,0,1,1,0,1,0,1,1,1,0,0,1,0,0,0,0,0,1,1,0,1,0,1,1 },
|
|
|
|
{ 0,1,0,0,1,1,1,0,1,0,1,1,0,0,0,0,0,1,0,0,1,1,1,0,1,0 },
|
|
|
|
{ 1,0,1,0,0,1,1,1,1,1,0,1,1,0,0,0,1,0,1,0,0,1,1,1,1,1 },
|
|
|
|
{ 1,1,1,0,1,1,1,1,0,0,0,1,0,0,1,0,1,1,1,0,1,1,1,1,0,0 },
|
|
|
|
},
|
|
|
|
{ /* TSC set 2, table 5.2.3b */
|
|
|
|
{ 0,1,1,0,0,0,1,0,0,0,1,0,0,1,0,0,1,1,1,1,0,1,0,1,1,1 },
|
|
|
|
{ 0,1,0,1,1,1,1,0,1,0,0,1,1,0,1,1,1,0,1,1,1,0,0,0,0,1 },
|
|
|
|
{ 0,1,0,0,0,0,0,1,0,1,1,0,0,0,1,1,1,0,1,1,1,0,1,1,0,0 },
|
|
|
|
{ 0,0,1,0,1,1,0,1,1,1,0,1,1,1,0,0,1,1,1,1,0,1,0,0,0,0 },
|
|
|
|
{ 0,1,1,1,0,1,0,0,1,1,1,1,0,1,0,0,1,1,1,0,1,1,1,1,1,0 },
|
|
|
|
{ 0,1,0,0,0,0,0,1,0,0,1,1,0,1,0,1,0,0,1,1,1,1,0,0,1,1 },
|
|
|
|
{ 0,0,0,1,0,0,0,0,1,1,0,1,0,0,0,0,1,1,0,1,1,1,0,1,0,1 },
|
|
|
|
{ 0,1,0,0,0,1,0,1,1,1,0,0,1,1,1,1,1,1,0,0,1,0,1,0,0,1 },
|
|
|
|
},
|
|
|
|
{ /* TSC set 3, table 5.2.3c */
|
|
|
|
{ 1,1,0,0,0,0,1,0,0,1,0,0,0,1,1,1,1,0,1,0,1,0,0,0,1,0 },
|
|
|
|
{ 0,0,1,0,1,1,1,1,1,0,0,0,1,0,0,1,0,1,0,0,0,0,1,0,0,0 },
|
|
|
|
{ 1,1,0,0,1,0,0,0,1,1,1,1,1,0,1,1,1,0,1,0,1,1,0,1,1,0 },
|
|
|
|
{ 0,0,1,1,0,0,0,0,1,0,1,0,0,1,1,0,0,0,0,0,1,0,1,1,0,0 },
|
|
|
|
{ 0,0,0,1,1,1,1,0,1,0,1,1,1,0,1,0,0,0,0,1,0,0,0,1,1,0 },
|
|
|
|
{ 1,1,0,0,1,1,1,1,0,1,0,1,0,1,1,1,1,0,0,1,0,0,0,0,0,0 },
|
|
|
|
{ 1,0,1,1,1,0,0,1,1,0,1,0,1,1,1,1,1,1,0,0,0,1,0,0,0,0 },
|
|
|
|
{ 1,1,1,0,0,1,0,1,1,1,1,0,1,1,1,0,0,0,0,0,1,0,0,1,0,0 },
|
|
|
|
},
|
|
|
|
{ /* TSC set 4, table 5.2.3d */
|
|
|
|
{ 1,1,0,0,1,1,1,0,1,0,0,0,0,0,1,0,0,0,1,1,0,1,0,0,0,0 },
|
|
|
|
{ 0,1,1,0,0,0,1,0,0,0,0,1,0,1,0,0,0,1,0,1,1,1,0,0,0,0 },
|
|
|
|
{ 1,1,1,0,0,1,0,0,0,0,0,1,0,1,0,1,0,0,1,1,1,0,0,0,0,0 },
|
|
|
|
{ 0,1,1,0,1,1,0,0,1,1,1,1,1,0,1,0,1,0,0,0,0,1,1,0,0,0 },
|
|
|
|
{ 1,1,0,1,1,0,0,0,0,1,0,0,0,0,1,0,0,0,1,0,1,1,0,0,0,0 },
|
|
|
|
{ 1,1,0,1,0,0,1,1,1,1,1,1,1,0,1,0,0,0,1,1,0,1,0,1,1,0 },
|
|
|
|
{ 0,0,1,0,0,1,1,1,1,1,1,1,0,0,1,0,1,0,1,0,1,1,0,0,0,0 },
|
|
|
|
{ 0,1,0,1,1,1,0,0,0,0,0,0,1,0,1,0,0,1,1,0,0,0,1,1,1,0 },
|
|
|
|
},
|
2013-02-05 10:45:28 +00:00
|
|
|
};
|
|
|
|
|
2021-05-19 01:47:47 +00:00
|
|
|
const ubit_t _sched_train_seq_8psk_nb[8][78] = {
|
2016-07-06 20:29:25 +00:00
|
|
|
{ 1,1,1,1,1,1,0,0,1,1,1,1,1,1,1,0,0,1,1,1,1,0,0,1,0,0,
|
|
|
|
1,0,0,1,1,1,1,1,1,1,1,1,1,1,1,1,0,0,1,1,1,1,1,1,1,1,
|
|
|
|
1,1,0,0,1,1,1,1,1,1,1,0,0,1,1,1,1,0,0,1,0,0,1,0,0,1, },
|
|
|
|
{ 1,1,1,1,1,1,0,0,1,1,1,1,0,0,1,0,0,1,1,1,1,0,0,1,0,0,
|
|
|
|
1,0,0,1,1,1,1,0,0,1,0,0,1,0,0,1,0,0,1,1,1,1,1,1,1,1,
|
|
|
|
1,1,0,0,1,1,1,1,0,0,1,0,0,1,1,1,1,0,0,1,0,0,1,0,0,1, },
|
|
|
|
{ 1,1,1,0,0,1,1,1,1,1,1,1,1,1,1,1,1,1,0,0,1,0,0,1,0,0,
|
|
|
|
1,1,1,1,0,0,1,0,0,1,0,0,1,1,1,1,0,0,1,1,1,1,1,1,1,0,
|
|
|
|
0,1,1,1,1,1,1,1,1,1,1,1,1,1,0,0,1,0,0,1,0,0,1,1,1,1, },
|
|
|
|
{ 1,1,1,0,0,1,1,1,1,1,1,1,1,1,1,0,0,1,0,0,1,0,0,1,0,0,
|
|
|
|
1,1,1,1,0,0,1,0,0,1,1,1,1,0,0,1,1,1,1,1,1,1,1,1,1,0,
|
|
|
|
0,1,1,1,1,1,1,1,1,1,1,0,0,1,0,0,1,0,0,1,0,0,1,1,1,1, },
|
|
|
|
{ 1,1,1,1,1,1,1,1,1,0,0,1,0,0,1,1,1,1,0,0,1,1,1,1,0,0,
|
|
|
|
1,0,0,1,0,0,1,1,1,1,1,1,1,0,0,1,1,1,1,1,1,1,1,1,1,1,
|
|
|
|
1,1,1,1,1,0,0,1,0,0,1,1,1,1,0,0,1,1,1,1,0,0,1,0,0,1, },
|
|
|
|
{ 1,1,1,0,0,1,1,1,1,1,1,1,0,0,1,0,0,1,0,0,1,1,1,1,0,0,
|
|
|
|
1,1,1,1,0,0,1,0,0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0,
|
|
|
|
0,1,1,1,1,1,1,1,0,0,1,0,0,1,0,0,1,1,1,1,0,0,1,1,1,1, },
|
|
|
|
{ 0,0,1,1,1,1,0,0,1,1,1,1,1,1,1,0,0,1,0,0,1,0,0,1,0,0,
|
|
|
|
1,0,0,1,1,1,1,0,0,1,0,0,1,1,1,1,1,1,1,1,1,1,0,0,1,1,
|
|
|
|
1,1,0,0,1,1,1,1,1,1,1,0,0,1,0,0,1,0,0,1,0,0,1,0,0,1, },
|
|
|
|
{ 0,0,1,0,0,1,0,0,1,1,1,1,0,0,1,0,0,1,0,0,1,0,0,1,1,1,
|
|
|
|
1,1,1,1,1,1,1,0,0,1,1,1,1,1,1,1,0,0,1,1,1,1,0,0,1,0,
|
|
|
|
0,1,0,0,1,1,1,1,0,0,1,0,0,1,0,0,1,0,0,1,1,1,1,1,1,1, },
|
|
|
|
};
|
|
|
|
|
2017-06-04 11:26:00 +00:00
|
|
|
/*! \brief SCH training sequence (TS 05.02 Chapter 5.2.5) */
|
2021-05-19 01:47:47 +00:00
|
|
|
const ubit_t _sched_train_seq_gmsk_sb[64] = {
|
2013-02-05 10:45:28 +00:00
|
|
|
1,0,1,1,1,0,0,1,0,1,1,0,0,0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,1,1,1,1,
|
|
|
|
0,0,1,0,1,1,0,1,0,1,0,0,0,1,0,1,0,1,1,1,0,1,1,0,0,0,0,1,1,0,1,1,
|
|
|
|
};
|
|
|
|
|
2019-06-01 15:54:15 +00:00
|
|
|
/* Logical channel (TRXC_*) description */
|
2016-01-09 21:17:52 +00:00
|
|
|
const struct trx_chan_desc trx_chan_desc[_TRX_CHAN_MAX] = {
|
2019-06-01 15:54:15 +00:00
|
|
|
[TRXC_IDLE] = {
|
|
|
|
.name = "IDLE",
|
|
|
|
.desc = "Idle channel",
|
|
|
|
},
|
|
|
|
[TRXC_FCCH] = {
|
|
|
|
.name = "FCCH", /* 3GPP TS 05.02, section 3.3.2.1 */
|
|
|
|
.desc = "Frequency correction channel",
|
|
|
|
|
|
|
|
/* Tx only, frequency correction bursts */
|
|
|
|
.dl_fn = tx_fcch_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SCH] = {
|
|
|
|
.name = "SCH", /* 3GPP TS 05.02, section 3.3.2.2 */
|
|
|
|
.desc = "Synchronization channel",
|
|
|
|
|
|
|
|
/* Tx only, synchronization bursts */
|
|
|
|
.dl_fn = tx_sch_fn,
|
|
|
|
},
|
|
|
|
[TRXC_BCCH] = {
|
|
|
|
.name = "BCCH", /* 3GPP TS 05.02, section 3.3.2.3 */
|
|
|
|
.desc = "Broadcast control channel",
|
|
|
|
.chan_nr = RSL_CHAN_BCCH,
|
|
|
|
|
|
|
|
/* Tx only, xCCH convolutional coding (3GPP TS 05.03, section 4.4),
|
|
|
|
* regular interleaving (3GPP TS 05.02, clause 7, table 3):
|
|
|
|
* a L2 frame is interleaved over 4 consecutive bursts. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_RACH] = {
|
|
|
|
.name = "RACH", /* 3GPP TS 05.02, section 3.3.3.1 */
|
|
|
|
.desc = "Random access channel",
|
|
|
|
.chan_nr = RSL_CHAN_RACH,
|
|
|
|
|
|
|
|
/* Rx only, RACH convolutional coding (3GPP TS 05.03, section 4.6). */
|
|
|
|
.ul_fn = rx_rach_fn,
|
|
|
|
},
|
|
|
|
[TRXC_CCCH] = {
|
|
|
|
.name = "CCCH", /* 3GPP TS 05.02, section 3.3.3.1 */
|
|
|
|
.desc = "Common control channel",
|
|
|
|
.chan_nr = RSL_CHAN_PCH_AGCH,
|
|
|
|
|
|
|
|
/* Tx only, xCCH convolutional coding (3GPP TS 05.03, section 4.4),
|
|
|
|
* regular interleaving (3GPP TS 05.02, clause 7, table 3):
|
|
|
|
* a L2 frame is interleaved over 4 consecutive bursts. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_TCHF] = {
|
|
|
|
.name = "TCH/F", /* 3GPP TS 05.02, section 3.2 */
|
|
|
|
.desc = "Full Rate traffic channel",
|
|
|
|
.chan_nr = RSL_CHAN_Bm_ACCHs,
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Rx and Tx, multiple convolutional coding types (3GPP TS 05.03,
|
|
|
|
* chapter 3), block diagonal interleaving (3GPP TS 05.02, clause 7):
|
|
|
|
*
|
|
|
|
* - a traffic frame is interleaved over 8 consecutive bursts
|
|
|
|
* using the even numbered bits of the first 4 bursts
|
|
|
|
* and odd numbered bits of the last 4 bursts;
|
|
|
|
* - a FACCH/F frame 'steals' (replaces) one traffic frame,
|
|
|
|
* interleaving is done in the same way. */
|
|
|
|
.rts_fn = rts_tchf_fn,
|
|
|
|
.dl_fn = tx_tchf_fn,
|
|
|
|
.ul_fn = rx_tchf_fn,
|
|
|
|
},
|
|
|
|
[TRXC_TCHH_0] = {
|
|
|
|
.name = "TCH/H(0)", /* 3GPP TS 05.02, section 3.2 */
|
|
|
|
.desc = "Half Rate traffic channel (sub-channel 0)",
|
|
|
|
.chan_nr = RSL_CHAN_Lm_ACCHs + (0 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Rx and Tx, multiple convolutional coding types (3GPP TS 05.03,
|
|
|
|
* chapter 3), block diagonal interleaving (3GPP TS 05.02, clause 7):
|
|
|
|
*
|
2021-09-29 19:57:10 +00:00
|
|
|
* - a traffic frame is interleaved over 4 consecutive bursts
|
2019-06-01 15:54:15 +00:00
|
|
|
* using the even numbered bits of the first 2 bursts,
|
|
|
|
* and odd numbered bits of the last 2 bursts;
|
|
|
|
* - a FACCH/H frame 'steals' (replaces) two traffic frames,
|
2021-09-29 19:57:10 +00:00
|
|
|
* interleaving is done over 6 consecutive bursts,
|
|
|
|
* using the even numbered bits of the first 2 bursts,
|
|
|
|
* all bits of the middle two 2 bursts,
|
|
|
|
* and odd numbered bits of the last 2 bursts. */
|
2019-06-01 15:54:15 +00:00
|
|
|
.rts_fn = rts_tchh_fn,
|
|
|
|
.dl_fn = tx_tchh_fn,
|
|
|
|
.ul_fn = rx_tchh_fn,
|
|
|
|
},
|
|
|
|
[TRXC_TCHH_1] = {
|
|
|
|
.name = "TCH/H(1)", /* 3GPP TS 05.02, section 3.2 */
|
|
|
|
.desc = "Half Rate traffic channel (sub-channel 1)",
|
|
|
|
.chan_nr = RSL_CHAN_Lm_ACCHs + (1 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_TCHH_0, see above. */
|
|
|
|
.rts_fn = rts_tchh_fn,
|
|
|
|
.dl_fn = tx_tchh_fn,
|
|
|
|
.ul_fn = rx_tchh_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH4_0] = {
|
|
|
|
.name = "SDCCH/4(0)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 0)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH4_ACCH + (0 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH4_1] = {
|
|
|
|
.name = "SDCCH/4(1)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 1)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH4_ACCH + (1 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH4_2] = {
|
|
|
|
.name = "SDCCH/4(2)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 2)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH4_ACCH + (2 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH4_3] = {
|
|
|
|
.name = "SDCCH/4(3)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 3)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH4_ACCH + (3 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH8_0] = {
|
|
|
|
.name = "SDCCH/8(0)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 0)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (0 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH8_1] = {
|
|
|
|
.name = "SDCCH/8(1)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 1)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (1 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH8_2] = {
|
|
|
|
.name = "SDCCH/8(2)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 2)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (2 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH8_3] = {
|
|
|
|
.name = "SDCCH/8(3)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 3)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (3 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH8_4] = {
|
|
|
|
.name = "SDCCH/8(4)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 4)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (4 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH8_5] = {
|
|
|
|
.name = "SDCCH/8(5)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 5)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (5 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH8_6] = {
|
|
|
|
.name = "SDCCH/8(6)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 6)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (6 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SDCCH8_7] = {
|
|
|
|
.name = "SDCCH/8(7)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Stand-alone dedicated control channel (sub-channel 7)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (7 << 3),
|
|
|
|
.link_id = LID_DEDIC,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCHTF] = {
|
|
|
|
.name = "SACCH/TF", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow TCH/F associated control channel",
|
|
|
|
.chan_nr = RSL_CHAN_Bm_ACCHs,
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCHTH_0] = {
|
|
|
|
.name = "SACCH/TH(0)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow TCH/H associated control channel (sub-channel 0)",
|
|
|
|
.chan_nr = RSL_CHAN_Lm_ACCHs + (0 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCHTH_1] = {
|
|
|
|
.name = "SACCH/TH(1)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow TCH/H associated control channel (sub-channel 1)",
|
|
|
|
.chan_nr = RSL_CHAN_Lm_ACCHs + (1 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH4_0] = {
|
|
|
|
.name = "SACCH/4(0)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/4 associated control channel (sub-channel 0)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH4_ACCH + (0 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH4_1] = {
|
|
|
|
.name = "SACCH/4(1)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/4 associated control channel (sub-channel 1)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH4_ACCH + (1 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH4_2] = {
|
|
|
|
.name = "SACCH/4(2)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/4 associated control channel (sub-channel 2)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH4_ACCH + (2 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH4_3] = {
|
|
|
|
.name = "SACCH/4(3)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/4 associated control channel (sub-channel 3)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH4_ACCH + (3 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH4_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH8_0] = {
|
|
|
|
.name = "SACCH/8(0)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/8 associated control channel (sub-channel 0)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (0 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH8_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH8_1] = {
|
|
|
|
.name = "SACCH/8(1)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/8 associated control channel (sub-channel 1)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (1 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH8_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH8_2] = {
|
|
|
|
.name = "SACCH/8(2)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/8 associated control channel (sub-channel 2)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (2 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH8_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH8_3] = {
|
|
|
|
.name = "SACCH/8(3)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/8 associated control channel (sub-channel 3)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (3 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH8_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH8_4] = {
|
|
|
|
.name = "SACCH/8(4)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/8 associated control channel (sub-channel 4)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (4 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH8_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH8_5] = {
|
|
|
|
.name = "SACCH/8(5)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/8 associated control channel (sub-channel 5)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (5 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH8_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH8_6] = {
|
|
|
|
.name = "SACCH/8(6)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/8 associated control channel (sub-channel 6)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (6 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH8_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_SACCH8_7] = {
|
|
|
|
.name = "SACCH/8(7)", /* 3GPP TS 05.02, section 3.3.4.1 */
|
|
|
|
.desc = "Slow SDCCH/8 associated control channel (sub-channel 7)",
|
|
|
|
.chan_nr = RSL_CHAN_SDCCH8_ACCH + (7 << 3),
|
|
|
|
.link_id = LID_SACCH,
|
|
|
|
|
|
|
|
/* Same as for TRXC_BCCH and TRXC_SDCCH8_* (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
.ul_fn = rx_data_fn,
|
|
|
|
},
|
|
|
|
[TRXC_PDTCH] = {
|
|
|
|
.name = "PDTCH", /* 3GPP TS 05.02, sections 3.2.4, 3.3.2.4 */
|
|
|
|
.desc = "Packet data traffic & control channel",
|
|
|
|
.chan_nr = RSL_CHAN_OSMO_PDCH,
|
|
|
|
|
|
|
|
/* Rx and Tx, multiple coding schemes: CS-2..4 and MCS-1..9 (3GPP TS
|
2023-03-05 22:35:16 +00:00
|
|
|
* 05.03, chapter 5), regular interleaving as specified for xCCH. */
|
2019-06-01 15:54:15 +00:00
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_pdtch_fn,
|
|
|
|
.ul_fn = rx_pdtch_fn,
|
|
|
|
},
|
|
|
|
[TRXC_PTCCH] = {
|
|
|
|
.name = "PTCCH", /* 3GPP TS 05.02, section 3.3.4.2 */
|
|
|
|
.desc = "Packet Timing advance control channel",
|
|
|
|
.chan_nr = RSL_CHAN_OSMO_PDCH,
|
|
|
|
|
scheduler: fix handling of PTCCH/U and PTCCH/D logical channels
According to 3GPP TS 45.010, section 5.6.2, for packet-switched
channels the BTS shall monitor the delay of the Access Bursts
sent by the MS on PTCCH and respond with timing advance values
for all MS performing the procedure on that PDCH.
According to 3GPP TS 45.002, section 3.3.4.2, PTCCH (Packet Timing
advance control channel) is a packet dedicated channel, that is
used for continuous Timing Advance control (mentioned above).
There are two sub-types of that logical channel:
- PTCCH/U (Uplink): used to transmit random Access Bursts
to allow estimation of the Timing Advance for one MS in
packet transfer mode.
- PTCCH/D (Downlink): used by the network to transmit
Timing Advance updates for several MS.
As per 3GPP TS 45.003, section 5.2, the coding scheme used for
PTCCH/U is the same as for PRACH as specified in subclause 5.3,
while the coding scheme used for PTCCH/D is the same as for
CS-1 as specified in subclause 5.1.1.
The way we used to handle both PTCCH/U and PTCCH/D is absolutely
wrong - they have nothing to do with xCCH coding. Instead, we
need to use tx_pdtch_fn() for Downlink and rx_rach_fn() for Uplink.
In l1sap_ph_rach_ind() we need to check if an Access Burst was
received on PTCCH/U and forward it to OsmoPCU with proper SAPI
value (PCU_IF_SAPI_PTCCH). To be able to specify a SAPI, a new
parameter is introduced to pcu_tx_rach_ind().
Change-Id: I232e5f514fbad2c51daaa59ff516004aba97c8a3
Related: OS#4102
2019-10-02 16:00:54 +00:00
|
|
|
/* On the Uplink, mobile stations transmit random Access Bursts
|
|
|
|
* to allow estimation of the timing advance for one MS in packet
|
|
|
|
* transfer mode. On Downlink, the network sends timing advance
|
|
|
|
* updates for several mobile stations. The coding scheme used
|
|
|
|
* for PTCCH/D messages is the same as for PDTCH CS-1. */
|
2019-06-01 15:54:15 +00:00
|
|
|
.rts_fn = rts_data_fn,
|
scheduler: fix handling of PTCCH/U and PTCCH/D logical channels
According to 3GPP TS 45.010, section 5.6.2, for packet-switched
channels the BTS shall monitor the delay of the Access Bursts
sent by the MS on PTCCH and respond with timing advance values
for all MS performing the procedure on that PDCH.
According to 3GPP TS 45.002, section 3.3.4.2, PTCCH (Packet Timing
advance control channel) is a packet dedicated channel, that is
used for continuous Timing Advance control (mentioned above).
There are two sub-types of that logical channel:
- PTCCH/U (Uplink): used to transmit random Access Bursts
to allow estimation of the Timing Advance for one MS in
packet transfer mode.
- PTCCH/D (Downlink): used by the network to transmit
Timing Advance updates for several MS.
As per 3GPP TS 45.003, section 5.2, the coding scheme used for
PTCCH/U is the same as for PRACH as specified in subclause 5.3,
while the coding scheme used for PTCCH/D is the same as for
CS-1 as specified in subclause 5.1.1.
The way we used to handle both PTCCH/U and PTCCH/D is absolutely
wrong - they have nothing to do with xCCH coding. Instead, we
need to use tx_pdtch_fn() for Downlink and rx_rach_fn() for Uplink.
In l1sap_ph_rach_ind() we need to check if an Access Burst was
received on PTCCH/U and forward it to OsmoPCU with proper SAPI
value (PCU_IF_SAPI_PTCCH). To be able to specify a SAPI, a new
parameter is introduced to pcu_tx_rach_ind().
Change-Id: I232e5f514fbad2c51daaa59ff516004aba97c8a3
Related: OS#4102
2019-10-02 16:00:54 +00:00
|
|
|
.dl_fn = tx_pdtch_fn,
|
|
|
|
.ul_fn = rx_rach_fn,
|
2019-06-01 15:54:15 +00:00
|
|
|
},
|
|
|
|
[TRXC_CBCH] = {
|
|
|
|
/* TODO: distinguish CBCH on SDCCH/4 and SDCCH/8 */
|
|
|
|
.name = "CBCH", /* 3GPP TS 05.02, section 3.3.5 */
|
|
|
|
.desc = "Cell Broadcast channel",
|
|
|
|
.chan_nr = RSL_CHAN_OSMO_CBCH4,
|
|
|
|
|
|
|
|
/* Tx only, same as for TRXC_BCCH (xCCH), see above. */
|
|
|
|
.rts_fn = rts_data_fn,
|
|
|
|
.dl_fn = tx_data_fn,
|
|
|
|
},
|
2017-01-09 12:37:02 +00:00
|
|
|
};
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2020-06-16 14:02:55 +00:00
|
|
|
enum {
|
|
|
|
L1SCHED_TS_CTR_DL_LATE,
|
2020-06-16 14:38:54 +00:00
|
|
|
L1SCHED_TS_CTR_DL_NOT_FOUND,
|
2020-06-16 14:02:55 +00:00
|
|
|
};
|
|
|
|
|
|
|
|
static const struct rate_ctr_desc l1sched_ts_ctr_desc[] = {
|
|
|
|
[L1SCHED_TS_CTR_DL_LATE] = {"l1sched_ts:dl_late", "Downlink frames arrived too late to submit to lower layers"},
|
2020-06-16 14:38:54 +00:00
|
|
|
[L1SCHED_TS_CTR_DL_NOT_FOUND] = {"l1sched_ts:dl_not_found", "Downlink frames not found while scheduling"},
|
2020-06-16 14:02:55 +00:00
|
|
|
};
|
|
|
|
static const struct rate_ctr_group_desc l1sched_ts_ctrg_desc = {
|
|
|
|
"l1sched_ts",
|
|
|
|
"L1 scheduler timeslot",
|
|
|
|
OSMO_STATS_CLASS_GLOBAL,
|
|
|
|
ARRAY_SIZE(l1sched_ts_ctr_desc),
|
|
|
|
l1sched_ts_ctr_desc
|
|
|
|
};
|
|
|
|
|
2013-02-05 10:45:28 +00:00
|
|
|
/*
|
|
|
|
* init / exit
|
|
|
|
*/
|
|
|
|
|
2021-05-27 19:51:44 +00:00
|
|
|
static void trx_sched_init_ts(struct gsm_bts_trx_ts *ts,
|
|
|
|
const unsigned int rate_ctr_idx)
|
|
|
|
{
|
|
|
|
struct l1sched_ts *l1ts;
|
|
|
|
unsigned int i;
|
2021-06-06 20:18:17 +00:00
|
|
|
char name[128];
|
2021-05-27 19:51:44 +00:00
|
|
|
|
|
|
|
l1ts = talloc_zero(ts->trx, struct l1sched_ts);
|
|
|
|
OSMO_ASSERT(l1ts != NULL);
|
|
|
|
|
|
|
|
/* Link both structures */
|
|
|
|
ts->priv = l1ts;
|
|
|
|
l1ts->ts = ts;
|
|
|
|
|
|
|
|
l1ts->ctrs = rate_ctr_group_alloc(ts->trx,
|
|
|
|
&l1sched_ts_ctrg_desc,
|
|
|
|
rate_ctr_idx);
|
2021-06-06 20:18:17 +00:00
|
|
|
snprintf(name, sizeof(name), "bts%u-trx%u-ts%u%s",
|
|
|
|
ts->trx->bts->nr, ts->trx->nr, ts->nr,
|
|
|
|
ts->vamos.is_shadow ? "-shadow" : "");
|
|
|
|
rate_ctr_group_set_name(l1ts->ctrs, name);
|
|
|
|
|
2021-05-27 19:51:44 +00:00
|
|
|
INIT_LLIST_HEAD(&l1ts->dl_prims);
|
|
|
|
|
|
|
|
for (i = 0; i < ARRAY_SIZE(l1ts->chan_state); i++) {
|
|
|
|
struct l1sched_chan_state *chan_state;
|
|
|
|
chan_state = &l1ts->chan_state[i];
|
|
|
|
chan_state->active = false;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
void trx_sched_init(struct gsm_bts_trx *trx)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
2021-05-27 19:51:44 +00:00
|
|
|
unsigned int tn;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2021-05-19 13:52:07 +00:00
|
|
|
OSMO_ASSERT(trx != NULL);
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGPTRX(trx, DL1C, LOGL_DEBUG, "Init scheduler structures\n");
|
2016-11-24 11:42:25 +00:00
|
|
|
|
2021-05-27 19:51:44 +00:00
|
|
|
/* Allocate shadow timeslots */
|
|
|
|
gsm_bts_trx_init_shadow_ts(trx);
|
2016-01-09 12:13:37 +00:00
|
|
|
|
2021-05-27 19:51:44 +00:00
|
|
|
for (tn = 0; tn < ARRAY_SIZE(trx->ts); tn++) {
|
|
|
|
unsigned int rate_ctr_idx = trx->nr * 100 + tn;
|
|
|
|
struct gsm_bts_trx_ts *ts = &trx->ts[tn];
|
2020-06-16 14:02:55 +00:00
|
|
|
|
2021-05-27 19:51:44 +00:00
|
|
|
/* Init primary and shadow timeslots */
|
|
|
|
trx_sched_init_ts(ts, rate_ctr_idx);
|
|
|
|
trx_sched_init_ts(ts->vamos.peer, rate_ctr_idx + 10);
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2021-09-22 14:41:12 +00:00
|
|
|
static void trx_sched_clean_ts(struct gsm_bts_trx_ts *ts)
|
|
|
|
{
|
|
|
|
struct l1sched_ts *l1ts = ts->priv;
|
|
|
|
unsigned int i;
|
|
|
|
|
2022-08-11 15:59:27 +00:00
|
|
|
msgb_queue_free(&l1ts->dl_prims);
|
2021-09-22 14:41:12 +00:00
|
|
|
rate_ctr_group_free(l1ts->ctrs);
|
|
|
|
l1ts->ctrs = NULL;
|
2021-12-12 15:53:40 +00:00
|
|
|
|
2021-09-22 14:41:12 +00:00
|
|
|
/* clear lchan channel states */
|
|
|
|
for (i = 0; i < ARRAY_SIZE(ts->lchan); i++)
|
|
|
|
lchan_set_state(&ts->lchan[i], LCHAN_S_NONE);
|
2021-10-08 16:34:49 +00:00
|
|
|
|
|
|
|
talloc_free(l1ts);
|
|
|
|
ts->priv = NULL;
|
2021-09-22 14:41:12 +00:00
|
|
|
}
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
void trx_sched_clean(struct gsm_bts_trx *trx)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
2021-09-22 14:41:12 +00:00
|
|
|
unsigned int tn;
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
|
|
|
|
LOGPTRX(trx, DL1C, LOGL_DEBUG, "Clean scheduler structures\n");
|
2013-02-05 10:45:28 +00:00
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
for (tn = 0; tn < ARRAY_SIZE(trx->ts); tn++) {
|
|
|
|
struct gsm_bts_trx_ts *ts = &trx->ts[tn];
|
2021-09-22 14:41:12 +00:00
|
|
|
|
|
|
|
/* Clean primary and shadow timeslots */
|
|
|
|
trx_sched_clean_ts(ts);
|
|
|
|
trx_sched_clean_ts(ts->vamos.peer);
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
2021-10-11 09:05:30 +00:00
|
|
|
|
|
|
|
/* Free previously allocated shadow timeslots */
|
|
|
|
gsm_bts_trx_free_shadow_ts(trx);
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
struct msgb *_sched_dequeue_prim(struct l1sched_ts *l1ts, const struct trx_dl_burst_req *br)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
2013-02-14 10:21:13 +00:00
|
|
|
struct msgb *msg, *msg2;
|
2020-06-16 11:54:35 +00:00
|
|
|
uint32_t prim_fn, l1sap_fn;
|
2013-02-14 10:21:13 +00:00
|
|
|
uint8_t chan_nr, link_id;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2013-02-14 10:21:13 +00:00
|
|
|
/* get prim of current fn from queue */
|
2016-01-09 20:33:58 +00:00
|
|
|
llist_for_each_entry_safe(msg, msg2, &l1ts->dl_prims, list) {
|
2020-10-17 07:45:42 +00:00
|
|
|
struct osmo_phsap_prim *l1sap = msgb_l1sap_prim(msg);
|
2013-02-14 10:21:13 +00:00
|
|
|
switch (l1sap->oph.primitive) {
|
|
|
|
case PRIM_PH_DATA:
|
|
|
|
chan_nr = l1sap->u.data.chan_nr;
|
|
|
|
link_id = l1sap->u.data.link_id;
|
2020-06-16 11:54:35 +00:00
|
|
|
l1sap_fn = l1sap->u.data.fn;
|
2013-02-14 10:21:13 +00:00
|
|
|
break;
|
|
|
|
case PRIM_TCH:
|
|
|
|
chan_nr = l1sap->u.tch.chan_nr;
|
|
|
|
link_id = 0;
|
2020-06-16 11:54:35 +00:00
|
|
|
l1sap_fn = l1sap->u.tch.fn;
|
2013-02-14 10:21:13 +00:00
|
|
|
break;
|
|
|
|
default:
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGL1SB(DL1P, LOGL_ERROR, l1ts, br, "Prim has wrong type.\n");
|
2020-06-16 14:26:43 +00:00
|
|
|
goto free_msg;
|
2013-02-14 10:21:13 +00:00
|
|
|
}
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
prim_fn = GSM_TDMA_FN_SUB(l1sap_fn, br->fn);
|
2020-06-16 12:34:25 +00:00
|
|
|
if (prim_fn > 100) { /* l1sap_fn < fn */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGL1SB(DL1P, LOGL_NOTICE, l1ts, br,
|
2020-06-16 11:54:35 +00:00
|
|
|
"Prim %u is out of range (%u vs exp %u), or channel %s with "
|
2017-03-13 12:21:20 +00:00
|
|
|
"type %s is already disabled. If this happens in "
|
2018-02-26 21:31:56 +00:00
|
|
|
"conjunction with PCU, increase 'rts-advance' by 5.\n",
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
prim_fn, l1sap_fn, br->fn,
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
get_lchan_by_chan_nr(l1ts->ts->trx, chan_nr)->name,
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
trx_chan_desc[br->chan].name);
|
2020-06-16 14:02:55 +00:00
|
|
|
rate_ctr_inc2(l1ts->ctrs, L1SCHED_TS_CTR_DL_LATE);
|
2013-02-05 10:45:28 +00:00
|
|
|
/* unlink and free message */
|
|
|
|
llist_del(&msg->list);
|
|
|
|
msgb_free(msg);
|
|
|
|
continue;
|
|
|
|
}
|
2020-06-16 12:34:25 +00:00
|
|
|
if (prim_fn > 0) /* l1sap_fn > fn */
|
2020-06-16 14:38:54 +00:00
|
|
|
break;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2020-06-16 12:34:25 +00:00
|
|
|
/* l1sap_fn == fn */
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
if ((chan_nr ^ (trx_chan_desc[br->chan].chan_nr | br->tn))
|
|
|
|
|| ((link_id & 0xc0) ^ trx_chan_desc[br->chan].link_id)) {
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGL1SB(DL1P, LOGL_ERROR, l1ts, br, "Prim has wrong chan_nr=0x%02x link_id=%02x, "
|
2020-06-16 14:37:53 +00:00
|
|
|
"expecting chan_nr=0x%02x link_id=%02x.\n", chan_nr, link_id,
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
trx_chan_desc[br->chan].chan_nr | br->tn, trx_chan_desc[br->chan].link_id);
|
2020-06-16 14:37:53 +00:00
|
|
|
goto free_msg;
|
|
|
|
}
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2020-06-16 14:37:53 +00:00
|
|
|
/* unlink and return message */
|
|
|
|
llist_del(&msg->list);
|
|
|
|
return msg;
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
2020-06-16 14:38:54 +00:00
|
|
|
/* Queue was traversed with no candidate, no prim is available for current FN: */
|
|
|
|
rate_ctr_inc2(l1ts->ctrs, L1SCHED_TS_CTR_DL_NOT_FOUND);
|
2020-06-16 14:37:53 +00:00
|
|
|
return NULL;
|
2020-06-16 14:26:43 +00:00
|
|
|
|
|
|
|
free_msg:
|
|
|
|
/* unlink and free message */
|
|
|
|
llist_del(&msg->list);
|
|
|
|
msgb_free(msg);
|
|
|
|
return NULL;
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int _sched_compose_ph_data_ind(struct l1sched_ts *l1ts, uint32_t fn,
|
2023-07-05 17:43:21 +00:00
|
|
|
enum trx_chan_type chan,
|
2023-07-05 17:51:01 +00:00
|
|
|
const uint8_t *data, size_t data_len,
|
2023-07-05 17:43:21 +00:00
|
|
|
uint16_t ber10k, float rssi,
|
2018-02-27 15:58:46 +00:00
|
|
|
int16_t ta_offs_256bits, int16_t link_qual_cb,
|
2016-07-28 12:46:00 +00:00
|
|
|
enum osmo_ph_pres_info_type presence_info)
|
2013-02-15 06:51:01 +00:00
|
|
|
{
|
|
|
|
struct msgb *msg;
|
|
|
|
struct osmo_phsap_prim *l1sap;
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
uint8_t chan_nr = trx_chan_desc[chan].chan_nr | l1ts->ts->nr;
|
2013-02-15 06:51:01 +00:00
|
|
|
|
2021-05-27 16:26:29 +00:00
|
|
|
/* VAMOS: use Osmocom specific channel number */
|
|
|
|
if (l1ts->ts->vamos.is_shadow)
|
|
|
|
chan_nr |= RSL_CHAN_OSMO_VAMOS_MASK;
|
|
|
|
|
2013-02-15 06:51:01 +00:00
|
|
|
/* compose primitive */
|
2023-07-05 17:43:21 +00:00
|
|
|
msg = l1sap_msgb_alloc(data_len);
|
2013-02-15 06:51:01 +00:00
|
|
|
l1sap = msgb_l1sap_prim(msg);
|
|
|
|
osmo_prim_init(&l1sap->oph, SAP_GSM_PH, PRIM_PH_DATA,
|
|
|
|
PRIM_OP_INDICATION, msg);
|
2013-06-06 11:24:40 +00:00
|
|
|
l1sap->u.data.chan_nr = chan_nr;
|
2013-02-15 06:51:01 +00:00
|
|
|
l1sap->u.data.link_id = trx_chan_desc[chan].link_id;
|
|
|
|
l1sap->u.data.fn = fn;
|
2013-03-16 15:46:13 +00:00
|
|
|
l1sap->u.data.rssi = (int8_t) (rssi);
|
2016-07-28 12:46:00 +00:00
|
|
|
l1sap->u.data.ber10k = ber10k;
|
2018-02-27 15:58:46 +00:00
|
|
|
l1sap->u.data.ta_offs_256bits = ta_offs_256bits;
|
2016-07-28 12:46:00 +00:00
|
|
|
l1sap->u.data.lqual_cb = link_qual_cb;
|
2016-02-18 16:48:07 +00:00
|
|
|
l1sap->u.data.pdch_presence_info = presence_info;
|
2023-07-05 17:43:21 +00:00
|
|
|
msg->l2h = msgb_put(msg, data_len);
|
|
|
|
if (data_len)
|
|
|
|
memcpy(msg->l2h, data, data_len);
|
2013-02-15 06:51:01 +00:00
|
|
|
|
|
|
|
/* forward primitive */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
l1sap_up(l1ts->ts->trx, l1sap);
|
2013-02-15 06:51:01 +00:00
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int _sched_compose_tch_ind(struct l1sched_ts *l1ts, uint32_t fn,
|
2023-07-05 17:43:21 +00:00
|
|
|
enum trx_chan_type chan,
|
2023-07-05 17:51:01 +00:00
|
|
|
const uint8_t *data, size_t data_len,
|
2023-07-05 17:43:21 +00:00
|
|
|
uint16_t ber10k, float rssi,
|
|
|
|
int16_t ta_offs_256bits, int16_t link_qual_cb,
|
|
|
|
uint8_t is_sub)
|
2013-02-15 06:51:01 +00:00
|
|
|
{
|
|
|
|
struct msgb *msg;
|
|
|
|
struct osmo_phsap_prim *l1sap;
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
uint8_t chan_nr = trx_chan_desc[chan].chan_nr | l1ts->ts->nr;
|
|
|
|
struct gsm_lchan *lchan = &l1ts->ts->lchan[l1sap_chan2ss(chan_nr)];
|
2013-02-15 06:51:01 +00:00
|
|
|
|
2021-05-27 16:26:29 +00:00
|
|
|
/* VAMOS: use Osmocom specific channel number */
|
|
|
|
if (l1ts->ts->vamos.is_shadow)
|
|
|
|
chan_nr |= RSL_CHAN_OSMO_VAMOS_MASK;
|
|
|
|
|
2013-02-15 06:51:01 +00:00
|
|
|
/* compose primitive */
|
2023-07-05 17:43:21 +00:00
|
|
|
msg = l1sap_msgb_alloc(data_len);
|
2013-02-15 06:51:01 +00:00
|
|
|
l1sap = msgb_l1sap_prim(msg);
|
|
|
|
osmo_prim_init(&l1sap->oph, SAP_GSM_PH, PRIM_TCH,
|
|
|
|
PRIM_OP_INDICATION, msg);
|
2018-07-19 14:03:24 +00:00
|
|
|
l1sap->u.tch.chan_nr = chan_nr;
|
2013-02-15 06:51:01 +00:00
|
|
|
l1sap->u.tch.fn = fn;
|
2019-10-31 08:36:17 +00:00
|
|
|
l1sap->u.tch.rssi = (int8_t) (rssi);
|
|
|
|
l1sap->u.tch.ber10k = ber10k;
|
|
|
|
l1sap->u.tch.ta_offs_256bits = ta_offs_256bits;
|
2021-09-27 18:10:56 +00:00
|
|
|
l1sap->u.tch.lqual_cb = link_qual_cb;
|
2020-02-06 13:31:22 +00:00
|
|
|
l1sap->u.tch.is_sub = is_sub & 1;
|
2019-10-31 08:36:17 +00:00
|
|
|
|
2023-07-05 17:43:21 +00:00
|
|
|
msg->l2h = msgb_put(msg, data_len);
|
|
|
|
if (data_len)
|
|
|
|
memcpy(msg->l2h, data, data_len);
|
2013-02-15 06:51:01 +00:00
|
|
|
|
2023-07-05 16:58:14 +00:00
|
|
|
LOGL1S(DL1P, LOGL_DEBUG, l1ts, chan, l1sap->u.tch.fn, "%s Rx -> RTP: %s\n",
|
2023-07-05 17:01:22 +00:00
|
|
|
gsm_lchan_name(lchan), msgb_hexdump_l2(msg));
|
2013-02-15 06:51:01 +00:00
|
|
|
/* forward primitive */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
l1sap_up(l1ts->ts->trx, l1sap);
|
2013-02-15 06:51:01 +00:00
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
2013-02-05 10:45:28 +00:00
|
|
|
|
|
|
|
|
2013-02-14 10:21:13 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
/*
|
|
|
|
* data request (from upper layer)
|
|
|
|
*/
|
2013-02-05 10:45:28 +00:00
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int trx_sched_ph_data_req(struct gsm_bts_trx *trx, struct osmo_phsap_prim *l1sap)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
uint8_t tn = L1SAP_CHAN2TS(l1sap->u.data.chan_nr);
|
|
|
|
struct l1sched_ts *l1ts = trx->ts[tn].priv;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGL1S(DL1P, LOGL_DEBUG, l1ts, -1, l1sap->u.data.fn,
|
2017-12-02 15:29:15 +00:00
|
|
|
"PH-DATA.req: chan_nr=0x%02x link_id=0x%02x\n",
|
|
|
|
l1sap->u.data.chan_nr, l1sap->u.data.link_id);
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
/* ignore empty frame */
|
2021-11-03 17:28:40 +00:00
|
|
|
if (!l1sap->oph.msg->l2h || msgb_l2len(l1sap->oph.msg) == 0) {
|
2016-01-09 21:17:52 +00:00
|
|
|
msgb_free(l1sap->oph.msg);
|
|
|
|
return 0;
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
2021-05-27 16:26:29 +00:00
|
|
|
/* VAMOS: convert Osmocom specific channel number to a generic one */
|
|
|
|
if (trx->ts[tn].vamos.is_shadow)
|
|
|
|
l1sap->u.data.chan_nr &= ~RSL_CHAN_OSMO_VAMOS_MASK;
|
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
msgb_enqueue(&l1ts->dl_prims, l1sap->oph.msg);
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
return 0;
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int trx_sched_tch_req(struct gsm_bts_trx *trx, struct osmo_phsap_prim *l1sap)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
2021-06-22 16:49:34 +00:00
|
|
|
uint8_t tn = L1SAP_CHAN2TS(l1sap->u.tch.chan_nr);
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
struct l1sched_ts *l1ts = trx->ts[tn].priv;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGL1S(DL1P, LOGL_DEBUG, l1ts, -1, l1sap->u.tch.fn,
|
|
|
|
"TCH.req: chan_nr=0x%02x\n", l1sap->u.tch.chan_nr);
|
2013-02-15 06:51:01 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
/* ignore empty frame */
|
|
|
|
if (!msgb_l2len(l1sap->oph.msg)) {
|
|
|
|
msgb_free(l1sap->oph.msg);
|
|
|
|
return 0;
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
2021-05-27 16:26:29 +00:00
|
|
|
/* VAMOS: convert Osmocom specific channel number to a generic one */
|
|
|
|
if (trx->ts[tn].vamos.is_shadow)
|
|
|
|
l1sap->u.tch.chan_nr &= ~RSL_CHAN_OSMO_VAMOS_MASK;
|
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
msgb_enqueue(&l1ts->dl_prims, l1sap->oph.msg);
|
2013-03-14 06:56:05 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
return 0;
|
2013-03-14 06:56:05 +00:00
|
|
|
}
|
|
|
|
|
2013-02-14 10:21:13 +00:00
|
|
|
|
2020-06-09 15:56:34 +00:00
|
|
|
/*
|
2016-01-09 21:17:52 +00:00
|
|
|
* ready-to-send indication (to upper layer)
|
|
|
|
*/
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
/* RTS for data frame */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
static int rts_data_fn(const struct l1sched_ts *l1ts, const struct trx_dl_burst_req *br)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
2016-01-09 21:17:52 +00:00
|
|
|
uint8_t chan_nr, link_id;
|
|
|
|
struct msgb *msg;
|
|
|
|
struct osmo_phsap_prim *l1sap;
|
2013-03-31 10:17:02 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
/* get data for RTS indication */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
chan_nr = trx_chan_desc[br->chan].chan_nr | br->tn;
|
|
|
|
link_id = trx_chan_desc[br->chan].link_id;
|
2013-03-31 10:17:02 +00:00
|
|
|
|
2021-05-27 16:26:29 +00:00
|
|
|
|
|
|
|
/* VAMOS: use Osmocom specific channel number */
|
|
|
|
if (l1ts->ts->vamos.is_shadow)
|
|
|
|
chan_nr |= RSL_CHAN_OSMO_VAMOS_MASK;
|
|
|
|
|
2020-11-04 13:31:41 +00:00
|
|
|
/* For handover detection, there are cases where the SACCH should remain inactive until the first RACH
|
|
|
|
* indicating the TA is received. */
|
|
|
|
if (L1SAP_IS_LINK_SACCH(link_id)
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
&& !l1ts->chan_state[br->chan].lchan->want_dl_sacch_active)
|
2020-11-04 13:31:41 +00:00
|
|
|
return 0;
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGL1SB(DL1P, LOGL_DEBUG, l1ts, br, "PH-RTS.ind: chan_nr=0x%02x link_id=0x%02x\n", chan_nr, link_id);
|
2013-02-05 10:45:28 +00:00
|
|
|
|
|
|
|
/* generate prim */
|
2016-01-09 21:17:52 +00:00
|
|
|
msg = l1sap_msgb_alloc(200);
|
|
|
|
if (!msg)
|
|
|
|
return -ENOMEM;
|
|
|
|
l1sap = msgb_l1sap_prim(msg);
|
|
|
|
osmo_prim_init(&l1sap->oph, SAP_GSM_PH, PRIM_PH_RTS,
|
|
|
|
PRIM_OP_INDICATION, msg);
|
|
|
|
l1sap->u.data.chan_nr = chan_nr;
|
|
|
|
l1sap->u.data.link_id = link_id;
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
l1sap->u.data.fn = br->fn;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
return l1sap_up(l1ts->ts->trx, l1sap);
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
static int rts_tch_common(const struct l1sched_ts *l1ts,
|
|
|
|
const struct trx_dl_burst_req *br,
|
|
|
|
bool facch)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
2016-01-09 21:17:52 +00:00
|
|
|
uint8_t chan_nr, link_id;
|
|
|
|
struct msgb *msg;
|
|
|
|
struct osmo_phsap_prim *l1sap;
|
|
|
|
int rc = 0;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
/* get data for RTS indication */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
chan_nr = trx_chan_desc[br->chan].chan_nr | br->tn;
|
|
|
|
link_id = trx_chan_desc[br->chan].link_id;
|
2013-02-07 12:16:28 +00:00
|
|
|
|
2021-05-27 16:26:29 +00:00
|
|
|
|
|
|
|
/* VAMOS: use Osmocom specific channel number */
|
|
|
|
if (l1ts->ts->vamos.is_shadow)
|
|
|
|
chan_nr |= RSL_CHAN_OSMO_VAMOS_MASK;
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGL1SB(DL1P, LOGL_DEBUG, l1ts, br, "TCH RTS.ind: chan_nr=0x%02x\n", chan_nr);
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
/* only send, if FACCH is selected */
|
|
|
|
if (facch) {
|
|
|
|
/* generate prim */
|
|
|
|
msg = l1sap_msgb_alloc(200);
|
|
|
|
if (!msg)
|
2013-02-05 10:45:28 +00:00
|
|
|
return -ENOMEM;
|
2016-01-09 21:17:52 +00:00
|
|
|
l1sap = msgb_l1sap_prim(msg);
|
|
|
|
osmo_prim_init(&l1sap->oph, SAP_GSM_PH, PRIM_PH_RTS,
|
|
|
|
PRIM_OP_INDICATION, msg);
|
|
|
|
l1sap->u.data.chan_nr = chan_nr;
|
|
|
|
l1sap->u.data.link_id = link_id;
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
l1sap->u.data.fn = br->fn;
|
2015-04-05 21:12:02 +00:00
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
rc = l1sap_up(l1ts->ts->trx, l1sap);
|
2013-02-15 12:29:29 +00:00
|
|
|
}
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2019-10-13 17:09:39 +00:00
|
|
|
/* don't send, if TCH is in signalling only mode */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
if (l1ts->chan_state[br->chan].rsl_cmode != RSL_CMOD_SPD_SIGN) {
|
2016-01-09 21:17:52 +00:00
|
|
|
/* generate prim */
|
|
|
|
msg = l1sap_msgb_alloc(200);
|
|
|
|
if (!msg)
|
2013-02-05 10:45:28 +00:00
|
|
|
return -ENOMEM;
|
2016-01-09 21:17:52 +00:00
|
|
|
l1sap = msgb_l1sap_prim(msg);
|
|
|
|
osmo_prim_init(&l1sap->oph, SAP_GSM_PH, PRIM_TCH_RTS,
|
|
|
|
PRIM_OP_INDICATION, msg);
|
|
|
|
l1sap->u.tch.chan_nr = chan_nr;
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
l1sap->u.tch.fn = br->fn;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
return l1sap_up(l1ts->ts->trx, l1sap);
|
2013-02-15 06:51:01 +00:00
|
|
|
}
|
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
return rc;
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
/* RTS for full rate traffic frame */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
static int rts_tchf_fn(const struct l1sched_ts *l1ts, const struct trx_dl_burst_req *br)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
2016-01-09 21:17:52 +00:00
|
|
|
/* TCH/F may include FACCH on every 4th burst */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
return rts_tch_common(l1ts, br, true);
|
2016-01-09 21:17:52 +00:00
|
|
|
}
|
2013-03-31 10:17:02 +00:00
|
|
|
|
2022-04-09 22:22:47 +00:00
|
|
|
/* FACCH/H channel mapping for Downlink (see 3GPP TS 45.002, table 1).
|
|
|
|
* This mapping is valid for both FACCH/H(0) and FACCH/H(1). */
|
2022-04-19 16:37:54 +00:00
|
|
|
const uint8_t sched_tchh_dl_facch_map[26] = {
|
2022-04-09 22:22:47 +00:00
|
|
|
[4] = 1, /* FACCH/H(0): B0(4,6,8,10,13,15) */
|
|
|
|
[5] = 1, /* FACCH/H(1): B0(5,7,9,11,14,16) */
|
|
|
|
[13] = 1, /* FACCH/H(0): B1(13,15,17,19,21,23) */
|
|
|
|
[14] = 1, /* FACCH/H(1): B1(14,16,18,20,22,24) */
|
|
|
|
[21] = 1, /* FACCH/H(0): B2(21,23,0,2,4,6) */
|
|
|
|
[22] = 1, /* FACCH/H(1): B2(22,24,1,3,5,7) */
|
|
|
|
};
|
2013-03-31 10:17:02 +00:00
|
|
|
|
2016-01-09 21:17:52 +00:00
|
|
|
/* RTS for half rate traffic frame */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
static int rts_tchh_fn(const struct l1sched_ts *l1ts, const struct trx_dl_burst_req *br)
|
2016-01-09 21:17:52 +00:00
|
|
|
{
|
2022-04-09 22:22:47 +00:00
|
|
|
return rts_tch_common(l1ts, br, sched_tchh_dl_facch_map[br->fn % 26]);
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
2018-02-23 12:11:14 +00:00
|
|
|
/* set multiframe scheduler to given pchan */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int trx_sched_set_pchan(struct gsm_bts_trx_ts *ts, enum gsm_phys_chan_config pchan)
|
2018-02-23 12:11:14 +00:00
|
|
|
{
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
struct l1sched_ts *l1ts = ts->priv;
|
|
|
|
int i = find_sched_mframe_idx(pchan, ts->nr);
|
2018-02-23 12:11:14 +00:00
|
|
|
if (i < 0) {
|
2023-03-19 20:59:11 +00:00
|
|
|
LOGP(DL1C, LOGL_NOTICE, "%s Failed to configure multiframe (pchan=0x%02x)\n",
|
|
|
|
gsm_ts_name(ts), pchan);
|
2018-02-23 12:11:14 +00:00
|
|
|
return -ENOTSUP;
|
|
|
|
}
|
|
|
|
l1ts->mf_index = i;
|
|
|
|
l1ts->mf_period = trx_sched_multiframes[i].period;
|
|
|
|
l1ts->mf_frames = trx_sched_multiframes[i].frames;
|
2021-05-27 19:51:44 +00:00
|
|
|
if (ts->vamos.peer != NULL) {
|
|
|
|
l1ts = ts->vamos.peer->priv;
|
|
|
|
l1ts->mf_index = i;
|
|
|
|
l1ts->mf_period = trx_sched_multiframes[i].period;
|
|
|
|
l1ts->mf_frames = trx_sched_multiframes[i].frames;
|
|
|
|
}
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGP(DL1C, LOGL_NOTICE, "%s Configured multiframe with '%s'\n",
|
|
|
|
gsm_ts_name(ts), trx_sched_multiframes[i].name);
|
2018-02-23 12:11:14 +00:00
|
|
|
return 0;
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
2020-10-17 08:18:05 +00:00
|
|
|
/* Remove all matching (by chan_nr & link_id) primitives from the given queue */
|
|
|
|
static void trx_sched_queue_filter(struct llist_head *q, uint8_t chan_nr, uint8_t link_id)
|
|
|
|
{
|
|
|
|
struct msgb *msg, *_msg;
|
|
|
|
|
|
|
|
llist_for_each_entry_safe(msg, _msg, q, list) {
|
|
|
|
struct osmo_phsap_prim *l1sap = msgb_l1sap_prim(msg);
|
|
|
|
switch (l1sap->oph.primitive) {
|
|
|
|
case PRIM_PH_DATA:
|
|
|
|
if (l1sap->u.data.chan_nr != chan_nr)
|
|
|
|
continue;
|
|
|
|
if (l1sap->u.data.link_id != link_id)
|
|
|
|
continue;
|
|
|
|
break;
|
|
|
|
case PRIM_TCH:
|
|
|
|
if (l1sap->u.tch.chan_nr != chan_nr)
|
|
|
|
continue;
|
|
|
|
if (link_id != 0x00)
|
|
|
|
continue;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
/* Shall not happen */
|
|
|
|
OSMO_ASSERT(0);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Unlink and free() */
|
|
|
|
llist_del(&msg->list);
|
|
|
|
talloc_free(msg);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-03-07 01:52:25 +00:00
|
|
|
static void _trx_sched_set_lchan(struct gsm_lchan *lchan,
|
|
|
|
enum trx_chan_type chan,
|
|
|
|
bool active)
|
|
|
|
{
|
|
|
|
struct l1sched_ts *l1ts = lchan->ts->priv;
|
|
|
|
struct l1sched_chan_state *chan_state;
|
|
|
|
|
|
|
|
OSMO_ASSERT(l1ts != NULL);
|
|
|
|
chan_state = &l1ts->chan_state[chan];
|
|
|
|
|
|
|
|
LOGPLCHAN(lchan, DL1C, LOGL_INFO, "%s %s\n",
|
|
|
|
(active) ? "Activating" : "Deactivating",
|
|
|
|
trx_chan_desc[chan].name);
|
|
|
|
|
|
|
|
if (active) {
|
|
|
|
/* Clean up everything */
|
|
|
|
memset(chan_state, 0, sizeof(*chan_state));
|
|
|
|
|
|
|
|
/* Bind to generic 'struct gsm_lchan' */
|
|
|
|
chan_state->lchan = lchan;
|
2023-03-05 22:35:16 +00:00
|
|
|
|
|
|
|
/* Allocate memory for Rx/Tx burst buffers. Use the maximim size
|
2023-05-15 09:37:49 +00:00
|
|
|
* of 24 * (2 * 58) bytes, which is sufficient to store up to 24 GMSK
|
|
|
|
* modulated bursts for CSD or up to 8 8PSK modulated bursts for EGPRS. */
|
|
|
|
const size_t buf_size = 24 * GSM_NBITS_NB_GMSK_PAYLOAD;
|
2023-03-05 22:35:16 +00:00
|
|
|
if (trx_chan_desc[chan].dl_fn != NULL)
|
|
|
|
chan_state->dl_bursts = talloc_zero_size(l1ts, buf_size);
|
|
|
|
if (trx_chan_desc[chan].ul_fn != NULL) {
|
|
|
|
chan_state->ul_bursts = talloc_zero_size(l1ts, buf_size);
|
|
|
|
if (L1SAP_IS_LINK_SACCH(trx_chan_desc[chan].link_id))
|
|
|
|
chan_state->ul_bursts_prev = talloc_zero_size(l1ts, buf_size);
|
|
|
|
}
|
2023-03-07 01:52:25 +00:00
|
|
|
} else {
|
|
|
|
chan_state->ho_rach_detect = 0;
|
|
|
|
|
|
|
|
/* Remove pending Tx prims belonging to this lchan */
|
|
|
|
trx_sched_queue_filter(&l1ts->dl_prims,
|
|
|
|
trx_chan_desc[chan].chan_nr,
|
|
|
|
trx_chan_desc[chan].link_id);
|
2023-03-05 22:35:16 +00:00
|
|
|
|
|
|
|
/* Release memory used by Rx/Tx burst buffers */
|
|
|
|
TALLOC_FREE(chan_state->dl_bursts);
|
|
|
|
TALLOC_FREE(chan_state->ul_bursts);
|
|
|
|
TALLOC_FREE(chan_state->ul_bursts_prev);
|
2023-03-07 01:52:25 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
chan_state->active = active;
|
|
|
|
}
|
|
|
|
|
2013-02-05 10:45:28 +00:00
|
|
|
/* setting all logical channels given attributes to active/inactive */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int trx_sched_set_lchan(struct gsm_lchan *lchan, uint8_t chan_nr, uint8_t link_id, bool active)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
struct l1sched_ts *l1ts = lchan->ts->priv;
|
2013-02-05 10:45:28 +00:00
|
|
|
uint8_t tn = L1SAP_CHAN2TS(chan_nr);
|
2013-06-12 14:53:55 +00:00
|
|
|
uint8_t ss = l1sap_chan2ss(chan_nr);
|
2020-10-17 07:28:55 +00:00
|
|
|
bool found = false;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2021-10-26 16:18:27 +00:00
|
|
|
if (!l1ts) {
|
|
|
|
LOGPLCHAN(lchan, DL1C, LOGL_ERROR, "%s lchan with uninitialized scheduler structure\n",
|
|
|
|
(active) ? "Activating" : "Deactivating");
|
|
|
|
return -EINVAL;
|
|
|
|
}
|
|
|
|
|
2021-05-27 16:26:29 +00:00
|
|
|
/* VAMOS: convert Osmocom specific channel number to a generic one,
|
|
|
|
* otherwise we won't match anything in trx_chan_desc[]. */
|
|
|
|
if (lchan->ts->vamos.is_shadow)
|
|
|
|
chan_nr &= ~RSL_CHAN_OSMO_VAMOS_MASK;
|
|
|
|
|
2013-02-05 10:45:28 +00:00
|
|
|
/* look for all matching chan_nr/link_id */
|
2023-03-07 01:52:25 +00:00
|
|
|
for (enum trx_chan_type chan = 0; chan < _TRX_CHAN_MAX; chan++) {
|
|
|
|
if (trx_chan_desc[chan].chan_nr != (chan_nr & RSL_CHAN_NR_MASK))
|
2020-10-17 07:07:46 +00:00
|
|
|
continue;
|
2023-03-07 01:52:25 +00:00
|
|
|
if (trx_chan_desc[chan].link_id != link_id)
|
2020-10-17 07:07:46 +00:00
|
|
|
continue;
|
2023-03-07 01:52:25 +00:00
|
|
|
if (l1ts->chan_state[chan].active == active)
|
2020-10-17 07:07:46 +00:00
|
|
|
continue;
|
2020-10-17 07:28:55 +00:00
|
|
|
found = true;
|
2023-03-07 01:52:25 +00:00
|
|
|
_trx_sched_set_lchan(lchan, chan, active);
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
2013-06-12 14:53:55 +00:00
|
|
|
/* disable handover detection (on deactivation) */
|
2016-01-09 22:21:00 +00:00
|
|
|
if (!active)
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
_sched_act_rach_det(lchan->ts->trx, tn, ss, 0);
|
2013-06-12 14:53:55 +00:00
|
|
|
|
2020-10-17 07:28:55 +00:00
|
|
|
return found ? 0 : -EINVAL;
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
2023-03-07 01:52:25 +00:00
|
|
|
int trx_sched_set_bcch_ccch(struct gsm_lchan *lchan, bool active)
|
|
|
|
{
|
|
|
|
struct l1sched_ts *l1ts = lchan->ts->priv;
|
|
|
|
static const enum trx_chan_type chans[] = {
|
|
|
|
TRXC_FCCH,
|
|
|
|
TRXC_SCH,
|
|
|
|
TRXC_BCCH,
|
|
|
|
TRXC_RACH,
|
|
|
|
TRXC_CCCH,
|
|
|
|
};
|
|
|
|
|
|
|
|
if (!l1ts)
|
|
|
|
return -EINVAL;
|
|
|
|
|
|
|
|
for (unsigned int i = 0; i < ARRAY_SIZE(chans); i++) {
|
|
|
|
enum trx_chan_type chan = chans[i];
|
|
|
|
|
|
|
|
if (l1ts->chan_state[chan].active == active)
|
|
|
|
continue;
|
|
|
|
_trx_sched_set_lchan(lchan, chan, active);
|
|
|
|
}
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2013-02-14 10:21:13 +00:00
|
|
|
/* setting all logical channels given attributes to active/inactive */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int trx_sched_set_mode(struct gsm_bts_trx_ts *ts, uint8_t chan_nr, uint8_t rsl_cmode,
|
2013-03-26 08:05:14 +00:00
|
|
|
uint8_t tch_mode, int codecs, uint8_t codec0, uint8_t codec1,
|
2013-06-12 07:12:04 +00:00
|
|
|
uint8_t codec2, uint8_t codec3, uint8_t initial_id, uint8_t handover)
|
2013-02-14 10:21:13 +00:00
|
|
|
{
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
struct l1sched_ts *l1ts = ts->priv;
|
2013-02-14 10:21:13 +00:00
|
|
|
uint8_t tn = L1SAP_CHAN2TS(chan_nr);
|
2013-06-12 07:12:04 +00:00
|
|
|
uint8_t ss = l1sap_chan2ss(chan_nr);
|
2013-02-14 10:21:13 +00:00
|
|
|
int i;
|
|
|
|
int rc = -EINVAL;
|
|
|
|
|
2013-06-29 19:42:58 +00:00
|
|
|
/* no mode for PDCH */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
if (ts->pchan == GSM_PCHAN_PDCH)
|
2013-06-29 19:42:58 +00:00
|
|
|
return 0;
|
|
|
|
|
2021-05-27 16:26:29 +00:00
|
|
|
/* VAMOS: convert Osmocom specific channel number to a generic one,
|
|
|
|
* otherwise we won't match anything in trx_chan_desc[]. */
|
|
|
|
if (ts->vamos.is_shadow)
|
|
|
|
chan_nr &= ~RSL_CHAN_OSMO_VAMOS_MASK;
|
|
|
|
|
2013-02-14 10:21:13 +00:00
|
|
|
/* look for all matching chan_nr/link_id */
|
|
|
|
for (i = 0; i < _TRX_CHAN_MAX; i++) {
|
|
|
|
if (trx_chan_desc[i].chan_nr == (chan_nr & 0xf8)
|
|
|
|
&& trx_chan_desc[i].link_id == 0x00) {
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
struct l1sched_chan_state *chan_state = &l1ts->chan_state[i];
|
|
|
|
|
2022-03-02 18:02:16 +00:00
|
|
|
LOGP(DL1C, LOGL_INFO,
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
"%s Set mode for %s (rsl_cmode=%u, tch_mode=%u, handover=%u)\n",
|
|
|
|
gsm_ts_name(ts), trx_chan_desc[i].name,
|
|
|
|
rsl_cmode, tch_mode, handover);
|
|
|
|
|
2013-03-26 08:05:14 +00:00
|
|
|
chan_state->rsl_cmode = rsl_cmode;
|
|
|
|
chan_state->tch_mode = tch_mode;
|
2013-06-12 07:12:04 +00:00
|
|
|
chan_state->ho_rach_detect = handover;
|
2013-03-26 08:05:14 +00:00
|
|
|
if (rsl_cmode == RSL_CMOD_SPD_SPEECH
|
|
|
|
&& tch_mode == GSM48_CMODE_SPEECH_AMR) {
|
|
|
|
chan_state->codecs = codecs;
|
|
|
|
chan_state->codec[0] = codec0;
|
|
|
|
chan_state->codec[1] = codec1;
|
|
|
|
chan_state->codec[2] = codec2;
|
|
|
|
chan_state->codec[3] = codec3;
|
|
|
|
chan_state->ul_ft = initial_id;
|
|
|
|
chan_state->dl_ft = initial_id;
|
|
|
|
chan_state->ul_cmr = initial_id;
|
|
|
|
chan_state->dl_cmr = initial_id;
|
2022-04-12 13:12:41 +00:00
|
|
|
chan_state->lqual_cb_sum = 0;
|
|
|
|
chan_state->lqual_cb_num = 0;
|
2013-03-26 08:05:14 +00:00
|
|
|
}
|
2013-02-14 10:21:13 +00:00
|
|
|
rc = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2013-06-12 07:12:04 +00:00
|
|
|
/* command rach detection
|
|
|
|
* always enable handover, even if state is still set (due to loss
|
|
|
|
* of transceiver link).
|
|
|
|
* disable handover, if state is still set, since we might not know
|
|
|
|
* the actual state of transceiver (due to loss of link) */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
_sched_act_rach_det(ts->trx, tn, ss, handover);
|
2013-06-12 07:12:04 +00:00
|
|
|
|
2013-02-14 10:21:13 +00:00
|
|
|
return rc;
|
|
|
|
}
|
|
|
|
|
2013-02-21 08:27:52 +00:00
|
|
|
/* setting cipher on logical channels */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int trx_sched_set_cipher(struct gsm_lchan *lchan, uint8_t chan_nr, bool downlink)
|
2013-02-21 08:27:52 +00:00
|
|
|
{
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int algo = lchan->encr.alg_id - 1;
|
|
|
|
int i, rc = -EINVAL;
|
2013-02-21 08:27:52 +00:00
|
|
|
|
2013-06-29 19:42:58 +00:00
|
|
|
/* no cipher for PDCH */
|
2021-06-22 14:01:43 +00:00
|
|
|
if (ts_pchan(lchan->ts) == GSM_PCHAN_PDCH)
|
2013-06-29 19:42:58 +00:00
|
|
|
return 0;
|
|
|
|
|
2021-05-27 16:26:29 +00:00
|
|
|
/* VAMOS: convert Osmocom specific channel number to a generic one,
|
|
|
|
* otherwise we won't match anything in trx_chan_desc[]. */
|
|
|
|
if (lchan->ts->vamos.is_shadow)
|
|
|
|
chan_nr &= ~RSL_CHAN_OSMO_VAMOS_MASK;
|
|
|
|
|
2013-06-20 18:10:46 +00:00
|
|
|
/* no algorithm given means a5/0 */
|
|
|
|
if (algo <= 0)
|
|
|
|
algo = 0;
|
2021-06-09 02:01:18 +00:00
|
|
|
else if (lchan->encr.key_len != 8 && lchan->encr.key_len != 16) {
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGPLCHAN(lchan, DL1C, LOGL_ERROR,
|
|
|
|
"Algo A5/%d not supported with given key_len=%u\n",
|
|
|
|
algo, lchan->encr.key_len);
|
2013-02-21 08:27:52 +00:00
|
|
|
return -ENOTSUP;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* look for all matching chan_nr */
|
|
|
|
for (i = 0; i < _TRX_CHAN_MAX; i++) {
|
2020-10-18 10:56:51 +00:00
|
|
|
if (trx_chan_desc[i].chan_nr == (chan_nr & RSL_CHAN_NR_MASK)) {
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
struct l1sched_ts *l1ts = lchan->ts->priv;
|
|
|
|
struct l1sched_chan_state *l1cs = &l1ts->chan_state[i];
|
|
|
|
|
2022-03-02 18:02:16 +00:00
|
|
|
LOGPLCHAN(lchan, DL1C, LOGL_INFO, "Set A5/%d %s for %s\n",
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
algo, (downlink) ? "downlink" : "uplink",
|
|
|
|
trx_chan_desc[i].name);
|
|
|
|
|
2013-02-21 08:27:52 +00:00
|
|
|
if (downlink) {
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
l1cs->dl_encr_algo = algo;
|
|
|
|
memcpy(l1cs->dl_encr_key, lchan->encr.key, lchan->encr.key_len);
|
|
|
|
l1cs->dl_encr_key_len = lchan->encr.key_len;
|
2013-02-21 08:27:52 +00:00
|
|
|
} else {
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
l1cs->ul_encr_algo = algo;
|
|
|
|
memcpy(l1cs->ul_encr_key, lchan->encr.key, lchan->encr.key_len);
|
|
|
|
l1cs->ul_encr_key_len = lchan->encr.key_len;
|
2013-02-21 08:27:52 +00:00
|
|
|
}
|
|
|
|
rc = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return rc;
|
|
|
|
}
|
|
|
|
|
2013-02-05 10:45:28 +00:00
|
|
|
/* process ready-to-send */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int _sched_rts(const struct l1sched_ts *l1ts, uint32_t fn)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
2016-01-09 12:43:50 +00:00
|
|
|
const struct trx_sched_frame *frame;
|
2013-02-05 10:45:28 +00:00
|
|
|
uint8_t offset, period, bid;
|
|
|
|
trx_sched_rts_func *func;
|
|
|
|
enum trx_chan_type chan;
|
|
|
|
|
|
|
|
/* no multiframe set */
|
2016-01-09 20:33:58 +00:00
|
|
|
if (!l1ts->mf_index)
|
2013-02-05 10:45:28 +00:00
|
|
|
return 0;
|
|
|
|
|
|
|
|
/* get frame from multiframe */
|
2016-01-09 20:33:58 +00:00
|
|
|
period = l1ts->mf_period;
|
2013-02-05 10:45:28 +00:00
|
|
|
offset = fn % period;
|
2016-01-09 20:33:58 +00:00
|
|
|
frame = l1ts->mf_frames + offset;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
|
|
|
chan = frame->dl_chan;
|
|
|
|
bid = frame->dl_bid;
|
|
|
|
func = trx_chan_desc[frame->dl_chan].rts_fn;
|
|
|
|
|
|
|
|
/* only on bid == 0 */
|
|
|
|
if (bid != 0)
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
/* no RTS function */
|
|
|
|
if (!func)
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
/* check if channel is active */
|
2023-03-07 01:52:25 +00:00
|
|
|
if (!l1ts->chan_state[chan].active)
|
2013-02-05 10:45:28 +00:00
|
|
|
return -EINVAL;
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
/* There is no burst, just for logging */
|
|
|
|
struct trx_dl_burst_req dbr = {
|
|
|
|
.fn = fn,
|
|
|
|
.tn = l1ts->ts->nr,
|
|
|
|
.bid = bid,
|
|
|
|
.chan = chan,
|
|
|
|
};
|
|
|
|
|
|
|
|
return func(l1ts, &dbr);
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
2021-08-29 13:32:51 +00:00
|
|
|
static void trx_sched_apply_att(const struct gsm_lchan *lchan,
|
|
|
|
struct trx_dl_burst_req *br)
|
|
|
|
{
|
|
|
|
const struct trx_chan_desc *desc = &trx_chan_desc[br->chan];
|
|
|
|
|
|
|
|
/* Current BS power reduction value in dB */
|
|
|
|
br->att = lchan->bs_power_ctrl.current;
|
|
|
|
|
|
|
|
/* Temporary Overpower for SACCH/FACCH bursts */
|
2021-10-22 00:23:58 +00:00
|
|
|
if (!lchan->top_acch_active)
|
2021-08-29 13:32:51 +00:00
|
|
|
return;
|
2021-10-21 21:33:25 +00:00
|
|
|
if ((lchan->top_acch_cap.sacch_enable && desc->link_id == LID_SACCH) ||
|
|
|
|
(lchan->top_acch_cap.facch_enable && br->flags & TRX_BR_F_FACCH)) {
|
|
|
|
if (br->att > lchan->top_acch_cap.overpower_db)
|
|
|
|
br->att -= lchan->top_acch_cap.overpower_db;
|
2021-08-29 13:32:51 +00:00
|
|
|
else
|
|
|
|
br->att = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2013-02-05 10:45:28 +00:00
|
|
|
/* process downlink burst */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
void _sched_dl_burst(struct l1sched_ts *l1ts, struct trx_dl_burst_req *br)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
const struct l1sched_chan_state *l1cs;
|
2016-01-09 12:43:50 +00:00
|
|
|
const struct trx_sched_frame *frame;
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
uint8_t offset, period;
|
2013-02-05 10:45:28 +00:00
|
|
|
trx_sched_dl_func *func;
|
|
|
|
|
2016-01-09 20:33:58 +00:00
|
|
|
if (!l1ts->mf_index)
|
2020-06-28 03:48:50 +00:00
|
|
|
return;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
|
|
|
/* get frame from multiframe */
|
2016-01-09 20:33:58 +00:00
|
|
|
period = l1ts->mf_period;
|
2020-06-13 14:45:33 +00:00
|
|
|
offset = br->fn % period;
|
2016-01-09 20:33:58 +00:00
|
|
|
frame = l1ts->mf_frames + offset;
|
2016-01-09 17:11:39 +00:00
|
|
|
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
br->chan = frame->dl_chan;
|
|
|
|
br->bid = frame->dl_bid;
|
|
|
|
func = trx_chan_desc[br->chan].dl_fn;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
l1cs = &l1ts->chan_state[br->chan];
|
2016-01-09 20:33:58 +00:00
|
|
|
|
2013-02-05 10:45:28 +00:00
|
|
|
/* check if channel is active */
|
2023-03-07 01:52:25 +00:00
|
|
|
if (!l1cs->active)
|
2020-06-28 03:48:50 +00:00
|
|
|
return;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2021-05-19 00:50:30 +00:00
|
|
|
/* Training Sequence Code and Set */
|
2021-05-22 01:33:13 +00:00
|
|
|
br->tsc_set = l1ts->ts->tsc_set;
|
|
|
|
br->tsc = l1ts->ts->tsc;
|
2021-05-19 00:50:30 +00:00
|
|
|
|
2013-02-05 10:45:28 +00:00
|
|
|
/* get burst from function */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
if (func(l1ts, br) != 0)
|
2020-06-28 03:48:50 +00:00
|
|
|
return;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2021-05-19 00:50:30 +00:00
|
|
|
/* Modulation is indicated by func() */
|
|
|
|
br->mod = l1cs->dl_mod_type;
|
|
|
|
|
2020-06-15 11:51:01 +00:00
|
|
|
/* BS Power reduction (in dB) per logical channel */
|
2020-06-15 13:51:21 +00:00
|
|
|
if (l1cs->lchan != NULL)
|
2021-08-29 13:32:51 +00:00
|
|
|
trx_sched_apply_att(l1cs->lchan, br);
|
2020-06-15 13:51:21 +00:00
|
|
|
|
2013-02-21 08:27:52 +00:00
|
|
|
/* encrypt */
|
2020-06-13 14:45:33 +00:00
|
|
|
if (br->burst_len && l1cs->dl_encr_algo) {
|
2013-02-21 08:27:52 +00:00
|
|
|
ubit_t ks[114];
|
|
|
|
int i;
|
|
|
|
|
2020-06-13 14:45:33 +00:00
|
|
|
osmo_a5(l1cs->dl_encr_algo, l1cs->dl_encr_key, br->fn, ks, NULL);
|
2013-02-21 08:27:52 +00:00
|
|
|
for (i = 0; i < 57; i++) {
|
2020-06-13 14:45:33 +00:00
|
|
|
br->burst[i + 3] ^= ks[i];
|
|
|
|
br->burst[i + 88] ^= ks[i + 57];
|
2013-02-21 08:27:52 +00:00
|
|
|
}
|
|
|
|
}
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
static int trx_sched_calc_frame_loss(struct l1sched_ts *l1ts,
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
struct l1sched_chan_state *l1cs,
|
|
|
|
const struct trx_ul_burst_ind *bi)
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
{
|
|
|
|
const struct trx_sched_frame *frame;
|
|
|
|
uint32_t elapsed_fs;
|
|
|
|
uint8_t offset, i;
|
|
|
|
uint32_t fn_i;
|
|
|
|
|
|
|
|
/**
|
|
|
|
* When a channel is just activated, the MS needs some time
|
|
|
|
* to synchronize and start burst transmission,
|
|
|
|
* so let's wait until the first UL burst...
|
|
|
|
*/
|
|
|
|
if (l1cs->proc_tdma_fs == 0)
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
/* Not applicable for some logical channels */
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
switch (bi->chan) {
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
case TRXC_IDLE:
|
|
|
|
case TRXC_RACH:
|
|
|
|
case TRXC_PDTCH:
|
|
|
|
case TRXC_PTCCH:
|
|
|
|
return 0;
|
|
|
|
default:
|
|
|
|
/* No applicable if we are waiting for handover RACH */
|
|
|
|
if (l1cs->ho_rach_detect)
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* How many frames elapsed since the last one? */
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
elapsed_fs = GSM_TDMA_FN_SUB(bi->fn, l1cs->last_tdma_fn);
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
if (elapsed_fs > l1ts->mf_period) { /* Too many! */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGL1SB(DL1P, LOGL_ERROR, l1ts, bi,
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
"Too many (>%u) contiguous TDMA frames=%u elapsed "
|
|
|
|
"since the last processed fn=%u\n", l1ts->mf_period,
|
|
|
|
elapsed_fs, l1cs->last_tdma_fn);
|
|
|
|
/* FIXME: how should this affect the measurements? */
|
|
|
|
return -EINVAL;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* There are several TDMA frames between the last processed
|
|
|
|
* frame and currently received one. Let's walk through this
|
|
|
|
* path and count potentially lost frames, i.e. for which
|
2019-10-13 17:09:39 +00:00
|
|
|
* we didn't receive the corresponding UL bursts.
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
*
|
|
|
|
* Start counting from the last_fn + 1.
|
|
|
|
*/
|
|
|
|
for (i = 1; i < elapsed_fs; i++) {
|
2020-06-16 22:08:54 +00:00
|
|
|
fn_i = GSM_TDMA_FN_SUM(l1cs->last_tdma_fn, i);
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
offset = fn_i % l1ts->mf_period;
|
|
|
|
frame = l1ts->mf_frames + offset;
|
|
|
|
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
if (frame->ul_chan == bi->chan)
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
l1cs->lost_tdma_fs++;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (l1cs->lost_tdma_fs > 0) {
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGL1SB(DL1P, LOGL_NOTICE, l1ts, bi,
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
"At least %u TDMA frames were lost since the last "
|
|
|
|
"processed fn=%u\n", l1cs->lost_tdma_fs, l1cs->last_tdma_fn);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* HACK: substitute lost bursts by zero-filled ones
|
|
|
|
*
|
|
|
|
* Instead of doing this, it makes sense to use the
|
|
|
|
* amount of lost frames in measurement calculations.
|
|
|
|
*/
|
|
|
|
trx_sched_ul_func *func;
|
|
|
|
|
2019-06-26 20:57:11 +00:00
|
|
|
/* Prepare dummy burst indication */
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
struct trx_ul_burst_ind dbi = {
|
2019-06-26 20:57:11 +00:00
|
|
|
.flags = TRX_BI_F_NOPE_IND,
|
|
|
|
.burst_len = GSM_BURST_LEN,
|
|
|
|
.burst = { 0 },
|
|
|
|
.rssi = -128,
|
|
|
|
.toa256 = 0,
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
.chan = bi->chan,
|
2019-06-26 20:57:11 +00:00
|
|
|
/* TDMA FN is set below */
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
.tn = bi->tn,
|
2019-06-26 20:57:11 +00:00
|
|
|
};
|
|
|
|
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
for (i = 1; i < elapsed_fs; i++) {
|
2020-06-16 22:08:54 +00:00
|
|
|
fn_i = GSM_TDMA_FN_SUM(l1cs->last_tdma_fn, i);
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
offset = fn_i % l1ts->mf_period;
|
|
|
|
frame = l1ts->mf_frames + offset;
|
|
|
|
func = trx_chan_desc[frame->ul_chan].ul_fn;
|
|
|
|
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
if (frame->ul_chan != bi->chan)
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
continue;
|
|
|
|
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
dbi.bid = frame->ul_bid;
|
|
|
|
dbi.fn = fn_i;
|
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
LOGL1SB(DL1P, LOGL_NOTICE, l1ts, &dbi,
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
"Substituting lost burst with NOPE.ind\n");
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
func(l1ts, &dbi);
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
|
|
|
|
l1cs->lost_tdma_fs--;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2021-06-08 15:54:24 +00:00
|
|
|
/* Process a single noise measurement for an inactive timeslot. */
|
|
|
|
static void trx_sched_noise_meas(struct l1sched_chan_state *l1cs,
|
|
|
|
const struct trx_ul_burst_ind *bi)
|
|
|
|
{
|
|
|
|
int *Avg = &l1cs->meas.interf_avg;
|
|
|
|
|
|
|
|
/* EWMA (Exponentially Weighted Moving Average):
|
|
|
|
*
|
|
|
|
* Avg[n] = a * Val[n] + (1 - a) * Avg[n - 1]
|
|
|
|
*
|
|
|
|
* Implemented using the '+=' operator:
|
|
|
|
*
|
|
|
|
* Avg += a * Val - a * Avg
|
|
|
|
* Avg += a * (Val - Avg)
|
|
|
|
*
|
|
|
|
* We use constant 'a' = 0.5, what is equal to:
|
|
|
|
*
|
|
|
|
* Avg += (Val - Avg) / 2
|
|
|
|
*
|
|
|
|
* We don't really need precisity here, so no scaling.
|
|
|
|
*/
|
|
|
|
|
|
|
|
*Avg += (bi->rssi - *Avg) / 2;
|
|
|
|
}
|
|
|
|
|
osmo-bts-trx/trx_if.c: introduce TRXD header version handling
It may be necessary to extend the message specific header with
more information. Since this is not a TLV-based protocol, we
need to include the header format version.
+-----------------+---------------------------+
| 7 6 5 4 3 2 1 0 | bit numbers (value range) |
+-----------------+---------------------------+
| X X X X . . . . | header version (0..15) |
+-----------------+---------------------------+
| . . . . . X X X | TDMA TN (0..7) |
+-----------------+---------------------------+
| . . . . X . . . | RESERVED (0) |
+-----------------+---------------------------+
Instead of prepending an additional byte, it was decided to use
4 MSB bits of the first octet, which used to be zero-initialized
due to the value range of TDMA TN (0..7). Therefore the current
header format has implicit version 0.
Otherwise Wireshark (or trx_sniff.py) would have to guess the
header version, or alternatively follow the control channel
looking for the version setting command.
This change introduces a new structure 'trx_ul_burst_ind', which
represents an Uplink burst and the corresponding meta info. The
purpose of this structure is to avoid overloading the existing
functions, such as trx_sched_ul_burst(), with more and more
arguments every time we bump the version.
On receipt of a TRXD message, trx_data_read_cb() now parses
the header version, and calls the corresponding dissector
functions, e.g. trx_data_handle_(hdr|burst)_v0().
Change-Id: I171c18229ca3e5cab70de0064a31e47c78602c0c
Related: OS#4006
2019-06-25 11:23:14 +00:00
|
|
|
/* Process an Uplink burst indication */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
int trx_sched_ul_burst(struct l1sched_ts *l1ts, struct trx_ul_burst_ind *bi)
|
2013-02-05 10:45:28 +00:00
|
|
|
{
|
2016-01-09 20:33:58 +00:00
|
|
|
struct l1sched_chan_state *l1cs;
|
2016-01-09 12:43:50 +00:00
|
|
|
const struct trx_sched_frame *frame;
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
uint8_t offset, period;
|
2013-02-05 10:45:28 +00:00
|
|
|
trx_sched_ul_func *func;
|
|
|
|
|
2021-05-27 19:51:44 +00:00
|
|
|
/* VAMOS: redirect to the shadow timeslot */
|
|
|
|
if (bi->flags & TRX_BI_F_SHADOW_IND)
|
|
|
|
l1ts = l1ts->ts->vamos.peer->priv;
|
|
|
|
|
2016-01-09 20:33:58 +00:00
|
|
|
if (!l1ts->mf_index)
|
2013-02-05 10:45:28 +00:00
|
|
|
return -EINVAL;
|
|
|
|
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
/* get frame from multiframe */
|
|
|
|
period = l1ts->mf_period;
|
osmo-bts-trx/trx_if.c: introduce TRXD header version handling
It may be necessary to extend the message specific header with
more information. Since this is not a TLV-based protocol, we
need to include the header format version.
+-----------------+---------------------------+
| 7 6 5 4 3 2 1 0 | bit numbers (value range) |
+-----------------+---------------------------+
| X X X X . . . . | header version (0..15) |
+-----------------+---------------------------+
| . . . . . X X X | TDMA TN (0..7) |
+-----------------+---------------------------+
| . . . . X . . . | RESERVED (0) |
+-----------------+---------------------------+
Instead of prepending an additional byte, it was decided to use
4 MSB bits of the first octet, which used to be zero-initialized
due to the value range of TDMA TN (0..7). Therefore the current
header format has implicit version 0.
Otherwise Wireshark (or trx_sniff.py) would have to guess the
header version, or alternatively follow the control channel
looking for the version setting command.
This change introduces a new structure 'trx_ul_burst_ind', which
represents an Uplink burst and the corresponding meta info. The
purpose of this structure is to avoid overloading the existing
functions, such as trx_sched_ul_burst(), with more and more
arguments every time we bump the version.
On receipt of a TRXD message, trx_data_read_cb() now parses
the header version, and calls the corresponding dissector
functions, e.g. trx_data_handle_(hdr|burst)_v0().
Change-Id: I171c18229ca3e5cab70de0064a31e47c78602c0c
Related: OS#4006
2019-06-25 11:23:14 +00:00
|
|
|
offset = bi->fn % period;
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
frame = l1ts->mf_frames + offset;
|
2013-02-15 15:17:43 +00:00
|
|
|
|
[VAMOS] osmo-bts-trx: move {chan,bid} to trx_{dl,ul}_burst_{req,ind}
Historically the logical channel handlers like rx_data_fn() used to accept
quite a lot of arguments. With the introduction of additional measurement
parameters it has become clear that we need to group the arguments into
structures. This is why both 'trx_{dl,ul}_burst_{req,ind}' structures
were introduced.
However, both channel type and burst ID were kept untouched, so until
now we had them being passed between the scheduler functions here and
there. This change is a logical conclusion of the original change
mentioned above.
As a part of this change, the new LOGL1SB() macro is introduced. It
does accept a pointer to 'trx_{dl,ul}_burst_{req,ind}' and expands the
context information for the old LOGL1S() macro.
Change-Id: Ic5a02b074662b3e429bf18e05a982f3f3e7b7444
2021-05-07 14:20:58 +00:00
|
|
|
bi->chan = frame->ul_chan;
|
|
|
|
bi->bid = frame->ul_bid;
|
|
|
|
l1cs = &l1ts->chan_state[bi->chan];
|
|
|
|
func = trx_chan_desc[bi->chan].ul_fn;
|
2013-02-15 15:17:43 +00:00
|
|
|
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
/* check if channel is active */
|
2023-03-07 01:52:25 +00:00
|
|
|
if (!l1cs->active) {
|
2021-06-17 21:50:55 +00:00
|
|
|
/* handle noise measurements on dedicated and idle channels */
|
|
|
|
if (TRX_CHAN_IS_DEDIC(bi->chan) || bi->chan == TRXC_IDLE)
|
2021-06-08 15:54:24 +00:00
|
|
|
trx_sched_noise_meas(l1cs, bi);
|
|
|
|
return 0;
|
|
|
|
}
|
2013-02-21 08:27:52 +00:00
|
|
|
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
/* omit bursts which have no handler, like IDLE bursts */
|
|
|
|
if (!func)
|
|
|
|
return -EINVAL;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
/* calculate how many TDMA frames were potentially lost */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
trx_sched_calc_frame_loss(l1ts, l1cs, bi);
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
|
|
|
|
/* update TDMA frame counters */
|
osmo-bts-trx/trx_if.c: introduce TRXD header version handling
It may be necessary to extend the message specific header with
more information. Since this is not a TLV-based protocol, we
need to include the header format version.
+-----------------+---------------------------+
| 7 6 5 4 3 2 1 0 | bit numbers (value range) |
+-----------------+---------------------------+
| X X X X . . . . | header version (0..15) |
+-----------------+---------------------------+
| . . . . . X X X | TDMA TN (0..7) |
+-----------------+---------------------------+
| . . . . X . . . | RESERVED (0) |
+-----------------+---------------------------+
Instead of prepending an additional byte, it was decided to use
4 MSB bits of the first octet, which used to be zero-initialized
due to the value range of TDMA TN (0..7). Therefore the current
header format has implicit version 0.
Otherwise Wireshark (or trx_sniff.py) would have to guess the
header version, or alternatively follow the control channel
looking for the version setting command.
This change introduces a new structure 'trx_ul_burst_ind', which
represents an Uplink burst and the corresponding meta info. The
purpose of this structure is to avoid overloading the existing
functions, such as trx_sched_ul_burst(), with more and more
arguments every time we bump the version.
On receipt of a TRXD message, trx_data_read_cb() now parses
the header version, and calls the corresponding dissector
functions, e.g. trx_data_handle_(hdr|burst)_v0().
Change-Id: I171c18229ca3e5cab70de0064a31e47c78602c0c
Related: OS#4006
2019-06-25 11:23:14 +00:00
|
|
|
l1cs->last_tdma_fn = bi->fn;
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
l1cs->proc_tdma_fs++;
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2020-03-20 11:43:51 +00:00
|
|
|
/* handle NOPE indications */
|
2019-11-06 10:33:31 +00:00
|
|
|
if (bi->flags & TRX_BI_F_NOPE_IND) {
|
2022-03-20 09:04:38 +00:00
|
|
|
/* NOTE: Uplink burst handler must check bi->burst_len before
|
|
|
|
* accessing bi->burst to avoid uninitialized memory access. */
|
|
|
|
return func(l1ts, bi);
|
2019-11-06 10:33:31 +00:00
|
|
|
}
|
|
|
|
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
/* decrypt */
|
osmo-bts-trx/trx_if.c: introduce TRXD header version handling
It may be necessary to extend the message specific header with
more information. Since this is not a TLV-based protocol, we
need to include the header format version.
+-----------------+---------------------------+
| 7 6 5 4 3 2 1 0 | bit numbers (value range) |
+-----------------+---------------------------+
| X X X X . . . . | header version (0..15) |
+-----------------+---------------------------+
| . . . . . X X X | TDMA TN (0..7) |
+-----------------+---------------------------+
| . . . . X . . . | RESERVED (0) |
+-----------------+---------------------------+
Instead of prepending an additional byte, it was decided to use
4 MSB bits of the first octet, which used to be zero-initialized
due to the value range of TDMA TN (0..7). Therefore the current
header format has implicit version 0.
Otherwise Wireshark (or trx_sniff.py) would have to guess the
header version, or alternatively follow the control channel
looking for the version setting command.
This change introduces a new structure 'trx_ul_burst_ind', which
represents an Uplink burst and the corresponding meta info. The
purpose of this structure is to avoid overloading the existing
functions, such as trx_sched_ul_burst(), with more and more
arguments every time we bump the version.
On receipt of a TRXD message, trx_data_read_cb() now parses
the header version, and calls the corresponding dissector
functions, e.g. trx_data_handle_(hdr|burst)_v0().
Change-Id: I171c18229ca3e5cab70de0064a31e47c78602c0c
Related: OS#4006
2019-06-25 11:23:14 +00:00
|
|
|
if (bi->burst_len && l1cs->ul_encr_algo) {
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
ubit_t ks[114];
|
|
|
|
int i;
|
|
|
|
|
osmo-bts-trx/trx_if.c: introduce TRXD header version handling
It may be necessary to extend the message specific header with
more information. Since this is not a TLV-based protocol, we
need to include the header format version.
+-----------------+---------------------------+
| 7 6 5 4 3 2 1 0 | bit numbers (value range) |
+-----------------+---------------------------+
| X X X X . . . . | header version (0..15) |
+-----------------+---------------------------+
| . . . . . X X X | TDMA TN (0..7) |
+-----------------+---------------------------+
| . . . . X . . . | RESERVED (0) |
+-----------------+---------------------------+
Instead of prepending an additional byte, it was decided to use
4 MSB bits of the first octet, which used to be zero-initialized
due to the value range of TDMA TN (0..7). Therefore the current
header format has implicit version 0.
Otherwise Wireshark (or trx_sniff.py) would have to guess the
header version, or alternatively follow the control channel
looking for the version setting command.
This change introduces a new structure 'trx_ul_burst_ind', which
represents an Uplink burst and the corresponding meta info. The
purpose of this structure is to avoid overloading the existing
functions, such as trx_sched_ul_burst(), with more and more
arguments every time we bump the version.
On receipt of a TRXD message, trx_data_read_cb() now parses
the header version, and calls the corresponding dissector
functions, e.g. trx_data_handle_(hdr|burst)_v0().
Change-Id: I171c18229ca3e5cab70de0064a31e47c78602c0c
Related: OS#4006
2019-06-25 11:23:14 +00:00
|
|
|
osmo_a5(l1cs->ul_encr_algo, l1cs->ul_encr_key, bi->fn, NULL, ks);
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
for (i = 0; i < 57; i++) {
|
|
|
|
if (ks[i])
|
osmo-bts-trx/trx_if.c: introduce TRXD header version handling
It may be necessary to extend the message specific header with
more information. Since this is not a TLV-based protocol, we
need to include the header format version.
+-----------------+---------------------------+
| 7 6 5 4 3 2 1 0 | bit numbers (value range) |
+-----------------+---------------------------+
| X X X X . . . . | header version (0..15) |
+-----------------+---------------------------+
| . . . . . X X X | TDMA TN (0..7) |
+-----------------+---------------------------+
| . . . . X . . . | RESERVED (0) |
+-----------------+---------------------------+
Instead of prepending an additional byte, it was decided to use
4 MSB bits of the first octet, which used to be zero-initialized
due to the value range of TDMA TN (0..7). Therefore the current
header format has implicit version 0.
Otherwise Wireshark (or trx_sniff.py) would have to guess the
header version, or alternatively follow the control channel
looking for the version setting command.
This change introduces a new structure 'trx_ul_burst_ind', which
represents an Uplink burst and the corresponding meta info. The
purpose of this structure is to avoid overloading the existing
functions, such as trx_sched_ul_burst(), with more and more
arguments every time we bump the version.
On receipt of a TRXD message, trx_data_read_cb() now parses
the header version, and calls the corresponding dissector
functions, e.g. trx_data_handle_(hdr|burst)_v0().
Change-Id: I171c18229ca3e5cab70de0064a31e47c78602c0c
Related: OS#4006
2019-06-25 11:23:14 +00:00
|
|
|
bi->burst[i + 3] = - bi->burst[i + 3];
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
if (ks[i + 57])
|
osmo-bts-trx/trx_if.c: introduce TRXD header version handling
It may be necessary to extend the message specific header with
more information. Since this is not a TLV-based protocol, we
need to include the header format version.
+-----------------+---------------------------+
| 7 6 5 4 3 2 1 0 | bit numbers (value range) |
+-----------------+---------------------------+
| X X X X . . . . | header version (0..15) |
+-----------------+---------------------------+
| . . . . . X X X | TDMA TN (0..7) |
+-----------------+---------------------------+
| . . . . X . . . | RESERVED (0) |
+-----------------+---------------------------+
Instead of prepending an additional byte, it was decided to use
4 MSB bits of the first octet, which used to be zero-initialized
due to the value range of TDMA TN (0..7). Therefore the current
header format has implicit version 0.
Otherwise Wireshark (or trx_sniff.py) would have to guess the
header version, or alternatively follow the control channel
looking for the version setting command.
This change introduces a new structure 'trx_ul_burst_ind', which
represents an Uplink burst and the corresponding meta info. The
purpose of this structure is to avoid overloading the existing
functions, such as trx_sched_ul_burst(), with more and more
arguments every time we bump the version.
On receipt of a TRXD message, trx_data_read_cb() now parses
the header version, and calls the corresponding dissector
functions, e.g. trx_data_handle_(hdr|burst)_v0().
Change-Id: I171c18229ca3e5cab70de0064a31e47c78602c0c
Related: OS#4006
2019-06-25 11:23:14 +00:00
|
|
|
bi->burst[i + 88] = - bi->burst[i + 88];
|
common/scheduler.c: track TDMA frame loss per logical channels
This change modifies the logic of TDMA frame loss tracking. To
be more precise, the tracking logic was moved from per timeslot
level to per logical channel level, what makes OsmoBTS more
accurate in its measurements.
But before getting into details, it's important to clarify some
things about the Uplink burst processing in transceiver (OsmoTRX).
If an Uplink burst is detected, OsmoTRX demodulates it and sends
to OsmoBTS. If nothing is detected on a particular timeslot,
OsmoTRX will do nothing. In other words, it will not
notify OsmoBTS about this.
Meanwhile, there are usually a few logical channels mapped to a
single TDMA timeslot. Let's use SDCCH8 channel configuration as
an example (simplified layout):
/* SDCCH/8 (ss=0), subscriber A (active) */
{ TRXC_SDCCH8_0, bid=0 },
{ TRXC_SDCCH8_0, bid=1 },
{ TRXC_SDCCH8_0, bid=2 },
{ TRXC_SDCCH8_0, bid=3 }, // <-- last_fn=X
/* SDCCH/8 (ss=1), subscriber B (inactive) */
{ TRXC_SDCCH8_1, bid=0 },
{ TRXC_SDCCH8_1, bid=1 },
{ TRXC_SDCCH8_1, bid=2 },
{ TRXC_SDCCH8_1, bid=3 },
/* SDCCH/8 (ss=2), subscriber C (active) */
{ TRXC_SDCCH8_2, bid=0 }, // <-- current_fn=X+5
{ TRXC_SDCCH8_2, bid=1 },
{ TRXC_SDCCH8_2, bid=2 },
{ TRXC_SDCCH8_2, bid=3 },
SDCCH8 has 8 sub-slots, so up to 8 subscribers can use a single
timeslot. Let's imagine there are three subscribers: A, B, and C.
Both A and C are active subscribers, i.e. they are continuously
transmitting UL bursts, while B is not using ss=1 anymore.
The original way of TDMA frame loss tracking was the following:
- when an UL burst is received, store it's frame number in
the timeslot state structure (last_fn);
- when the next UL burst is received on same timeslot, compute
how many frames elapsed since the last_fn;
- if elapsed = (current_fn - last_fn) is lower than 10, then
iterate from (last_fn + 1) until the current_fn and send
dummy zero-filled bursts to the higher layers;
- otherwise (elapsed > 10), process the current burst,
and do nothing :/
According to our example, subscriber A is sending 4 bursts, then
nobody is sending anything, and then subscriber C is sending
4 bursts. So, there is a 4 frames long gap between the both
transmissions, which is being substituted by dummy bursts. But,
as the logical channel on ss=1 is not active, they are dropped.
This is not that scary, but the current algorithm produces lots
of false-positives, and moreover is not able to track real frame
drops in longer periods (i.e. >10). So, tracking the frame loss
per individual logical channels makes much more sense.
Let's finally drop this hackish 'while (42) { ... }', and track
the amount of lost / received TDMA frames (bursts) individually
per logical channels. Let's also use the multiframe period as
the loss detection period, instead of hardcoded 10. And finally,
let's print more informative debug messages.
Also, it makes sense to use the amount of lost / received bursts
during the calculation of the measurement reports, instead of
sending dummy bursts, but let's do this separately.
Change-Id: I70d05b67a35ddcbdd1b6394dbd7198404a440e76
Related: OS#3428
2018-08-02 09:22:17 +00:00
|
|
|
}
|
2013-02-15 15:17:43 +00:00
|
|
|
}
|
2013-02-11 11:52:56 +00:00
|
|
|
|
2019-06-26 20:57:11 +00:00
|
|
|
/* Invoke the logical channel handler */
|
[VAMOS] Re-organize osmo-bts-trx specific structures
Together with the 'generic' structures which used to be shared between
osmo-bsc and osmo-bts some time ago, we also have the following
osmo-bts-trx specific structures (in hierarchical order):
- struct l1sched_trx (struct gsm_bts_trx),
- struct l1sched_ts (struct gsm_bts_trx_ts),
- struct l1sched_chan_state (struct gsm_lchan).
These structures are not integrated into the tree of the generic
structures, but maintained in a _separate tree_ instead. Until
recently, only the 'l1sched_trx' had a pointer to generic
'gsm_bts_trx', so in order to find the corresponding 'gsm_lchan' for
'l1sched_chan_state' one would need to traverse all the way up to
'l1sched_trx' and then tracerse another three backwards.
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ l1sched_trx --------------------> gsm_bts_trx (0..255)
| |
--+ l1sched_trx_ts --+ gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
I find this architecture a bit over-complicated, especially given
that 'l1sched_trx' is kind of a dummy node containing nothing else
than a pointer to 'gsm_bts_trx' and the list of 'l1sched_trx_ts'.
In this path I slightly change the architecture as follows:
+ gsm_network
|
--+ gsm_bts (0..255)
|
--+ gsm_bts_trx (0..255)
|
--+ l1sched_trx_ts <----------------> gsm_bts_trx_ts (8)
| |
--+ l1sched_chan_state --+ gsm_lchan (up to 8)
Note that unfortunately we cannot 1:1 map 'l1sched_chan_state' to
'gsm_lchan' (like we do for 'l1sched_trx_ts' and 'gsm_bts_trx_ts')
because there is no direct mapping. The former is a higl-level
representation of a logical channel, while the later represents
one specific logical channel type like FCCH, SDCCH/0 or SACCH/0.
osmo-bts-virtual re-uses the osmo-bts-trx hierarchy, so it's also
affected by this change.
Change-Id: I7c4379e43a25e9d858d582a99bf6c4b65c9af481
2021-05-07 13:47:57 +00:00
|
|
|
func(l1ts, bi);
|
2013-02-05 10:45:28 +00:00
|
|
|
|
2013-02-15 15:17:43 +00:00
|
|
|
return 0;
|
2013-02-05 10:45:28 +00:00
|
|
|
}
|