mirror of
https://github.com/portapack-mayhem/mayhem-firmware.git
synced 2026-08-22 07:29:03 +00:00
fix ADSB RX weak signal on pro (#3282)
This commit is contained in:
@@ -144,6 +144,10 @@ static rf::Direction cached_direction = rf::Direction::Receive;
|
||||
static bool cached_rf_amp = false;
|
||||
static int_fast8_t cached_lna_gain = 0;
|
||||
static int_fast8_t cached_vga_gain = 0;
|
||||
/* FPGA quarter-rate shift mode currently programmed, in gateware encoding
|
||||
* (0b00 none / 0b11 up / 0b01 down). The baseband filter width depends on it,
|
||||
* so ReceiverModel reads it back through get_quarter_shift(). */
|
||||
static uint8_t cached_quarter_shift = 0;
|
||||
#endif
|
||||
|
||||
void init() {
|
||||
@@ -182,18 +186,15 @@ void init() {
|
||||
|
||||
fpga_set_mode(FPGA_MODE_RX);
|
||||
|
||||
// These FPGA registers control DC_BLOCK, Q-Inv, QUARTER SHIFT, and Decimation.
|
||||
fpga_debug_register_write(FPGA_REG_CTRL, FPGA_CTRL_DC_BLOCK_EN); // DC_BLOCK=1, QUARTER_SHIFT=0, Q_INVERT=0
|
||||
fpga_debug_register_write(FPGA_REG_DECIM, 0x00); // RX_DECIM=No Decim
|
||||
|
||||
// RX Mode: Register 3 is RX Digital Gain. Start with 0dB (no shift).
|
||||
fpga_debug_register_write(FPGA_REG_RX_DIGITAL_GAIN, FPGA_RX_DEFAULT_DIGITAL_GAIN);
|
||||
|
||||
/* RX Mode: Initialize DC Block parameters to standard Praline values.
|
||||
* 0x04 Width and 0x08 Adapt Rate are typical for 40MHz stability.
|
||||
*/
|
||||
fpga_debug_register_write(FPGA_REG_RX_DC_BLOCK_WIDTH, FPGA_RX_DEFAULT_DC_WIDTH);
|
||||
fpga_debug_register_write(FPGA_REG_RX_DC_ADAPT_RATE, FPGA_RX_DEFAULT_ADAPT_RATE);
|
||||
/* Boot register state, matching fpga_init() in hackrf/firmware/common/fpga.c:
|
||||
* DC block on, no PRBS, no external trigger, no quarter shift, TX NCO off.
|
||||
* The decimation ratio and the quarter shift are programmed later by
|
||||
* ClockManager::set_sampling_frequency() and set_tuning_frequency(). */
|
||||
fpga_debug_register_write(FPGA_REG_CTRL, FPGA_CTRL_DC_BLOCK_EN);
|
||||
fpga_debug_register_write(FPGA_REG_DECIM, 0x00); // RX_DECIM = no decimation
|
||||
fpga_debug_register_write(FPGA_REG_RX_PSTEP, 0x00); // quarter shift off
|
||||
fpga_debug_register_write(FPGA_REG_TX_CONTROL, 0x00);
|
||||
cached_quarter_shift = 0;
|
||||
|
||||
ssp1_arbiter.invalidate();
|
||||
chThdSleepMilliseconds(10); // Let FPGA registers settle
|
||||
@@ -224,13 +225,13 @@ void set_direction(const rf::Direction new_direction) {
|
||||
fpga_debug_register_write(FPGA_REG_TX_PHASE_STEP, 0x00);
|
||||
} else {
|
||||
fpga_set_mode(FPGA_MODE_RX);
|
||||
// RX Mode: Ensure NCO is disabled and reset digital gain
|
||||
fpga_debug_register_write(FPGA_REG_RX_DIGITAL_GAIN, FPGA_RX_DEFAULT_DIGITAL_GAIN);
|
||||
/* RX Mode: Initialize DC Block parameters to standard Praline values.
|
||||
* 0x04 Width and 0x08 Adapt Rate are typical for 40MHz stability.
|
||||
*/
|
||||
fpga_debug_register_write(FPGA_REG_RX_DC_BLOCK_WIDTH, FPGA_RX_DEFAULT_DC_WIDTH);
|
||||
fpga_debug_register_write(FPGA_REG_RX_DC_ADAPT_RATE, FPGA_RX_DEFAULT_ADAPT_RATE);
|
||||
/* RX Mode: DC block on, TX NCO off. The quarter shift is re-applied by
|
||||
* set_tuning_frequency(); clear it here so a stale TX/RX transition
|
||||
* cannot leave a rotation programmed with no matching LO offset. */
|
||||
fpga_debug_register_write(FPGA_REG_CTRL, FPGA_CTRL_DC_BLOCK_EN);
|
||||
fpga_debug_register_write(FPGA_REG_TX_CONTROL, 0x00);
|
||||
fpga_debug_register_write(FPGA_REG_RX_PSTEP, 0x00);
|
||||
cached_quarter_shift = 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -309,7 +310,19 @@ bool set_tuning_frequency(const rf::Frequency frequency) {
|
||||
final_frequency = final_frequency + portapack::persistent_memory::config_freq_rx_correction();
|
||||
}
|
||||
|
||||
#ifdef PRALINE
|
||||
/* The PRALINE tuning tables offset the analogue passband by a quarter of
|
||||
* the ADC sample rate and have the FPGA rotate it back to DC, so the
|
||||
* planner needs to know the AFE rate. See tuning.cpp. */
|
||||
const uint32_t afe_rate = portapack::clock_manager.get_sampling_frequency()
|
||||
<< portapack::clock_manager.get_resampling_n();
|
||||
const auto tuning_config = tuning::config::create(
|
||||
final_frequency,
|
||||
afe_rate,
|
||||
direction == rf::Direction::Transmit);
|
||||
#else
|
||||
const auto tuning_config = tuning::config::create(final_frequency);
|
||||
#endif
|
||||
if (tuning_config.is_valid()) {
|
||||
first_if.disable();
|
||||
|
||||
@@ -339,6 +352,22 @@ bool set_tuning_frequency(const rf::Frequency frequency) {
|
||||
LPC_GPIO->CLR[0] = (1 << 13); // SGPIO12 = 0 (Q normal)
|
||||
}
|
||||
|
||||
/* Program the FPGA's quarter-rate shift to match the offset the tuning
|
||||
* table just applied to the analogue centre frequency. The gateware
|
||||
* (hackrf/firmware/fpga/top/standard.py) takes both bits from the top
|
||||
* of register 0x03 (rx_pstep):
|
||||
* rx_pstep[6] -> quarter_shift.enable
|
||||
* rx_pstep[7] -> quarter_shift.up
|
||||
* which is exactly fpga_set_rx_quarter_shift_mode() in
|
||||
* hackrf/firmware/common/fpga.c: write (mode & 0b11) << 6.
|
||||
*
|
||||
* These two settings MUST be programmed together. Tuning off-centre
|
||||
* without the rotation puts the signal outside the decimation filter's
|
||||
* passband and it disappears entirely; rotating without the offset
|
||||
* moves the wanted signal off DC by the same amount. */
|
||||
cached_quarter_shift = tuning_config.quarter_shift;
|
||||
fpga_debug_register_write(FPGA_REG_RX_PSTEP, (cached_quarter_shift & 0b11) << 6);
|
||||
|
||||
ssp1_arbiter.invalidate();
|
||||
#else
|
||||
baseband_cpld.set_invert(mixer_invert ^ baseband_invert);
|
||||
@@ -469,6 +498,10 @@ int_fast8_t get_cached_lna_gain() {
|
||||
int_fast8_t get_cached_vga_gain() {
|
||||
return cached_vga_gain;
|
||||
}
|
||||
|
||||
uint8_t get_cached_quarter_shift() {
|
||||
return cached_quarter_shift;
|
||||
}
|
||||
#endif
|
||||
|
||||
namespace first_if {
|
||||
@@ -570,18 +603,11 @@ void register_write(const size_t register_number, uint32_t value) {
|
||||
void init() {
|
||||
fpga_set_mode(FPGA_MODE_RX);
|
||||
|
||||
// These FPGA registers control DC_BLOCK, Q-Inv, QUARTER SHIFT, and Decimation.
|
||||
fpga_debug_register_write(FPGA_REG_CTRL, FPGA_CTRL_DC_BLOCK_EN); // DC_BLOCK=1, QUARTER_SHIFT=0, Q_INVERT=0
|
||||
fpga_debug_register_write(FPGA_REG_DECIM, 0x00); // RX_DECIM=No Decim
|
||||
|
||||
// RX Mode: Register 3 is RX Digital Gain. Start with 0dB (no shift).
|
||||
fpga_debug_register_write(FPGA_REG_RX_DIGITAL_GAIN, FPGA_RX_DEFAULT_DIGITAL_GAIN);
|
||||
|
||||
/* RX Mode: Initialize DC Block parameters to standard Praline values.
|
||||
* 0x04 Width and 0x08 Adapt Rate are typical for 40MHz stability.
|
||||
*/
|
||||
fpga_debug_register_write(FPGA_REG_RX_DC_BLOCK_WIDTH, FPGA_RX_DEFAULT_DC_WIDTH);
|
||||
fpga_debug_register_write(FPGA_REG_RX_DC_ADAPT_RATE, FPGA_RX_DEFAULT_ADAPT_RATE);
|
||||
/* Same boot state as fpga_init() in hackrf/firmware/common/fpga.c. */
|
||||
fpga_debug_register_write(FPGA_REG_CTRL, FPGA_CTRL_DC_BLOCK_EN);
|
||||
fpga_debug_register_write(FPGA_REG_DECIM, 0x00); // RX_DECIM = no decimation
|
||||
fpga_debug_register_write(FPGA_REG_RX_PSTEP, 0x00); // quarter shift off
|
||||
fpga_debug_register_write(FPGA_REG_TX_CONTROL, 0x00);
|
||||
|
||||
ssp1_arbiter.invalidate(); // Force arbiter to reconfigure on next transfer
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user