# K230 Linux SDK New Board Adaptation Guide

## Document Purpose

This document describes how to adapt devices that are not officially supported to the K230 Linux SDK.

---

## Adapt Based on Existing Configuration (Recommended)

Select a configuration whose hardware setup is close to that of the target board, and directly modify the relevant files. This chapter uses `k230_canmv_01studio_defconfig` as an example.

### 01studio Main Configuration File

| Item              | Description                                                                                                          |
| ------------      | -------------------------------------------------------------------------------------------------------------------- |
| **File Path**     | `buildroot-overlay/configs/k230_canmv_01studio_defconfig`                                                           |
| **Function**      | SDK configuration file, which can enable software packages, configure rootfs size, and configure the configuration files used by U-Boot and the kernel, etc. |
| **Modification Method** | Modify directly, or run `make menuconfig; make savedefconfig` to modify                                     |
| **How to Take Effect** | `make CONF=k230_canmv_01studio_defconfig ; make`                                                              |

**Key Configuration Item Description**

```bash
BR2_LINUX_KERNEL_DEFCONFIG="k230"  # Kernel default configuration file k230_defconfig
BR2_LINUX_KERNEL_CONFIG_FRAGMENT_FILES="board/canaan/k230-soc/fragment/linux.fragment"  # Kernel configuration append file
BR2_LINUX_KERNEL_INTREE_DTS_NAME="canaan/k230-canmv-01studio-lcd canaan/k230-canmv-01studio"  # Kernel device tree
BR2_PACKAGE_BUSYBOX_CONFIG_FRAGMENT_FILES="board/canaan/k230-soc/fragment/busybox.fragment"  # BusyBox configuration file
BR2_TARGET_UBOOT_BOARDNAME="k230_canmv_01studio"  # Configuration file used by U-Boot
BR2_TARGET_ROOTFS_EXT2_SIZE="400M"  # rootfs size
```

---

### Key Files Under U-Boot

#### U-Boot Configuration File

| Item              | Description                                                                                                                                                                                                                    |
| ------------      | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| **File Path**     | `buildroot-overlay/boot/uboot/u-boot-2022.10-overlay/configs/k230_canmv_01studio_defconfig`                                                                                                                                    |
| **Modification Method** | Modify manually, or run `cd output/k230_canmv_01studio_defconfig/build/uboot-2022.10; make menuconfig; cp .config ../../../../buildroot-overlay/boot/uboot/u-boot-2022.10-overlay/configs/k230_canmv_01studio_defconfig; cd -` |
| **How to Take Effect** | `make`                                                                                                                                                                                                                     |

**Key Configuration Item Description:**

```makefile
CONFIG_DEFAULT_DEVICE_TREE="k230_canmv_01studio"  # Configure the device tree file to use
CONFIG_CANMV_01STUDIO_LPDDR4_2667=y  # DDR type and frequency
CONFIG_TARGET_K230_CANMV_01STUDIO=y  # 01studio development board
```

#### U-Boot Device Tree

| Item              | Description                                                                                         |
| ------------      | --------------------------------------------------------------------------------------------------- |
| **File Path**     | `buildroot-overlay/boot/uboot/u-boot-2022.10-overlay/arch/riscv/dts/k230_canmv_01studio.dts`        |
| **Remarks**       | Determined by `CONFIG_DEFAULT_DEVICE_TREE` which device tree to use                                |
| **How to Take Effect** | `make`                                                                                        |

**Key Code Description:**

