### Minimal Cortex-M Application Setup (Rust) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search=std%3A%3Avec Demonstrates a basic 'no_main', 'no_std' Rust application using cortex-m-rt. It includes a panic handler and defines the main function as the entry point. This requires a 'memory.x' linker script and linking with 'link.x'. ```rust #![no_main] #![no_std] // Some panic handler needs to be included. This one halts the processor on panic. use panic_halt as _; use cortex_m_rt::entry; // Use `main` as the entry point of this application, which may not return. #[entry] fn main() -> ! { // initialization loop { // application logic } } ``` -------------------------------- ### Assembly for `__pre_init` Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/index_search=Option%3CT%3E%2C+%28T+-%3E+U%29+-%3E+Option%3CU%3E This example shows how to define the `__pre_init` function using assembly language with `global_asm`. This function runs before RAM initialization, making it suitable for tasks that require low-level setup or cannot rely on Rust's memory safety guarantees. ```assembly global_asm!(include_str!("pre_init.s")); ``` -------------------------------- ### Specify Text Section Start in Linker Script (text) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search=u32+-%3E+bool This example shows how to use the `_stext` symbol in a linker script to control the placement of the `.text` section. This is useful for devices where configuration data or other sections need to precede the executable code in the `FLASH` memory. If `_stext` is omitted, the `.text` section starts immediately after the vector table. ```text MEMORY { /* .. */ } /* _stext can be defined here to control .text section placement */ ``` -------------------------------- ### Heap Start API Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search= Retrieves a pointer to the beginning of the heap. The returned pointer is guaranteed to be 4-byte aligned. ```APIDOC ## GET /heap/start ### Description Returns a pointer to the start of the heap. The returned pointer is guaranteed to be 4-byte aligned. ### Method GET ### Endpoint /heap/start ### Parameters None ### Request Example ``` GET /heap/start ``` ### Response #### Success Response (200) - **heap_start_pointer** (*u32) - A pointer to the start of the heap. #### Response Example ```json { "heap_start_pointer": "0x20000000" } ``` ``` -------------------------------- ### Get Heap Start Pointer (Rust) Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/fn.heap_start_search=Option%3CT%3E%2C+%28T+-%3E+U%29+-%3E+Option%3CU%3E The `heap_start` function in `cortex-m-rt` returns a raw pointer to the beginning of the heap. This pointer is guaranteed to be aligned to a 4-byte boundary, which is crucial for memory allocation operations. ```Rust pub fn heap_start() -> *mut u32 ``` -------------------------------- ### Minimal Cortex-M Application Setup (Rust) Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/index This Rust code demonstrates a minimal application using `cortex-m-rt`. It requires a `memory.x` linker script and defines handlers for hard faults and exceptions. The `#[entry]` attribute designates `main` as the application's entry point, which is expected to loop indefinitely. ```rust #![no_main] #![no_std] // Some panic handler needs to be included. This one halts the processor on panic. use panic_halt as _; use cortex_m_rt::entry; // Use `main` as the entry point of this application, which may not return. #[entry] fn main() -> ! { // initialization loop { // application logic } } ``` -------------------------------- ### Heap Start Pointer Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs Retrieves a pointer to the beginning of the heap memory region. ```APIDOC ## Heap Start Pointer ### Description This function returns a mutable pointer to the start of the heap. The pointer is guaranteed to be 4-byte aligned, which is a common requirement for heap allocations. ### Method `heap_start()` ### Endpoint N/A (This is a function call, not an HTTP endpoint) ### Parameters None ### Request Example ```rust let heap_ptr = heap_start(); // Use heap_ptr for memory allocation or manipulation ``` ### Response #### Success Response - `*mut u32`: A mutable pointer to the start of the heap, guaranteed to be 4-byte aligned. #### Response Example ```rust // The return value is a raw pointer, e.g.: // 0x20001000 as *mut u32 ``` ``` -------------------------------- ### Configure Stack Pointer with _stack_start and _stack_end (Linker Script) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs This example shows how to configure the program's call stack using the `_stack_start` and `_stack_end` symbols in a linker script. It illustrates placing the stack in a dedicated memory region (CCRAM) for faster access, ensuring proper alignment for Cortex-M architecture. ```text _stack_start = ORIGIN(CCRAM) + LENGTH(CCRAM); _stack_end = ORIGIN(CCRAM); /* Optional, add if used by the application */ ``` -------------------------------- ### Inspecting Section Sizes with `size` Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search=u32+-%3E+bool Using the `size` command to inspect the memory sections of a compiled Cortex-M application. This example shows how to view the size and address of sections like `.vector_table` in the output binary. ```bash $ size -Ax target/thumbv7m-none-eabi/examples/app target/thumbv7m-none-eabi/release/examples/app : section size addr .vector_table 0x400 0x8000000 ``` -------------------------------- ### Inspecting ELF Binary Sections with size Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs Command to display the sizes of different sections within an ELF executable. This example shows how to inspect the `app` binary, specifically highlighting the size and address of the `.vector_table` section, which is managed by `cortex-m-rt`. ```bash size -Ax target/thumbv7m-none-eabi/examples/app ``` -------------------------------- ### Control Text Section Placement with _stext (Linker Script) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs This example demonstrates how to use the `_stext` symbol in a linker script to control the placement of the `.text` section. This is useful for devices where specific memory regions, like flash configuration settings, must precede the executable code. ```text MEMORY { /* .. */ } _stext = ORIGIN(FLASH) + 0x1000; /* Example: Place .text after 4KB offset */ ``` -------------------------------- ### Define Memory Regions in Linker Script (C) Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/index_search=std%3A%3Avec This example demonstrates how to define the `FLASH` and `RAM` memory regions in a linker script (`memory.x`) for a Cortex-M microcontroller. These definitions are crucial for the `cortex-m-rt` crate to correctly place program sections and manage memory. ```c /* Linker script for the STM32F103C8T6 */ MEMORY { FLASH : ORIGIN = 0x08000000, LENGTH = 64K RAM : ORIGIN = 0x20000000, LENGTH = 20K } ``` -------------------------------- ### Define Memory Layout with MEMORY Regions (Linker Script) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs This example demonstrates how to define memory regions for a Cortex-M microcontroller using a linker script. It specifies the `FLASH` and `RAM` memory areas, including their origin addresses and lengths, which are essential for the `cortex-m-rt` crate to correctly place program sections and manage memory. ```text /* Linker script for the STM32F103C8T6 */ MEMORY { FLASH : ORIGIN = 0x08000000, LENGTH = 64K RAM : ORIGIN = 0x20000000, LENGTH = 20K } ``` ```text /* Linker script for the STM32F303VCT6 with stack in CCM */ MEMORY { FLASH : ORIGIN = 0x08000000, LENGTH = 256K /* .bss, .data and the heap go in this region */ RAM : ORIGIN = 0x20000000, LENGTH = 40K /* Core coupled (faster) RAM dedicated to hold the stack */ CCRAM : ORIGIN = 0x10000000, LENGTH = 8K } _stack_start = ORIGIN(CCRAM) + LENGTH(CCRAM); _stack_end = ORIGIN(CCRAM); /* Optional, add if used by the application */ ``` -------------------------------- ### Configure Stack with Custom Memory Region in Linker Script (C) Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/index_search=std%3A%3Avec This example shows how to configure the stack pointer (`_stack_start`) to reside in a custom memory region (e.g., `CCRAM`) within the linker script. It also defines `_stack_end` for application use and ensures proper memory region definitions for `FLASH` and `RAM`. ```c /* Linker script for the STM32F303VCT6 with stack in CCM */ MEMORY { FLASH : ORIGIN = 0x08000000, LENGTH = 256K /* .bss, .data and the heap go in this region */ RAM : ORIGIN = 0x20000000, LENGTH = 40K /* Core coupled (faster) RAM dedicated to hold the stack */ CCRAM : ORIGIN = 0x10000000, LENGTH = 8K } _stack_start = ORIGIN(CCRAM) + LENGTH(CCRAM); _stack_end = ORIGIN(CCRAM); /* Optional, add if used by the application */ ``` -------------------------------- ### Get Heap Start Pointer (Rust) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs Returns a pointer to the start of the heap, guaranteed to be 4-byte aligned. It uses an external static mutable variable `__sheap` and `core::ptr::addr_of_mut!` to obtain the pointer. ```Rust pub fn heap_start() -> *mut u32 { extern "C" { static mut __sheap: u32; } #[allow(unused_unsafe)] // no longer unsafe since rust 1.82.0 unsafe { core::ptr::addr_of_mut!(__sheap) } } ``` -------------------------------- ### Building and Inspecting a Cortex-M Application (Shell) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search=std%3A%3Avec Commands to build a Rust application for a Cortex-M target and inspect its ELF file using the 'file' and 'size' commands. This demonstrates the compilation process and how to view section sizes. ```text $ cat > memory.x < memory.x < memory.x < !`. ```rust #[exception(trampoline = true)] unsafe fn HardFault(_frame: &ExceptionFrame) -> ! { // Handler logic } ``` -------------------------------- ### Override SysTick Handler in Rust Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search=u32+-%3E+bool Shows how to override the `SysTick` handler using the `exception` attribute. This example increments a static counter on each SysTick interrupt, demonstrating mutable static variable access within an exception handler. It requires the `cortex_m_rt::exception` module. ```rust use cortex_m_rt::exception; #[exception] fn SysTick() { static mut COUNT: i32 = 0; // `COUNT` is safe to access and has type `&mut i32` *COUNT += 1; println!("{}", COUNT); } # fn main() {} ``` -------------------------------- ### Displaying Section Sizes with `size` Command Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search=std%3A%3Avec Demonstrates how to use the `size` command to display the sizes of different memory sections (.text, .data, .bss) for a compiled application. This is useful for understanding memory usage and optimization. ```text $ size target/thumbv7m-none-eabi/examples/app text data bss dec hex filename 1160 0 0 1660 67c target/thumbv7m-none-eabi/release/app ``` -------------------------------- ### Configure HardFault Handler with Trampoline in Rust Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/attr.exception_search= This example illustrates setting the `HardFault` handler with the `trampoline` parameter set to `true`. When `trampoline` is true, the handler must have the signature `unsafe fn(&ExceptionFrame) -> !`. If `trampoline` is false or omitted, the signature should be `unsafe fn() -> !`. ```rust #[exception(trampoline = true)] unsafe fn HardFault(ef: &ExceptionFrame) -> ! // Handler logic here ``` -------------------------------- ### Mark Pre-Initialization Function (Rust) Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/index_search= The `#[pre_init]` attribute marks a function that will be called at the very beginning of the reset handler, before the main entry point. This is useful for essential setup tasks that need to occur before general program execution, such as initializing custom memory sections. ```rust #[pre_init] fn pre_init() { // Initialization code here } ``` -------------------------------- ### Defining a Custom Entry Point in Rust Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search=Option%3CT%3E%2C+%28T+-%3E+U%29+-%3E+Option%3CU%3E Illustrates how to define a custom entry point for a Rust program targeting embedded systems. The `#[entry]` attribute is used to mark the `main` function, which will be called upon reset after essential initializations. The entry function must have the signature `extern "C" fn() -> !`. ```rust #[entry] fn main() -> ! // Your application code here } ``` -------------------------------- ### Minimal Cortex-M Application Entry Point (Rust) Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/index_search=std%3A%3Avec This Rust code snippet demonstrates a minimal embedded application using `cortex-m-rt`. It requires `#![no_main]` and `#![no_std]` attributes, a panic handler (e.g., `panic_halt`), and the `#[entry]` attribute to mark the `main` function as the application's entry point. The `main` function typically contains initialization code and an infinite loop for the application logic. ```rust #![no_main] #![no_std] // Some panic handler needs to be included. This one halts the processor on panic. use panic_halt as _; use cortex_m_rt::entry; // Use `main` as the entry point of this application, which may not return. #[entry] fn main() -> ! { // initialization loop { // application logic } } ``` -------------------------------- ### Initialize RAM with Zeros (Assembly) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs Initializes RAM with zeros if the 'zero-init-ram' feature is enabled. This is typically for safety-critical hardware with checksum-based memory integrity measures. It uses assembly instructions to load start and end addresses and fill memory with zeros. ```assembly ldr r0, =_ram_start ldr r1, =_ram_end movs r2, #0 0: cmp r1, r0 beq 1f stm r0!, {{r2}} b 0b 1: ``` -------------------------------- ### Declare Program Entry Point (Rust) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search=std%3A%3Avec The `#[entry]` attribute designates the main function of the program, which serves as the entry point. This function is invoked by the reset handler after RAM initialization and, for specific targets like `thumbv7em-none-eabihf`, after the FPU is enabled. The function signature must be `[unsafe] fn() -> !`, indicating a function that never returns. ```rust /// Attribute to declare the entry point of the program /// /// The specified function will be called by the reset handler *after* RAM has been initialized. In /// the case of the `thumbv7em-none-eabihf` target the FPU will also be enabled before the function /// is called. /// /// The type of the specified function must be `[unsafe] fn() -> !` (never ending function) /// /// # Properties /// ``` -------------------------------- ### Initialize .bss Memory (Assembly) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs Initializes the .bss memory section, typically used for uninitialized global and static variables. It reads the start and end symbols (`__sbss` and `__ebss`) from the linker script and fills the section with zeros. This is used when the 'zero-init-ram' feature is not enabled. ```assembly ldr r0, =__sbss ldr r1, =__ebss movs r2, #0 0: cmp r1, r0 beq 1f stm r0!, {{r2}} b 0b 1: ``` -------------------------------- ### heap_start Function Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/fn.heap_start Retrieves a pointer to the beginning of the heap. This function is essential for dynamic memory allocation in embedded systems using cortex-m-rt. ```APIDOC ## heap_start ### Description Returns a pointer to the start of the heap. The returned pointer is guaranteed to be 4-byte aligned. ### Method ``` pub fn heap_start() -> *mut u32 ``` ### Endpoint N/A (This is a function call within the cortex-m-rt crate, not a web endpoint) ### Parameters None ### Request Example N/A ### Response #### Success Response - **Return Value** (*mut u32) - A raw mutable pointer to the start of the heap. #### Response Example ```rust let heap_ptr = cortex_m_rt::heap_start(); // Use heap_ptr for memory allocation ``` ``` -------------------------------- ### Define Entry Point for Cortex-M RT Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search=std%3A%3Avec The `entry` attribute marks the main function as the program's entry point, called by the reset handler. Variables declared as `static mut` within the entry point are safely accessible and modified, with the compiler transforming them into `&'static mut` references. ```rust #![no_main] use cortex_m_rt::entry; #[entry] fn main() -> ! { loop { /* .. */ } } ``` ```rust #![no_main] use cortex_m_rt::entry; #[entry] fn main() -> ! { static mut FOO: u32 = 0; let foo: &'static mut u32 = FOO; assert_eq!(*foo, 0); *foo = 1; assert_eq!(*foo, 1); loop { /* .. */ } } ``` -------------------------------- ### Declare Program Entry Point (Rust) Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/index This Rust code snippet shows how to declare the entry point of a Cortex-M application using the `#[entry]` attribute provided by the `cortex-m-rt` crate. This function will be executed after the system has been initialized. ```rust use cortex_m_rt::entry; #[entry] fn main() -> ! { // Your application code here loop { // ... } } ``` -------------------------------- ### Safe Modification of Static Mut Variables in Entry Point (Rust) Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/attr.entry_search=u32+-%3E+bool Static mutable variables declared within an #[entry] function are safe to access and modify. The compiler transforms these declarations to `let FOO: &'static mut u32;`, ensuring safe mutable access. This example demonstrates modifying a static mutable variable within the entry point. ```rust #[entry] fn main() -> ! { static mut FOO: u32 = 0; let foo: &'static mut u32 = FOO; assert_eq!(*foo, 0); *foo = 1; assert_eq!(*foo, 1); loop { /* .. */ } } ``` -------------------------------- ### Define Entry Point for Cortex-M Application (Rust) Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs The `entry` attribute marks the main function as the program's entry point, called by the reset handler. `static mut` variables declared within this function are safely accessible and transformed by the compiler into mutable static references. ```rust #![no_main] use cortex_m_rt::entry; #[entry] fn main() -> ! { loop { /* .. */ } } ``` -------------------------------- ### Using a Custom Linker Script Source: https://docs.rs/cortex-m-rt/latest/src/cortex_m_rt/lib.rs_search=Option%3CT%3E%2C+%28T+-%3E+U%29+-%3E+Option%3CU%3E Explains how to instruct the Rust compiler to use a custom linker script instead of the default one. This is achieved by passing the `-C link-arg=-Tmy_script.ld` flag during compilation. The provided `link.x` file can serve as a template for custom scripts. ```bash rustc ... -C link-arg=-Tmy_script.ld ``` -------------------------------- ### Generate Linker Script in Rust Build Script Source: https://docs.rs/cortex-m-rt/latest/cortex_m_rt/index This Rust build script demonstrates how to create a linker script (`device.x`) and place it in the output directory. It uses `cargo:rustc-link-search` to inform the linker where to find the script. This is crucial for integrating custom linker scripts provided by dependencies. ```rust 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("device.x")) .unwrap() .write_all(include_bytes!("device.x")) .unwrap(); println!("cargo:rustc-link-search={}", out.display()); } ```