laforge has submitted this change. ( 
https://gerrit.osmocom.org/c/osmo-bsc/+/21977 )

Change subject: hodec2: clarify current and target rxlev per candidate
......................................................................

hodec2: clarify current and target rxlev per candidate

Store the rxlev of the current lchan and the target BTS in the
ho_candidate, to clarify the code.

No functional change, cosmetically prepare for
I2704899c85c35dfd4eba43468452483f40016ca2.

Change-Id: Ie6c165e17bb3c99eebc967a6bb02529db8bdfc98
---
M src/osmo-bsc/handover_decision_2.c
1 file changed, 51 insertions(+), 48 deletions(-)

Approvals:
  Jenkins Builder: Verified
  laforge: Looks good to me, but someone else must approve
  pespin: Looks good to me, approved



diff --git a/src/osmo-bsc/handover_decision_2.c 
b/src/osmo-bsc/handover_decision_2.c
index 7854f09..ae9435f 100644
--- a/src/osmo-bsc/handover_decision_2.c
+++ b/src/osmo-bsc/handover_decision_2.c
@@ -104,7 +104,8 @@
        struct gsm_bts *bts;            /* target BTS in local BSS */
        const struct gsm0808_cell_id_list2 *cil; /* target cells in remote BSS 
*/
        uint8_t requirements;           /* what is fulfilled */
-       int avg;                        /* average RX level */
+       int rxlev_current;
+       int rxlev_target;
 };

 enum ho_reason {
@@ -236,6 +237,15 @@
        return NULL;
 }

+static int current_rxlev(struct gsm_lchan *lchan)
+{
+       struct gsm_bts *bts = lchan->ts->trx->bts;
+       return get_meas_rep_avg(lchan,
+                               ho_get_hodec2_full_tdma(bts->ho) ?
+                                       MEAS_REP_DL_RXLEV_FULL : 
MEAS_REP_DL_RXLEV_SUB,
+                               ho_get_hodec2_rxlev_avg_win(bts->ho));
+}
+
 /* obtain averaged rxlev for given neighbor */
 static int neigh_meas_avg(struct neigh_meas_proc *nmp, int window)
 {
@@ -814,7 +824,7 @@

 /* verbosely log about a handover candidate */
 static inline void debug_candidate(struct ho_candidate *candidate,
-                                  int8_t rxlev, int tchf_count, int tchh_count)
+                                  int tchf_count, int tchh_count)
 {
        struct gsm_lchan *lchan = candidate->lchan;

@@ -831,25 +841,25 @@
        if (candidate->cil)
                LOGPHOLCHANTOREMOTE(lchan, candidate->cil, LOGL_DEBUG,
                                    "RX level %d dBm -> %d dBm\n",
-                                   rxlev2dbm(rxlev), 
rxlev2dbm(candidate->avg));
+                                   rxlev2dbm(candidate->rxlev_current), 
rxlev2dbm(candidate->rxlev_target));

        if (candidate->bts == lchan->ts->trx->bts)
                LOGPHOLCHANTOBTS(lchan, candidate->bts, LOGL_DEBUG,
                     "RX level %d dBm; "
                     HO_CANDIDATE_FMT(f, F) "; " HO_CANDIDATE_FMT(h, H) "\n",
-                    rxlev2dbm(candidate->avg),
+                    rxlev2dbm(candidate->rxlev_current),
                     HO_CANDIDATE_ARGS(f, F), HO_CANDIDATE_ARGS(h, H));
        else if (candidate->bts)
                LOGPHOLCHANTOBTS(lchan, candidate->bts, LOGL_DEBUG,
                     "RX level %d dBm -> %d dBm; "
                     HO_CANDIDATE_FMT(f, F) "; " HO_CANDIDATE_FMT(h, H) "\n",
-                    rxlev2dbm(rxlev), rxlev2dbm(candidate->avg),
+                    rxlev2dbm(candidate->rxlev_current), 
rxlev2dbm(candidate->rxlev_target),
                     HO_CANDIDATE_ARGS(f, F), HO_CANDIDATE_ARGS(h, H));
 }

 /* add candidate for re-assignment within the current cell */
 static void collect_assignment_candidate(struct gsm_lchan *lchan, struct 
ho_candidate *clist,
-                                        unsigned int *candidates, int av_rxlev)
+                                        unsigned int *candidates, int 
rxlev_current)
 {
        struct gsm_bts *bts = lchan->ts->trx->bts;
        int tchf_count, tchh_count;
@@ -862,10 +872,11 @@
                .lchan = lchan,
                .bts = bts,
                .requirements = check_requirements(lchan, bts, tchf_count, 
tchh_count),
-               .avg = av_rxlev,
+               .rxlev_current = rxlev_current,
+               .rxlev_target = rxlev_current, /* same cell, same rxlev */
        };

