本文章為《STM32MP157 Linux系統移植開發篇》系列中的一篇,筆者使用的開發平台為華清遠見FS-MP1A開發闆(STM32MP157開發闆)。stm32mp157是ARM雙核,2個A7核,1個M4核,A7核上可以跑Linux作業系統,M4核上可以跑FreeRTOS、RT-Thread等實時作業系統,STM32MP157開發闆是以既可以學嵌入式linux,也可以學stm32單片機。 針對FS-MP1A開發闆,除了Linux系統移植篇外,還包括其他多系列教程,包括Cortex-A7開發篇、Cortex-M4開發篇、擴充闆驅動移植篇、Linux應用開發篇、FreeRTOS系統移植篇、Linux驅動開發篇、硬體設計篇、人工智能機器視覺篇、Qt應用程式設計篇、Qt綜合項目實戰篇等。歡迎關注,更多stm32mp157開發教程及視訊,可加技術交流Q群459754978,感謝關注。 關于FS-MP1A開發闆: 手機淘寶分享碼:複制本行文字打開手淘₤T4FPXn3YYJ2₤ 連結:https://item.taobao.com/item.htm?id=622457259672
1.實驗原理
參考原理圖可知eMMC使用的是sdmmc2總線,目前所使用的裝置樹檔案中沒有sdmmc2的支援,是以需要增加相關内容才能正常驅動eMMC。

