Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use flash-algorithm crate #19

Merged
merged 4 commits into from
Feb 18, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 0 additions & 5 deletions .cargo/config
Original file line number Diff line number Diff line change
@@ -1,15 +1,10 @@
[unstable]
build-std = ["core"]
build-std-features = ["panic_immediate_abort"]

[target.'cfg(all(target_arch = "arm", target_os = "none"))']

rustflags = [
"-C", "link-arg=--nmagic",
"-C", "link-arg=-Tlink.x",

# Code-size optimizations.
"-Z", "trap-unreachable=no",
"-C", "inline-threshold=5",
"-C", "no-vectorize-loops",
"-C", "force-frame-pointers=no",
Expand Down
5 changes: 0 additions & 5 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -11,17 +11,12 @@ env:

jobs:
build:

runs-on: ubuntu-latest

steps:
- uses: actions/checkout@v2
- name: Install Dependencies
run: |
sudo apt update
rustup component add rust-src
cargo install cargo-binutils
rustup component add llvm-tools-preview
- name: Build
run: |
./build.sh
Expand Down
1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ version = "0.1.0"

[dependencies]
cortex-m = "0.7.0"
flash-algorithm = "0.4.0"

# this lets you use `cargo fix`!
[[bin]]
Expand Down
16 changes: 10 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,23 +5,27 @@ It implements the CMSIS-Pack ABI, so it's compatible with any tools that use it,

## Dependencies

Run the following requirements:
Run the following to install the requirements:

```bash
cargo install cargo-binutils && rustup component add llvm-tools-preview rust-src
cargo install cargo-binutils
```
## Building

Building requires nightly Rust.
The `rust-toolchain` file will get you the targets and components you need.

## Building

Just run `build.sh`. It spits out the flash algo in the probe-rs YAML format:

flash-algo$ ./build.sh
```console
flash-algo$ ./build.sh
instructions: sLUUIACIGUoBRguI...wRwAgcEc=
pc_init: 0x00000000
pc_uninit: 0x0000007c
pc_program_page: 0x00000088
pc_erase_sector: 0x00000084
pc_erase_all: 0x00000080
```

## Hacking

Expand All @@ -30,7 +34,7 @@ the glue functions for a given struct implementing it. This is generic for all c

`main.rs` has the actual implementation for RP2040.

# License
## License

This thingy is licensed under either of

Expand Down
6 changes: 5 additions & 1 deletion rust-toolchain
Original file line number Diff line number Diff line change
@@ -1 +1,5 @@
nightly
[toolchain]
channel = "stable"
components = [ "llvm-tools" ]
profile = "minimal"
targets = ["thumbv6m-none-eabi"]
103 changes: 0 additions & 103 deletions src/algo.rs

This file was deleted.

94 changes: 53 additions & 41 deletions src/main.rs
Original file line number Diff line number Diff line change
@@ -1,30 +1,25 @@
#![no_std]
#![no_main]

mod algo;

use core::mem;
use core::mem::MaybeUninit;

use self::algo::*;

fn find_func<T>(tag: [u8; 2]) -> T {
let tag = u16::from_le_bytes(tag);

use flash_algorithm::*;

fn find_func<T>(tag: [u8; 2]) -> Option<T> {
let tag = u16::from_le_bytes(tag) as u32;
type RomTableLookupFn = unsafe extern "C" fn(table: *const u16, code: u32) -> usize;
/// This location in flash holds a 16-bit truncated pointer for the ROM lookup function
const ROM_TABLE_LOOKUP_PTR: *const u16 = 0x0000_0018 as _;
/// This location in flash holds a 16-bit truncated pointer for the ROM function table
/// (there's also a ROM data table which we don't need)
const FUNC_TABLE: *const u16 = 0x0000_0014 as _;
unsafe {
let mut entry = *(0x00000014 as *const u16) as *const u16;
loop {
let entry_tag = entry.read();
if entry_tag == 0 {
panic!("Func not found");
}
entry = entry.add(1);
let entry_addr = entry.read();
entry = entry.add(1);
if entry_tag == tag {
return mem::transmute_copy(&(entry_addr as u32));
}
let lookup_func = ROM_TABLE_LOOKUP_PTR.read() as usize;
let lookup_func: RomTableLookupFn = core::mem::transmute(lookup_func);
let table = FUNC_TABLE.read() as usize;
let result = lookup_func(table as *const u16, tag);
if result == 0 {
return None;
}
Some(core::mem::transmute_copy(&result))
}
}

Expand All @@ -38,34 +33,42 @@ struct ROMFuncs {
}

impl ROMFuncs {
fn load() -> Self {
ROMFuncs {
connect_internal_flash: find_func(*b"IF"),
flash_exit_xip: find_func(*b"EX"),
flash_range_erase: find_func(*b"RE"),
flash_range_program: find_func(*b"RP"),
flash_flush_cache: find_func(*b"FC"),
flash_enter_cmd_xip: find_func(*b"CX"),
}
fn load() -> Option<Self> {
Some(ROMFuncs {
connect_internal_flash: find_func(*b"IF")?,
flash_exit_xip: find_func(*b"EX")?,
flash_range_erase: find_func(*b"RE")?,
flash_range_program: find_func(*b"RP")?,
flash_flush_cache: find_func(*b"FC")?,
flash_enter_cmd_xip: find_func(*b"CX")?,
})
}
}

struct RP2040Algo {
funcs: ROMFuncs,
}

algo!(RP2040Algo);
algorithm!(RP2040Algo, {
flash_address: 0x1000_0000,
flash_size: 0x0100_0000,
page_size: 0x100,
empty_value: 0xFF,
sectors: [{
size: 0x1000,
address: 0x10000000,
}]
});

const BLOCK_SIZE: u32 = 65536;
const SECTOR_SIZE: u32 = 4096;
const PAGE_SIZE: u32 = 256;
const BLOCK_ERASE_CMD: u8 = 0xd8;
const FLASH_BASE: u32 = 0x1000_0000;

impl FlashAlgo for RP2040Algo {
fn new(_address: u32, _clock: u32, _function: u32) -> Result<Self, ErrorCode> {
let funcs = ROMFuncs::load();

impl FlashAlgorithm for RP2040Algo {
fn new(_address: u32, _clock: u32, _function: Function) -> Result<Self, ErrorCode> {
let Some(funcs) = ROMFuncs::load() else {
return Err(ErrorCode::new(1).unwrap());
};
(funcs.connect_internal_flash)();
(funcs.flash_exit_xip)();
Ok(Self { funcs })
Expand All @@ -77,12 +80,21 @@ impl FlashAlgo for RP2040Algo {
}

fn erase_sector(&mut self, addr: u32) -> Result<(), ErrorCode> {
(self.funcs.flash_range_erase)(addr - FLASH_BASE, SECTOR_SIZE, BLOCK_SIZE, BLOCK_ERASE_CMD);
(self.funcs.flash_range_erase)(
addr - FlashDevice.dev_addr,
SECTOR_SIZE,
BLOCK_SIZE,
BLOCK_ERASE_CMD,
);
Ok(())
}

fn program_page(&mut self, addr: u32, size: u32, data: *const u8) -> Result<(), ErrorCode> {
(self.funcs.flash_range_program)(addr - FLASH_BASE, data, size);
fn program_page(&mut self, addr: u32, data: &[u8]) -> Result<(), ErrorCode> {
(self.funcs.flash_range_program)(
addr - FlashDevice.dev_addr,
data.as_ptr(),
data.len() as u32,
);
Ok(())
}
}
Expand Down
Loading