stm32h7xx-hal

repository·master·Indexed 43 days ago

https://github.com/stm32-rs/stm32h7xx-hal

Hardware Abstraction Layer (HAL) implementation for the STMicroelectronics STM32H7 series microcontrollers, built on top of the stm32h7 peripheral access crate. Version 0.16.0 supports various families including stm32h743v, stm32h753v, stm32h747cm7, stm32h7b3, stm32h7b0, stm32h7a3, and stm32h735. It provides abstractions for CRC units, DMA streams (including DoubleBufferedStream and MasterStream for MDMA), and power configuration for internal SMPS or LDO schemes.

Tokens
15.2K
Snippets
45
Records
68
Agent score
54%

What's inside stm32h7xx-hal

  1. Supported STM32H7 Configurations

    master

    The HAL supports several families of the STM32H7 series. When selecting a feature, ensure it matches your hardware revision.

    Supported Families

    • stm32h743v (Revision V: covers stm32h743, stm32h742, stm32h750)
    • stm32h753v
    • stm32h747cm7 (covers stm32h747, stm32h757)
    • stm32h7b3
    • stm32h7b0
    • stm32h7a3
    • stm32h735 (covers stm32h723, stm32h725, stm32h730, stm32h733, stm32h735)

    Hardware Revisions (Revision V vs Revision Y)

    For stm32h742, stm32h743, stm32h750, and stm32h753, ST released a Revision V in 2019 which contains breaking hardware changes.

    • Revision V: Use the feature gate with the v suffix (e.g., stm32h743v).
    • Revision Y (Old): Use the feature gate without the v suffix (e.g., stm32h743).

    Limitations

    • Dual Core: On dual-core parts (Cortex M7 + Cortex M4), currently only the Cortex M7 core is supported.
    • Unsupported: STM32H7R3/7S3 are not directly supported.
  2. Enable logging via RTT, Semihosting, or ITM

    master

    The HAL examples support several logging methods via feature flags. If no logging feature is selected, logging is disabled and the panic handler will simply halt.

    To enable a specific logging method, include the corresponding feature flag in your cargo build command. Note that you must also specify your target chip feature (e.g., stm32h750v).

    ### RTT (Real Time Trace)
    ```bash
    cargo build --features=stm32h750v,rt,log-rtt --examples

    Semihosting (Very slow)

    cargo build --features=stm32h750v,rt,log-semihost --examples

    ITM (Instrumentation Trace Macrocell)

    cargo build --features=stm32h750v,rt,log-itm --examples
  3. How to start a new STM32H7 project

    master

    To build a custom application using stm32h7xx-hal, follow these steps to set up a new binary crate:

    1. Install the target: Ensure the Rust cross-compiler is installed:
      rustup target add thumbv7em-none-eabihf
    2. Initialize crate: Run cargo init to create a new binary crate.
    3. Configure Cargo: Create a .cargo/config.toml file and set target = "thumbv7em-none-eabihf" to ensure cross-compilation.
    4. Linker Script: Copy a memory.x file into your project root. This file is required by the linker to define memory boundaries.
    5. Add HAL Dependency: In Cargo.toml, add stm32h7xx-hal and ensure the features array matches your specific chip (e.g., stm32h743v).
    6. Implement Code: Copy logic from existing examples (like blinky.rs) into src/main.rs, adjusting for your specific board requirements.
    [dependencies.stm32h7xx-hal]
    version = "^0"
    features = ["stm32h743v"]
  4. Install stm32h7xx-hal as a dependency

    master

    To use stm32h7xx-hal in a standalone project, you must specify the target device feature in your Cargo.toml. You typically also need cortex-m and cortex-m-rt.

    Note: The target device feature name depends on your specific chip (e.g., stm32h743v).

    [dependencies]
    cortex-m = "0.7.4"
    cortex-m-rt = "0.7.1"
    stm32h7xx-hal = {version = "0.16.0", features = ["stm32h743v","rt"]}
  5. Overview of stm32h7xx-hal functionality

    master

    The stm32h7xx-hal provides a Hardware Abstraction Layer for STM32H7 microcontrollers, organized into several functional modules. Many modules require specific Cargo features to be enabled.

    Setup and Configuration

    Digital IO

    Analog IO

    Digital Busses

    External Memory

    Timing functions

    Others

  6. The DoubleBufferedStream trait for advanced DMA

    master

    The DoubleBufferedStream trait extends Stream to support advanced DMA features like double buffering, circular buffering, and memory/peripheral increments.

    Safety Warnings:

    • set_peripheral_address: The provided address must be a valid peripheral hardware address and must not be accessed by the application once set.
    • set_memory_address: The provided buffer must not be accessed by the application once provided; the DMA peripheral logically owns the memory.
    • set_memory_size / set_peripheral_size: The size must match the alignment of the buffer used in the transfer.

    Key Features:

    • Buffering: Enable/disable double buffering (set_double_buffer), circular buffering (set_circular_buffer), and half-transfer interrupts (set_half_transfer_interrupt_enable).
    • Addressing: Set memory/peripheral addresses and increments (set_memory_increment, set_peripheral_increment).
    • Transfer Control: Set the number of transfers (set_number_of_transfers) and the direction (set_direction).
    • Buffer Tracking: Use get_current_buffer and get_inactive_buffer to manage buffers in double-buffer mode.
    pub trait DoubleBufferedStream: Stream + Sealed {
        unsafe fn set_peripheral_address(&mut self, value: usize);
        unsafe fn set_memory_address(&mut self, buffer: CurrentBuffer, value: usize);
        fn set_half_transfer_interrupt_enable(&mut self, transfer_complete_interrupt: bool);
        fn clear_half_transfer_interrupt(&mut self);
        fn get_half_transfer_flag() -> bool;
        fn get_memory_address(&self, buffer: CurrentBuffer) -> usize;
        fn set_memory_increment(&mut self, increment: bool);
        fn set_peripheral_increment(&mut self, increment: bool);
        fn set_number_of_transfers(&mut self, value: u16);
        fn get_number_of_transfers() -> u16;
        unsafe fn set_memory_size(&mut self, size: u8);
        unsafe fn set_peripheral_size(&mut self, size: u8);
        fn set_direction(&mut self, direction: DmaDirection);
        fn set_circular_buffer(&mut self, circular_buffer: bool);
        fn set_double_buffer(&mut self, double_buffer: bool);
        fn get_current_buffer() -> CurrentBuffer;
        fn get_inactive_buffer() -> Option<CurrentBuffer>;
    }
  7. Configure I2C Stop condition mode

    master

    When performing master operations, you can specify how the STOP condition is generated using the Stop enum:

    • Stop::Software: The STOP condition must be manually generated by writing to the peripheral registers (e.g., calling master_stop()).
    • Stop::Automatic: A STOP condition is automatically generated by the hardware once the configured number of bytes have been transferred.
  8. The Stream trait for DMA operations

    master

    The Stream trait is the base abstraction for all DMA streams. It provides methods for basic configuration, interrupt management, and stream control (enabling/disabling).

    Key capabilities include:

    • Configuration: Apply a stream-specific Config using apply_config.
    • Interrupt Management: Clear interrupts (clear_interrupts, clear_transfer_complete_flag, etc.), enable/disable interrupts (enable_interrupts, disable_interrupts), and check status (get_transfer_complete_flag, get_interrupts_enable).
    • Control: Enable the stream via enable (unsafe) and disable it via disable (which also clears interrupt flags if the stream is active).
    • Priority & Request: Set the DMA request line via set_request_line and priority via set_priority.
    pub trait Stream: Sealed {
        type Config;
        type Interrupts: Copy + Debug;
    
        fn apply_config(&mut self, config: Self::Config);
        fn clear_interrupts(&mut self);
        fn clear_transfer_complete_flag(&mut self);
        fn clear_transfer_complete_interrupt(&mut self);
        fn clear_transfer_error_interrupt(&mut self);
        fn get_transfer_complete_flag() -> bool;
        unsafe fn enable(&mut self);
        fn is_enabled() -> bool;
        fn disable(&mut self);
        fn set_request_line(&mut self, request_line: u8);
        fn set_priority(&mut self, priority: config::Priority);
        fn disable_interrupts(&mut self);
        fn enable_interrupts(&mut self, interrupts: Self::Interrupts);
        fn get_interrupts_enable() -> Self::Interrupts;
        fn set_transfer_complete_interrupt_enable(&mut self, transfer_complete_interrupt: bool);
        fn set_transfer_error_interrupt_enable(&mut self, transfer_error_interrupt: bool);
    }
  9. Configure shared group kernel clocks

    master

    Some peripherals share a single kernel clock multiplexer (PKSU) with other peripherals in their group. Because the multiplexer is shared, you cannot set the clock source via the individual peripheral's REC object. Instead, you must use the kernel_<group_name>_clk_mux method on the PeripheralREC object itself.

    // Set group kernel clock via the PeripheralREC object
    let mut ccdr = ...; // Returned by freeze()
    ccdr.peripheral.kernel_i2c123_clk_mux(I2c123ClkSel::PLL3_R);
    
    // Now the individual peripheral reflects the group setting
    let i2c3_prec = ccdr.peripheral.I2C3.enable().reset();
    assert_eq!(i2c3_prec.get_kernel_clk_mux(), I2c123ClkSel::PLL3_R);
  10. The MasterStream trait for MDMA

    master

    The MasterStream trait is used for Master DMA (MDMA) operations. It provides fine-grained control over source/destination addresses, burst sizes, and trigger modes.

    Safety Warnings:

    • set_source_address / set_destination_address: Must have the same alignment as configured for the transfer.
    • set_source_burst_size / set_destination_burst_size: Must be less than the transfer length.
    • set_transfer_length / set_block_bytes: Must be a multiple of both the source and destination size.
    • set_source_offset / set_destination_offset: If the source/destination is TCM/AHB and the burst is not a single transfer, the address must be aligned with the offset.

    Key Features:

    • Triggering: Set software/hardware triggers (set_software_triggered, set_trigger_selection) and trigger modes (set_trigger_mode).
    • Transfer Details: Manage block bytes (set_block_bytes, get_block_bytes) and source/destination sizes and offsets.
    • Interrupts: Manage buffer transfer complete (tcie), block transfer complete (btie), and block repeat transfer complete (brtie) interrupts.
    pub trait MasterStream: Stream + Sealed {
        unsafe fn set_source_address(&mut self, value: usize);
        unsafe fn set_destination_address(&mut self, value: usize);
        unsafe fn set_source_burst_size(&mut self, value: u8);
        unsafe fn set_destination_burst_size(&mut self, value: u8);
        fn get_source_burst_size() -> u8;
        fn get_destination_burst_size() -> u8;
        fn set_software_triggered(&mut self, sw_triggered: bool);
        fn set_trigger_selection(&mut self, trigger: u8);
        fn set_trigger_mode(&mut self, trigger_mode: mdma::MdmaTrigger);
        unsafe fn set_transfer_length(&mut self, value: u8);
        fn get_transfer_length() -> u8;
        unsafe fn set_block_bytes(&mut self, value: u32);
        fn get_block_bytes() -> u32;
        fn source_destination_size_offset(
            config: &Self::Config,
            peripheral_size: mdma::MdmaSize,
            memory_size: mdma::MdmaSize,
            direction: DmaDirection,
        ) -> ((mdma::MdmaSize, mdma::MdmaSize), (mdma::MdmaSize, mdma::MdmaSize));
        unsafe fn set_source_size(&mut self, size: mdma::MdmaSize);
        fn get_source_size() -> mdma::MdmaSize;
        unsafe fn set_source_offset(&mut self, offset: mdma::MdmaSize);
        unsafe fn set_destination_size(&mut self, size: mdma::MdmaSize);
        fn get_destination_size() -> mdma::MdmaSize;
        unsafe fn set_destination_offset(&mut self, offset: mdma::MdmaSize);
        fn set_buffer_transfer_complete_interrupt_enable(&mut self, buffer_transfer_complete_interrupt: bool);
        fn clear_buffer_transfer_complete_interrupt(&mut self);
        fn get_buffer_transfer_complete_flag() -> bool;
        fn set_block_transfer_complete_interrupt_enable(&mut self, transfer_complete_interrupt: bool);
        fn clear_block_transfer_complete_interrupt(&mut self);
        fn get_block_transfer_complete_flag() -> bool;
        fn set_block_repeat_transfer_complete_interrupt_enable(&mut self, transfer_complete_interrupt: bool);
        fn clear_block_repeat_transfer_complete_interrupt(&mut self);
        fn get_block_repeat_transfer_complete_flag() -> bool;
    }