-       debug_candidate(&c, 0, tchf_count, tchh_count);
+       debug_candidate(&c, tchf_count, tchh_count);

        if (!c.requirements)
                return;
@@ -877,7 +888,7 @@
 /* add candidates for handover to all neighbor cells */
 static void collect_handover_candidate(struct gsm_lchan *lchan, struct 
neigh_meas_proc *nmp,
                                       struct ho_candidate *clist, unsigned int 
*candidates,
-                                      bool include_weaker_rxlev, int av_rxlev,
+                                      bool include_weaker_rxlev, int 
rxlev_current,
                                       int *neighbors_count)
 {
        struct gsm_bts *bts = lchan->ts->trx->bts;
@@ -890,7 +901,6 @@
                .arfcn = nmp->arfcn,
                .bsic = nmp->bsic,
        };
-       int avg;
        struct ho_candidate c;
        int min_rxlev;
        struct handover_cfg *neigh_cfg;
@@ -929,27 +939,25 @@
         * instead assume the local BTS' config to apply. */
        neigh_cfg = (neighbor_bts ? : bts)->ho;

-       /* calculate average rxlev for this cell over the window */
-       avg = neigh_meas_avg(nmp, ho_get_hodec2_rxlev_neigh_avg_win(bts->ho));
-
        c = (struct ho_candidate){
                .lchan = lchan,
-               .avg = avg,
                .nik = ni,
                .bts = neighbor_bts,
                .cil = neighbor_cil,
+               .rxlev_current = rxlev_current,
+               .rxlev_target = neigh_meas_avg(nmp, 
ho_get_hodec2_rxlev_neigh_avg_win(bts->ho)),
        };

        /* Heed rxlev hysteresis only if the RXLEV/RXQUAL/TA levels of the MS 
aren't critically bad and
         * we're just looking for an improvement. If levels are critical, we 
desperately need a handover
         * and thus skip the hysteresis check. */
        if (!include_weaker_rxlev) {
-               unsigned int pwr_hyst = ho_get_hodec2_pwr_hysteresis(bts->ho);
-               if (avg <= (av_rxlev + pwr_hyst)) {
+               int pwr_hyst = ho_get_hodec2_pwr_hysteresis(bts->ho);
+               if ((c.rxlev_target - c.rxlev_current) <= pwr_hyst) {
                        LOGPHOCAND(&c, LOGL_DEBUG,
                                   "Not a candidate, because RX level (%d dBm) 
is lower"
                                   " or equal than current RX level (%d dBm) + 
hysteresis (%d)\n",
-                                  rxlev2dbm(avg), rxlev2dbm(av_rxlev), 
pwr_hyst);
+                                  rxlev2dbm(c.rxlev_target), 
rxlev2dbm(c.rxlev_current), pwr_hyst);
                        return;
                }
        }
@@ -957,11 +965,11 @@
        /* if the minimum level is not reached.
         * In case of a remote-BSS, use the current BTS' configuration. */
        min_rxlev = ho_get_hodec2_min_rxlev(neigh_cfg);
-       if (rxlev2dbm(avg) < min_rxlev) {
+       if (rxlev2dbm(c.rxlev_target) < min_rxlev) {
                LOGPHOCAND(&c, LOGL_DEBUG,
                           "Not a candidate, because RX level (%d dBm) is lower"
                           " than the minimum required RX level (%d dBm)\n",
-                          rxlev2dbm(avg), min_rxlev);
+                          rxlev2dbm(c.rxlev_target), min_rxlev);
                return;
        }

@@ -973,7 +981,7 @@
        } else
                c.requirements = check_requirements_remote_bss(lchan, 
neighbor_cil);

-       debug_candidate(&c, av_rxlev, tchf_count, tchh_count);
+       debug_candidate(&c, tchf_count, tchh_count);

        if (!c.requirements)
                return;
