1
0
Fork 0

libboard_zynq: complete ddr without ps7_init for cora_z7_10

This commit is contained in:
Astro 2020-11-10 14:33:31 +01:00
parent 515d3bb381
commit b9323653bb
4 changed files with 144 additions and 23 deletions

View File

@ -93,8 +93,6 @@ pub fn main_core0() {
println!("\nZynq experiments"); println!("\nZynq experiments");
let mut interrupt_controller = gic::InterruptController::gic(mpcore::RegisterBlock::mpcore()); let mut interrupt_controller = gic::InterruptController::gic(mpcore::RegisterBlock::mpcore());
interrupt_controller.enable_interrupts(); interrupt_controller.enable_interrupts();
// ps7_init::apply();
libboard_zynq::stdio::drop_uart();
libboard_zynq::logger::init().unwrap(); libboard_zynq::logger::init().unwrap();
log::set_max_level(log::LevelFilter::Trace); log::set_max_level(log::LevelFilter::Trace);

View File

@ -4,7 +4,7 @@ use crate::{print, println};
use super::slcr::{self, DdriobVrefSel}; use super::slcr::{self, DdriobVrefSel};
use super::clocks::{Clocks, source::{DdrPll, ClockSource}}; use super::clocks::{Clocks, source::{DdrPll, ClockSource}};
#[cfg(any(feature = "target_redpitaya", feature = "target_cora_z7_10"))] #[cfg(feature = "target_redpitaya")]
use super::ps7_init; use super::ps7_init;
mod regs; mod regs;
@ -30,18 +30,18 @@ pub struct DdrRam {
impl DdrRam { impl DdrRam {
pub fn ddrram() -> Self { pub fn ddrram() -> Self {
if cfg!(any(feature = "target_redpitaya", feature = "target_cora_z7_10")) { if cfg!(feature = "target_redpitaya") {
// We have not yet fixed red pitaya initialization yet. It seems // We have not yet fixed red pitaya initialization yet. It seems
// that the clock configuration, iob settings and ddr settings are // that the clock configuration, iob settings and ddr settings are
// all problematic // all problematic
#[cfg(any(feature = "target_redpitaya", feature = "target_cora_z7_10"))] #[cfg(feature = "target_redpitaya")]
ps7_init::apply(); ps7_init::apply();
let regs = regs::RegisterBlock::ddrc(); let regs = regs::RegisterBlock::ddrc();
DdrRam { regs } DdrRam { regs }
} else { } else {
let clocks = Self::clock_setup(); let clocks = Self::clock_setup();
Self::calibrate_iob_impedance(&clocks);
Self::configure_iob(); Self::configure_iob();
Self::calibrate_iob_impedance(&clocks);
let regs = regs::RegisterBlock::ddrc(); let regs = regs::RegisterBlock::ddrc();
let mut ddr = DdrRam { regs }; let mut ddr = DdrRam { regs };
ddr.reset_ddrc(|ddr| ddr.configure()); ddr.reset_ddrc(|ddr| ddr.configure());
@ -218,12 +218,12 @@ impl DdrRam {
slcr.ddriob_drive_slew_clock.write(0x00F9861C); slcr.ddriob_drive_slew_clock.write(0x00F9861C);
} }
// Enable external V[REF]
#[cfg(feature = "target_cora_z7_10")] #[cfg(feature = "target_cora_z7_10")]
slcr.ddriob_ddr_ctrl.modify(|_, w| w slcr.ddriob_ddr_ctrl.modify(|_, w| w
.vref_int_en(false) .vref_int_en(false)
.vref_ext_en_lower(true) .vref_ext_en_lower(true)
.vref_ext_en_upper(false) .vref_ext_en_upper(false)
.refio_en(true)
); );
#[cfg(feature = "target_zc706")] #[cfg(feature = "target_zc706")]
slcr.ddriob_ddr_ctrl.modify(|_, w| w slcr.ddriob_ddr_ctrl.modify(|_, w| w
@ -242,6 +242,14 @@ impl DdrRam {
} }
fn configure(&mut self) { fn configure(&mut self) {
#[cfg(feature = "target_cora_z7_10")]
self.regs.dram_param0.write(
regs::DramParam0::zeroed()
.t_rc(0x1a)
.t_rfc_min(0x9e)
.post_selfref_gap_x32(0x10)
);
#[cfg(feature = "target_zc706")]
self.regs.dram_param0.write( self.regs.dram_param0.write(
regs::DramParam0::zeroed() regs::DramParam0::zeroed()
.t_rc(0x1b) .t_rc(0x1b)
@ -249,6 +257,17 @@ impl DdrRam {
.post_selfref_gap_x32(0x10) .post_selfref_gap_x32(0x10)
); );
#[cfg(feature = "target_cora_z7_10")]
self.regs.dram_param1.write(
regs::DramParam1::zeroed()
.wr2pre(0x12)
.powerdown_to_x32(0x6)
.t_faw(0x15)
.t_ras_max(0x23)
.t_ras_min(0x13)
.t_cke(0x4)
);
self.regs.dram_param2.write( self.regs.dram_param2.write(
regs::DramParam2::zeroed() regs::DramParam2::zeroed()
.write_latency(0x5) .write_latency(0x5)
@ -260,12 +279,43 @@ impl DdrRam {
.t_rcd(0x7) .t_rcd(0x7)
); );
#[cfg(feature = "target_cora_z7_10")]
self.regs.dram_param3.write(
regs::DramParam3::zeroed()
.t_ccd(4)
.t_rrd(6)
.refresh_margin(2)
.t_rp(7)
.refresh_to_x32(8)
.mobile(false)
.dfi_dram_clk_disable(false)
.read_latency(7)
.mode_ddr1_ddr2(true)
.dis_pad_pd(false)
);
self.regs.dram_emr_mr.write( self.regs.dram_emr_mr.write(
regs::DramEmrMr::zeroed() regs::DramEmrMr::zeroed()
.mr(0x930) .mr(0x930)
.emr(0x4) .emr(0x4)
); );
#[cfg(feature = "target_cora_z7_10")]
self.regs.dram_burst8_rdwr.write(
regs::Burst8Rdwr::zeroed()
.burst_rdwr(4)
.pre_cke_x1024(0x167)
.post_cke_x1024(0x1)
);
#[cfg(feature = "target_cora_z7_10")]
self.regs.phy_config2.modify(
|_, w| w.data_slice_in_use(false)
);
#[cfg(feature = "target_cora_z7_10")]
self.regs.phy_config3.modify(
|_, w| w.data_slice_in_use(false)
);
self.regs.phy_cmd_timeout_rddata_cpt.modify( self.regs.phy_cmd_timeout_rddata_cpt.modify(
|_, w| w |_, w| w
.rd_cmd_to_data(0x0) .rd_cmd_to_data(0x0)
@ -298,12 +348,26 @@ impl DdrRam {
.ctrlup_max(0x40) .ctrlup_max(0x40)
); );
#[cfg(feature = "target_cora_z7_10")]
self.regs.phy_init_ratio3.write(
regs::PhyInitRatio::zeroed()
.wrlvl_init_ratio(0x0)
.gatelvl_init_ratio(0x76)
);
#[cfg(feature = "target_zc706")]
self.regs.phy_init_ratio3.write( self.regs.phy_init_ratio3.write(
regs::PhyInitRatio::zeroed() regs::PhyInitRatio::zeroed()
.wrlvl_init_ratio(0x21) .wrlvl_init_ratio(0x21)
.gatelvl_init_ratio(0xee) .gatelvl_init_ratio(0xee)
); );
#[cfg(feature = "target_cora_z7_10")]
self.regs.reg_64.modify(
|_, w| w
.phy_ctrl_slave_ratio(0x100)
.phy_invert_clkout(true)
);
self.regs.reg_65.write( self.regs.reg_65.write(
regs::Reg65::zeroed() regs::Reg65::zeroed()
.wr_rl_delay(0x2) .wr_rl_delay(0x2)
@ -315,6 +379,18 @@ impl DdrRam {
.dis_calib_rst(false) .dis_calib_rst(false)
.ctrl_slave_delay(0x0) .ctrl_slave_delay(0x0)
); );
#[cfg(feature = "target_cora_z7_10")]
for axi_priority_rd_port in &mut self.regs.axi_priority_rd_ports {
axi_priority_rd_port.modify(
|_, w| w
.arb_pri_rd_portn(0x3ff)
.arb_disable_aging_rd_portn(false)
.arb_disable_urgent_rd_portn(false)
.arb_disable_page_match_rd_portn(false)
.arb_set_hpr_rd_portn(false)
);
}
} }
/// Reset DDR controller /// Reset DDR controller
@ -370,7 +446,7 @@ impl DdrRam {
#[cfg(feature = "target_zc706")] #[cfg(feature = "target_zc706")]
let megabytes = 1023; let megabytes = 1023;
#[cfg(feature = "target_cora_z7_10")] #[cfg(feature = "target_cora_z7_10")]
let megabytes = 511; let megabytes = 512;
#[cfg(feature = "target_redpitaya")] #[cfg(feature = "target_redpitaya")]
let megabytes = 511; let megabytes = 511;

View File

@ -33,14 +33,14 @@ pub struct RegisterBlock {
pub lpr: RW<u32>, pub lpr: RW<u32>,
pub wr: RW<u32>, pub wr: RW<u32>,
pub dram_param0: DramParam0, pub dram_param0: DramParam0,
pub dram_param1: RW<u32>, pub dram_param1: DramParam1,
pub dram_param2: DramParam2, pub dram_param2: DramParam2,
pub dram_param3: RW<u32>, pub dram_param3: DramParam3,
pub dram_param4: RW<u32>, pub dram_param4: RW<u32>,
pub dram_init_param: RW<u32>, pub dram_init_param: RW<u32>,
pub dram_emr: RW<u32>, pub dram_emr: RW<u32>,
pub dram_emr_mr: DramEmrMr, pub dram_emr_mr: DramEmrMr,
pub dram_burst8_rdwr: RW<u32>, pub dram_burst8_rdwr: Burst8Rdwr,
pub dram_disable_dq: RW<u32>, pub dram_disable_dq: RW<u32>,
pub dram_addr_map_bank: RW<u32>, pub dram_addr_map_bank: RW<u32>,
pub dram_addr_map_col: RW<u32>, pub dram_addr_map_col: RW<u32>,
@ -84,10 +84,10 @@ pub struct RegisterBlock {
pub che_ecc_corr_bit_mask_63_32_offset: RW<u32>, pub che_ecc_corr_bit_mask_63_32_offset: RW<u32>,
_unused3: [RO<u32>; 5], _unused3: [RO<u32>; 5],
pub phy_rcvr_enable: RW<u32>, pub phy_rcvr_enable: RW<u32>,
pub phy_config0: RW<u32>, pub phy_config0: PhyConfig,
pub phy_config1: RW<u32>, pub phy_config1: PhyConfig,
pub phy_config2: RW<u32>, pub phy_config2: PhyConfig,
pub phy_config3: RW<u32>, pub phy_config3: PhyConfig,
_unused4: RO<u32>, _unused4: RO<u32>,
pub phy_init_ratio0: PhyInitRatio, pub phy_init_ratio0: PhyInitRatio,
pub phy_init_ratio1: PhyInitRatio, pub phy_init_ratio1: PhyInitRatio,
@ -114,7 +114,7 @@ pub struct RegisterBlock {
pub wr_data_slv2: RW<u32>, pub wr_data_slv2: RW<u32>,
pub wr_data_slv3: RW<u32>, pub wr_data_slv3: RW<u32>,
_unused9: RO<u32>, _unused9: RO<u32>,
pub reg_64: RW<u32>, pub reg_64: Reg64,
pub reg_65: Reg65, pub reg_65: Reg65,
_unused10: [RO<u32>; 3], _unused10: [RO<u32>; 3],
pub reg69_6a0: RW<u32>, pub reg69_6a0: RW<u32>,
@ -142,10 +142,7 @@ pub struct RegisterBlock {
pub axi_priority_wr_port1: RW<u32>, pub axi_priority_wr_port1: RW<u32>,
pub axi_priority_wr_port2: RW<u32>, pub axi_priority_wr_port2: RW<u32>,
pub axi_priority_wr_port3: RW<u32>, pub axi_priority_wr_port3: RW<u32>,
pub axi_priority_rd_port0: RW<u32>, pub axi_priority_rd_ports: [AxiPriorityRd; 4],
pub axi_priority_rd_port1: RW<u32>,
pub axi_priority_rd_port2: RW<u32>,
pub axi_priority_rd_port3: RW<u32>,
_unused15: [RO<u32>; 27], _unused15: [RO<u32>; 27],
pub excl_access_cfg0: RW<u32>, pub excl_access_cfg0: RW<u32>,
pub excl_access_cfg1: RW<u32>, pub excl_access_cfg1: RW<u32>,
@ -173,6 +170,14 @@ register_bits!(dram_param0, t_rc, u8, 0, 5);
register_bits!(dram_param0, t_rfc_min, u8, 6, 13); register_bits!(dram_param0, t_rfc_min, u8, 6, 13);
register_bits!(dram_param0, post_selfref_gap_x32, u8, 14, 20); register_bits!(dram_param0, post_selfref_gap_x32, u8, 14, 20);
register!(dram_param1, DramParam1, RW, u32);
register_bits!(dram_param1, wr2pre, u8, 0, 4);
register_bits!(dram_param1, powerdown_to_x32, u8, 5, 9);
register_bits!(dram_param1, t_faw, u8, 10, 15);
register_bits!(dram_param1, t_ras_max, u8, 16, 21);
register_bits!(dram_param1, t_ras_min, u8, 22, 26);
register_bits!(dram_param1, t_cke, u8, 28, 31);
register!(dram_param2, DramParam2, RW, u32); register!(dram_param2, DramParam2, RW, u32);
register_bits!(dram_param2, write_latency, u8, 0, 4); register_bits!(dram_param2, write_latency, u8, 0, 4);
register_bits!(dram_param2, rd2wr, u8, 5, 9); register_bits!(dram_param2, rd2wr, u8, 5, 9);
@ -182,10 +187,29 @@ register_bits!(dram_param2, pad_pd, u8, 20, 22);
register_bits!(dram_param2, rd2pre, u8, 23, 27); register_bits!(dram_param2, rd2pre, u8, 23, 27);
register_bits!(dram_param2, t_rcd, u8, 28, 31); register_bits!(dram_param2, t_rcd, u8, 28, 31);
register!(dram_param3, DramParam3, RW, u32);
register_bits!(dram_param3, t_ccd, u8, 2, 4);
register_bits!(dram_param3, t_rrd, u8, 5, 7);
register_bits!(dram_param3, refresh_margin, u8, 8, 11);
register_bits!(dram_param3, t_rp, u8, 12, 15);
register_bits!(dram_param3, refresh_to_x32, u8, 16, 20);
register_bit!(dram_param3, sdram, 21);
register_bit!(dram_param3, mobile, 22);
register_bit!(dram_param3, dfi_dram_clk_disable, 23);
register_bits!(dram_param3, read_latency, u8, 24, 28);
register_bit!(dram_param3, mode_ddr1_ddr2, 29);
register_bit!(dram_param3, dis_pad_pd, 30);
register!(dram_emr_mr, DramEmrMr, RW, u32); register!(dram_emr_mr, DramEmrMr, RW, u32);
register_bits!(dram_emr_mr, mr, u16, 0, 15); register_bits!(dram_emr_mr, mr, u16, 0, 15);
register_bits!(dram_emr_mr, emr, u16, 16, 31); register_bits!(dram_emr_mr, emr, u16, 16, 31);
register!(burst8_rdwr, Burst8Rdwr, RW, u32);
register_bits!(burst8_rdwr, burst_rdwr, u8, 0, 3);
register_bits!(burst8_rdwr, pre_cke_x1024, u16, 4, 13);
register_bits!(burst8_rdwr, post_cke_x1024, u16, 16, 25);
register_bit!(burst8_rdwr, burstchop, 28);
register!(phy_cmd_timeout_rddata_cpt, PhyCmdTimeoutRddataCpt, RW, u32); register!(phy_cmd_timeout_rddata_cpt, PhyCmdTimeoutRddataCpt, RW, u32);
register_bits!(phy_cmd_timeout_rddata_cpt, rd_cmd_to_data, u8, 0, 3); register_bits!(phy_cmd_timeout_rddata_cpt, rd_cmd_to_data, u8, 0, 3);
register_bits!(phy_cmd_timeout_rddata_cpt, wr_cmd_to_data, u8, 4, 7); register_bits!(phy_cmd_timeout_rddata_cpt, wr_cmd_to_data, u8, 4, 7);
@ -212,10 +236,27 @@ register_bits!(dfi_timing, rddata_en, u8, 0, 4);
register_bits!(dfi_timing, ctrlup_min, u16, 5, 14); register_bits!(dfi_timing, ctrlup_min, u16, 5, 14);
register_bits!(dfi_timing, ctrlup_max, u16, 15, 24); register_bits!(dfi_timing, ctrlup_max, u16, 15, 24);
register!(phy_config, PhyConfig, RW, u32);
register_bit!(phy_config, data_slice_in_use, 0);
register_bit!(phy_config, rdlvl_inc_mode, 1);
register_bit!(phy_config, gatelvl_inc_mode, 2);
register_bit!(phy_config, wrlvl_inc_mode, 3);
register_bits!(phy_config, dq_offset, u8, 24, 30);
register!(phy_init_ratio, PhyInitRatio, RW, u32); register!(phy_init_ratio, PhyInitRatio, RW, u32);
register_bits!(phy_init_ratio, wrlvl_init_ratio, u16, 0, 9); register_bits!(phy_init_ratio, wrlvl_init_ratio, u16, 0, 9);
register_bits!(phy_init_ratio, gatelvl_init_ratio, u16, 10, 19); register_bits!(phy_init_ratio, gatelvl_init_ratio, u16, 10, 19);
register!(reg_64, Reg64, RW, u32);
register_bit!(reg_64, phy_bl2, 1);
register_bit!(reg_64, phy_invert_clkout, 7);
register_bit!(reg_64, phy_sel_logic, 9);
register_bits!(reg_64, phy_ctrl_slave_ratio, u16, 10, 19);
register_bit!(reg_64, phy_ctrl_slave_force, 20);
register_bits!(reg_64, phy_ctrl_slave_delay, u8, 21, 27);
register_bit!(reg_64, phy_lpddr, 29);
register_bit!(reg_64, phy_cmd_latency, 30);
register!(reg_65, Reg65, RW, u32); register!(reg_65, Reg65, RW, u32);
register_bits!(reg_65, wr_rl_delay, u8, 0, 4); register_bits!(reg_65, wr_rl_delay, u8, 0, 4);
register_bits!(reg_65, rd_rl_delay, u8, 5, 9); register_bits!(reg_65, rd_rl_delay, u8, 5, 9);
@ -231,3 +272,10 @@ register!(mode_sts_reg,
ModeStsReg, RO, u32); ModeStsReg, RO, u32);
register_bits_typed!(mode_sts_reg, operating_mode, u8, ControllerStatus, 0, 2); register_bits_typed!(mode_sts_reg, operating_mode, u8, ControllerStatus, 0, 2);
// (mode_sts_reg) ... // (mode_sts_reg) ...
register!(axi_priority_rd, AxiPriorityRd, RW, u32);
register_bits!(axi_priority_rd, arb_pri_rd_portn, u16, 0, 9);
register_bit!(axi_priority_rd, arb_disable_aging_rd_portn, 16);
register_bit!(axi_priority_rd, arb_disable_urgent_rd_portn, 17);
register_bit!(axi_priority_rd, arb_disable_page_match_rd_portn, 18);
register_bit!(axi_priority_rd, arb_set_hpr_rd_portn, 19);

View File

@ -3978,5 +3978,4 @@ pub const INIT_DATA: &'static [InitOp] = &[
// .. .. FINISH: NOR CHIP SELECT // .. .. FINISH: NOR CHIP SELECT
// .. FINISH: SMC TIMING CALCULATION REGISTER UPDATE // .. FINISH: SMC TIMING CALCULATION REGISTER UPDATE
// FINISH: top // FINISH: top
]; ];