forked from M-Labs/artiq
firmware: load slave FPGA in bootloader
This commit is contained in:
parent
389a8f587a
commit
a78e493b72
|
@ -11,6 +11,8 @@ use core::{ptr, slice};
|
||||||
use crc::crc32;
|
use crc::crc32;
|
||||||
use byteorder::{ByteOrder, BigEndian};
|
use byteorder::{ByteOrder, BigEndian};
|
||||||
use board_misoc::{ident, cache, sdram, boot, mem as board_mem};
|
use board_misoc::{ident, cache, sdram, boot, mem as board_mem};
|
||||||
|
#[cfg(has_slave_fpga_cfg)]
|
||||||
|
use board_misoc::slave_fpga;
|
||||||
#[cfg(has_ethmac)]
|
#[cfg(has_ethmac)]
|
||||||
use board_misoc::{clock, ethmac, net_settings};
|
use board_misoc::{clock, ethmac, net_settings};
|
||||||
use board_misoc::uart_console::Console;
|
use board_misoc::uart_console::Console;
|
||||||
|
@ -110,6 +112,43 @@ fn startup() -> bool {
|
||||||
true
|
true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(has_slave_fpga_cfg)]
|
||||||
|
fn load_slave_fpga() {
|
||||||
|
println!("Loading slave FPGA gateware...");
|
||||||
|
|
||||||
|
const GATEWARE: *mut u8 = board_misoc::csr::CONFIG_SLAVE_FPGA_GATEWARE as *mut u8;
|
||||||
|
|
||||||
|
let header = unsafe { slice::from_raw_parts(GATEWARE, 8) };
|
||||||
|
let magic = BigEndian::read_u32(&header[0..]);
|
||||||
|
let length = BigEndian::read_u32(&header[4..]) as usize;
|
||||||
|
println!(" magic: 0x{:08x}, length: 0x{:08x}", magic, length);
|
||||||
|
if magic != 0x5352544d {
|
||||||
|
println!(" ...Error: bad magic");
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if length > 0x220000 {
|
||||||
|
println!(" ...Error: too long (corrupted?)");
|
||||||
|
return
|
||||||
|
}
|
||||||
|
let payload = unsafe { slice::from_raw_parts(GATEWARE.offset(8), length) };
|
||||||
|
|
||||||
|
if let Err(e) = slave_fpga::prepare() {
|
||||||
|
println!(" ...Error during preparation: {}", e);
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if let Err(e) = slave_fpga::input(payload) {
|
||||||
|
println!(" ...Error during loading: {}", e);
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if let Err(e) = slave_fpga::complete() {
|
||||||
|
println!(" ...Error during completion: {}", e);
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
println!(" ...done");
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
fn flash_boot() {
|
fn flash_boot() {
|
||||||
const FIRMWARE: *mut u8 = board_mem::FLASH_BOOT_ADDRESS as *mut u8;
|
const FIRMWARE: *mut u8 = board_mem::FLASH_BOOT_ADDRESS as *mut u8;
|
||||||
const MAIN_RAM: *mut u8 = board_mem::MAIN_RAM_BASE as *mut u8;
|
const MAIN_RAM: *mut u8 = board_mem::MAIN_RAM_BASE as *mut u8;
|
||||||
|
@ -379,6 +418,8 @@ pub extern fn main() -> i32 {
|
||||||
|
|
||||||
if startup() {
|
if startup() {
|
||||||
println!("");
|
println!("");
|
||||||
|
#[cfg(has_slave_fpga_cfg)]
|
||||||
|
load_slave_fpga();
|
||||||
flash_boot();
|
flash_boot();
|
||||||
#[cfg(has_ethmac)]
|
#[cfg(has_ethmac)]
|
||||||
network_boot();
|
network_boot();
|
||||||
|
|
|
@ -27,8 +27,6 @@ pub mod rpc_queue;
|
||||||
#[cfg(has_si5324)]
|
#[cfg(has_si5324)]
|
||||||
pub mod si5324;
|
pub mod si5324;
|
||||||
|
|
||||||
#[cfg(has_slave_fpga_cfg)]
|
|
||||||
pub mod slave_fpga;
|
|
||||||
#[cfg(has_hmc830_7043)]
|
#[cfg(has_hmc830_7043)]
|
||||||
pub mod hmc830_7043;
|
pub mod hmc830_7043;
|
||||||
#[cfg(has_ad9154)]
|
#[cfg(has_ad9154)]
|
||||||
|
|
|
@ -27,8 +27,10 @@ pub mod uart;
|
||||||
pub mod spiflash;
|
pub mod spiflash;
|
||||||
pub mod config;
|
pub mod config;
|
||||||
#[cfg(feature = "uart_console")]
|
#[cfg(feature = "uart_console")]
|
||||||
|
#[macro_use]
|
||||||
pub mod uart_console;
|
pub mod uart_console;
|
||||||
#[cfg(all(feature = "uart_console", feature = "log"))]
|
#[cfg(all(feature = "uart_console", feature = "log"))]
|
||||||
|
#[macro_use]
|
||||||
pub mod uart_logger;
|
pub mod uart_logger;
|
||||||
#[cfg(all(has_ethmac, feature = "smoltcp"))]
|
#[cfg(all(has_ethmac, feature = "smoltcp"))]
|
||||||
pub mod ethmac;
|
pub mod ethmac;
|
||||||
|
@ -37,3 +39,5 @@ pub mod i2c;
|
||||||
pub mod i2c_eeprom;
|
pub mod i2c_eeprom;
|
||||||
#[cfg(all(has_ethmac, feature = "smoltcp"))]
|
#[cfg(all(has_ethmac, feature = "smoltcp"))]
|
||||||
pub mod net_settings;
|
pub mod net_settings;
|
||||||
|
#[cfg(has_slave_fpga_cfg)]
|
||||||
|
pub mod slave_fpga;
|
||||||
|
|
|
@ -1,6 +1,4 @@
|
||||||
use board_misoc::{csr, clock};
|
use super::{csr, clock};
|
||||||
use core::slice;
|
|
||||||
use byteorder::{ByteOrder, BigEndian};
|
|
||||||
|
|
||||||
const CCLK_BIT: u8 = 1 << 0;
|
const CCLK_BIT: u8 = 1 << 0;
|
||||||
const DIN_BIT: u8 = 1 << 1;
|
const DIN_BIT: u8 = 1 << 1;
|
||||||
|
@ -8,8 +6,6 @@ const DONE_BIT: u8 = 1 << 2;
|
||||||
const INIT_B_BIT: u8 = 1 << 3;
|
const INIT_B_BIT: u8 = 1 << 3;
|
||||||
const PROGRAM_B_BIT: u8 = 1 << 4;
|
const PROGRAM_B_BIT: u8 = 1 << 4;
|
||||||
|
|
||||||
const GATEWARE: *mut u8 = csr::CONFIG_SLAVE_FPGA_GATEWARE as *mut u8;
|
|
||||||
|
|
||||||
unsafe fn shift_u8(data: u8) {
|
unsafe fn shift_u8(data: u8) {
|
||||||
for i in 0..8 {
|
for i in 0..8 {
|
||||||
let mut bits: u8 = PROGRAM_B_BIT;
|
let mut bits: u8 = PROGRAM_B_BIT;
|
||||||
|
@ -27,10 +23,10 @@ unsafe fn shift_u8(data: u8) {
|
||||||
pub fn prepare() -> Result<(), &'static str> {
|
pub fn prepare() -> Result<(), &'static str> {
|
||||||
unsafe {
|
unsafe {
|
||||||
if csr::slave_fpga_cfg::in_read() & DONE_BIT != 0 {
|
if csr::slave_fpga_cfg::in_read() & DONE_BIT != 0 {
|
||||||
info!(" DONE before loading");
|
println!(" DONE before loading");
|
||||||
}
|
}
|
||||||
if csr::slave_fpga_cfg::in_read() & INIT_B_BIT == 0 {
|
if csr::slave_fpga_cfg::in_read() & INIT_B_BIT == 0 {
|
||||||
info!(" INIT asserted before loading");
|
println!(" INIT asserted before loading");
|
||||||
}
|
}
|
||||||
|
|
||||||
csr::slave_fpga_cfg::out_write(0);
|
csr::slave_fpga_cfg::out_write(0);
|
||||||
|
@ -78,26 +74,3 @@ pub fn complete() -> Result<(), &'static str> {
|
||||||
}
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn load() -> Result<(), &'static str> {
|
|
||||||
info!("Loading slave FPGA gateware...");
|
|
||||||
|
|
||||||
let header = unsafe { slice::from_raw_parts(GATEWARE, 8) };
|
|
||||||
|
|
||||||
let magic = BigEndian::read_u32(&header[0..]);
|
|
||||||
let length = BigEndian::read_u32(&header[4..]) as usize;
|
|
||||||
info!(" magic: 0x{:08x}, length: 0x{:08x}", magic, length);
|
|
||||||
if magic != 0x5352544d { // "SRTM", see sayma_rtm target as well
|
|
||||||
return Err("Bad magic");
|
|
||||||
}
|
|
||||||
if length > 0x220000 {
|
|
||||||
return Err("Too large (corrupted?)");
|
|
||||||
}
|
|
||||||
|
|
||||||
prepare()?;
|
|
||||||
input(unsafe { slice::from_raw_parts(GATEWARE.offset(8), length) })?;
|
|
||||||
complete()?;
|
|
||||||
|
|
||||||
info!(" ...done");
|
|
||||||
Ok(())
|
|
||||||
}
|
|
|
@ -89,9 +89,6 @@ fn setup_log_levels() {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn sayma_hw_init() {
|
fn sayma_hw_init() {
|
||||||
#[cfg(has_slave_fpga_cfg)]
|
|
||||||
board_artiq::slave_fpga::load().expect("cannot load RTM FPGA gateware");
|
|
||||||
|
|
||||||
#[cfg(has_hmc830_7043)]
|
#[cfg(has_hmc830_7043)]
|
||||||
/* must be the first SPI init because of HMC830 SPI mode selection */
|
/* must be the first SPI init because of HMC830 SPI mode selection */
|
||||||
board_artiq::hmc830_7043::init().expect("cannot initialize HMC830/7043");
|
board_artiq::hmc830_7043::init().expect("cannot initialize HMC830/7043");
|
||||||
|
|
|
@ -448,9 +448,6 @@ pub extern fn main() -> i32 {
|
||||||
info!("software ident {}", csr::CONFIG_IDENTIFIER_STR);
|
info!("software ident {}", csr::CONFIG_IDENTIFIER_STR);
|
||||||
info!("gateware ident {}", ident::read(&mut [0; 64]));
|
info!("gateware ident {}", ident::read(&mut [0; 64]));
|
||||||
|
|
||||||
#[cfg(has_slave_fpga_cfg)]
|
|
||||||
board_artiq::slave_fpga::load().expect("cannot load RTM FPGA gateware");
|
|
||||||
|
|
||||||
i2c::init().expect("I2C initialization failed");
|
i2c::init().expect("I2C initialization failed");
|
||||||
si5324::setup(&SI5324_SETTINGS, si5324::Input::Ckin1).expect("cannot initialize Si5324");
|
si5324::setup(&SI5324_SETTINGS, si5324::Input::Ckin1).expect("cannot initialize Si5324");
|
||||||
unsafe {
|
unsafe {
|
||||||
|
|
Loading…
Reference in New Issue