PoC
This commit is contained in:
commit
45eebb1b18
|
@ -0,0 +1,12 @@
|
|||
[target.thumbv7m-none-eabi]
|
||||
runner = "gdb -q -x openocd.gdb"
|
||||
rustflags = [
|
||||
"-C", "link-arg=-Tlink.x",
|
||||
]
|
||||
|
||||
[build]
|
||||
# Pick ONE of these compilation targets
|
||||
# target = "thumbv6m-none-eabi" # Cortex-M0 and Cortex-M0+
|
||||
target = "thumbv7m-none-eabi" # Cortex-M3
|
||||
# target = "thumbv7em-none-eabi" # Cortex-M4 and Cortex-M7 (no FPU)
|
||||
# target = "thumbv7em-none-eabihf" # Cortex-M4F and Cortex-M7F (with FPU)
|
|
@ -0,0 +1,35 @@
|
|||
[package]
|
||||
categories = ["embedded", "no-std"]
|
||||
name = "pentatube"
|
||||
license = "GPL-3.0-only"
|
||||
authors = ["Astro <astro@spaceboyz.net>"]
|
||||
version = "0.0.0"
|
||||
edition = "2018"
|
||||
|
||||
[badges]
|
||||
maintenance = { status = "experimental" }
|
||||
|
||||
[package.metadata.docs.rs]
|
||||
features = []
|
||||
default-target = "thumbv7m-none-eabi"
|
||||
|
||||
[dependencies]
|
||||
panic-abort = "0.3.1"
|
||||
bare-metal = "0.2"
|
||||
cortex-m = "0.5"
|
||||
cortex-m-rt = { version = "0.6", features = ["device"] }
|
||||
cortex-m-log = { version = "0.4", features = ["log-integration"] }
|
||||
stm32f1 = { version = "0.6", features = ["rt", "stm32f103"] }
|
||||
embedded-hal = "0.2.2"
|
||||
stm32f1xx-hal = { git = "https://github.com/stm32-rs/stm32f1xx-hal", features = ["rt", "stm32f103"] }
|
||||
#stm32f1xx-hal = { path = "../stm32f4xx-hal", features = ["rt", "stm32f429"] }
|
||||
|
||||
[features]
|
||||
default = []
|
||||
|
||||
[profile.release]
|
||||
codegen-units = 1
|
||||
incremental = false
|
||||
debug = true
|
||||
opt-level = "s"
|
||||
lto = true
|
|
@ -0,0 +1,18 @@
|
|||
use std::env;
|
||||
use std::fs::File;
|
||||
use std::io::Write;
|
||||
use std::path::PathBuf;
|
||||
|
||||
fn main() {
|
||||
// Put the linker script somewhere the linker can find it
|
||||
let out = &PathBuf::from(env::var_os("OUT_DIR").unwrap());
|
||||
File::create(out.join("memory.x"))
|
||||
.unwrap()
|
||||
.write_all(include_bytes!("memory.x"))
|
||||
.unwrap();
|
||||
println!("cargo:rustc-link-search={}", out.display());
|
||||
|
||||
// Only re-run the build script when memory.x is changed,
|
||||
// instead of when any part of the source code changes.
|
||||
println!("cargo:rerun-if-changed=memory.x");
|
||||
}
|
|
@ -0,0 +1,50 @@
|
|||
{ # Use master branch of the overlay by default
|
||||
mozillaOverlay ? import (builtins.fetchTarball https://github.com/mozilla/nixpkgs-mozilla/archive/master.tar.gz),
|
||||
rustManifest ? builtins.fetchurl "https://static.rust-lang.org/dist/channel-rust-nightly.toml"
|
||||
}:
|
||||
|
||||
let
|
||||
pkgs = import <nixpkgs> { overlays = [ mozillaOverlay ]; };
|
||||
in
|
||||
with pkgs;
|
||||
let
|
||||
targets = [
|
||||
"x86_64-unknown-linux-gnu"
|
||||
"thumbv6m-none-eabi"
|
||||
"thumbv7m-none-eabi"
|
||||
"thumbv7em-none-eabi"
|
||||
"thumbv7em-none-eabihf"
|
||||
];
|
||||
rust =
|
||||
rustChannelOfTargets "nightly" null targets;
|
||||
rustPlatform = recurseIntoAttrs (makeRustPlatform {
|
||||
rustc = rust;
|
||||
cargo = rust;
|
||||
});
|
||||
|
||||
openocd =
|
||||
stdenv.mkDerivation {
|
||||
name = "openocd-stlink-blackpill";
|
||||
buildInputs = [
|
||||
pkgs.openocd
|
||||
makeWrapper
|
||||
];
|
||||
src = ./src;
|
||||
noBuild = true;
|
||||
installPhase =
|
||||
let
|
||||
openOcdFlags = [
|
||||
"-f" "${pkgs.openocd}/share/openocd/scripts/interface/stlink-v2-1.cfg"
|
||||
"-f" "${pkgs.openocd}/share/openocd/scripts/target/stm32f1x.cfg"
|
||||
"-c" "init"
|
||||
];
|
||||
in ''
|
||||
mkdir -p $out/bin
|
||||
|
||||
makeWrapper ${pkgs.openocd}/bin/openocd $out/bin/openocd-stlink-blackpill \
|
||||
--add-flags "${lib.escapeShellArgs openOcdFlags}"
|
||||
'';
|
||||
};
|
||||
in {
|
||||
inherit pkgs rustPlatform openocd;
|
||||
}
|
|
@ -0,0 +1,6 @@
|
|||
/* Linker script for the STM32F103C8T6 */
|
||||
MEMORY
|
||||
{
|
||||
FLASH : ORIGIN = 0x08000000, LENGTH = 64K
|
||||
RAM : ORIGIN = 0x20000000, LENGTH = 20K
|
||||
}
|
|
@ -0,0 +1,10 @@
|
|||
target remote :3333
|
||||
|
||||
# print demangled symbols by default
|
||||
set print asm-demangle on
|
||||
|
||||
monitor arm semihosting enable
|
||||
|
||||
load
|
||||
continue
|
||||
#step
|
|
@ -0,0 +1,23 @@
|
|||
let
|
||||
project = import ./default.nix {};
|
||||
in
|
||||
with project.pkgs;
|
||||
stdenv.mkDerivation {
|
||||
name = "project-env";
|
||||
buildInputs = with project.rustPlatform.rust; [
|
||||
rustc cargo gdb project.openocd
|
||||
];
|
||||
|
||||
# Set Environment Variables
|
||||
RUST_BACKTRACE = 1;
|
||||
|
||||
shellHook = ''
|
||||
echo "Starting openocd…"
|
||||
${project.openocd}/bin/openocd-stlink-blackpill -c "reset init" &
|
||||
|
||||
# Let openocd output scroll by
|
||||
sleep 1
|
||||
|
||||
echo "Run 'cargo run --release'"
|
||||
'';
|
||||
}
|
|
@ -0,0 +1,131 @@
|
|||
#![no_std]
|
||||
#![no_main]
|
||||
// #![deny(warnings, unused)]
|
||||
|
||||
#[allow(unused_extern_crates)]
|
||||
extern crate panic_abort;
|
||||
|
||||
// use cortex_m::asm::{wfi, nop};
|
||||
use cortex_m_rt::entry;
|
||||
use embedded_hal::{
|
||||
digital::OutputPin,
|
||||
spi::MODE_0,
|
||||
blocking::spi::Write as SpiWrite,
|
||||
// watchdog::{WatchdogEnable, Watchdog},
|
||||
};
|
||||
use stm32f1xx_hal::{
|
||||
flash::FlashExt,
|
||||
rcc::RccExt,
|
||||
gpio::GpioExt,
|
||||
afio::AfioExt,
|
||||
time::U32Ext,
|
||||
spi::Spi,
|
||||
stm32::{CorePeripherals, Peripherals},
|
||||
};
|
||||
|
||||
|
||||
pub struct PwmGraphics {
|
||||
t: u8,
|
||||
}
|
||||
|
||||
impl PwmGraphics {
|
||||
pub fn new() -> Self {
|
||||
PwmGraphics { t: 0 }
|
||||
}
|
||||
|
||||
pub fn generate_frame(&mut self, rgb: &[[u8; 3]; 8]) -> [u8; 3] {
|
||||
let mut bgr = [0u8; 3];
|
||||
|
||||
for i in 0..bgr.len() {
|
||||
for x in 0..rgb.len() {
|
||||
if self.t < rgb[x][i] {
|
||||
bgr[2 - i] |= 1 << x;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
self.t += 1;
|
||||
bgr
|
||||
}
|
||||
}
|
||||
|
||||
/// Initialization and main loop
|
||||
#[entry]
|
||||
fn main() -> ! {
|
||||
let mut cp = CorePeripherals::take().unwrap();
|
||||
cp.SCB.enable_icache();
|
||||
cp.SCB.enable_dcache(&mut cp.CPUID);
|
||||
|
||||
let dp = Peripherals::take().unwrap();
|
||||
let mut flash = dp.FLASH.constrain();
|
||||
let mut rcc = dp.RCC.constrain();
|
||||
let clocks = rcc.cfgr
|
||||
.use_hse(8.mhz())
|
||||
.sysclk(72.mhz())
|
||||
.hclk(72.mhz())
|
||||
.pclk1(36.mhz())
|
||||
.pclk2(72.mhz())
|
||||
.freeze(&mut flash.acr);
|
||||
|
||||
// let mut wd = IndependentWatchdog::new(dp.IWDG);
|
||||
// wd.start(1000u32.ms());
|
||||
// wd.feed();
|
||||
|
||||
let mut gpioa = dp.GPIOA.split(&mut rcc.apb2);
|
||||
let mut gpiob = dp.GPIOB.split(&mut rcc.apb2);
|
||||
|
||||
let mut led = gpiob.pb12.into_push_pull_output(&mut gpiob.crh);
|
||||
|
||||
// (srclk) violet, nucleo: D13
|
||||
let sck = gpioa.pa5.into_alternate_push_pull(&mut gpioa.crl);
|
||||
// not connected
|
||||
let miso = gpioa.pa6.into_floating_input(&mut gpioa.crl);
|
||||
// (serin) blue, nucleo: D11
|
||||
let mosi = gpioa.pa7.into_alternate_push_pull(&mut gpioa.crl);
|
||||
let pins = (sck, miso, mosi);
|
||||
let mut parts = dp.AFIO.constrain(&mut rcc.apb2);
|
||||
let mut spi = Spi::spi1(dp.SPI1, pins, &mut parts.mapr, MODE_0, 36u32.mhz(), clocks, &mut rcc.apb2);
|
||||
|
||||
// (rclk) brown, nucleo: D8
|
||||
let mut rclk = gpioa.pa4.into_push_pull_output(&mut gpioa.crl);
|
||||
// (srclr) green, nucleo: D9
|
||||
let mut srclr = gpioa.pa3.into_push_pull_output(&mut gpioa.crl);
|
||||
|
||||
// timer::setup(cp.SYST, clocks);
|
||||
|
||||
srclr.set_high();
|
||||
rclk.set_low();
|
||||
let mut pg = PwmGraphics::new();
|
||||
let mut t = 0usize;
|
||||
loop {
|
||||
let mut frame = [[0u8; 3]; 8];
|
||||
for x in 0..frame.len() {
|
||||
frame[x][0] = (t >> 10) as u8;
|
||||
frame[x][1] = ((t >> 10) + (x << 1)) as u8;
|
||||
frame[x][2] = ((t >> 9) - (x << 2)) as u8;
|
||||
}
|
||||
let data = pg.generate_frame(&frame);
|
||||
spi.write(&data)
|
||||
.unwrap();
|
||||
|
||||
rclk.set_high();
|
||||
// for _ in 0..200 {
|
||||
// nop();
|
||||
// }
|
||||
rclk.set_low();
|
||||
|
||||
t += 1;
|
||||
if (t / 1_000) % 2 == 0 {
|
||||
led.set_high();
|
||||
} else {
|
||||
led.set_low();
|
||||
}
|
||||
// // for _ in 0..100000 {
|
||||
// // nop();
|
||||
// // }
|
||||
|
||||
// // Update watchdog
|
||||
// wd.feed();
|
||||
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue