Compare commits

..

No commits in common. "5c62716a996c45b1e70b4ea1df5a932e0994f363" and "ceeaa6427e7032be1dab97fe329cccda1077e58d" have entirely different histories.

9 changed files with 102 additions and 119 deletions

17
Cargo.lock generated
View File

@ -20,14 +20,6 @@ name = "compiler_builtins"
version = "0.1.19" version = "0.1.19"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "linked_list_allocator"
version = "0.6.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"spin 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]] [[package]]
name = "managed" name = "managed"
version = "0.7.1" version = "0.7.1"
@ -48,11 +40,6 @@ dependencies = [
"managed 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)", "managed 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)",
] ]
[[package]]
name = "spin"
version = "0.5.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]] [[package]]
name = "vcell" name = "vcell"
version = "0.1.0" version = "0.1.0"
@ -72,10 +59,8 @@ version = "0.0.0"
dependencies = [ dependencies = [
"bit_field 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)", "bit_field 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.19 (registry+https://github.com/rust-lang/crates.io-index)", "compiler_builtins 0.1.19 (registry+https://github.com/rust-lang/crates.io-index)",
"linked_list_allocator 0.6.4 (registry+https://github.com/rust-lang/crates.io-index)",
"r0 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", "r0 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)",
"smoltcp 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", "smoltcp 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)",
"vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"volatile-register 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", "volatile-register 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
] ]
@ -84,10 +69,8 @@ dependencies = [
"checksum bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3d155346769a6855b86399e9bc3814ab343cd3d62c7e985113d46a0ec3c281fd" "checksum bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3d155346769a6855b86399e9bc3814ab343cd3d62c7e985113d46a0ec3c281fd"
"checksum byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)" = "a7c3dd8985a7111efc5c80b44e23ecdd8c007de8ade3b96595387e812b957cf5" "checksum byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)" = "a7c3dd8985a7111efc5c80b44e23ecdd8c007de8ade3b96595387e812b957cf5"
"checksum compiler_builtins 0.1.19 (registry+https://github.com/rust-lang/crates.io-index)" = "4e32b9fc11fdb3aefbd0a4761a8d3a2b7419608b759fa14a26525df4ea5deaba" "checksum compiler_builtins 0.1.19 (registry+https://github.com/rust-lang/crates.io-index)" = "4e32b9fc11fdb3aefbd0a4761a8d3a2b7419608b759fa14a26525df4ea5deaba"
"checksum linked_list_allocator 0.6.4 (registry+https://github.com/rust-lang/crates.io-index)" = "47314ec1d29aa869ee7cb5a5be57be9b1055c56567d59c3fb6689926743e0bea"
"checksum managed 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)" = "fdcec5e97041c7f0f1c5b7d93f12e57293c831c646f4cc7a5db59460c7ea8de6" "checksum managed 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)" = "fdcec5e97041c7f0f1c5b7d93f12e57293c831c646f4cc7a5db59460c7ea8de6"
"checksum r0 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e2a38df5b15c8d5c7e8654189744d8e396bddc18ad48041a500ce52d6948941f" "checksum r0 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e2a38df5b15c8d5c7e8654189744d8e396bddc18ad48041a500ce52d6948941f"
"checksum smoltcp 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fef582369edb298c6c41319a544ca9c4e83622f226055ccfcb35974fbb55ed34" "checksum smoltcp 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fef582369edb298c6c41319a544ca9c4e83622f226055ccfcb35974fbb55ed34"
"checksum spin 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "6e63cff320ae2c57904679ba7cb63280a3dc4613885beafb148ee7bf9aa9042d"
"checksum vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "45c297f0afb6928cd08ab1ff9d95e99392595ea25ae1b5ecf822ff8764e57a0d" "checksum vcell 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "45c297f0afb6928cd08ab1ff9d95e99392595ea25ae1b5ecf822ff8764e57a0d"
"checksum volatile-register 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "0d67cb4616d99b940db1d6bd28844ff97108b498a6ca850e5b6191a532063286" "checksum volatile-register 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "0d67cb4616d99b940db1d6bd28844ff97108b498a6ca850e5b6191a532063286"

View File

@ -19,9 +19,7 @@ default = ["target_zc706"]
[dependencies] [dependencies]
r0 = "0.2" r0 = "0.2"
vcell = "0.1"
volatile-register = "0.2" volatile-register = "0.2"
bit_field = "0.10" bit_field = "0.10"
compiler_builtins = { version = "~0.1", default-features = false, features = ["mem", "no-lang-items"]} compiler_builtins = { version = "~0.1", default-features = false, features = ["mem", "no-lang-items"]}
smoltcp = { version = "0.5", default-features = false, features = ["proto-ipv4", "socket-tcp"] } smoltcp = { version = "0.5", default-features = false, features = ["proto-ipv4", "socket-tcp"] }
linked_list_allocator = "0.6"

View File

@ -1,5 +1,5 @@
source ./digilent_jtag_smt2_nc.cfg source ./digilent_jtag_smt2_nc.cfg
adapter_khz 1000 adapter_khz 10000
set PL_TAPID 0x23731093 set PL_TAPID 0x23731093
set SMP 1 set SMP 1

View File

@ -5,7 +5,6 @@
#![feature(naked_functions)] #![feature(naked_functions)]
#![feature(compiler_builtins_lib)] #![feature(compiler_builtins_lib)]
#![feature(never_type)] #![feature(never_type)]
#![feature(alloc_error_handler)]
// TODO: disallow unused/dead_code when code moves into a lib crate // TODO: disallow unused/dead_code when code moves into a lib crate
#![allow(dead_code)] #![allow(dead_code)]
@ -16,12 +15,12 @@ use smoltcp::wire::{EthernetAddress, IpAddress, IpCidr};
use smoltcp::iface::{NeighborCache, EthernetInterfaceBuilder, EthernetInterface}; use smoltcp::iface::{NeighborCache, EthernetInterfaceBuilder, EthernetInterface};
use smoltcp::time::Instant; use smoltcp::time::Instant;
use smoltcp::socket::SocketSet; use smoltcp::socket::SocketSet;
use linked_list_allocator::LockedHeap;
mod regs; mod regs;
mod cortex_a9; mod cortex_a9;
mod stdio; mod stdio;
mod zynq; mod zynq;
mod ram;
use crate::regs::{RegisterR, RegisterW}; use crate::regs::{RegisterR, RegisterW};
use crate::cortex_a9::{asm, regs::*, mmu}; use crate::cortex_a9::{asm, regs::*, mmu};
@ -84,9 +83,6 @@ fn l1_cache_init() {
dciall(); dciall();
} }
#[global_allocator]
static ALLOCATOR: LockedHeap = LockedHeap::empty();
const HWADDR: [u8; 6] = [0, 0x23, 0xde, 0xea, 0xbe, 0xef]; const HWADDR: [u8; 6] = [0, 0x23, 0xde, 0xea, 0xbe, 0xef];
fn main() { fn main() {
@ -96,10 +92,6 @@ fn main() {
println!("DDR: {:?}", ddr.status()); println!("DDR: {:?}", ddr.status());
ddr.memtest(); ddr.memtest();
unsafe {
ALLOCATOR.lock().init(ddr.ptr::<u8>() as usize, ddr.size());
}
let eth = zynq::eth::Eth::default(HWADDR.clone()); let eth = zynq::eth::Eth::default(HWADDR.clone());
println!("Eth on"); println!("Eth on");
@ -184,11 +176,6 @@ fn panic(info: &core::panic::PanicInfo) -> ! {
loop {} loop {}
} }
#[alloc_error_handler]
fn alloc_error(_: core::alloc::Layout) -> ! {
panic!("alloc_error")
}
#[no_mangle] #[no_mangle]
pub unsafe extern "C" fn PrefetchAbort() { pub unsafe extern "C" fn PrefetchAbort() {
println!("PrefetchAbort"); println!("PrefetchAbort");

75
src/ram.rs Normal file
View File

@ -0,0 +1,75 @@
use core::mem::{align_of, size_of};
pub trait RAM {
#[inline(always)]
fn addr(&self) -> usize;
#[inline(always)]
fn size(&self) -> usize;
#[inline(always)]
fn into_memory_region(&self) -> MemoryRegion {
MemoryRegion {
addr: self.addr(),
size: self.size(),
}
}
}
pub struct MemoryRegion {
addr: usize,
size: usize,
}
impl MemoryRegion {
#[inline(always)]
fn split(&mut self, offset: usize) -> MemoryRegion {
if offset > self.size {
panic!("StaticAllocator: unable to split {}/{} bytes", offset, self.size);
}
let result = MemoryRegion {
addr: self.addr,
size: offset,
};
self.addr += offset;
self.size -= offset;
result
}
unsafe fn clear<T>(self) -> *mut T {
let result = self.addr as *mut T;
for b in core::slice::from_raw_parts_mut::<u8>(result as *mut u8, self.size) {
*b = 0;
}
result
}
pub fn align(&mut self, alignment: usize) {
let mask = alignment - 1;
let addr = (self.addr | mask) + 1;
self.size -= addr - self.addr;
self.addr = addr;
}
}
pub struct StaticAllocator {
free: MemoryRegion,
}
impl StaticAllocator {
pub fn new<R: RAM>(r: R) -> Self {
StaticAllocator {
free: r.into_memory_region(),
}
}
pub fn alloc<'a: 'b, 'b, T: Sized>(&'a mut self) -> &'b mut T {
self.free.align(align_of::<T>());
let size = size_of::<T>();
let region = self.free.split(size);
unsafe { &mut *region.clear() }
}
}

View File

@ -2,7 +2,6 @@
//! svd2rust generates. //! svd2rust generates.
#![allow(unused)] #![allow(unused)]
use vcell::VolatileCell;
use volatile_register::{RO, WO, RW}; use volatile_register::{RO, WO, RW};
use bit_field::BitField; use bit_field::BitField;
@ -65,7 +64,7 @@ macro_rules! register_r {
#[macro_export] #[macro_export]
macro_rules! register_w { macro_rules! register_w {
($mod_name: ident, $struct_name: ident) => ( ($mod_name: ident, $struct_name: ident) => (
impl crate::regs::RegisterW for $struct_name { impl crate::regs::RegisterW for $struct_name {
type W = $mod_name::Write; type W = $mod_name::Write;
fn zeroed() -> $mod_name::Write { fn zeroed() -> $mod_name::Write {
@ -97,40 +96,6 @@ macro_rules! register_rw {
); );
} }
#[doc(hidden)]
#[macro_export]
macro_rules! register_vcell {
($mod_name: ident, $struct_name: ident) => (
impl crate::regs::RegisterR for $struct_name {
type R = $mod_name::Read;
fn read(&self) -> Self::R {
let inner = self.inner.get();
$mod_name::Read { inner }
}
}
impl crate::regs::RegisterW for $struct_name {
type W = $mod_name::Write;
fn zeroed() -> $mod_name::Write {
$mod_name::Write { inner: 0 }
}
fn write(&mut self, w: Self::W) {
self.inner.set(w.inner);
}
}
impl crate::regs::RegisterRW for $struct_name {
fn modify<F: FnOnce(Self::R, Self::W) -> Self::W>(&mut self, f: F) {
let r = self.read();
let w = $mod_name::Write { inner: r.inner };
let w = f(r, w);
self.write(w);
}
}
);
}
/// Main macro for register definition /// Main macro for register definition
#[macro_export] #[macro_export]
macro_rules! register { macro_rules! register {
@ -153,12 +118,6 @@ macro_rules! register {
crate::register_w!($mod_name, $struct_name); crate::register_w!($mod_name, $struct_name);
crate::register_rw!($mod_name, $struct_name); crate::register_rw!($mod_name, $struct_name);
); );
// Define read-write register
($mod_name: ident, $struct_name: ident, VolatileCell, $inner: ty) => (
crate::register_common!($mod_name, $struct_name, VolatileCell<$inner>, $inner);
crate::register_vcell!($mod_name, $struct_name);
);
} }
/// Define a 1-bit field of a register /// Define a 1-bit field of a register

View File

@ -1,5 +1,5 @@
use crate::regs::{RegisterR, RegisterW, RegisterRW}; use crate::regs::{RegisterR, RegisterW, RegisterRW};
use crate::{print, println}; use crate::println;
use super::slcr; use super::slcr;
use super::clocks::CpuClocks; use super::clocks::CpuClocks;
@ -178,15 +178,15 @@ impl DdrRam {
} }
// TODO: move into trait // TODO: move into trait
pub fn ptr<T>(&mut self) -> *mut T { pub fn ptr(&mut self) -> *mut u8 {
0x0010_0000 as *mut _ 0x0010_0000 as *mut _
} }
pub fn size(&self) -> usize { pub fn size(&self) -> usize {
#[cfg(feature = "target_zc706")] #[cfg(feature = "target_zc706")]
let megabytes = 511; let megabytes = 1024;
#[cfg(feature = "target_cora_z7_10")] #[cfg(feature = "target_cora_z7_10")]
let megabytes = 511; let megabytes = 512;
megabytes * 1024 * 1024 megabytes * 1024 * 1024
} }
@ -195,27 +195,28 @@ impl DdrRam {
let slice = unsafe { let slice = unsafe {
core::slice::from_raw_parts_mut(self.ptr(), self.size()) core::slice::from_raw_parts_mut(self.ptr(), self.size())
}; };
let patterns: &'static [u32] = &[0xffff_ffff, 0x5555_5555, 0xaaaa_aaaa, 0]; let patterns: &'static [u8] = &[0, 0xff, 0x55, 0xaa, 0];
let mut expected = None; let mut expected = None;
for (i, pattern) in patterns.iter().enumerate() { for (i, pattern) in patterns.iter().enumerate() {
println!("memtest phase {} (status: {:?})", i, self.status()); println!("memtest phase {} (status: {:?})", i, self.status());
for megabyte in 0..=(slice.len() / (1024 * 1024)) { // shift by 7 bits to be able to multiply with 100 (%)
let start = megabyte * 1024 * 1024 / 4; let progress_max = (slice.len() >> 7) - 1;
let end = ((megabyte + 1) * 1024 * 1024 / 4).min(slice.len()); let mut progress = 0;
for b in slice[start..end].iter_mut() { for (j, b) in slice.iter_mut().enumerate() {
expected.map(|expected| { expected.map(|expected| {
let read: u32 = *b; let read: u8 = *b;
if read != expected { if read != expected {
println!("{:08X}: expected {:08X}, read {:08X}", b as *mut _ as usize, expected, read); println!("{:08X}: expected {:02X}, read {:02X}", b as *mut u8 as usize, expected, read);
} }
}); });
*b = *pattern; *b = *pattern;
let new_progress = 100 * (j >> 7) / progress_max;
if new_progress != progress {
progress = new_progress;
println!("{}%", progress);
} }
print!("\r{} MB", megabyte);
} }
println!(" Ok");
expected = Some(*pattern); expected = Some(*pattern);
} }

View File

@ -1,5 +1,4 @@
use core::ops::Deref; use core::ops::Deref;
use vcell::VolatileCell;
use crate::{register, register_bit, register_bits, regs::*}; use crate::{register, register_bit, register_bits, regs::*};
use super::MTU; use super::MTU;
@ -20,16 +19,7 @@ pub struct DescEntry {
word1: DescWord1, word1: DescWord1,
} }
impl DescEntry { register!(desc_word0, DescWord0, RW, u32);
pub fn zeroed() -> Self {
DescEntry {
word0: DescWord0 { inner: VolatileCell::new(0) },
word1: DescWord1 { inner: VolatileCell::new(0) },
}
}
}
register!(desc_word0, DescWord0, VolatileCell, u32);
register_bit!(desc_word0, register_bit!(desc_word0,
/// true if owned by software, false if owned by hardware /// true if owned by software, false if owned by hardware
used, 0); used, 0);
@ -38,7 +28,7 @@ register_bit!(desc_word0,
wrap, 1); wrap, 1);
register_bits!(desc_word0, address, u32, 2, 31); register_bits!(desc_word0, address, u32, 2, 31);
register!(desc_word1, DescWord1, VolatileCell, u32); register!(desc_word1, DescWord1, RW, u32);
register_bits!(desc_word1, frame_length_lsbs, u16, 0, 12); register_bits!(desc_word1, frame_length_lsbs, u16, 0, 12);
register_bit!(desc_word1, bad_fcs, 13); register_bit!(desc_word1, bad_fcs, 13);
register_bit!(desc_word1, start_of_frame, 14); register_bit!(desc_word1, start_of_frame, 14);

View File

@ -1,5 +1,4 @@
use core::ops::{Deref, DerefMut}; use core::ops::{Deref, DerefMut};
use vcell::VolatileCell;
use crate::{register, register_bit, register_bits, regs::*}; use crate::{register, register_bit, register_bits, regs::*};
use crate::cortex_a9::asm; use crate::cortex_a9::asm;
use super::{MTU, regs}; use super::{MTU, regs};
@ -11,10 +10,10 @@ pub struct DescEntry {
word1: DescWord1, word1: DescWord1,
} }
register!(desc_word0, DescWord0, VolatileCell, u32); register!(desc_word0, DescWord0, RW, u32);
register_bits!(desc_word0, address, u32, 0, 31); register_bits!(desc_word0, address, u32, 0, 31);
register!(desc_word1, DescWord1, VolatileCell, u32); register!(desc_word1, DescWord1, RW, u32);
register_bits!(desc_word1, length, u16, 0, 13); register_bits!(desc_word1, length, u16, 0, 13);
register_bit!(desc_word1, last_buffer, 15); register_bit!(desc_word1, last_buffer, 15);
register_bit!(desc_word1, no_crc_append, 16); register_bit!(desc_word1, no_crc_append, 16);
@ -29,15 +28,6 @@ register_bit!(desc_word1,
/// true if owned by software, false if owned by hardware /// true if owned by software, false if owned by hardware
used, 31); used, 31);
impl DescEntry {
pub fn zeroed() -> Self {
DescEntry {
word0: DescWord0 { inner: VolatileCell::new(0) },
word1: DescWord1 { inner: VolatileCell::new(0) },
}
}
}
/// Number of descriptors /// Number of descriptors
pub const DESCS: usize = 8; pub const DESCS: usize = 8;