1
0
Fork 0
mirror of https://github.com/CTCaer/hekate.git synced 2024-11-22 18:06:40 +00:00

minerva: name needs_training flags

This commit is contained in:
CTCaer 2022-01-16 01:41:24 +02:00
parent 6092994240
commit d1c0d464dc
2 changed files with 87 additions and 58 deletions

View file

@ -51,6 +51,27 @@
#define EMC_PERIODIC_TRAIN_MS 100 #define EMC_PERIODIC_TRAIN_MS 100
#define EMC_TEMP_COMP_MS 1000 #define EMC_TEMP_COMP_MS 1000
/* Training types */
#define NEEDS_TRAINING_CA BIT(0)
#define NEEDS_TRAINING_CA_VREF BIT(1)
#define NEEDS_TRAINING_QUSE BIT(2)
#define NEEDS_TRAINING_QUSE_VREF BIT(3)
#define NEEDS_TRAINING_WR BIT(4)
#define NEEDS_TRAINING_WR_VREF BIT(5)
#define NEEDS_TRAINING_RD BIT(6)
#define NEEDS_TRAINING_RD_VREF BIT(7)
#define NEEDS_TRAINING_SWAP_RANK BIT(8)
#define NEEDS_TRAINING_IN_SELF_REFRESH BIT(9)
#define NEEDS_TRISTATE_TRAINING (NEEDS_TRAINING_CA | NEEDS_TRAINING_CA_VREF | \
NEEDS_TRAINING_QUSE | NEEDS_TRAINING_WR | \
NEEDS_TRAINING_WR_VREF | NEEDS_TRAINING_RD | \
NEEDS_TRAINING_RD_VREF)
#define NEEDS_TRAINING_CA_COMBO (NEEDS_TRAINING_CA | NEEDS_TRAINING_CA_VREF)
#define NEEDS_TRAINING_QUSE_COMBO (NEEDS_TRAINING_QUSE | NEEDS_TRAINING_QUSE_VREF)
#define NEEDS_TRAINING_WR_COMBO (NEEDS_TRAINING_WR | NEEDS_TRAINING_WR_VREF)
#define NEEDS_TRAINING_RD_COMBO (NEEDS_TRAINING_RD | NEEDS_TRAINING_RD_VREF)
typedef struct typedef struct
{ {
u32 rate_to; u32 rate_to;

View file

@ -1411,7 +1411,7 @@ static u32 _dvfs_power_ramp_down(bool flip_backward, emc_table_t *src_emc_table_
return ramp_down_wait; return ramp_down_wait;
} }
static u32 _dvfs_power_ramp_up(bool flip_backward, emc_table_t *src_emc_table_entry, emc_table_t *dst_emc_table_entry, u8 needs_training, u32 dst_clock_period) static u32 _dvfs_power_ramp_up(bool flip_backward, emc_table_t *src_emc_table_entry, emc_table_t *dst_emc_table_entry, u32 needs_training, u32 dst_clock_period)
{ {
u32 pmacro_cmd_pad; u32 pmacro_cmd_pad;
u32 pmacro_dq_pad; u32 pmacro_dq_pad;
@ -1431,7 +1431,7 @@ static u32 _dvfs_power_ramp_up(bool flip_backward, emc_table_t *src_emc_table_en
pmacro_cfg5 = src_emc_table_entry->burst_regs.emc_fbio_cfg5_idx; pmacro_cfg5 = src_emc_table_entry->burst_regs.emc_fbio_cfg5_idx;
pmacro_common_tx = src_emc_table_entry->burst_regs.emc_pmacro_common_pad_tx_ctrl_idx; pmacro_common_tx = src_emc_table_entry->burst_regs.emc_pmacro_common_pad_tx_ctrl_idx;
} }
else if (needs_training & 3) else if (needs_training & NEEDS_TRAINING_CA_COMBO)
{ {
pmacro_cmd_pad = dst_emc_table_entry->shadow_regs_ca_train.emc_pmacro_cmd_pad_tx_ctrl_idx; pmacro_cmd_pad = dst_emc_table_entry->shadow_regs_ca_train.emc_pmacro_cmd_pad_tx_ctrl_idx;
pmacro_dq_pad = dst_emc_table_entry->shadow_regs_ca_train.emc_pmacro_data_pad_tx_ctrl_idx; pmacro_dq_pad = dst_emc_table_entry->shadow_regs_ca_train.emc_pmacro_data_pad_tx_ctrl_idx;
@ -1439,7 +1439,7 @@ static u32 _dvfs_power_ramp_up(bool flip_backward, emc_table_t *src_emc_table_en
pmacro_cfg5 = dst_emc_table_entry->shadow_regs_ca_train.emc_fbio_cfg5_idx; pmacro_cfg5 = dst_emc_table_entry->shadow_regs_ca_train.emc_fbio_cfg5_idx;
pmacro_common_tx = dst_emc_table_entry->shadow_regs_ca_train.emc_pmacro_common_pad_tx_ctrl_idx; pmacro_common_tx = dst_emc_table_entry->shadow_regs_ca_train.emc_pmacro_common_pad_tx_ctrl_idx;
} }
else if (needs_training & 0xC) else if (needs_training & NEEDS_TRAINING_QUSE_COMBO)
{ {
pmacro_cmd_pad = dst_emc_table_entry->shadow_regs_quse_train.emc_pmacro_cmd_pad_tx_ctrl_idx; pmacro_cmd_pad = dst_emc_table_entry->shadow_regs_quse_train.emc_pmacro_cmd_pad_tx_ctrl_idx;
pmacro_dq_pad = dst_emc_table_entry->shadow_regs_quse_train.emc_pmacro_data_pad_tx_ctrl_idx; pmacro_dq_pad = dst_emc_table_entry->shadow_regs_quse_train.emc_pmacro_data_pad_tx_ctrl_idx;
@ -1447,7 +1447,7 @@ static u32 _dvfs_power_ramp_up(bool flip_backward, emc_table_t *src_emc_table_en
pmacro_cfg5 = dst_emc_table_entry->shadow_regs_quse_train.emc_fbio_cfg5_idx; pmacro_cfg5 = dst_emc_table_entry->shadow_regs_quse_train.emc_fbio_cfg5_idx;
pmacro_common_tx = dst_emc_table_entry->shadow_regs_quse_train.emc_pmacro_common_pad_tx_ctrl_idx; pmacro_common_tx = dst_emc_table_entry->shadow_regs_quse_train.emc_pmacro_common_pad_tx_ctrl_idx;
} }
else if (needs_training & 0xF0) else if (needs_training & (NEEDS_TRAINING_WR_COMBO | NEEDS_TRAINING_RD_COMBO))
{ {
pmacro_cmd_pad = dst_emc_table_entry->shadow_regs_rdwr_train.emc_pmacro_cmd_pad_tx_ctrl_idx; pmacro_cmd_pad = dst_emc_table_entry->shadow_regs_rdwr_train.emc_pmacro_cmd_pad_tx_ctrl_idx;
pmacro_dq_pad = dst_emc_table_entry->shadow_regs_rdwr_train.emc_pmacro_data_pad_tx_ctrl_idx; pmacro_dq_pad = dst_emc_table_entry->shadow_regs_rdwr_train.emc_pmacro_data_pad_tx_ctrl_idx;
@ -2190,15 +2190,15 @@ static bool _check_freq_changed(u32 dst_entry_rate_KHz, u32 dst_entry_clk_src_em
static void _save_train_results(emc_table_t *mtc_table_entry, u32 needs_training, u32 dram_dev_num, bool channel1_enabled) static void _save_train_results(emc_table_t *mtc_table_entry, u32 needs_training, u32 dram_dev_num, bool channel1_enabled)
{ {
bool needs_ca_training = needs_training & 1; bool needs_ca_training = !!(needs_training & NEEDS_TRAINING_CA);
bool needs_ca_vref_training = (needs_training >> 1) & 1; bool needs_ca_vref_training = !!(needs_training & NEEDS_TRAINING_CA_VREF);
bool needs_quse_training = (needs_training >> 2) & 1; bool needs_quse_training = !!(needs_training & NEEDS_TRAINING_QUSE);
bool needs_quse_vref_training = (needs_training >> 3) & 1; bool needs_quse_vref_training = !!(needs_training & NEEDS_TRAINING_QUSE_VREF);
bool needs_wr_training = (needs_training >> 4) & 1; bool needs_wr_training = !!(needs_training & NEEDS_TRAINING_WR);
bool needs_wr_vref_training = (needs_training >> 5) & 1; bool needs_wr_vref_training = !!(needs_training & NEEDS_TRAINING_WR_VREF);
bool needs_rd_training = (needs_training >> 6) & 1; bool needs_rd_training = !!(needs_training & NEEDS_TRAINING_RD);
bool needs_rd_vref_training = (needs_training >> 7) & 1; bool needs_rd_vref_training = !!(needs_training & NEEDS_TRAINING_RD_VREF);
bool needs_training_in_self_refresh = (needs_training >> 9) & 1; bool needs_training_in_self_refresh = !!(needs_training & NEEDS_TRAINING_IN_SELF_REFRESH);
if (needs_ca_training) if (needs_ca_training)
{ {
@ -2565,32 +2565,35 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
u32 mr13_flip_fspwr = 0; u32 mr13_flip_fspwr = 0;
u32 mr13_catr_enable; u32 mr13_catr_enable;
/* needs_training LOBYTE table var */ /* needs_training flags */
/* /*
| bit | Description | | bit | Description |
|-----|----------------------------| |-----|----------------------------------|
| 0 | Needs CA training | | 0 | Needs CA training |
| 1 | Needs CA_VREF training | | 1 | Needs CA_VREF training |
| 2 | Needs QUSE training | | 2 | Needs QUSE training |
| 3 | Needs QUSE_VREF training | | 3 | Needs QUSE_VREF training |
| 4 | Needs WR training | | 4 | Needs WR training |
| 5 | Needs WR_VREF training | | 5 | Needs WR_VREF training |
| 6 | Needs RD training | | 6 | Needs RD training |
| 7 | Needs RD_VREF training | | 7 | Needs RD_VREF training |
| 8 | Needs SWAP_RANK training |
| 9 | Needs IN_SELF_REFRESH training |
*/ */
bool compensate_trimmer_applicable = false; bool compensate_trimmer_applicable = false;
bool needs_ca_or_cavref_training = (needs_training & 3) != 0; bool needs_ca_combo_training = !!(needs_training & NEEDS_TRAINING_CA_COMBO);
bool needs_tristate_training = (needs_training & 0xF7) != 0; bool needs_tristate_training = !!(needs_training & NEEDS_TRISTATE_TRAINING);
bool needs_ca_training = needs_training & 1;
bool needs_ca_vref_training = (needs_training >> 1) & 1; bool needs_ca_training = !!(needs_training & NEEDS_TRAINING_CA);
bool needs_quse_training = (needs_training >> 2) & 1; bool needs_ca_vref_training = !!(needs_training & NEEDS_TRAINING_CA_VREF);
bool needs_quse_vref_training = (needs_training >> 3) & 1; bool needs_quse_training = !!(needs_training & NEEDS_TRAINING_QUSE);
bool needs_wr_training = (needs_training >> 4) & 1; bool needs_quse_vref_training = !!(needs_training & NEEDS_TRAINING_QUSE_VREF);
bool needs_wr_vref_training = (needs_training >> 5) & 1; bool needs_wr_training = !!(needs_training & NEEDS_TRAINING_WR);
bool needs_rd_training = (needs_training >> 6) & 1; bool needs_wr_vref_training = !!(needs_training & NEEDS_TRAINING_WR_VREF);
bool needs_rd_vref_training = (needs_training >> 7) & 1; bool needs_rd_training = !!(needs_training & NEEDS_TRAINING_RD);
bool needs_swap_rank_training = (needs_training >> 8) & 1; bool needs_rd_vref_training = !!(needs_training & NEEDS_TRAINING_RD_VREF);
bool needs_swap_rank_training = !!(needs_training & NEEDS_TRAINING_SWAP_RANK);
bool zcal_resistor_shared = (src_emc_entry->burst_regs.emc_zcal_wait_cnt_idx >> 31) & 1; bool zcal_resistor_shared = (src_emc_entry->burst_regs.emc_zcal_wait_cnt_idx >> 31) & 1;
bool enable_bg_regulator = (dst_emc_entry->burst_regs.emc_pmacro_bg_bias_ctrl_0_idx & 1) ^ 1; bool enable_bg_regulator = (dst_emc_entry->burst_regs.emc_pmacro_bg_bias_ctrl_0_idx & 1) ^ 1;
@ -2748,7 +2751,7 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
// Step 7 - Bug 200024907 - Patch RP R2P. // Step 7 - Bug 200024907 - Patch RP R2P.
EPRINTF("Step 7"); EPRINTF("Step 7");
if (needs_ca_or_cavref_training && dram_dev_num == TWO_RANK) if (needs_ca_combo_training && dram_dev_num == TWO_RANK)
EMC(EMC_PIN) = 0x107; EMC(EMC_PIN) = 0x107;
u32 R2P_war = 0; u32 R2P_war = 0;
@ -2849,7 +2852,7 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
else else
mr13_catr_enable = (mr13_flip_fspwr & 0x3FFFFFFF) | 0x80000001; mr13_catr_enable = (mr13_flip_fspwr & 0x3FFFFFFF) | 0x80000001;
if (needs_ca_or_cavref_training) if (needs_ca_combo_training)
{ {
if (needs_swap_rank_training) if (needs_swap_rank_training)
mr13_flip_fspop = (mr13_flip_fspop & 0x3FFFFFFF) | 0x80000000; mr13_flip_fspop = (mr13_flip_fspop & 0x3FFFFFFF) | 0x80000000;
@ -2878,11 +2881,11 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
reg_addr = burst_regs_emc_addr_table[i]; reg_addr = burst_regs_emc_addr_table[i];
if (needs_tristate_training) if (needs_tristate_training)
{ {
if (needs_ca_or_cavref_training) if (needs_ca_combo_training)
reg_val = dst_burst_regs->shadow_regs_ca_train[i]; reg_val = dst_burst_regs->shadow_regs_ca_train[i];
else if (needs_training & 0xC) else if (needs_training & NEEDS_TRAINING_QUSE_COMBO)
reg_val = dst_burst_regs->shadow_regs_quse_train[i]; reg_val = dst_burst_regs->shadow_regs_quse_train[i];
else if (needs_training & 0xF0) else if (needs_training & (NEEDS_TRAINING_WR_COMBO | NEEDS_TRAINING_RD_COMBO))
reg_val = dst_burst_regs->shadow_regs_rdwr_train[i]; reg_val = dst_burst_regs->shadow_regs_rdwr_train[i];
else else
continue; continue;
@ -3069,7 +3072,7 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
EMC(EMC_DBG) = emc_dbg_o | 2; EMC(EMC_DBG) = emc_dbg_o | 2;
EMC(EMC_PMACRO_AUTOCAL_CFG_COMMON) = dst_emc_entry->burst_regs.emc_pmacro_autocal_cfg_common_idx | 0x10000; EMC(EMC_PMACRO_AUTOCAL_CFG_COMMON) = dst_emc_entry->burst_regs.emc_pmacro_autocal_cfg_common_idx | 0x10000;
if (needs_ca_or_cavref_training) if (needs_ca_combo_training)
EMC(EMC_FBIO_CFG5) = src_emc_entry->burst_regs.emc_fbio_cfg5_idx | 0x8000000; EMC(EMC_FBIO_CFG5) = src_emc_entry->burst_regs.emc_fbio_cfg5_idx | 0x8000000;
EMC(EMC_DBG) = emc_dbg_o; EMC(EMC_DBG) = emc_dbg_o;
@ -3084,7 +3087,7 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
EPRINTF("Step 10"); EPRINTF("Step 10");
_ccfifo_write(EMC_SELF_REF, 0x101, 0); _ccfifo_write(EMC_SELF_REF, 0x101, 0);
if (!needs_ca_or_cavref_training && (dst_clock_period <= 2000)) if (!needs_ca_combo_training && (dst_clock_period <= 2000))
{ {
_ccfifo_write(EMC_MRW3, mr13_flip_fspwr ^ 0x40, 0); _ccfifo_write(EMC_MRW3, mr13_flip_fspwr ^ 0x40, 0);
_ccfifo_write(EMC_MRW6, (src_emc_entry->burst_regs.emc_mrw6_idx & 0xC0C0) | (dst_emc_entry->burst_regs.emc_mrw6_idx & 0xFFFF3F3F), 0); _ccfifo_write(EMC_MRW6, (src_emc_entry->burst_regs.emc_mrw6_idx & 0xC0C0) | (dst_emc_entry->burst_regs.emc_mrw6_idx & 0xFFFF3F3F), 0);
@ -3114,7 +3117,7 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
_ccfifo_write(EMC_DBG, emc_dbg_val, 0); _ccfifo_write(EMC_DBG, emc_dbg_val, 0);
} }
if (needs_ca_or_cavref_training) if (needs_ca_combo_training)
{ {
_ccfifo_write(EMC_PMACRO_DATA_RX_TERM_MODE, src_emc_entry->burst_regs.emc_pmacro_data_rx_term_mode_idx & 0xFFFFFCCC, 0); _ccfifo_write(EMC_PMACRO_DATA_RX_TERM_MODE, src_emc_entry->burst_regs.emc_pmacro_data_rx_term_mode_idx & 0xFFFFFCCC, 0);
@ -3160,7 +3163,7 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
// Step 14 - Bringup CKE pins. // Step 14 - Bringup CKE pins.
EPRINTF("Step 14"); EPRINTF("Step 14");
u32 emc_pin_val_final = 0; u32 emc_pin_val_final = 0;
if (needs_ca_or_cavref_training) if (needs_ca_combo_training)
{ {
emc_pin_val_final = emc_pin_o & 0xFFFFFFF8; emc_pin_val_final = emc_pin_o & 0xFFFFFFF8;
if (dram_dev_num == TWO_RANK) if (dram_dev_num == TWO_RANK)
@ -3180,7 +3183,7 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
// Step 15 - Zqlatch. // Step 15 - Zqlatch.
EPRINTF("Step 15"); EPRINTF("Step 15");
if (!needs_ca_or_cavref_training) if (!needs_ca_combo_training)
{ {
s32 zq_latch_dvfs_wait_time; s32 zq_latch_dvfs_wait_time;
u32 T_PDEX_timing = div_o3(dst_emc_entry->dram_timings.t_pdex * 1000, dst_clock_period); u32 T_PDEX_timing = div_o3(dst_emc_entry->dram_timings.t_pdex * 1000, dst_clock_period);
@ -3291,7 +3294,7 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
_ccfifo_write(EMC_SWITCH_BACK_CTRL, 1, 0); _ccfifo_write(EMC_SWITCH_BACK_CTRL, 1, 0);
if (!needs_ca_or_cavref_training || needs_swap_rank_training) if (!needs_ca_combo_training || needs_swap_rank_training)
{ {
_ccfifo_write(EMC_MRW3, mr13_flip_fspop ^ 0xC0, 0); _ccfifo_write(EMC_MRW3, mr13_flip_fspop ^ 0xC0, 0);
_ccfifo_write(EMC_INTSTATUS, 0, 1000000 / dst_clock_period); _ccfifo_write(EMC_INTSTATUS, 0, 1000000 / dst_clock_period);
@ -3315,7 +3318,7 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
else else
_ccfifo_write(EMC_PIN, (emc_pin_o & 0xFFFFFFF8) | 1, 0); _ccfifo_write(EMC_PIN, (emc_pin_o & 0xFFFFFFF8) | 1, 0);
if (needs_ca_or_cavref_training) if (needs_ca_combo_training)
{ {
_ccfifo_write(EMC_TR_CTRL_0, 0x4A, 200000 / src_clock_period); _ccfifo_write(EMC_TR_CTRL_0, 0x4A, 200000 / src_clock_period);
_ccfifo_write(EMC_TR_CTRL_0, 0x40, 1000000 / src_clock_period); _ccfifo_write(EMC_TR_CTRL_0, 0x40, 1000000 / src_clock_period);
@ -3329,14 +3332,14 @@ static u32 _minerva_set_clock(emc_table_t *src_emc_entry, emc_table_t *dst_emc_e
_ccfifo_write(EMC_ZQ_CAL, 0x80000001, 0); _ccfifo_write(EMC_ZQ_CAL, 0x80000001, 0);
_ccfifo_write(EMC_ZQ_CAL, 0x80000002, 1000000 / src_clock_period); _ccfifo_write(EMC_ZQ_CAL, 0x80000002, 1000000 / src_clock_period);
if ((!needs_ca_or_cavref_training || needs_swap_rank_training) && dram_dev_num == TWO_RANK) if ((!needs_ca_combo_training || needs_swap_rank_training) && dram_dev_num == TWO_RANK)
{ {
_ccfifo_write(EMC_ZQ_CAL, 0x40000001, 0); _ccfifo_write(EMC_ZQ_CAL, 0x40000001, 0);
_ccfifo_write(EMC_ZQ_CAL, 0x40000002, 1000000 / src_clock_period); _ccfifo_write(EMC_ZQ_CAL, 0x40000002, 1000000 / src_clock_period);
} }
if (!needs_ca_or_cavref_training) if (!needs_ca_combo_training)
_ccfifo_write(EMC_MRW3, (mr13_flip_fspop & 0xF3FFFFF7) ^ 0xC0000C0, 0); _ccfifo_write(EMC_MRW3, (mr13_flip_fspop & 0xF3FFFFF7) ^ 0xC0000C0, 0);
_ccfifo_write(EMC_SELF_REF, 0, 0); // Was 0x100. _ccfifo_write(EMC_SELF_REF, 0, 0); // Was 0x100.
@ -3536,24 +3539,29 @@ static void _minerva_train_patterns(emc_table_t *src_emc_entry, emc_table_t *dst
if (!dst_emc_entry->trained) if (!dst_emc_entry->trained)
{ {
if (needs_training & 3) if (needs_training & NEEDS_TRAINING_CA_COMBO)
{ {
needs_training_emc_table[needs_training_idx++] = needs_training & 0x203; needs_training_emc_table[needs_training_idx++] =
needs_training & (NEEDS_TRAINING_CA_COMBO | NEEDS_TRAINING_IN_SELF_REFRESH);
if (MC(MC_EMEM_ADR_CFG) & 1) // if mapping W8 (1KB page). if (MC(MC_EMEM_ADR_CFG) & 1) // if mapping W8 (1KB page).
needs_training_emc_table[needs_training_idx++] = needs_training & 0x303; needs_training_emc_table[needs_training_idx++] =
needs_training & (NEEDS_TRAINING_CA_COMBO | NEEDS_TRAINING_SWAP_RANK | NEEDS_TRAINING_IN_SELF_REFRESH);
} }
if (needs_training & 0xC) if (needs_training & NEEDS_TRAINING_QUSE_COMBO)
{ {
needs_training_emc_table[needs_training_idx++] = needs_training & 0x20C; needs_training_emc_table[needs_training_idx++] =
needs_training & (NEEDS_TRAINING_QUSE_COMBO | NEEDS_TRAINING_IN_SELF_REFRESH);
if (MC(MC_EMEM_ADR_CFG) & 1) if (MC(MC_EMEM_ADR_CFG) & 1)
needs_training_emc_table[needs_training_idx++] = needs_training & 0x204; needs_training_emc_table[needs_training_idx++] =
needs_training & (NEEDS_TRAINING_QUSE | NEEDS_TRAINING_IN_SELF_REFRESH);
} }
if (needs_training & 0xF0) if (needs_training & (NEEDS_TRAINING_WR_COMBO | NEEDS_TRAINING_RD_COMBO))
needs_training_emc_table[needs_training_idx++] = needs_training & 0x2F0; needs_training_emc_table[needs_training_idx++] =
needs_training & (NEEDS_TRAINING_WR_COMBO | NEEDS_TRAINING_RD_COMBO | NEEDS_TRAINING_IN_SELF_REFRESH);
for (u32 i = 0; needs_training_idx > i; i++) // Runs more than once for needs_training & 0xF for (u32 i = 0; needs_training_idx > i; i++) // Runs more than once for needs_training CA/QUSE/WR/RD.
{ {
_minerva_set_clock(src_emc_entry, dst_emc_entry, needs_training_emc_table[i], selected_clk_src_emc); _minerva_set_clock(src_emc_entry, dst_emc_entry, needs_training_emc_table[i], selected_clk_src_emc);