/* Cesar project {{{ * * Copyright (C) 2009 Spidcom * * <<>> * * }}} */ /** * \file ce/rx/bitloading/src/common.c * \brief Common transition functions * \ingroup ce_rx */ #include "common/std.h" #include "ce/rx/bitloading/inc/initial.h" #include "ce/rx/bitloading/inc/common.h" #include "ce/rx/bitloading/inc/ber.h" #include "ce/rx/cp/inc/cp.h" #include "ce/rx/inc/trace.h" #include "ce/debug/gpio/gpio.h" #include "mac/common/timings.h" #include uint ce_rx_bl_min_time_between_ce_restart_ms[CE_RX_BL_DATE_CRITERIA_NB] = { 3000, 3000 }; void ce_rx_bl_start_bl (ce_rx_t *ce_rx, sta_t *sta, tonemask_info_t *ts) { /* Check parameters. */ dbg_assert (sta); /* Not using ts directly. */ /* Not using ce_rx directly. */ CE_RX_TRACE (BL_INITIAL, sta->tei); ce_debug_gpio_event (CE_DEBUG_GPIO_EVENT_CE_RX_BL_WORKING, true); /* Compute initial tone map. */ tonemap_t *initial_tm = ce_rx_bl_initial (ts, &ce_rx->tonemask, &sta->ce_rx_bt); /* Dump tone map in trace. */ if (CONFIG_TRACE) { dbg_assert (ts); #define OFFSET 2 int mod_count[OFFSET + CE_MOD_COUNT]; uint m; /* Initialize. */ mod_count[0] = phy_date (); mod_count[1] = sta->tei; for (m = OFFSET; m < COUNT (mod_count); m++) mod_count[m] = 0; /* Count. */ if (initial_tm) { TONEMAP_READ_BEGIN (initial_tm, ts->tonemask, m) { mod_count[m + OFFSET]++; } TONEMAP_READ_END; } /* Trace result. */ CE_RX_TRACE_N (TONEMAP, mod_count, COUNT (mod_count)); #undef OFFSET } u8 tmi; /* Compare with ROBO. */ if (initial_tm != NULL && ce_rx_bl_tonemap_better_than_robo (initial_tm, ts)) { /* Set it. */ tmi = tonemaps_set_first_free_tmi (sta->rx_tonemaps, initial_tm); /* This assert is required because this is the first time we ever * set a tone map in the life of this STA. So we MUST have an * empty tone map index available! */ dbg_assert (tmi != 0); ce_rx_bl_ber_sliding_mean_update (&sta->ce_rx_bt, initial_tm->ber_target_reached); } else { ce_debug_gpio_event (CE_DEBUG_GPIO_EVENT_CE_RX_BL_ROBO_BETTER, true); /* TMI ROBO. */ tmi = PHY_MOD_ROBO; /* Remove computed tone map. */ if (initial_tm != NULL) tonemap_free (initial_tm); ce_rx_bl_ber_sliding_mean_update (&sta->ce_rx_bt, ce_rx_bl_ber_pt_robo (ts->carrier_nb)); /* Trace it. */ CE_RX_TRACE (INITIAL_WORSE_THAN_ROBO, sta->tei); } sta->rx_tonemaps->default_tmi = tmi; ce_rx_cp_send_mme_new_tone_map (ce_rx, sta, TONEMAP_INDEX_IS_NEGOTIATED (tmi) ? tmi : 0, 0, true); /* Store next time the CE can restart. */ uint i; for (i = 0; i < CE_RX_BL_DATE_CRITERIA_NB; i++) sta->ce_rx_bt.next_date_min_for_restart_rtc_date[i] = cyg_current_time () + MAC_MS_TO_TCK (ce_rx_bl_min_time_between_ce_restart_ms[i]) / ce_rx->tck_per_rtc; ce_debug_gpio_event (CE_DEBUG_GPIO_EVENT_CE_RX_BL_WORKING, false); ce_debug_gpio_event (CE_DEBUG_GPIO_EVENT_CE_RX_BL_ROBO_BETTER, false); } bool ce_rx_bl_tonemap_better_than_robo (tonemap_t *tm, tonemask_info_t *ti) { /* Check parameters. */ dbg_assert (tm); dbg_assert (ti); if (tm->bits_per_symbol > ti->tonemap_robo[PHY_MOD_ROBO].bits_per_symbol) return true; else return false; }