由于在使STM32MP1晶片很多管腳為多功能複用管腳,且很多管腳具備同樣的功能,是以移植eMMC時需要确認硬體設計是使用的是那些管腳,根據原理圖确認後管腳對應關系為:
原理圖網絡編号 | 對應管腳 | 管腳功能 | 管腳功能碼 |
SD2_DATA0 | PB14 | SDMMC2_D0 | AF9 |
SD2_DATA1 | PB15 | SDMMC2_D1 | AF9 |
SD2_DATA2 | PB3 | SDMMC2_D2 | AF9 |
SD2_DATA3 | PB4 | SDMMC2_D3 | AF9 |
SD2_DATA4 | PA8 | SDMMC2_D4 | AF9 |
SD2_DATA5 | PA9 | SDMMC2_D5 | AF10 |
SD2_DATA6 | PE5 | SDMMC2_D6 | AF9 |
SD2_DATA7 | PD3 | SDMMC2_D7 | AF9 |
SD2_CLK | PE3 | SDMMC2_CK | AF9 |
SD2_CMD | PG6 | SDMMC2_CMD | AF10 |
- eMMC裝置樹節點
參考文檔:
Documentation/devicetree/bindings/mmc/mmc-controller.yaml
Documentation/devicetree/bindings/mmc/mmci.txt
核心中ST對STM32MP15x系列晶片的裝置樹資源了做了定義,可參見:
arch/arm/boot/dts/stm32mp151.dtsi
stm32mp151中sdmmc2定義如下:
sdmmc2: [email protected] {
compatible = "arm,pl18x", "arm,primecell";
arm,primecell-periphid = <0x00253180>;
reg = <0x58007000 0x1000>, <0x58008000 0x1000>;
interrupts = <GIC_SPI 124 IRQ_TYPE_LEVEL_HIGH>;
interrupt-names = "cmd_irq";
clocks = <&rcc SDMMC2_K>;
clock-names = "apb_pclk";
resets = <&rcc SDMMC2_R>;
cap-sd-highspeed;
cap-mmc-highspeed;
max-frequency = <120000000>;
status = "disabled";
};
上述代碼隻對sdmmc2做了基本的初始化,并沒有針對不同的硬體設計做适配,是以需結合硬體補全裝置樹節點資訊。
eMMC有8根資料線,且eMMC無需熱插拔等功能,結合硬體資訊添加sdmmc2節點資訊,也可參考核心中其他裝置樹檔案中相關描述,比如stm32mp15xx-edx.dtsi關于sdmmc2的描述符合我們的要求,内容如下:
&sdmmc2 {
pinctrl-names = "default", "opendrain", "sleep";
pinctrl-0 = <&sdmmc2_b4_pins_a &sdmmc2_d47_pins_a>;
pinctrl-1 = <&sdmmc2_b4_od_pins_a &sdmmc2_d47_pins_a>;
pinctrl-2 = <&sdmmc2_b4_sleep_pins_a &sdmmc2_d47_sleep_pins_a>;
non-removable;
no-sd;
no-sdio;
st,neg-edge;
bus-width = <8>;
vmmc-supply = <&v3v3>;
vqmmc-supply = <&vdd>;
mmc-ddr-3_3v;
status = "okay";
};
- 管腳定義
在核心中STM32MP1預設管腳定義在檔案arch/arm/dts/stm32mp15-pinctrl.dtsi中,檢視檔案中是否有需要的管腳定義:
檢視後确認有sdmmc2的管腳定義,且與FS-MP1A硬體使用情況一緻,定義如下:
sdmmc2_b4_pins_a: sdmmc2-b4-0 {
pins1 {
pinmux = <STM32_PINMUX('B', 14, AF9)>,
<STM32_PINMUX('B', 15, AF9)>,
<STM32_PINMUX('B', 3, AF9)>,
<STM32_PINMUX('B', 4, AF9)>,
<STM32_PINMUX('G', 6, AF10)>;
slew-rate = <1>;
drive-push-pull;
bias-pull-up;
};
pins2 {
pinmux = <STM32_PINMUX('E', 3, AF9)>;
slew-rate = <2>;
drive-push-pull;
bias-pull-up;
};
};
sdmmc2_b4_od_pins_a: sdmmc2-b4-od-0 {
pins1 {
pinmux = <STM32_PINMUX('B', 14, AF9)>,
<STM32_PINMUX('B', 15, AF9)>,
<STM32_PINMUX('B', 3, AF9)>,
<STM32_PINMUX('B', 4, AF9)>;
slew-rate = <1>;
drive-push-pull;
bias-pull-up;
};
pins2 {
pinmux = <STM32_PINMUX('E', 3, AF9)>;
slew-rate = <2>;
drive-push-pull;
bias-pull-up;
};
pins3 {
pinmux = <STM32_PINMUX('G', 6, AF10)>;
slew-rate = <1>;
drive-open-drain;
bias-pull-up;
};
};
sdmmc2_b4_sleep_pins_a: sdmmc2-b4-sleep-0 {
pins {
pinmux = <STM32_PINMUX('B', 14, ANALOG)>,
<STM32_PINMUX('B', 15, ANALOG)>,
<STM32_PINMUX('B', 3, ANALOG)>,
<STM32_PINMUX('B', 4, ANALOG)>,
<STM32_PINMUX('E', 3, ANALOG)>,
<STM32_PINMUX('G', 6, ANALOG)>;
};
};
sdmmc2_b4_pins_b: sdmmc2-b4-1 {
pins1 {
pinmux = <STM32_PINMUX('B', 14, AF9)>,
<STM32_PINMUX('B', 15, AF9)>,
<STM32_PINMUX('B', 3, AF9)>,
<STM32_PINMUX('B', 4, AF9)>,
<STM32_PINMUX('G', 6, AF10)>;
slew-rate = <1>;
drive-push-pull;
bias-disable;
};
pins2 {
pinmux = <STM32_PINMUX('E', 3, AF9)>;
slew-rate = <2>;
drive-push-pull;
bias-disable;
};
};
sdmmc2_b4_od_pins_b: sdmmc2-b4-od-1 {
pins1 {
pinmux = <STM32_PINMUX('B', 14, AF9)>,
<STM32_PINMUX('B', 15, AF9)>,
<STM32_PINMUX('B', 3, AF9)>,
<STM32_PINMUX('B', 4, AF9)>;
slew-rate = <1>;
drive-push-pull;
bias-disable;
};
pins2 {
pinmux = <STM32_PINMUX('E', 3, AF9)>;
slew-rate = <2>;
drive-push-pull;
bias-disable;
};
pins3 {
pinmux = <STM32_PINMUX('G', 6, AF10)>;
slew-rate = <1>;
drive-open-drain;
bias-disable;
};
};
sdmmc2_d47_pins_a: sdmmc2-d47-0 {
pins {
pinmux = <STM32_PINMUX('A', 8, AF9)>,
<STM32_PINMUX('A', 9, AF10)>,
<STM32_PINMUX('E', 5, AF9)>,
<STM32_PINMUX('D', 3, AF9)>;
slew-rate = <1>;
drive-push-pull;
bias-pull-up;
};
};
sdmmc2_d47_sleep_pins_a: sdmmc2-d47-sleep-0 {
pins {
pinmux = <STM32_PINMUX('A', 8, ANALOG)>,
<STM32_PINMUX('A', 9, ANALOG)>,
<STM32_PINMUX('E', 5, ANALOG)>,
<STM32_PINMUX('D', 3, ANALOG)>;
};
};
2.實驗目的
熟悉基于Linux作業系統下的塊裝置驅動移植配置過程。
3.實驗平台
華清遠見開發環境,FS-MP1A平台;
4.實驗步驟
1.導入交叉編譯工具鍊
[email protected]:$ source /opt/st/stm32mp1/3.1-openstlinux-5.4-dunfell-mp1-20-06-24/environment-setup-cortexa7t2hf-neon-vfpv4-ostl-linux-gnueabi
2.添加eMMC裝置樹配置
修改arch/arm/boot/dts/stm32mp15xx-fsmp1x.dtsi檔案
在原有sdmmc1節點下添加如下内容:
&sdmmc2 {
pinctrl-names = "default", "opendrain", "sleep";
pinctrl-0 = <&sdmmc2_b4_pins_a &sdmmc2_d47_pins_a>;
pinctrl-1 = <&sdmmc2_b4_od_pins_a &sdmmc2_d47_pins_a>;
pinctrl-2 = <&sdmmc2_b4_sleep_pins_a &sdmmc2_d47_sleep_pins_a>;
non-removable;
no-sd;
no-sdio;
st,neg-edge;
bus-width = <8>;
vmmc-supply = <&v3v3>;
vqmmc-supply = <&vdd>;
mmc-ddr-3_3v;
status = "okay";
};
3.配置核心
由于核心源碼預設配置已經支援eMMC,本節列出主要選項,如下
[email protected]:$ make menuconfig
Device Drivers --->
<*> MMC/SD/SDIO card support --->
[*] STMicroelectronics STM32 SDMMC Controller
4.編譯核心級裝置樹:
[email protected]:$ make -j4 uImage dtbs LOADADDR=0xC2000040
5.重新開機測試
将編譯好的裝置樹和核心鏡像拷貝到/tftpboot目錄下,通過tftp引導核心,重新開機裝置後可以看到如下啟動資訊:
由于eMMC中有出廠預
裝的FS-MP1A系統,是以可以正常完成檔案系統挂載進入系統:
硬體平台:華清遠見FS-MP1A開發闆(STM32MP157)
部分開發教程下載下傳:加QQ群459754978,群檔案裡有。
部分視訊課程收看:華清遠見研發中心的個人空間_哔哩哔哩_Bilibili
淘寶購買連結:華清遠見stm32mp157 linux開發闆stm32單片機arm開發嵌入式學習闆