#clock #arm64 #cru #rk3568

nightly no-std rk3568_clk

Clock and Reset Unit (CRU) driver for RK3568 SoC

1 unstable release

Uses new Rust 2024

0.1.0 Jan 27, 2026

#1122 in Embedded development


Used in axvisor-driver

GPL-3.0-or-later OR Apache-2.0 OR MIT

140KB
984 lines

RK3568_CLK

Clock and Reset Unit (CRU) driver for RK3568 SoC written in Rust

CI GitHub stars GitHub forks license

English | 中文

Overview

rk3568_clk is a no_std Rust driver for the Clock and Reset Unit (CRU) of the Rockchip RK3568 SoC. It provides safe and efficient access to CRU hardware registers for clock configuration, gating control, and reset management.

The RK3568 CRU consists of multiple control units:

  • PMUCRU (0xFDD00000) - Power management CRU for always-on systems
  • PMUSCRU (0xFDD30000) - Secure PMU CRU for always-on secure systems
  • CRU (0xFDD20000) - General system CRU (currently supported)
  • SCRU (0xFDD10000) - Secure system CRU

Features

  • PLL Management: Support for 6 fractional PLLs (APLL, PPLL, HPLL, DPLL, CPLL, GPLL) and 3 integer PLLs (MPLL, NPLL, VPLL)
  • Clock Configuration: Clock selection and divider configuration for various peripherals
  • Clock Gating: Enable/disable clocks for power management
  • Reset Control: Software reset control for peripherals
  • eMMC Support: Specialized eMMC clock and delay configuration
  • Safe Abstractions: Type-safe register access with bit-level control
  • No Std: Designed for bare-metal and embedded environments

Installation

Add this to your Cargo.toml:

[dependencies]
rk3568_clk = "0.1"

Usage

Basic Example

use rk3568_clk::CRU;
use rk3568_clk::cru_clksel_con28_bits::*;

// Initialize CRU with base address
let cru = unsafe { CRU::new(0xFDD20000 as *mut rk3568_clk::RegMap) };

// Configure eMMC clock to 200MHz
cru.cru_clksel_set_cclk_emmc(CRU_CLKSEL_CCLK_EMMC_GPL_DIV_200M);

// Enable eMMC clocks
cru.cru_enable_cclk_emmc();
cru.cru_enable_hclk_emmc();
cru.cru_enable_aclk_emmc();

// Check if clock is enabled
if cru.cru_cclk_emmc_is_enabled() {
    // Clock is running
}

eMMC Clock Configuration

The driver provides specialized functions for eMMC clock and delay configuration:

// Set eMMC drive delay parameters
cru.cru_set_emmc_drv_delaynum(0x20);
cru.cru_set_emmc_drv_degree(0x00);

// Set eMMC sample delay parameters
cru.cru_set_emmc_sample_delaynum(0x20);
cru.cru_set_emmc_sample_degree(0x00);

// Enable eMMC drive and sample
cru.cru_enable_emmc_drv();
cru.cru_enable_emmc_sample();

Reset Control

// Assert reset
cru.cru_enable_hreset_emmc();

// Release reset
cru.cru_disable_hreset_emmc();

// Check reset status
if cru.cru_hreset_emmc_is_finished() {
    // Reset is released
}

Documentation

For detailed API documentation, you can:

  1. View the inline comments in the source code
  2. Generate and view local documentation:
    cargo doc --open
    
  3. Visit docs.rs

Building and Testing

Build

cargo build --release

Run Tests

# Run QEMU tests
make test

# Run U-Boot tests on real hardware
cargo test --test test --  --show-output uboot

Makefile Targets

  • make build - Build the release binary
  • make test - Run tests with QEMU
  • cargo test --test test -- --show-output uboot - Run tests on U-Boot hardware
  • make clean - Clean build artifacts

Hardware Requirements

  • Rockchip RK3568 SoC or compatible platform
  • AArch64 (ARM64) architecture
  • Bare-metal or bare-metal compatible OS (e.g., AxRuntime, U-Boot)

Architecture

The CRU driver is organized as follows:

src/
└── cru.rs
    ├── RegMap          - Memory-mapped register layout (240 registers)
    ├── CRU             - Main driver struct with register access methods
    ├── cru_*_bits      - Bit field definitions for each register
    └── Register APIs   - Implementation for clock, gate, and reset operations

Register Access

The driver uses read_volatile() and write_volatile() for safe register access to prevent compiler optimizations that could affect hardware interactions.

Safety Considerations

Important: This driver provides basic register access. Special handling procedures (e.g., PLL reprogramming sequences, power-on reset sequences) are NOT included. Users must implement these procedures according to the RK3568 TRM (Technical Reference Manual).

For example, when changing PLL settings:

  1. Switch PLL to slow mode or deep slow mode
  2. Reprogram PLL parameters
  3. Wait for PLL lock
  4. Switch back to normal mode

License

This project is dual-licensed:

  • GPL-3.0-or-later - For use in GPL projects
  • Apache-2.0 - For use in Apache-licensed projects
  • MIT - For use in MIT-licensed projects

Choose the license that best fits your project.

Contributing

Contributions are welcome! Please feel free to:

  1. Fork the repository
  2. Create a feature branch
  3. Make your changes
  4. Submit a pull request

Acknowledgments

  • Rockchip for the RK3568 SoC and TRM documentation
  • The Rust embedded community for excellent embedded development tools

Resources

Dependencies

~0.9–1.3MB
~24K SLoC