@@ -984,30 +992,25 @@

 static void collect_candidates_for_lchan(struct gsm_lchan *lchan,
                                         struct ho_candidate *clist, unsigned 
int *candidates,
-                                        int *_av_rxlev, bool 
include_weaker_rxlev)
+                                        int *_rxlev_current, bool 
include_weaker_rxlev)
 {
        struct gsm_bts *bts = lchan->ts->trx->bts;
-       int av_rxlev;
+       int rxlev_current;
        bool assignment;
        bool handover;
        int neighbors_count = 0;
-       unsigned int rxlev_avg_win = ho_get_hodec2_rxlev_avg_win(bts->ho);

        OSMO_ASSERT(candidates);

-       /* calculate average rxlev for this cell over the window */
-       av_rxlev = get_meas_rep_avg(lchan,
-                                   ho_get_hodec2_full_tdma(bts->ho) ?
-                                   MEAS_REP_DL_RXLEV_FULL : 
MEAS_REP_DL_RXLEV_SUB,
-                                   rxlev_avg_win);
-       if (_av_rxlev)
-               *_av_rxlev = av_rxlev;
+       rxlev_current = current_rxlev(lchan);
+       if (_rxlev_current)
+               *_rxlev_current = rxlev_current;

        /* in case there is no measurement report (yet) */
-       if (av_rxlev < 0) {
+       if (rxlev_current < 0) {
                LOGPHOLCHAN(lchan, LOGL_DEBUG, "Not collecting candidates, not 
enough measurements"
                            " (got %d, want %u)\n",
-                           lchan->meas_rep_count, rxlev_avg_win);
+                           lchan->meas_rep_count, 
ho_get_hodec2_rxlev_avg_win(bts->ho));
                return;
        }

@@ -1015,14 +1018,14 @@
        handover = ho_get_ho_active(bts->ho);

        if (assignment)
-               collect_assignment_candidate(lchan, clist, candidates, 
av_rxlev);
+               collect_assignment_candidate(lchan, clist, candidates, 
rxlev_current);

        if (handover) {
                int i;
                for (i = 0; i < ARRAY_SIZE(lchan->neigh_meas); i++) {
                        collect_handover_candidate(lchan, &lchan->neigh_meas[i],
                                                   clist, candidates,
-                                                  include_weaker_rxlev, 
av_rxlev, &neighbors_count);
+                                                  include_weaker_rxlev, 
rxlev_current, &neighbors_count);
                }
        }
 }
@@ -1083,7 +1086,7 @@
        struct gsm_bts *bts = lchan->ts->trx->bts;
        int ahs = (lchan->tch_mode == GSM48_CMODE_SPEECH_AMR
                   && lchan->type == GSM_LCHAN_TCH_H);
-       int av_rxlev;
+       int rxlev_current;
        struct ho_candidate clist[1 + ARRAY_SIZE(lchan->neigh_meas)];
        unsigned int candidates = 0;
        int i;
@@ -1099,7 +1102,7 @@
                return 0;
        }

-       collect_candidates_for_lchan(lchan, clist, &candidates, &av_rxlev, 
include_weaker_rxlev);
+       collect_candidates_for_lchan(lchan, clist, &candidates, &rxlev_current, 
include_weaker_rxlev);

        /* If assignment is disabled and no neighbor cell report exists, or no 
neighbor cell qualifies,
         * we may not even have any candidates. */
@@ -1121,7 +1124,7 @@
                if (!clist[i].bts)
                        continue;

-               better = clist[i].avg - av_rxlev;
+               better = clist[i].rxlev_target - clist[i].rxlev_current;
                /* Apply AFS bias? */
                afs_bias = 0;
                if (ahs && (clist[i].requirements & REQUIREMENT_B_TCHF))
@@ -1137,7 +1140,7 @@
        /* perform handover, if there is a candidate */
        if (best_cand) {
                LOGPHOCAND(best_cand, LOGL_INFO, "Best candidate, RX level 
%d%s\n",
-                          rxlev2dbm(best_cand->avg),
+                          rxlev2dbm(best_cand->rxlev_target),
                           best_applied_afs_bias ? " (applied AHS -> AFS rxlev 
bias)" : "");
                return trigger_ho(best_cand, best_cand->requirements & 
REQUIREMENT_B_MASK);
        }
@@ -1154,7 +1157,7 @@
                if (!clist[i].bts)
                        continue;

-               better = clist[i].avg - av_rxlev;
+               better = clist[i].rxlev_target - clist[i].rxlev_current;
                /* Apply AFS bias? */
                afs_bias = 0;
                if (ahs && (clist[i].requirements & REQUIREMENT_C_TCHF))
@@ -1170,7 +1173,7 @@
        /* perform handover, if there is a candidate */
        if (best_cand) {
                LOGPHOCAND(best_cand, LOGL_INFO, "Best candidate, RX level 
%d%s\n",
-                          rxlev2dbm(best_cand->avg),
+                          rxlev2dbm(best_cand->rxlev_target),
                           best_applied_afs_bias? " (applied AHS -> AFS rxlev 
bias)" : "");
                return trigger_ho(best_cand, best_cand->requirements & 
REQUIREMENT_C_MASK);
        }
