use base_address::{BaseAddress, Dynamic, Static};
use volatile_register::{RO, RW};
use super::PHY;
#[repr(C)]
pub struct RegisterBlock {
pub pir: RW<u32>, pub pwrctl: RW<u32>, pub mrctrl0: RW<u32>, pub clken: RW<u32>, pub pgsr: [RW<u32>; 2], pub statr: RW<u32>, _reserved0: [u32; 4],
pub lp3mr11: RW<u32>, pub mr: [RW<u32>; 4], _reserved1: [u32; 1],
pub ptr: [RW<u32>; 5], pub dramtmg: [RW<u32>; 9], pub odtcfg: RW<u32>, pub pitmg: [RW<u32>; 2], pub lptpr: RW<u32>, pub rfshctl0: RW<u32>, pub rfshtmg: RW<u32>, pub rfshctl1: RW<u32>, pub pwrtmg: RW<u32>, pub asrc: RW<u32>, pub asrtc: RW<u32>, _reserved3: [u32; 5],
pub vtfcr: RW<u32>, pub dqsgmr: RW<u32>, pub dtcr: RW<u32>, pub dtar0: RW<u32>, _reserved4: [u32; 14],
pub pgcr: [RW<u32>; 4], pub iovcr0: RW<u32>, pub iovcr1: RW<u32>, _reserved5: [u32; 1],
pub dxccr: RW<u32>, pub odtmap: RW<u32>, pub zqctl: [RW<u32>; 2], _reserved6: [u32; 5],
pub zqcr: RW<u32>, pub zqsr: RW<u32>, pub zqdr: [RW<u32>; 3], _reserved7: [u32; 27],
pub sched: RW<u32>, pub perfhpr: [RW<u32>; 2], pub perflpr: [RW<u32>; 2], pub perfwr: [RW<u32>; 2], _reserved8: [u32; 9],
pub acmdlr: RW<u32>, pub acldlr: RW<u32>, pub aciocr0: RW<u32>, _reserved9: [u32; 61],
pub datx: [Datx8; 4], _reserved10: [u32; 226],
pub upd2: RW<u32>, }
#[repr(C)]
pub struct Datx8 {
pub mdlr: RW<u32>, pub lcdlr: [RW<u32>; 3], pub iocr: [RW<u32>; 11], pub sdlr6: RW<u32>, pub gtr: RW<u32>, pub gcr: RW<u32>, pub gsr0: RO<u32>, pub gsr1: RW<u32>, pub gsr2: RW<u32>, _reserved0: [u32; 11],
}
pub enum DqWidth {
X8,
X16,
}
impl<const B: usize> PHY<Static<B>> {
#[inline]
pub const unsafe fn steal_static() -> PHY<Static<B>> {
PHY { base: Static::<B> }
}
}
impl PHY<Dynamic> {
#[inline]
pub unsafe fn steal_dynamic(base: *const ()) -> PHY<Dynamic> {
PHY {
base: Dynamic::new(base as usize),
}
}
}
impl<A: BaseAddress> PHY<A> {
#[inline]
pub fn dqs_gate_detect(&self) {
let pgsr0 = self.pgsr[0].read();
let qsgerr = pgsr0 & (1 << 22) != 0;
if !qsgerr {
return;
}
let dx0_gsr0 = self.datx[0].gsr0.read();
let dx1_gsr0 = self.datx[1].gsr0.read();
let dx0_qsgerr = (dx0_gsr0 >> 26) & 0xf;
let dx1_qsgerr = (dx1_gsr0 >> 26) & 0xf;
if dx0_qsgerr & 0x2 != 0 {
if dx1_qsgerr & 0x2 != 0 {
return;
} else {
return;
}
} else {
if dx1_qsgerr != 0 {
} else {
}
}
}
}
#[cfg(test)]
mod tests {
use super::{Datx8, RegisterBlock};
use memoffset::offset_of;
#[test]
fn offset_phy() {
assert_eq!(offset_of!(RegisterBlock, lp3mr11), 0x2c);
assert_eq!(offset_of!(RegisterBlock, ptr), 0x44);
assert_eq!(offset_of!(RegisterBlock, pgcr), 0x100);
assert_eq!(offset_of!(RegisterBlock, zqcr), 0x140);
assert_eq!(offset_of!(RegisterBlock, sched), 0x1c0);
assert_eq!(offset_of!(RegisterBlock, acmdlr), 0x200);
assert_eq!(offset_of!(RegisterBlock, datx), 0x300);
assert_eq!(offset_of!(RegisterBlock, upd2), 0x888);
}
#[test]
fn offset_datx8() {
assert_eq!(offset_of!(Datx8, mdlr), 0x00);
assert_eq!(offset_of!(Datx8, lcdlr), 0x04);
assert_eq!(offset_of!(Datx8, iocr), 0x10);
assert_eq!(offset_of!(Datx8, sdlr6), 0x3c);
assert_eq!(offset_of!(Datx8, gsr0), 0x48);
}
}