mirror of
https://github.com/esp-rs/esp-hal.git
synced 2025-09-27 12:20:56 +00:00

* Newtype fugit Rate, Instant and Duration * Document, remove time::now * Fix perf * Tweak docs
149 lines
4.6 KiB
Rust
149 lines
4.6 KiB
Rust
//! LCD_CAM Camera and DPI tests
|
|
|
|
//% CHIPS: esp32s3
|
|
//% FEATURES: unstable
|
|
|
|
#![no_std]
|
|
#![no_main]
|
|
|
|
use esp_hal::{
|
|
dma::{DmaChannel, DmaRxBuf, DmaTxBuf},
|
|
dma_buffers,
|
|
gpio::Level,
|
|
lcd_cam::{
|
|
cam::{self, Camera, RxEightBits},
|
|
lcd::{
|
|
dpi,
|
|
dpi::{Dpi, Format, FrameTiming},
|
|
ClockMode,
|
|
Phase,
|
|
Polarity,
|
|
},
|
|
LcdCam,
|
|
},
|
|
peripherals::Peripherals,
|
|
time::Rate,
|
|
};
|
|
use hil_test as _;
|
|
|
|
struct Context {
|
|
peripherals: Peripherals,
|
|
dma_tx_buf: DmaTxBuf,
|
|
dma_rx_buf: DmaRxBuf,
|
|
}
|
|
|
|
#[cfg(test)]
|
|
#[embedded_test::tests]
|
|
mod tests {
|
|
use super::*;
|
|
|
|
#[init]
|
|
fn init() -> Context {
|
|
let peripherals = esp_hal::init(esp_hal::Config::default());
|
|
|
|
let (rx_buffer, rx_descriptors, tx_buffer, tx_descriptors) = dma_buffers!(50 * 50);
|
|
let dma_rx_buf = DmaRxBuf::new(rx_descriptors, rx_buffer).unwrap();
|
|
let dma_tx_buf = DmaTxBuf::new(tx_descriptors, tx_buffer).unwrap();
|
|
|
|
Context {
|
|
peripherals,
|
|
dma_tx_buf,
|
|
dma_rx_buf,
|
|
}
|
|
}
|
|
|
|
#[test]
|
|
fn test_camera_can_receive_from_rgb(ctx: Context) {
|
|
let peripherals = ctx.peripherals;
|
|
|
|
let lcd_cam = LcdCam::new(peripherals.LCD_CAM);
|
|
|
|
let (rx_channel, tx_channel) = peripherals.DMA_CH2.split();
|
|
|
|
let (vsync_in, vsync_out) = peripherals.GPIO6.split();
|
|
let (hsync_in, hsync_out) = peripherals.GPIO7.split();
|
|
let (de_in, de_out) = peripherals.GPIO14.split();
|
|
let (pclk_in, pclk_out) = peripherals.GPIO13.split();
|
|
let (d0_in, d0_out) = peripherals.GPIO11.split();
|
|
let (d1_in, d1_out) = peripherals.GPIO9.split();
|
|
let (d2_in, d2_out) = peripherals.GPIO8.split();
|
|
let (d3_in, d3_out) = peripherals.GPIO47.split();
|
|
let (d4_in, d4_out) = peripherals.GPIO12.split();
|
|
let (d5_in, d5_out) = peripherals.GPIO18.split();
|
|
let (d6_in, d6_out) = peripherals.GPIO17.split();
|
|
let (d7_in, d7_out) = peripherals.GPIO16.split();
|
|
|
|
let config = dpi::Config::default()
|
|
.with_clock_mode(ClockMode {
|
|
polarity: Polarity::IdleHigh,
|
|
phase: Phase::ShiftLow,
|
|
})
|
|
.with_frequency(Rate::from_khz(500))
|
|
.with_format(Format {
|
|
enable_2byte_mode: false,
|
|
..Default::default()
|
|
})
|
|
// Send a 50x50 video
|
|
.with_timing(FrameTiming {
|
|
horizontal_total_width: 65,
|
|
hsync_width: 5,
|
|
horizontal_blank_front_porch: 10,
|
|
horizontal_active_width: 50,
|
|
|
|
vertical_total_height: 65,
|
|
vsync_width: 5,
|
|
vertical_blank_front_porch: 10,
|
|
vertical_active_height: 50,
|
|
|
|
hsync_position: 0,
|
|
})
|
|
.with_vsync_idle_level(Level::High)
|
|
.with_hsync_idle_level(Level::High)
|
|
.with_de_idle_level(Level::Low)
|
|
.with_disable_black_region(false);
|
|
|
|
let dpi = Dpi::new(lcd_cam.lcd, tx_channel, config)
|
|
.unwrap()
|
|
.with_vsync(vsync_out)
|
|
.with_hsync(hsync_out)
|
|
.with_de(de_out)
|
|
.with_pclk(pclk_out)
|
|
.with_data0(d0_out)
|
|
.with_data1(d1_out)
|
|
.with_data2(d2_out)
|
|
.with_data3(d3_out)
|
|
.with_data4(d4_out)
|
|
.with_data5(d5_out)
|
|
.with_data6(d6_out)
|
|
.with_data7(d7_out);
|
|
|
|
let camera = Camera::new(
|
|
lcd_cam.cam,
|
|
rx_channel,
|
|
RxEightBits::new(d0_in, d1_in, d2_in, d3_in, d4_in, d5_in, d6_in, d7_in),
|
|
cam::Config::default().with_frequency(Rate::from_mhz(1)),
|
|
)
|
|
.unwrap()
|
|
.with_ctrl_pins_and_de(vsync_in, hsync_in, de_in)
|
|
.with_pixel_clock(pclk_in);
|
|
|
|
let mut dma_tx_buf = ctx.dma_tx_buf;
|
|
let mut dma_rx_buf = ctx.dma_rx_buf;
|
|
|
|
for (i, b) in dma_tx_buf.as_mut_slice().iter_mut().enumerate() {
|
|
*b = ((i + 0) % 256) as u8;
|
|
}
|
|
|
|
let camera_transfer = camera.receive(dma_rx_buf).map_err(|e| e.0).unwrap();
|
|
// Note: next_frame_en is not false because the RGB driver doesn't send a VSYNC
|
|
// at the end of the frame, which means the DMA doesn't flush the last
|
|
// few bytes it receives.
|
|
let dpi_transfer = dpi.send(true, dma_tx_buf).map_err(|e| e.0).unwrap();
|
|
|
|
(_, _, dma_rx_buf) = camera_transfer.wait();
|
|
(_, dma_tx_buf) = dpi_transfer.stop();
|
|
|
|
assert_eq!(dma_tx_buf.as_slice(), dma_rx_buf.as_slice());
|
|
}
|
|
}
|