osmo-bts/include/osmo-bts/scheduler.h

270 lines
8.3 KiB
C
Raw Normal View History

#ifndef TRX_SCHEDULER_H
#define TRX_SCHEDULER_H
#include <osmocom/core/utils.h>
#include <osmocom/core/rate_ctr.h>
#include <osmo-bts/gsm_data.h>
/* Whether a logical channel must be activated automatically */
#define TRX_CHAN_FLAG_AUTO_ACTIVE (1 << 0)
/* Whether a logical channel belongs to PDCH (packet switched data) */
#define TRX_CHAN_FLAG_PDCH (1 << 1)
/* FIXME: we should actually activate 'auto-active' channels */
#define TRX_CHAN_IS_ACTIVE(state, chan) \
(trx_chan_desc[chan].flags & TRX_CHAN_FLAG_AUTO_ACTIVE || (state)->active)
/* These types define the different channels on a multiframe.
* Each channel has queues and can be activated individually.
*/
enum trx_chan_type {
TRXC_IDLE = 0,
TRXC_FCCH,
TRXC_SCH,
TRXC_BCCH,
TRXC_RACH,
TRXC_CCCH,
TRXC_TCHF,
TRXC_TCHH_0,
TRXC_TCHH_1,
TRXC_SDCCH4_0,
TRXC_SDCCH4_1,
TRXC_SDCCH4_2,
TRXC_SDCCH4_3,
TRXC_SDCCH8_0,
TRXC_SDCCH8_1,
TRXC_SDCCH8_2,
TRXC_SDCCH8_3,
TRXC_SDCCH8_4,
TRXC_SDCCH8_5,
TRXC_SDCCH8_6,
TRXC_SDCCH8_7,
TRXC_SACCHTF,
TRXC_SACCHTH_0,
TRXC_SACCHTH_1,
TRXC_SACCH4_0,
TRXC_SACCH4_1,
TRXC_SACCH4_2,
TRXC_SACCH4_3,
TRXC_SACCH8_0,
TRXC_SACCH8_1,
TRXC_SACCH8_2,
TRXC_SACCH8_3,
TRXC_SACCH8_4,
TRXC_SACCH8_5,
TRXC_SACCH8_6,
TRXC_SACCH8_7,
TRXC_PDTCH,
TRXC_PTCCH,
TRXC_CBCH,
_TRX_CHAN_MAX
};
#define GSM_BURST_LEN 148
#define GPRS_BURST_LEN GSM_BURST_LEN
#define EGPRS_BURST_LEN 444
enum trx_burst_type {
TRX_BURST_GMSK,
TRX_BURST_8PSK,
};
/* States each channel on a multiframe */
struct l1sched_chan_state {
/* Pointer to the associated logical channel state from gsm_data_shared.
* Initialized during channel activation, thus may be NULL for inactive
* or auto-active channels. Always check before dereferencing! */
struct gsm_lchan *lchan;
/* scheduler */
bool active; /* Channel is active */
ubit_t *dl_bursts; /* burst buffer for TX */
enum trx_burst_type dl_burst_type; /* GMSK or 8PSK burst type */
sbit_t *ul_bursts; /* burst buffer for RX */
uint32_t ul_first_fn; /* fn of first burst */
uint8_t ul_mask; /* mask of received bursts */
/* measurements */
uint8_t rssi_num; /* number of RSSI values */
float rssi_sum; /* sum of RSSI values */
uint8_t toa_num; /* number of TOA values */
int32_t toa256_sum; /* sum of TOA values (1/256 symbol) */
uint8_t ci_cb_num; /* number of C/I values */
int32_t ci_cb_sum; /* sum of C/I values (in centiBels) */
/* loss detection */
uint8_t lost_frames; /* how many L2 frames were lost */
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
uint32_t last_tdma_fn; /* last processed TDMA frame number */
uint32_t proc_tdma_fs; /* how many TDMA frames were processed */
uint32_t lost_tdma_fs; /* how many TDMA frames were lost */
/* mode */
uint8_t rsl_cmode, tch_mode; /* mode for TCH channels */
/* AMR */
uint8_t codec[4]; /* 4 possible codecs for amr */
int codecs; /* number of possible codecs */
float ber_sum; /* sum of bit error rates */
int ber_num; /* number of bit error rates */
uint8_t ul_ft; /* current uplink FT index */
uint8_t dl_ft; /* current downlink FT index */
uint8_t ul_cmr; /* current uplink CMR index */
uint8_t dl_cmr; /* current downlink CMR index */
uint8_t amr_loop; /* if AMR loop is enabled */
uint8_t amr_last_dtx; /* last received dtx frame type */
/* TCH/H */
uint8_t dl_ongoing_facch; /* FACCH/H on downlink */
uint8_t ul_ongoing_facch; /* FACCH/H on uplink */
/* encryption */
int ul_encr_algo; /* A5/x encry algo downlink */
int dl_encr_algo; /* A5/x encry algo uplink */
int ul_encr_key_len;
int dl_encr_key_len;
uint8_t ul_encr_key[MAX_A5_KEY_LEN];
uint8_t dl_encr_key[MAX_A5_KEY_LEN];
/* measurements */
/* TODO: measurement history (ring buffer) will be added here */
/* handover */
bool ho_rach_detect; /* if rach detection is on */
};
struct l1sched_ts {
uint8_t mf_index; /* selected multiframe index */
uint8_t mf_period; /* period of multiframe */
const struct trx_sched_frame *mf_frames; /* pointer to frame layout */
struct llist_head dl_prims; /* Queue primitives for TX */
struct rate_ctr_group *ctrs; /* rate counters */
/* Channel states for all logical channels */
struct l1sched_chan_state chan_state[_TRX_CHAN_MAX];
};
struct l1sched_trx {
struct gsm_bts_trx *trx;
struct l1sched_ts ts[TRX_NR_TS];
};
struct l1sched_ts *l1sched_trx_get_ts(struct l1sched_trx *l1t, uint8_t tn);
/*! \brief Initialize the scheduler data structures */
int trx_sched_init(struct l1sched_trx *l1t, struct gsm_bts_trx *trx);
/*! \brief De-initialize the scheduler data structures */
void trx_sched_exit(struct l1sched_trx *l1t);
/*! \brief Handle a PH-DATA.req from L2 down to L1 */
int trx_sched_ph_data_req(struct l1sched_trx *l1t, struct osmo_phsap_prim *l1sap);
/*! \brief Handle a PH-TCH.req from L2 down to L1 */
int trx_sched_tch_req(struct l1sched_trx *l1t, struct osmo_phsap_prim *l1sap);
/*! \brief PHY informs us of new (current) GSM frame number */
int trx_sched_clock(struct gsm_bts *bts, uint32_t fn);
/*! \brief PHY informs us clock indications should start to be received */
int trx_sched_clock_started(struct gsm_bts *bts);
/*! \brief PHY informs us no more clock indications should be received anymore */
int trx_sched_clock_stopped(struct gsm_bts *bts);
/*! \brief set multiframe scheduler to given physical channel config */
int trx_sched_set_pchan(struct l1sched_trx *l1t, uint8_t tn,
enum gsm_phys_chan_config pchan);
/*! \brief set all matching logical channels active/inactive */
int trx_sched_set_lchan(struct l1sched_trx *l1t, uint8_t chan_nr, uint8_t link_id, bool active);
/*! \brief set mode of all matching logical channels to given mode(s) */
int trx_sched_set_mode(struct l1sched_trx *l1t, 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_codec,
uint8_t handover);
/*! \brief set ciphering on given logical channels */
int trx_sched_set_cipher(struct l1sched_trx *l1t, uint8_t chan_nr, int downlink,
2013-02-21 08:27:52 +00:00
int algo, uint8_t *key, int key_len);
/* frame structures */
struct trx_sched_frame {
/*! \brief downlink TRX channel type */
enum trx_chan_type dl_chan;
/*! \brief downlink block ID */
uint8_t dl_bid;
/*! \brief uplink TRX channel type */
enum trx_chan_type ul_chan;
/*! \brief uplink block ID */
uint8_t ul_bid;
};
/* multiframe structure */
struct trx_sched_multiframe {
/*! \brief physical channel config (channel combination) */
enum gsm_phys_chan_config pchan;
/*! \brief applies to which timeslots? */
uint8_t slotmask;
/*! \brief repeats how many frames */
uint8_t period;
/*! \brief pointer to scheduling structure */
const struct trx_sched_frame *frames;
/*! \brief human-readable name */
const char *name;
};
int find_sched_mframe_idx(enum gsm_phys_chan_config pchan, uint8_t tn);
/*! Determine if given frame number contains SACCH (true) or other (false) burst */
bool trx_sched_is_sacch_fn(struct gsm_bts_trx_ts *ts, uint32_t fn, bool uplink);
extern const struct trx_sched_multiframe trx_sched_multiframes[];
osmo-bts-trx/trx_if.c: introduce TRXD header version 0x01 support The new version adds the following fields to the TRX2L1 message, keeping the L12TRX message unchanged: +------+-----+-----+-----+--------------------+ | RSSI | ToA | MTS | C/I | soft-bits (254..0) | +------+-----+-----+-----+--------------------+ - MTS (1 octet) - Modulation and Training Sequence info, and - C/I (2 octets) - Carrier-to-Interference ratio (big endian). == Coding of MTS: Modulation and Training Sequence info 3GPP TS 45.002 version 15.1.0 defines several modulation types, and a few sets of training sequences for each type. The most common are GMSK and 8-PSK (which is used in EDGE). +-----------------+---------------------------------------+ | 7 6 5 4 3 2 1 0 | bit numbers (value range) | +-----------------+---------------------------------------+ | . . . . . X X X | Training Sequence Code (0..7) | +-----------------+---------------------------------------+ | . X X X X . . . | Modulation, TS set number (see below) | +-----------------+---------------------------------------+ | X . . . . . . . | IDLE / nope frame indication (0 or 1) | +-----------------+---------------------------------------+ The bit number 7 (MSB) is set to high when either nothing has been detected, or during IDLE frames, so we can deliver noise levels, and avoid clock gaps on the L1 side. Other bits are ignored, and should be set to low (0) in this case. == Coding of modulation and TS set number GMSK has 4 sets of training sequences (see tables 5.2.3a-d), while 8-PSK (see tables 5.2.3f-g) and the others have 2 sets. Access and Synchronization bursts also have several synch. sequences. +-----------------+---------------------------------------+ | 7 6 5 4 3 2 1 0 | bit numbers (value range) | +-----------------+---------------------------------------+ | . 0 0 X X . . . | GMSK, 4 TS sets (0..3) | +-----------------+---------------------------------------+ | . 0 1 0 X . . . | 8-PSK, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 0 1 1 X . . . | AQPSK, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 1 0 0 X . . . | 16QAM, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 1 0 1 X . . . | 32QAM, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 1 1 1 X . . . | RESERVED (0) | +-----------------+---------------------------------------+ == C/I: Carrier-to-Interference ratio The C/I value is computed from the training sequence of each burst, where we can compare the "ideal" training sequence with the actual training sequence, and then express that difference in centiBels. == Limitations - The only supported modulation types are GMSK and 8-PSK. Messages with other modulation types will be rejected. - IDLE / NOPE indications are not (yet) handled. - The logical channel handlers do not (yet) handle optional fields, such as TSC and C/I. This will be implemented in the follow-up changes. Change-Id: If61c71d20d590bf07bfd019afb33000a0b6135bd Related: OS#4006
2019-07-03 18:08:48 +00:00
#define TRX_BI_F_NOPE_IND (1 << 0)
#define TRX_BI_F_MOD_TYPE (1 << 1)
#define TRX_BI_F_TS_INFO (1 << 2)
#define TRX_BI_F_CI_CB (1 << 3)
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
/*! UL burst indication with the corresponding meta info */
struct trx_ul_burst_ind {
osmo-bts-trx/trx_if.c: introduce TRXD header version 0x01 support The new version adds the following fields to the TRX2L1 message, keeping the L12TRX message unchanged: +------+-----+-----+-----+--------------------+ | RSSI | ToA | MTS | C/I | soft-bits (254..0) | +------+-----+-----+-----+--------------------+ - MTS (1 octet) - Modulation and Training Sequence info, and - C/I (2 octets) - Carrier-to-Interference ratio (big endian). == Coding of MTS: Modulation and Training Sequence info 3GPP TS 45.002 version 15.1.0 defines several modulation types, and a few sets of training sequences for each type. The most common are GMSK and 8-PSK (which is used in EDGE). +-----------------+---------------------------------------+ | 7 6 5 4 3 2 1 0 | bit numbers (value range) | +-----------------+---------------------------------------+ | . . . . . X X X | Training Sequence Code (0..7) | +-----------------+---------------------------------------+ | . X X X X . . . | Modulation, TS set number (see below) | +-----------------+---------------------------------------+ | X . . . . . . . | IDLE / nope frame indication (0 or 1) | +-----------------+---------------------------------------+ The bit number 7 (MSB) is set to high when either nothing has been detected, or during IDLE frames, so we can deliver noise levels, and avoid clock gaps on the L1 side. Other bits are ignored, and should be set to low (0) in this case. == Coding of modulation and TS set number GMSK has 4 sets of training sequences (see tables 5.2.3a-d), while 8-PSK (see tables 5.2.3f-g) and the others have 2 sets. Access and Synchronization bursts also have several synch. sequences. +-----------------+---------------------------------------+ | 7 6 5 4 3 2 1 0 | bit numbers (value range) | +-----------------+---------------------------------------+ | . 0 0 X X . . . | GMSK, 4 TS sets (0..3) | +-----------------+---------------------------------------+ | . 0 1 0 X . . . | 8-PSK, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 0 1 1 X . . . | AQPSK, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 1 0 0 X . . . | 16QAM, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 1 0 1 X . . . | 32QAM, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 1 1 1 X . . . | RESERVED (0) | +-----------------+---------------------------------------+ == C/I: Carrier-to-Interference ratio The C/I value is computed from the training sequence of each burst, where we can compare the "ideal" training sequence with the actual training sequence, and then express that difference in centiBels. == Limitations - The only supported modulation types are GMSK and 8-PSK. Messages with other modulation types will be rejected. - IDLE / NOPE indications are not (yet) handled. - The logical channel handlers do not (yet) handle optional fields, such as TSC and C/I. This will be implemented in the follow-up changes. Change-Id: If61c71d20d590bf07bfd019afb33000a0b6135bd Related: OS#4006
2019-07-03 18:08:48 +00:00
/* Field presence bitmask (see TRX_BI_F_*) */
uint8_t flags;
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
/* Mandatory fields */
uint32_t fn; /*!< TDMA frame number */
uint8_t tn; /*!< TDMA time-slot number */
int16_t toa256; /*!< Timing of Arrival in units of 1/256 of symbol */
int8_t rssi; /*!< Received Signal Strength Indication */
osmo-bts-trx/trx_if.c: introduce TRXD header version 0x01 support The new version adds the following fields to the TRX2L1 message, keeping the L12TRX message unchanged: +------+-----+-----+-----+--------------------+ | RSSI | ToA | MTS | C/I | soft-bits (254..0) | +------+-----+-----+-----+--------------------+ - MTS (1 octet) - Modulation and Training Sequence info, and - C/I (2 octets) - Carrier-to-Interference ratio (big endian). == Coding of MTS: Modulation and Training Sequence info 3GPP TS 45.002 version 15.1.0 defines several modulation types, and a few sets of training sequences for each type. The most common are GMSK and 8-PSK (which is used in EDGE). +-----------------+---------------------------------------+ | 7 6 5 4 3 2 1 0 | bit numbers (value range) | +-----------------+---------------------------------------+ | . . . . . X X X | Training Sequence Code (0..7) | +-----------------+---------------------------------------+ | . X X X X . . . | Modulation, TS set number (see below) | +-----------------+---------------------------------------+ | X . . . . . . . | IDLE / nope frame indication (0 or 1) | +-----------------+---------------------------------------+ The bit number 7 (MSB) is set to high when either nothing has been detected, or during IDLE frames, so we can deliver noise levels, and avoid clock gaps on the L1 side. Other bits are ignored, and should be set to low (0) in this case. == Coding of modulation and TS set number GMSK has 4 sets of training sequences (see tables 5.2.3a-d), while 8-PSK (see tables 5.2.3f-g) and the others have 2 sets. Access and Synchronization bursts also have several synch. sequences. +-----------------+---------------------------------------+ | 7 6 5 4 3 2 1 0 | bit numbers (value range) | +-----------------+---------------------------------------+ | . 0 0 X X . . . | GMSK, 4 TS sets (0..3) | +-----------------+---------------------------------------+ | . 0 1 0 X . . . | 8-PSK, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 0 1 1 X . . . | AQPSK, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 1 0 0 X . . . | 16QAM, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 1 0 1 X . . . | 32QAM, 2 TS sets (0..1) | +-----------------+---------------------------------------+ | . 1 1 1 X . . . | RESERVED (0) | +-----------------+---------------------------------------+ == C/I: Carrier-to-Interference ratio The C/I value is computed from the training sequence of each burst, where we can compare the "ideal" training sequence with the actual training sequence, and then express that difference in centiBels. == Limitations - The only supported modulation types are GMSK and 8-PSK. Messages with other modulation types will be rejected. - IDLE / NOPE indications are not (yet) handled. - The logical channel handlers do not (yet) handle optional fields, such as TSC and C/I. This will be implemented in the follow-up changes. Change-Id: If61c71d20d590bf07bfd019afb33000a0b6135bd Related: OS#4006
2019-07-03 18:08:48 +00:00
/* Optional fields (defined by flags) */
enum trx_burst_type bt; /*!< Modulation type */
uint8_t tsc_set; /*!< Training Sequence Set */
uint8_t tsc; /*!< Training Sequence Code */
int16_t ci_cb; /*!< Carrier-to-Interference ratio (in centiBels) */
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
/*! Burst soft-bits buffer */
sbit_t burst[EGPRS_BURST_LEN];
size_t burst_len;
};
/*! DL burst request with the corresponding meta info */
struct trx_dl_burst_req {
uint32_t fn; /*!< TDMA frame number */
uint8_t tn; /*!< TDMA timeslot number */
uint8_t att; /*!< Tx power attenuation */
/*! Burst hard-bits buffer */
ubit_t burst[EGPRS_BURST_LEN];
size_t burst_len;
};
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
/*! Handle an UL burst received by PHY */
osmo-bts-trx/scheduler: implement baseband frequency hopping The idea behind the baseband frequency hopping is quite simple: we have several RF carriers (transceivers) transmitting and receiving on fixed frequencies (just like in a regular multi-trx setup), and an additional burst routing layer between the schedulear and the transceiver interface (TRXD over UDP). Speaking in terms of the proposed implementation: - on Downlink, dlfh_route_br() calculates the ARFCN corresponding to the current TDMA frame number according to the hopping sequence parametets, and picks the transceiver with matching ARFCN; - on Uplink, ulfh_route_bi() iterates over the transceiver list of of the BTS, calculating hopping ARFCNs for equivalent timeslots, and picks the one with ARFCN matching the received burst. In order to avoid frequent transceiver lookups on the Downlink path, dlfh_route_br() maintains a "cache" in the timeslot state structure. Unfortunately, this "cache" seems to be useless on the Uplink path, so ulfh_route_bi() always needs to lookup the matching transceiver for each burst received over the TRXD interface. It may also happen that the scheduler will be unable to route an Uplink or Downlink burst, e.g. due to inconsistent / incorrect hopping sequence parameters received from the BSC, or in case if a transceiver gets RF-locked by the BTS operator. Such events are logged as "FATAL" and aditionally signalled by the following osmo-bts-trx specific rate counters: - trx_sched:dl_fh_no_carrier (Downlink), and - trx_sched:ul_fh_no_carrier (Uplink). Change-Id: I68f4ae09fd0789ad0d8f1c1e17e17dfc4de8e462 Related: SYS#4868, OS#4546
2020-06-15 10:22:39 +00:00
int trx_sched_route_burst_ind(struct trx_ul_burst_ind *bi, struct l1sched_trx *l1t);
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
int trx_sched_ul_burst(struct l1sched_trx *l1t, struct trx_ul_burst_ind *bi);
#endif /* TRX_SCHEDULER_H */