```c
// BANK voltage settings must match the board hardware, otherwise the device may be permanently damaged
#define BANK_VOLTAGE_IO0_IO1  K230_MSC_1V8  // FIXED
#define BANK_VOLTAGE_IO2_IO13  K230_MSC_3V3
#define BANK_VOLTAGE_IO14_IO25  K230_MSC_3V3
#define BANK_VOLTAGE_IO26_IO37  K230_MSC_3V3
#define BANK_VOLTAGE_IO38_IO49  K230_MSC_3V3
#define BANK_VOLTAGE_IO50_IO61  K230_MSC_3V3
#define BANK_VOLTAGE_IO62_IO63  K230_MSC_1V8

// IOMUX function configuration, adjust according to the actual board situation
// SEL field selects IOMUX function, refer to: Appendix A
(IO2) (1<<SEL | 0<<SL | BANK_VOLTAGE_IO2_IO13<<MSC | 1<<IE | 1<<OE | 0<<PU | 0<<PD | 4<<DS | 0<<ST)
(IO3) (3<<SEL | 0<<SL | BANK_VOLTAGE_IO2_IO13<<MSC | 1<<IE | 1<<OE | 0<<PU | 0<<PD | 4<<DS | 0<<ST)
(IO4) (3<<SEL | 0<<SL | BANK_VOLTAGE_IO2_IO13<<MSC | 1<<IE | 1<<OE | 0<<PU | 0<<PD | 4<<DS | 0<<ST)
(IO5) (1<<SEL | 0<<SL | BANK_VOLTAGE_IO2_IO13<<MSC | 1<<IE | 1<<OE | 0<<PU | 0<<PD | 4<<DS | 0<<ST)
(IO6) (1<<SEL | 0<<SL | BANK_VOLTAGE_IO2_IO13<<MSC | 1<<IE | 1<<OE | 0<<PU | 0<<PD | 4<<DS | 0<<ST)
```