@@ -1191,7 +1194,7 @@
                if (!(clist[i].requirements & REQUIREMENT_A_MASK))
                        continue;

-               better = clist[i].avg - av_rxlev;
+               better = clist[i].rxlev_target - clist[i].rxlev_current;
                /* Apply AFS bias?
                 * (never to remote-BSS neighbors, since we will not change the 
lchan type for those.) */
                afs_bias = 0;
@@ -1209,7 +1212,7 @@
        /* perform handover, if there is a candidate */
        if (best_cand) {
                LOGPHOCAND(best_cand, LOGL_INFO, "Best candidate: RX level 
%d%s\n",
-                          rxlev2dbm(best_cand->avg),
+                          rxlev2dbm(best_cand->rxlev_target),
                           best_applied_afs_bias ? " (applied AHS -> AFS rxlev 
bias)" : "");
                return trigger_ho(best_cand, best_cand->requirements & 
REQUIREMENT_A_MASK);
        }
@@ -1475,7 +1478,7 @@
                    && (intra_cell && upgrade_to_tch_f))
                        continue;

-               avg_rxlev = c->avg;
+               avg_rxlev = c->rxlev_target;

                /* improve AHS */
                if (upgrade_to_tch_f)
@@ -1639,7 +1642,7 @@
                        LOGPHOCAND(&clist[i], LOGL_DEBUG, "#%d: req={TCH/F:" 
REQUIREMENTS_FMT ", TCH/H:" REQUIREMENTS_FMT "} avg-rxlev=%d dBm\n",
                                   i, REQUIREMENTS_ARGS(clist[i].requirements, 
F),
                                   REQUIREMENTS_ARGS(clist[i].requirements, H),
-                                  rxlev2dbm(clist[i].avg));
+                                  rxlev2dbm(clist[i].rxlev_target));
                }
        }

@@ -1662,7 +1665,7 @@
        if (best_cand) {
                any_ho = 1;
                LOGPHOCAND(best_cand, LOGL_DEBUG, "Best candidate: RX level 
%d%s\n",
-                          rxlev2dbm(best_cand->avg),
+                          rxlev2dbm(best_cand->rxlev_target),
                           is_improved ? " (applied AHS->AFS bias)" : "");
                trigger_ho(best_cand, best_cand->requirements & 
REQUIREMENT_B_MASK);
 #if 0
@@ -1703,7 +1706,7 @@
        if (best_cand) {
                any_ho = 1;
                LOGPHOCAND(best_cand, LOGL_INFO, "Worst candidate: RX level %d 
from TCH/H -> TCH/F%s\n",
-                          rxlev2dbm(best_cand->avg),
+                          rxlev2dbm(best_cand->rxlev_target),
                           is_improved ? " (applied AHS -> AFS rxlev bias)" : 
"");
                trigger_ho(best_cand, best_cand->requirements & 
REQUIREMENT_B_MASK);
 #if 0
@@ -1738,7 +1741,7 @@
        if (best_cand) {
                any_ho = 1;
                LOGPHOCAND(best_cand, LOGL_INFO, "Best candidate: RX level 
%d%s\n",
-                          rxlev2dbm(best_cand->avg),
+                          rxlev2dbm(best_cand->rxlev_target),
                           is_improved ? " (applied AHS -> AFS rxlev bias)" : 
"");
                trigger_ho(best_cand, best_cand->requirements & 
REQUIREMENT_C_MASK);
 #if 0
@@ -1781,7 +1784,7 @@
        if (best_cand) {
                any_ho = 1;
                LOGPHOCAND(best_cand, LOGL_INFO, "Worst candidate: RX level %d 
from TCH/H -> TCH/F%s\n",
-                          rxlev2dbm(best_cand->avg),
+                          rxlev2dbm(best_cand->rxlev_target),
                           is_improved ? " (applied AHS -> AFS rxlev bias)" : 
"");
                trigger_ho(best_cand, best_cand->requirements & 
REQUIREMENT_C_MASK);
 #if 0

--
To view, visit https://gerrit.osmocom.org/c/osmo-bsc/+/21977
To unsubscribe, or for help writing mail filters, visit 
https://gerrit.osmocom.org/settings

Gerrit-Project: osmo-bsc
Gerrit-Branch: master
Gerrit-Change-Id: Ie6c165e17bb3c99eebc967a6bb02529db8bdfc98
Gerrit-Change-Number: 21977
Gerrit-PatchSet: 1
Gerrit-Owner: neels <nhofm...@sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: laforge <lafo...@osmocom.org>
Gerrit-Reviewer: pespin <pes...@sysmocom.de>
Gerrit-MessageType: merged

Reply via email to