Skip to content

Commit

Permalink
clean up OLED init and SPI DMA
Browse files Browse the repository at this point in the history
  • Loading branch information
vk2seb committed Nov 4, 2023
1 parent d92a0d2 commit 248db0a
Showing 1 changed file with 74 additions and 34 deletions.
108 changes: 74 additions & 34 deletions firmware/litex-fw/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -57,11 +57,11 @@ litex_hal::timer! {
}

litex_hal::gpio! {
CTL: litex_pac::OLED_CTL,
OledGpio: litex_pac::OLED_CTL,
}

litex_hal::spi! {
SPI: (litex_pac::OLED_SPI, u8),
OledSpi: (litex_pac::OLED_SPI, u8),
}

const N_CHANNELS: usize = 4;
Expand Down Expand Up @@ -454,32 +454,54 @@ impl Encoder {
}
}

#[entry]
fn main() -> ! {
let peripherals = unsafe { pac::Peripherals::steal() };

log::init(peripherals.UART);
log::info!("hello from litex-fw!");
struct SpiDma {
spi_dma: pac::SPI_DMA,
}

let pmod0 = peripherals.EURORACK_PMOD0;
impl SpiDma {
fn new(spi_dma: pac::SPI_DMA,
target: *const pac::oled_spi::RegisterBlock) -> Self {
unsafe {
// TODO: Any way to get RegisterBlock sub-addresses automagically?
spi_dma.spi_control_reg_address.write(
|w| w.bits(target as u32));
spi_dma.spi_status_reg_address.write(
|w| w.bits(target as u32 + 0x04));
spi_dma.spi_mosi_reg_address.write(
|w| w.bits(target as u32 + 0x08));
}
Self {
spi_dma
}
}

let pca9635 = peripherals.PCA9635;
fn block(&self) {
while self.spi_dma.done.read().bits() == 0 {
// Wait for an existing transfer to complete.
}
}

fn transfer(&mut self, data_ptr: *const u8, data_len: usize) {
unsafe {
self.spi_dma.read_base.write(|w| w.bits(data_ptr as u32));
self.spi_dma.read_length.write(|w| w.bits(data_len as u32));
self.spi_dma.start.write(|w| w.start().bit(true));
self.spi_dma.start.write(|w| w.start().bit(false));
}
}
}

let mut timer = Timer::new(peripherals.TIMER0, SYSTEM_CLOCK_FREQUENCY);
unsafe fn reset_soc(ctrl: &pac::CTRL) {
ctrl.reset.write(|w| w.soc_rst().bit(true));
}

pca9635.reset_line(true);
pmod0.reset_line(true);
timer.delay_ms(10u32);
pca9635.reset_line(false);
pmod0.reset_line(false);
fn oled_init(timer: &mut Timer, oled_spi: pac::OLED_SPI)
-> ssd1322::Display<ssd1322::SpiInterface<OledSpi, OledGpio>> {

let dc = CTL { index: 0 };
let mut rstn = CTL { index: 1 };
let mut csn = CTL { index: 2 };
let spi = SPI {
registers: peripherals.OLED_SPI
};
let dc = OledGpio::new(0);
let mut rstn = OledGpio::new(1);
let mut csn = OledGpio::new(2);
let spi = OledSpi::new(oled_spi);

// Create the SpiInterface and Display.
let mut disp = oled::Display::new(
Expand Down Expand Up @@ -511,6 +533,30 @@ fn main() -> ! {
.com_deselect_voltage(7),
).unwrap();

disp
}

#[entry]
fn main() -> ! {
let peripherals = unsafe { pac::Peripherals::steal() };

log::init(peripherals.UART);
log::info!("hello from litex-fw!");

let pmod0 = peripherals.EURORACK_PMOD0;

let pca9635 = peripherals.PCA9635;


let mut timer = Timer::new(peripherals.TIMER0, SYSTEM_CLOCK_FREQUENCY);

pca9635.reset_line(true);
pmod0.reset_line(true);
timer.delay_ms(10u32);
pca9635.reset_line(false);
pmod0.reset_line(false);

let mut disp = oled_init(&mut timer, peripherals.OLED_SPI);

let character_style = MonoTextStyle::new(&FONT_5X7, Gray4::WHITE);
let font_small_white = MonoTextStyle::new(&FONT_4X6, Gray4::WHITE);
Expand All @@ -534,6 +580,8 @@ fn main() -> ! {
|w| w.bits(litex_pac::OLED_SPI::PTR as u32 + 0x08));
}

let mut spi_dma = SpiDma::new(peripherals.SPI_DMA, pac::OLED_SPI::PTR);

unsafe {

peripherals.DMA_ROUTER0.base_writer.write(|w| w.bits(BUF_IN.as_mut_ptr() as u32));
Expand Down Expand Up @@ -601,7 +649,7 @@ fn main() -> ! {
}

if encoder.long_press() {
peripherals.CTRL.reset.write(|w| w.soc_rst().bit(true));
unsafe { reset_soc(&peripherals.CTRL); }
}


Expand Down Expand Up @@ -686,17 +734,9 @@ fn main() -> ! {
}

let fb = disp.swap_clear();
unsafe {
fence();
while peripherals.SPI_DMA.done.read().bits() == 0 {
// Don't start to DMA a new framebuffer if we're still
// pushing through the last one.
}
peripherals.SPI_DMA.read_base.write(|w| w.bits(fb.as_ptr() as u32));
peripherals.SPI_DMA.read_length.write(|w| w.bits(fb.len() as u32));
peripherals.SPI_DMA.start.write(|w| w.start().bit(true));
peripherals.SPI_DMA.start.write(|w| w.start().bit(false));
}
fence();
spi_dma.block();
spi_dma.transfer(fb.as_ptr(), fb.len());

let cycle_cnt_now = timer.uptime();
let cycle_cnt_last = cycle_cnt;
Expand Down

0 comments on commit 248db0a

Please sign in to comment.