> **Note**: For IOMUX configuration, please refer to [Appendix A: IOMUX Pin Configuration Description](#appendix-a-iomux-pin-configuration)

#### U-Boot Board Directory

| Item              | Description                                                                                    |
| ------------      | ---------------------------------------------------------------------------------------------- |
| **Directory Path** | `buildroot-overlay/boot/uboot/u-boot-2022.10-overlay/board/canaan/k230_canmv_01studio/`       |
| **Modification Method** | Modify directly                                                                          |
| **How to Take Effect** | `make`                                                                                  |

**Key File Description:**

- `board.c`: Board-level initialization file

  ```c
  sysctl_boot_mode_e sysctl_boot_get_boot_mode(void)
  {
      return SYSCTL_BOOT_SDIO0;  // Force boot from MMC0
  }
  ```

- `lpddr4_init_32_swap_2667.c`: DDR4 initialization code

---

### Linux Key Files

#### Linux Device Tree

| Item         | Description                                                                                              |
| ------------ | -------------------------------------------------------------------------------------------------------- |
| **File Path** | `output/k230_canmv_01studio_defconfig/build/linux-*/arch/riscv/boot/dts/canaan/k230-canmv-01studio*.dts` |
| **Modification Method** | Direct modification                                                                             |
| **How to Apply** | `make linux-rebuild && make`                                                                             |
| **Other Notes** | Generated only after one compilation; filename with `lcd` indicates LCD display, without `lcd` indicates HDMI display |

**Key Configuration Snippets:**

```c
aliases {
    serial3 = &uart3;  // Define device number
    i2c0 = &i2c4;      // Define device number
    i2c1 = &i2c3;
    mmc0 = &mmc_sd0;   // Define device number
    mmc1 = &mmc_sd1;
};

&usb1 {
    dr_mode = "host";  // Force host mode
    status = "okay";   // Enable USB1
};
```

<a id="kernel-config-modification"></a>

#### Kernel Configuration File Modification

**Method One**: Directly add the required kernel configuration in `board/canaan/k230-soc/fragment/linux.fragment`.

**Method Two**: Execute the following commands to modify the kernel configuration:

```bash
make linux-menuconfig;
make linux-savedefconfig;
cp output/k230_test_defconfig/build/linux-*/defconfig buildroot-overlay/board/canaan/k230-soc/fragment/linux.fragment;
```

>How to apply after modification: `make linux-reconfigure;make`
---

## Fresh Adaptation (Not Recommended)

> **Note**: This method is not recommended; it is preferable to directly use existing configurations and modify them.

### Add Main Configuration File

Create a configuration file in the `buildroot-overlay/configs/` directory (using `k230_test_defconfig` as an example):

```bash
cd buildroot-overlay/configs/
cp k230_canmv_01studio_defconfig k230_test_defconfig
cd ../../
make CONF=k230_test_defconfig
```

### U-Boot Adaptation

#### Step 1: Add Board-Level Directory

```bash
cd buildroot-overlay/boot/uboot/u-boot-2022.10-overlay/board/canaan/
cp k230_canmv_01studio k230_test -r
cd -
```

#### Step 2: Modify Kconfig

- Add the following to `buildroot-overlay/boot/uboot/u-boot-2022.10-overlay/arch/riscv/Kconfig`:

```makefile
#buildroot-overlay/boot/uboot/u-boot-2022.10-overlay/arch/riscv/Kconfig file
#around line 50
config TARGET_K230_TEST
    bool "Support TEST BOARD"
    select SYS_CACHE_SHIFT_6

#around line 112
source "board/canaan/k230_test/Kconfig"
```

- Modify the `board/canaan/k230_test/Kconfig` file,
Replace `TARGET_K230_CANMV_01STUDIO` with `TARGET_K230_TEST`, similar to the following:

```makefile
if TARGET_K230_TEST
#......
config SYS_BOARD
    default "k230_test"
#......
endif
```

#### Step 3: Add and Modify U-Boot Device Tree

- Add a new device tree:

```bash
cd buildroot-overlay/boot/uboot/u-boot-2022.10-overlay/arch/riscv/dts/
cp k230_canmv_01studio.dts k230_test.dts
cd -
```

- Modify the device tree. Key modification points are as follows:

```c
// BANK voltage settings must match the board design; incorrect configuration may damage the chip
#define BANK_VOLTAGE_IO0_IO1           K230_MSC_1V8  // FIXED
#define BANK_VOLTAGE_IO2_IO13          K230_MSC_3V3
#define BANK_VOLTAGE_IO14_IO25         K230_MSC_3V3
#define BANK_VOLTAGE_IO26_IO37         K230_MSC_3V3
#define BANK_VOLTAGE_IO38_IO49         K230_MSC_3V3
#define BANK_VOLTAGE_IO50_IO61         K230_MSC_3V3
#define BANK_VOLTAGE_IO62_IO63         K230_MSC_3V3
#include "k230.dtsi"

&mmc0 {
    1-8-v;          // Configure MMC0 as 1.8V IO
    status = "okay";
};

&mmc1 {
    status = "okay";
};

&iomux {
    pinctrl-names = "default";
    pinctrl-0 = <&pins>;

    pins: iomux_pins {
        u-boot,dm-pre-reloc;
        pinctrl-single,pins = <
            (IO2)  (1<<SEL | 0<<SL | BANK_VOLTAGE_IO2_IO13<<MSC | 1<<IE | 0<<OE | 0<<PU | 1<<PD | 4<<DS | 1<<ST)
            (IO63) (0<<SEL | 0<<SL | BANK_VOLTAGE_IO62_IO63<<MSC | 1<<IE | 1<<OE | 0<<PU | 0<<PD | 7<<DS | 1<<ST)
        >;
    };
};
```

> **Note**: For IOMUX configuration, please refer to [Appendix A: IOMUX Pin Configuration Description](#appendix-a-iomux-pin-configuration)

#### Step 4: Add and Modify U-Boot Configuration File

- Add configuration file

```bash
cd buildroot-overlay/boot/uboot/u-boot-2022.10-overlay/configs/
cp k230_canmv_01studio_defconfig k230_test_defconfig
cd -
```

- Modify configuration items, key modification points:

```makefile
CONFIG_DEFAULT_DEVICE_TREE="k230_test"
CONFIG_TARGET_K230_TEST=y
CONFIG_CANMV_01STUDIO_LPDDR4_2667=y
```

#### Step 5: Modify SDK Configuration

Modify the `buildroot-overlay/configs/k230_test_defconfig` file:
Change BR2_TARGET_UBOOT_BOARDNAME to "k230_test"

```makefile
BR2_TARGET_UBOOT_BOARDNAME="k230_test"
```

#### Step 6: Build and Verify

```bash
# Enter the SDK main directory and execute the following commands
make k230_test_defconfig
make uboot-dirclean
make uboot
```

---

### Linux Adaptation

#### Step 1: Add Device Tree

```bash
cd output/k230_test_defconfig/build/linux-*/arch/riscv/boot/dts/canaan/
cp k230-canmv-01studio.dts k230-test.dts
cd -
```

**Key Configuration Examples:**

```c
aliases {
    serial3 = &uart3;
    i2c0 = &i2c4;
    i2c1 = &i2c3;
    mmc0 = &mmc_sd0;
    mmc1 = &mmc_sd1;
};

&usb1 {
    dr_mode = "host";
    status = "okay";
};

&mmc_sd0 {
    status = "okay";
    io_fixed_1v8;           // Configure MMC0 as 1.8V IO
    rx_delay_line = <0x0d>;
    tx_delay_line = <0x40>;
};
```

#### Step 2: Switch Device Tree

Modify `buildroot-overlay/configs/k230_test_defconfig`:
Change BR2_LINUX_KERNEL_INTREE_DTS_NAME to "canaan/k230-test"

```makefile
BR2_LINUX_KERNEL_INTREE_DTS_NAME="canaan/k230-test"
```

#### Step 3: Modify Kernel Configuration File

Refer to the [Kernel Configuration File Modification](#kernel-config-modification) section above.

---

## Development Board OTP Burning

### OTP Description

K230/K230D integrates a One Time Programmable (OTP) device internally. This device can store permanent binding information such as MAC, boot parameters, etc. Usually, we store the boot configuration in it.

> **!!! Burning incorrect OTP or firmware voltage configuration that does not match the hardware configuration may cause the chip to be burned out!!!**

### Automatically Generate OTP Configuration bin File Based on Hardware Settings

Canaan provides a convenient graphical WEB interface to automatically generate the OTP configuration bin file. During this process, it is essential to fully communicate with the hardware engineer to clarify hardware settings and voltage settings and other key information.

Configuration tool link: [OTP Configuration Tool](https://www.kendryte.com/zh/tools/otp_config_generation_tool)

![otp_tool](https://www.kendryte.com/api/post/attachment?id=551)

When generating the bin file, you need to carefully select the corresponding configuration based on the hardware schematic:

- UART IOMUX used by BOOT ROM printing: This option is used to select the serial port for BOOT log output (it is recommended to prioritize UART0)
- UART voltage used by BOOT ROM printing: The voltage used by the BOOT output serial port
- OSPI IO voltage: Voltage of the OSPI domain
- SDIO0 IO voltage: Voltage of the MMC0 domain
- SDIO1 IOMUX: Pins selected by MMC1
- SDIO1 IO voltage: Voltage of the MMC1 domain

Taking the 01Studio development board schematic as an example, the options can be determined based on these parts:

![1740391481653](https://www.kendryte.com/api/post/attachment?id=802)

![1740391571191](https://www.kendryte.com/api/post/attachment?id=560)

![1740391632742](https://www.kendryte.com/api/post/attachment?id=561)

![1740391686205](https://www.kendryte.com/api/post/attachment?id=562)
Based on the above information, the OTP configuration for 01Studio should be as follows
![01studio](https://www.kendryte.com/api/imagecdn/zh/01studio_otp.png)

Special reminder: Be sure to repeatedly verify the accuracy of the configuration with the hardware engineer. Once the configuration is incorrect and the burning operation is performed, it is very likely to cause permanent damage to the chip, which cannot be repaired!

After completing the above configuration, click the "Generate Configuration File" button to generate a bin file, as shown in the example below:

![1740392534136](https://www.kendryte.com/api/post/attachment?id=565)

>If the interface prompts "The settings are consistent with the default configuration, no need to generate a configuration file", it means that the default OTP can work and there is no need to re-burn the OTP. Please skip the OTP burning chapter.

### Burn OTP bin File

Burning tool download link: [Kendryte Developer Community - Resource Download](https://www.kendryte.com/zh/resource/download_tool,k230)

Please select the corresponding version for download according to the operating system you are using. At the same time, please be sure to note: Do not power the development board for a long time before the OTP burning is completed, to avoid chip burning.

![1740392907598](https://www.kendryte.com/api/imagecdn/zh/otp_burn.png)

Power on the chip, connect the UART0 interface, open the BurningTool software, and select the previously generated bin file:

![1740396173639](https://www.kendryte.com/api/post/attachment?id=568)

Click the "Start" button and patiently wait for the burning process to finish:

![1740469056238](https://www.kendryte.com/api/post/attachment?id=569)

After burning is complete, click "Confirm".

---

<a id="appendix-a-iomux-pin-configuration"></a>

## Appendix A: IOMUX Pin Configuration Description
>
>This chapter describes the iomux configuration under uboot
>For iomux under linux, please refer to [K230 linux IOMUX Guide](../app_develop_guide/driver/iomux.md)
>
### Configuration Principles

- IOMUX configuration needs to refer to the board schematic and **[iomux table](https://kendryte-download.canaan-creative.com/developer/k230/HDK/K230%E7%A1%AC%E4%BB%B6%E6%96%87%E6%A1%A3/K230_PINOUT_V1.2_20240822.xlsx)**
- Unused pins are recommended to be configured as GPIO to avoid function conflicts

### Configuration Parameter Description

The following uses IO7 configured as I2C4_SCL as an example:

```c
(IO7) (2<<SEL | 0<<SL | BANK_VOLTAGE_IO2_IO13<<MSC | 1<<IE | 1<<OE | 1<<PU | 0<<PD | 7<<DS | 1<<ST)
```

| Parameter | Description | Example |
| ------- | ------------------------------------------------------- | ---------------------------- |
| **SEL** | Function number selection, starting from 0 (Function Number - 1 in the iomux table) | I2C4_SCL corresponds to `2<<SEL` |
| **SL**  | Output slew rate control, configurable only for IO0/IO1 single voltage PAD | `0<<SL` |
| **MSC** | Operating voltage configuration, must be consistent with the board BANK power supply | `BANK_VOLTAGE_IO2_IO13<<MSC` |
| **IE**  | Input enable, 0 means input direction is invalid | `1<<IE` |
| **OE**  | Output enable, 0 means output direction is invalid | `1<<OE` |
| **PU**  | Pull-up configuration, recommended to enable for I2C and other buses | `1<<PU` |
| **PD**  | Pull-down configuration, related to functional requirements | `0<<PD` |
| **DS**  | Drive strength configuration, IO2~IO63 are all dual voltage PADs (16 drive) | `7<<DS` |
| **ST**  | Schmitt trigger configuration, generally configured as 1 | `1<<ST` |

![Pull Resistor](https://www.kendryte.com/api/post/attachment?id=443)

![Drive Strength](https://www.kendryte.com/api/post/attachment?id=442)

![Voltage Levels](https://www.kendryte.com/api/post/attachment?id=441)

### Drive Strength Description

- **Single voltage PAD**: 8 drive, 3bit effective, value range `0x0~0x7`
- **Dual voltage PAD (IO2~IO63)**: 16 drive, 4bit effective, value range `0x0~0xF`
