精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

實戰演練:設備樹(DTS)語法詳解 + LED控制實戰

開發 前端
在嵌入式系統的廣袤天地中,設備樹(Device Tree)宛如一座橋梁,橫跨在硬件與軟件之間,承擔著至關重要的溝通使命。

在嵌入式開發領域,設備樹(Device Tree)扮演著極為關鍵的角色。它如同一份精準的硬件說明書,讓操作系統能夠清晰識別并高效管理硬件資源。當我們著手為自定義硬件編寫設備樹時,就如同為新成員量身定制一套專屬 “檔案”,確保其能無縫融入系統 “大家庭”。

想象一下,你精心設計了一款獨特的硬件,滿心期待它在系統中發揮作用。但如果沒有正確編寫設備樹,操作系統很可能對其 “視而不見”,讓你的心血難以充分施展。那么,如何才能為自定義硬件編寫正確的設備樹呢?

接下來,我們將通過一系列實戰演練,帶你逐步攻克這一技術要點,從了解硬件配置的基礎信息,到精準修改設備樹源文件,再到生成可被系統讀取的二進制文件等,每一步都為你詳細拆解,助你在自定義硬件開發之路上穩步前行 。

一、設備樹初印象:為何而生?

在嵌入式系統的廣袤天地中,設備樹(Device Tree)宛如一座橋梁,橫跨在硬件與軟件之間,承擔著至關重要的溝通使命。在設備樹出現之前,嵌入式系統的開發可沒少讓開發者們頭疼。就拿 ARM 架構來說,不同開發板的硬件信息就像一團亂麻,緊緊地與內核代碼交織在一起。想象一下,每更換一次開發板,那密密麻麻的內核代碼就得大改特改,移植工作不僅繁瑣,還極易出錯,維護成本更是高得嚇人。

為了化解這些難題,設備樹應運而生。它最早在 PowerPC 架構中嶄露頭角,隨后便在 ARM、MIPS 等多種架構中廣泛應用,迅速成為嵌入式開發的得力助手。設備樹的核心使命,就是將硬件描述從內核代碼中剝離出來,實現兩者的解耦。如此一來,內核變得更加通用,開發板相關的特定信息則由設備樹文件專門負責描述。當我們要將內核移植到新的開發板時,只需對設備樹文件進行修改,這極大地降低了移植的難度和工作量,就像是給復雜的開發工作找到了一條捷徑。

舉個例子,在一個基于 ARM 架構的智能家居控制系統開發中,以往若要適配不同廠家生產的開發板,每個開發板都有獨特的硬件配置,如不同的 GPIO 引腳分配、外設接口等。在沒有設備樹時,針對每一款開發板,內核代碼中都要硬編碼大量的硬件相關信息,這導致內核代碼臃腫不堪,且維護極為困難。一旦硬件稍有變動,例如更換了一個不同型號的傳感器,與之相連的引腳發生變化,就需要在冗長的內核代碼中四處尋找并修改相關配置,不僅容易遺漏,而且修改過程繁瑣,極易引入新的錯誤。

有了設備樹后,情況就大為不同。硬件相關信息被清晰地描述在設備樹文件中。若要適配新的開發板,或者更改硬件配置,只需在設備樹文件中相應節點處修改屬性值即可。比如,要更改傳感器連接的 GPIO 引腳,只需在設備樹中找到對應的傳感器節點,修改其 GPIO 屬性值,而無需對內核代碼進行大規模改動。這使得開發過程更加靈活高效,同時也提高了代碼的可維護性和可移植性 。

1.1設備樹在ARM架構的引入

在之前使用 S3C2440 開發板移植 Linux 3.4.2 內核時,修改了很多關于 c 文件去適配開發板,和開發板相關的文件放在arch/arm/mxch-xxx目錄下,因此 linux 內核 arm 架構下添加了很多開發板的適配文件:

圖片圖片

這些 c 文件僅僅用來適配某款開發板,對于 Linux 內核來說并沒有提交什么新功能,但是每適配一款新的開發板就需要一堆文件,導致 Linux 內核越來越臃腫:

圖片圖片

終于 Linus 忍不住天天 merge 這些鬼東西,向 arm 社區發出了一封郵件,第一句話就足矣表現不滿:"This whole ARM thing is a f*cking pain in the ass"。

因此,Arm 社區開始引入之前 powerPC 架構就采用的設備樹,將描述這些板級信息的文件與 Linux 內核代碼分離,Linux 4.x 版本幾乎都支持設備樹,所有開發板的設備樹文件統一放在arch/arm/boot/dts目錄中。

1.2什么是設備樹

設備樹全稱 Device Tree,是一種數據結構,用來描述板級設備信息,比如 CPU 數量、外設基地址、總線設備等,如圖:

圖片圖片

DTS、DTB、DTC三種文件的區別

  • DTS 是設備樹源碼文件
  • DTB 是將DTS 編譯以后得到的二進制文件
  • DTC工具是將dts文件變成編譯成dtb的工具,就像.c文件變成成.o需要用到gcc編譯器一樣。

1.3 設備樹編譯

①簡單粗暴,編譯內核

make

②編譯全部設備樹文件

make dtbs

③編譯指定的設備樹文件

make <xxx.dtb>

二、設備樹語法

2.1設備樹相關術語全解析

在深入探索設備樹的世界之前,先來認識一下那些頻繁出現的術語,它們就像是開啟設備樹大門的鑰匙。

DT(Device Tree,設備樹):這是一種用于描述計算機系統硬件布局的數據結構,它將系統中的各類硬件組件及其連接關系,以層次化的樹狀結構呈現出來??梢园阉胂蟪墒怯布?“戶口簿”,詳細記錄著每個硬件設備的 “身份信息” 以及它們之間的 “親屬關系” ,為內核提供了清晰的硬件信息,讓內核能夠有條不紊地初始化和操作硬件設備。

FDT(Flattened Device Tree,扁平設備樹):FDT 是設備樹的二進制表示形式,就像是設備樹的 “壓縮包”。它由設備樹編譯器(dtc)精心打造而成,是 dts 文件編譯后的產物。這種緊湊的存儲方式,使其在系統啟動時能夠快速加載和解析,大大提高了系統啟動的效率 ,就好比將一本厚厚的書壓縮成了一個小巧的文件,攜帶和讀取都更加便捷。

dts(Device Tree Source,設備樹源文件):dts 文件是設備樹的源文件,以通俗易懂的文本格式編寫,是硬件開發人員或系統集成商施展拳腳的舞臺。他們通過編寫 dts 文件,詳細描述系統中的硬件設備及其屬性,就像建筑師繪制建筑藍圖一樣,為后續的硬件實現和系統開發奠定基礎。這個文件就像是設備樹的 “初稿”,記錄著最原始的硬件描述信息。

dtsi(Device Tree Source Include,設備樹源包含文件):dtsi 文件類似于編程中的頭文件,是設備樹源文件的得力助手。它通常包含一些被多個 dts 文件共享的硬件描述,通過 #include 指令巧妙地融入到具體的 dts 文件中。這樣一來,不僅避免了重復代碼,還讓硬件描述的管理和維護變得更加輕松,就像是一個公共的資源庫,各個 dts 文件都可以按需取用其中的內容 。

dtb(Device Tree Blob,設備樹二進制文件):dtb 文件是 dts 文件經過編譯后生成的二進制文件,包含了設備樹的扁平表示形式(FDT)。在系統啟動的關鍵時刻,引導加載程序(如 U-Boot)會將 dtb 文件從存儲設備中加載到內存,并恭敬地傳遞給操作系統內核。內核則依據 dtb 文件中描述的信息,對硬件進行初始化操作,它就像是一份被加密后的硬件說明書,只有內核能夠讀懂并依據它來配置硬件 。

dtc(Device Tree Compiler,設備樹編譯器):dtc 是設備樹世界中的 “翻譯官”,它肩負著將 dts 文件編譯為 dtb 文件的重任。不僅如此,在調試和修改設備樹時,它還能將 dtb 文件反編譯為 dts 文件,為開發者提供了極大的便利。就好比一個語言專家,能夠在不同格式的設備樹文件之間自由轉換 。

這些術語相互協作,共同構建起設備樹的生態系統。dts 和 dtsi 文件是設備樹的源代碼基礎,dtc 編譯器將它們轉換為內核能夠識別的 dtb 文件,而 FDT 則是 dtb 文件內部的一種高效存儲結構,DT 則是整個硬件描述概念的統稱 。

2.2設備樹源碼藏身何處

在 Linux 內核源碼的龐大體系中,設備樹源碼有著自己專屬的 “棲息地”。對于 32 位系統而言,設備樹源碼通常存放在 “源碼 /arch/arm/boot/dts” 目錄下;而在 64 位系統中,它們則位于 “源碼 /arch/arm64/boot/dts” 目錄 。

在這些目錄中,你能找到眾多以.dts 和.dtsi 為擴展名的文件,它們就像是隱藏在代碼海洋中的寶藏,記錄著硬件設備的詳細信息 。不同架構的設備樹文件存放位置和命名規則可能會略有差異,所以在探索時,一定要查閱對應架構的文檔或源碼,這樣才能準確找到所需的設備樹文件 。

2.3DTC 工具的神奇用法

DTC 工具作為設備樹編譯和反編譯的利器,掌握它的使用方法至關重要。下面就來看看如何使用 DTC 工具進行設備樹的編譯和反編譯操作 。

(1)編譯設備樹

基本的編譯命令格式為 “dtc -I dts -O dtb -o output_file.dtb input_file.dts”。其中,“dtc” 是調用設備樹編譯器;“-I dts” 明確指定輸入文件的格式為設備樹源文件(DTS),就像是告訴編譯器要處理的是哪種類型的 “原材料”;“-O dtb” 指定輸出文件的格式為設備樹二進制文件(DTB),也就是確定了 “成品” 的格式;“-o output_file.dtb” 則指定了輸出文件的名稱,讓編譯器知道要把生成的文件保存成什么名字;“input_file.dts” 自然就是指定輸入的設備樹源文件了 。

例如,我們有一個名為 “my_device.dts” 的設備樹源文件,想要將其編譯成二進制文件 “my_device.dtb”,就可以在命令行中輸入 “dtc -I dts -O dtb -o my_device.dtb my_device.dts”,按下回車鍵,DTC 工具就會迅速行動,將 dts 文件編譯成 dtb 文件 。

(2)反編譯設備樹

反編譯的命令格式為 “dtc -I dtb -O dts -o example.dts example.dtb”。這里的參數含義與編譯時類似,只是輸入和輸出的格式進行了互換?!?I dtb” 表示輸入文件是設備樹二進制文件(DTB),“-O dts” 表示輸出文件為設備樹源文件(DTS) 。

假設我們有一個 “example.dtb” 的二進制文件,想要查看其原始的設備樹描述內容,就可以使用 “dtc -I dtb -O dts -o example.dts example.dtb” 命令,將 dtb 文件反編譯成 dts 文件,方便我們進行查看和修改 。

在實際操作過程中,還可能會用到其他一些參數。比如,“-q” 參數可以讓編譯過程更加安靜,減少不必要的提示信息;“-i” 參數可以添加搜索包含文件的路徑,方便在編譯時找到所需的 dtsi 文件等 。掌握這些參數的用法,能夠讓我們更加靈活地使用 DTC 工具,應對各種設備樹處理的需求 。

三、深入設備樹語法殿堂

3.1節點:設備樹的基石

節點是設備樹的基本組成單元,就像是樹狀結構中的一個個 “樹枝分叉點” ,每個節點都代表著一個硬件設備或組件。節點的命名遵循特定規則,通常以 “node-name@unit-address” 的形式出現 。其中,“node-name” 是節點的名稱,一般由字母、數字和下劃線組成,用來描述節點所代表的設備類型或功能,如 “uart” 代表串口設備,“i2c” 代表 I2C 總線設備等 。

“unit-address” 則是設備的單元地址,通常表示設備在內存空間或總線上的地址,像 “0x10000000” 這樣的十六進制數,它與設備的 “reg” 屬性密切相關 。若節點沒有地址相關信息,“@unit-address” 部分可以省略 。

每個節點內部可以包含多個屬性和子節點。屬性以鍵值對的形式存在,用于描述節點的各種特性;子節點則進一步細化硬件設備的層次結構 。例如,在描述一個 SPI 控制器時,可能會有如下節點:

spi@12340000 {
    compatible = "fsl,imx6ul-spi";
    reg = <0x12340000 0x1000>;
    interrupts = <GIC_SPI 32 IRQ_TYPE_LEVEL_HIGH>;
    #address-cells = <1>;
    #size-cells = <0>;

    spi_device: spi@0 {
        compatible = "my_spi_device";
        reg = <0>;
        spi-max-frequency = <5000000>;
    };
};

在這個例子中,“spi@12340000” 是 SPI 控制器節點,包含了描述其兼容性、地址、中斷等屬性 。而 “spi_device: spi@0” 則是 SPI 控制器下的一個子節點,表示連接在該 SPI 總線上的一個設備,有自己的兼容性、設備地址和最大工作頻率等屬性 。

3.2屬性:描述設備的關鍵

屬性是節點的重要組成部分,以 “name = value” 的形式存在,用于詳細描述節點所代表設備的各種特性 。屬性的值可以是多種數據類型,常見的有以下幾種:

  1. 32 位無符號整數:用尖括號 “<>” 括起來,如 “interrupts = <17 0xc>”,表示該設備的中斷號為 17,觸發方式為 0xc(具體含義根據中斷控制器的定義) 。
  2. 字符串:用雙引號 “""” 括起來,如 “compatible ="arm,cortex-a7"”,“compatible” 屬性用于驅動與設備的匹配,這里表示該設備與 “arm,cortex-a7” 類型兼容 。
  3. 字節數組:用方括號 “[]” 括起來,每個字節用兩個十六進制數表示,如 “local-mac-address = [00 00 12 34 56 78]”,用于表示設備的本地 MAC 地址 。
  4. 復合類型:可以是多種值的組合,用逗號 “,” 隔開,如 “example = <0xf00f0000 19>, "a strange property format"” 。

在眾多屬性中,“compatible” 和 “reg” 屬性尤為常用 ?!癱ompatible” 屬性就像是設備的 “身份證”,用于設備與驅動程序的匹配 。內核在尋找設備驅動時,會根據設備節點的 “compatible” 屬性值,在驅動列表中查找與之匹配的驅動 。例如,“compatible = "fsl,imx6ul-spi", "spi-gpio"”,表示該設備首先嘗試匹配 “fsl,imx6ul-spi” 驅動,若找不到,則嘗試匹配 “spi-gpio” 驅動 。

“reg” 屬性用于描述設備的寄存器地址范圍,其值是一系列的 “address size” 對 ?!癮ddress” 表示設備寄存器的起始地址,“size” 表示地址范圍的大小 。這兩個值的表示方式由其父節點的 “#address-cells” 和 “#size-cells” 屬性決定 。比如,在下面的例子中:

soc {
    #address-cells = <1>;
    #size-cells = <1>;

    spi@12340000 {
        reg = <0x12340000 0x1000>;
        ...
    };
};

由于 “soc” 節點的 “#address-cells = <1>” 和 “#size-cells = <1>”,所以 “spi@12340000” 節點的 “reg” 屬性中,“0x12340000” 用 1 個 32 位整數表示起始地址,“0x1000” 用 1 個 32 位整數表示地址范圍大小 。

3.3包含文件:代碼復用的利器

在設備樹開發中,為了提高代碼的復用性和可維護性,常常會使用包含文件(dtsi) 。dtsi 文件類似于 C 語言中的頭文件,用于存放被多個 dts 文件共享的設備樹描述 。通過使用包含文件,可以避免在多個 dts 文件中重復編寫相同的硬件描述代碼 。

在 dts 文件中,可以使用 “#include” 指令來引用 dtsi 文件 。例如:

#include "common.dtsi"

這樣,“common.dtsi” 文件中的內容就會被包含到當前 dts 文件中 。除了 dtsi 文件,設備樹源文件也可以包含標準的 C 頭文件(.h) 。這在需要使用一些宏定義或常量時非常方便 。例如,在 dts 文件中可能會包含如下頭文件:

#include <dt-bindings/gpio/gpio.h>

通過包含這個頭文件,可以在設備樹中使用其中定義的 GPIO 相關宏,如 “GPIO_ACTIVE_HIGH”“GPIO_ACTIVE_LOW” 等 。這樣不僅提高了代碼的可讀性,還減少了人為錯誤 。

3.4節點路徑:精準定位節點

在設備樹這個龐大的 “家族樹” 中,每個節點都有其唯一的路徑,就像每個人在家族族譜中都有獨特的位置標識一樣 。節點路徑是從根節點開始,通過各級子節點的名稱和地址,以 “/” 分隔組成的 。例如,對于前面提到的 SPI 控制器節點,其路徑為 “/soc/spi@12340000” 。

通過節點路徑,我們可以在設備樹中精準地訪問特定節點 。在 Linux 內核中,提供了一系列函數來通過節點路徑查找節點 。例如,“of_find_node_by_path (const char *path)” 函數,它接收一個節點路徑作為參數,返回對應節點的指針 。假設我們要獲取 SPI 控制器節點的信息,就可以使用如下代碼:

#include <linux/of.h>
#include <linux/device.h>

struct device_node *spi_node;
spi_node = of_find_node_by_path("/soc/spi@12340000");
if (spi_node) {
    // 在這里可以對找到的節點進行操作,如獲取屬性等
    of_node_put(spi_node);
}

在實際應用中,節點路徑常用于設備驅動開發 。驅動程序需要根據設備樹中節點的信息來初始化和操作硬件設備,通過節點路徑可以快速準確地找到對應的設備節點,從而獲取設備的屬性和配置信息 。

3.5別名:便捷訪問節點

別名就像是設備樹節點的 “昵稱”,為了更方便地訪問設備樹中的節點而存在 。通過定義別名,可以使用一個簡短的名稱來代替冗長的節點路徑 。別名的定義通常在設備樹的根節點下,使用 “aliases” 屬性 。例如:

aliases {
    spi0 = &spi@12340000;
    uart1 = &uart@101f0000;
};

在這個例子中,為 “spi@12340000” 節點定義了別名 “spi0”,為 “uart@101f0000” 節點定義了別名 “uart1” 。這樣,在設備樹的其他部分,或者在驅動程序中,就可以使用這些別名來代替完整的節點路徑 。例如,在驅動程序中,可以使用 “of_find_node_by_phandle (of_parse_phandle (aliases, "spi0", 0))” 來通過別名 “spi0” 找到對應的 SPI 控制器節點 。

別名的使用不僅提高了設備樹的可讀性,還使代碼更加簡潔和易于維護 。特別是在大型設備樹中,當需要頻繁訪問某些節點時,使用別名可以大大減少代碼中冗長路徑的出現,降低出錯的概率 。

3.6復合節點與定義引用:復雜關系的處理

在描述復雜的硬件設備關系時,復合節點和定義引用發揮著重要作用 。復合節點是指一個節點可以包含多個子節點,這些子節點共同描述一個復雜的硬件設備或功能 。例如,在描述一個包含多個功能模塊的芯片時,可能會有如下復合節點:

chip@10000000 {
    compatible = "my_chip";
    reg = <0x10000000 0x10000>;

    module1: submodule@1000 {
        compatible = "module1_type";
        reg = <0x1000 0x100>;
    };

    module2: submodule@2000 {
        compatible = "module2_type";
        reg = <0x2000 0x200>;
    };
};

在這個例子中,“chip@10000000” 是一個復合節點,包含了 “module1” 和 “module2” 兩個子節點,分別描述芯片中的兩個不同功能模塊 。

定義引用則是通過 “&label” 的方式來引用其他節點 。例如,在前面的例子中,如果有另一個節點需要使用 “module1” 節點的信息,可以這樣引用:

other_node {
    depends_on = <&module1>;
    // 其他屬性和子節點
};

這里的 “depends_on = <&module1>” 表示 “other_node” 節點依賴于 “module1” 節點 。通過這種方式,可以清晰地表達硬件設備之間的依賴關系 。

在實際應用中,復合節點和定義引用常用于描述復雜的硬件系統,如片上系統(SoC) 。SoC 通常包含多個處理器核心、各種外設控制器等,通過復合節點和定義引用,可以準確地描述這些組件之間的層次結構和相互關系,為內核提供完整的硬件信息 。

四、實戰:設備樹實例深度剖析

4.1GPIO設備樹實例詳解

以某款基于 ARM 架構的開發板為例,其設備樹中 GPIO 設備樹節點如下:

gpio0: gpio@10000000 {
    compatible = "fsl,imx6ul-gpio", "gpio-generic";
    reg = <0x10000000 0x1000>;
    interrupts = <GIC_SPI 66 IRQ_TYPE_LEVEL_HIGH>;
    gpio-controller;
    #gpio-cells = <2>;
};

在這個節點中,“compatible” 屬性表明該 GPIO 控制器與 “fsl,imx6ul-gpio” 和 “gpio-generic” 兼容,這使得內核能夠準確找到與之匹配的驅動程序 ?!皉eg” 屬性指定了 GPIO 控制器的寄存器地址范圍,起始地址為 0x10000000,大小為 0x1000 字節 ?!癷nterrupts” 屬性描述了 GPIO 控制器的中斷信息,使用 GIC_SPI 類型的中斷,中斷號為 66,觸發方式為高電平觸發 。

“gpio-controller” 屬性標識該節點為 GPIO 控制器 ?!?gpio-cells = <2>” 則表示在引用該 GPIO 控制器時,需要兩個 32 位的參數 。第一個參數表示 GPIO 的編號,第二個參數表示 GPIO 的觸發類型 。例如,在其他節點中引用該 GPIO 控制器的某個引腳時,可能會這樣寫:

my_device {
    gpios = <&gpio0 10 GPIO_ACTIVE_HIGH>;
    ...
};

這里表示使用 “gpio0” 控制器的第 10 號引腳,觸發類型為高電平有效 。這種屬性設置方式,為系統中其他設備使用 GPIO 提供了清晰的規范和接口 。

4.2LED設備樹實例全解析

假設我們要在開發板上實現一個 LED 驅動,首先在設備樹中定義 LED 節點:

leds {
    compatible = "gpio-leds";
    pinctrl-names = "default";
    pinctrl-0 = <&led_pins>;

    led_red: red_led {
        label = "red_led";
        gpios = <&gpio1 18 GPIO_ACTIVE_LOW>;
        default-state = "off";
    };
};

pinctrl: pinctrl@10000400 {
    compatible = "fsl,imx6ul-pinctrl";
    reg = <0x10000400 0x1000>;

    led_pins: ledgrp {
        fsl,pins = <
            MX6UL_PAD_GPIO1_IO18__GPIO1_IO18 0x10b0
        >;
    };
};

在這個設備樹實例中,“leds” 節點的 “compatible = "gpio-leds"” 屬性表明這是一個基于 GPIO 的 LED 設備 ?!皃inctrl-names” 和 “pinctrl-0” 屬性用于引腳控制,通過引用 “led_pins” 節點來配置 LED 所使用的引腳 。

“led_red” 子節點定義了一個紅色 LED,“label” 屬性為其命名,“gpios” 屬性指定該 LED 連接到 “gpio1” 控制器的 18 號引腳,且為低電平有效 ?!癲efault-state = "off"” 表示 LED 默認處于熄滅狀態 。

在驅動開發中,內核驅動會根據 “compatible” 屬性找到對應的 LED 驅動程序 。在驅動的 probe 函數中,通過設備樹 API 函數來獲取設備樹節點信息 。例如,使用 “of_find_node_by_path” 函數找到 “leds” 節點,再通過 “of_get_child_by_name” 函數獲取 “led_red” 子節點 。

然后,利用 “of_property_read_u32_array” 函數讀取 “gpios” 屬性的值,從而獲取 LED 所連接的 GPIO 引腳信息 。最后,根據這些信息進行 GPIO 的初始化和 LED 的控制操作 。

4.3自定義設備樹節點與驅動匹配實例

假設我們要添加一個自定義的溫度傳感器設備,首先在設備樹中創建自定義節點:

temperature_sensor: sensor@1234 {
    compatible = "mycompany,temperature-sensor";
    reg = <0x1234 0x100>;
    sensor_type = "temperature";
    sampling_rate = <100>;
};

這個自定義節點 “temperature_sensor” 的 “compatible” 屬性設置為 “mycompany,temperature-sensor”,用于與驅動程序進行匹配 ?!皉eg” 屬性指定了傳感器的寄存器地址范圍 。“sensor_type” 和 “sampling_rate” 是自定義屬性,分別表示傳感器類型和采樣率 。

接下來編寫對應的內核驅動:

#include <linux/module.h>
#include <linux/platform_device.h>
#include <linux/of.h>

static int my_sensor_probe(struct platform_device *pdev) {
    struct device_node *np = pdev->dev.of_node;
    u32 reg_val, sampling_rate;
    const char *sensor_type;

    if (!np)
        return -EINVAL;

    // 讀取reg屬性
    if (of_property_read_u32(np, "reg", ?_val) != 0) {
        dev_err(&pdev->dev, "Failed to read reg property\n");
        return -EINVAL;
    }

    // 讀取sensor_type屬性
    if (of_property_read_string(np, "sensor_type", &sensor_type) != 0) {
        dev_err(&pdev->dev, "Failed to read sensor_type property\n");
        return -EINVAL;
    }

    // 讀取sampling_rate屬性
    if (of_property_read_u32(np, "sampling_rate", &sampling_rate) != 0) {
        dev_err(&pdev->dev, "Failed to read sampling_rate property\n");
        return -EINVAL;
    }

    // 這里可以根據讀取到的屬性進行傳感器的初始化和操作
    dev_info(&pdev->dev, "Sensor initialized: reg = 0x%x, type = %s, sampling_rate = %d\n", reg_val, sensor_type, sampling_rate);

    return 0;
}

static int my_sensor_remove(struct platform_device *pdev) {
    // 清理操作
    return 0;
}

static const struct of_device_id my_sensor_of_match[] = {
    {.compatible = "mycompany,temperature-sensor"},
    {},
};
MODULE_DEVICE_TABLE(of, my_sensor_of_match);

static struct platform_driver my_sensor_driver = {
   .probe = my_sensor_probe,
   .remove = my_sensor_remove,
   .driver = {
       .name = "mycompany-temperature-sensor-driver",
       .of_match_table = my_sensor_of_match,
    },
};

module_platform_driver(my_sensor_driver);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("Your Name");
MODULE_DESCRIPTION("Custom Temperature Sensor Driver");

在這個驅動程序中,“my_sensor_of_match” 數組用于匹配設備樹中自定義節點的 “compatible” 屬性 。“my_sensor_probe” 函數在設備探測時被調用,通過設備樹 API 函數讀取設備樹節點的屬性信息,并進行相應的初始化操作 。這樣,通過 “compatible” 屬性,設備樹中的自定義節點與內核驅動成功匹配,驅動能夠正確解析設備樹屬性并對設備進行控制 。

責任編輯:武曉燕 來源: 深度Linux
相關推薦

2022-12-21 14:39:35

機器學習案發決策樹

2024-08-09 10:15:34

2009-09-18 14:31:33

CLR觸發器

2024-10-29 11:54:25

2022-08-25 09:00:00

Python編程語言開源庫

2012-11-09 09:35:18

Win 8

2024-08-05 09:31:00

MySQLDTS數據

2025-06-26 04:00:00

Spring數據綁定技術

2024-08-07 08:32:30

2010-05-26 18:16:31

MySQL數據庫安裝

2024-07-17 08:17:20

2024-11-22 09:21:18

WinForm

2025-11-17 00:00:55

2023-02-10 14:54:20

編譯工具cmake

2010-01-21 11:51:11

2017-04-26 08:51:36

MongoDB集群實戰

2023-11-07 10:22:26

自動駕駛技術

2024-07-15 09:13:48

2017-11-23 15:24:35

Python速覽實戰

2024-05-20 08:31:33

檢索增強生成LLM大型語言模型
點贊
收藏

51CTO技術棧公眾號

91视频99| 亚洲无限av看| 日韩精品一区在线视频| 天天干天天爱天天操| 亚洲女同在线| 久久精品视频在线观看| 成人在线电影网站| 精品三区视频| 一卡二卡三卡日韩欧美| 麻豆91蜜桃| www.国产.com| 日本中文在线一区| 欧美国产欧美亚洲国产日韩mv天天看完整| 国产网站无遮挡| 欧洲一区在线| 欧美在线视频全部完| 好色先生视频污| 精品三级久久久久久久电影聊斋| 国产精品1024| 国产精品欧美日韩| 丰满少妇乱子伦精品看片| 欧美黄色录像片| 亚洲精品自在久久| 日本泡妞xxxx免费视频软件| 欧美专区福利免费| 午夜免费久久看| 艳母动漫在线观看| 国产女主播在线直播| 成人a免费在线看| 成人免费自拍视频| 中文字幕日日夜夜| 亚洲欧美日本日韩| 国模极品一区二区三区| 国产亚洲人成a一在线v站| 欧美性色黄大片人与善| 亚洲国产成人一区二区| 久久99这里只有精品| 日本午夜在线亚洲.国产| 国产一级在线播放| 欧美淫片网站| 日韩中文字幕在线看| 中文字幕av久久爽一区| 一本久久青青| 亚洲欧洲午夜一线一品| 狠狠人妻久久久久久综合蜜桃| 试看120秒一区二区三区| 欧美精品tushy高清| 五月天婷婷亚洲| 国产精品99久久久久久董美香| 色综合咪咪久久| 97国产在线播放| 亚洲精品国产精品国产| 大伊人狠狠躁夜夜躁av一区| 极品粉嫩国产18尤物| 国产蜜臀在线| 亚洲成人精品一区| 国产美女主播在线播放| a级片免费在线观看| 亚洲一区二区在线观看视频| av一区二区三区免费观看| 日本在线观看高清完整版| 亚洲女子a中天字幕| ijzzijzzij亚洲大全| av免费在线免费| 一区二区日韩电影| 男人天堂手机在线视频| 国产白浆在线免费观看| 欧美午夜激情视频| 欧美丰满熟妇xxxxx| 粉嫩一区二区三区| 欧美日韩精品免费观看视频| 国产九九热视频| 国产一精品一av一免费爽爽| 欧美成人在线直播| 少妇精品无码一区二区三区| 亚洲男人都懂第一日本| 一区二区在线视频| 亚洲人做受高潮| 欧美精品成人| 欧美一区二区三区精品电影| 三级视频在线观看| 免费在线观看精品| 666精品在线| 瑟瑟在线观看| 国产精品免费观看视频| 337p亚洲精品色噜噜狠狠p| 8x8ⅹ拨牐拨牐拨牐在线观看| 亚洲h在线观看| 国产免费999| 日本一区二区三区播放| 亚洲精品自在久久| 卡通动漫亚洲综合| 国产亚洲精品v| 国产精品偷伦视频免费观看国产 | 全黄一级裸体片| 日韩理论片av| 韩国精品美女www爽爽爽视频| 国产精品suv一区| 国产一区二区在线免费观看| 国产一区二区三区色淫影院| 成在在线免费视频| 亚洲二区在线观看| www.污网站| 国产精品片aa在线观看| 在线日韩日本国产亚洲| 国产性猛交普通话对白| 美女免费视频一区二区| 精品国产乱码久久久久久88av| √天堂资源地址在线官网| 亚洲福利视频导航| 中文字幕第22页| 自拍偷拍一区| 91精品国产亚洲| 99国产揄拍国产精品| 国产视频一区在线播放| 免费高清一区二区三区| 欧美久久久网站| 亚洲色图综合网| 久久夜靖品2区| 国产精品自在欧美一区| 手机看片福利永久国产日韩| а√在线中文在线新版| 91精品国产综合久久精品性色 | 国产ts人妖调教重口男| 国产欧美日韩精品在线| 免费看一级大黄情大片| www.亚洲一二| 欧美大片va欧美在线播放| 在线观看国产精品入口男同| 国产偷国产偷精品高清尤物| 男人日女人逼逼| 粉嫩一区二区三区四区公司1| 久久综合国产精品台湾中文娱乐网| 亚洲欧美偷拍视频| 99麻豆久久久国产精品免费优播| 免费极品av一视觉盛宴| 亚洲网站免费| 色综合亚洲精品激情狠狠| 精产国品一区二区| 91美女视频网站| 无码熟妇人妻av在线电影| 久久婷婷五月综合色丁香| 亚洲性视频网址| 999视频在线| 久久久91精品国产一区二区三区| 日本福利视频在线| 亚欧洲精品视频在线观看| 91精品国产91久久久| 人妻精品一区二区三区| 五月婷婷综合激情| 日本国产在线视频| 99国产精品久久久久久久| 久久久久久久久一区二区| 美女扒开腿让男人桶爽久久软| 亚洲精品电影在线| 综合网在线观看| 国产亚洲综合性久久久影院| 韩国中文字幕av| 成人激情视频| 亚洲自拍中文字幕| 免费在线国产视频| 亚洲精品久久久久国产| 国产污视频网站| 国产精品久久看| 三上悠亚 电影| 亚洲久久一区二区| 欧美一区三区二区在线观看| 久久久加勒比| 欧美疯狂xxxx大交乱88av| 欧美熟妇交换久久久久久分类 | 久久天天躁狠狠躁老女人| 国产视频手机在线| 亚洲福中文字幕伊人影院| 日本少妇色视频| 麻豆精品精品国产自在97香蕉| 福利网在线观看| 日韩精品视频一区二区三区| 91精品国产色综合| 在线免费观看黄| 日韩女优视频免费观看| 成年人视频在线免费看| 国产精品久久久久影院色老大| √天堂资源在线| 亚洲黄色在线| 亚洲成人第一| 成人知道污网站| 国产精品毛片a∨一区二区三区|国 | 欧美经典一区| 97超级碰碰人国产在线观看| av在线电影网| 亚洲第一精品夜夜躁人人爽| 波多野结衣爱爱| 亚洲综合成人网| 免费视频91蜜桃| 懂色av一区二区三区蜜臀 | 日本一区免费网站| 久久久女女女女999久久| 国产露出视频在线观看| 精品久久人人做人人爰| 中文字幕免费高清在线观看| 亚洲一区二区精品3399| 亚洲精品91在线| 成人自拍视频在线观看| 五月天婷婷亚洲| 99av国产精品欲麻豆| 永久免费在线看片视频| 欧美日韩国产免费观看视频| 国产精品免费视频一区二区| 国产第一亚洲| 欧洲中文字幕国产精品| 国内高清免费在线视频| 日韩中文综合网| 精品视频一二三| 亚洲精品国产精品自产a区红杏吧 亚洲精品国产精品乱码不99按摩 亚洲精品国产精品久久清纯直播 亚洲精品国产精品国自产在线 | 欧美一级理论性理论a| 加勒比在线一区| 精品国产91久久久久久| 欧美成人一二三区| 中文字幕一区二区三区蜜月 | 国产调教一区二区三区| 国产精品区二区三区日本| 91成人福利社区| 国产精品三级美女白浆呻吟 | 91精品在线国产| 精品免费av在线| 日韩美女视频中文字幕| 日韩在线伦理| 97视频在线观看视频免费视频| 牛牛精品在线| 欧美激情亚洲自拍| 中文在线免费| 欧美成人亚洲成人日韩成人| 欧美极品视频| 日韩一区二区在线视频| 免费网站成人| 久久亚洲精品小早川怜子66| 一广人看www在线观看免费视频| 亚洲精品国产精品国自产观看浪潮| 午夜精品小视频| 日韩视频免费观看高清在线视频| 91 中文字幕| 日韩一区二区三区精品视频| 国产精品视频在线观看免费| 91精品国产色综合久久| 国产伦理一区二区| 日韩欧美国产高清| 亚洲精品喷潮一区二区三区| 日韩女同互慰一区二区| 亚洲av无码国产精品永久一区| 欧美成人激情免费网| 亚洲美女福利视频| 亚洲国产婷婷香蕉久久久久久| 五月婷婷免费视频| 亚洲天堂色网站| 中文字幕日本在线观看| 久久这里有精品视频| 日本理论片午伦夜理片在线观看| 欧美激情图片区| 都市激情国产精品| 日韩免费在线看| 91嫩草国产线观看亚洲一区二区| 91亚洲精华国产精华| 涩爱av色老久久精品偷偷鲁| 精品免费日产一区一区三区免费| 免费成人av| 亚洲欧洲一区二区在线观看| 中文字幕亚洲综合久久五月天色无吗''| 在线观看17c| 99视频一区| 五月天婷婷激情视频| 久久99精品国产91久久来源| 波多野结衣中文字幕在线播放| 成人免费福利片| 亚洲日本精品视频| 中文字幕一区二区在线播放| 国产大片aaa| 91官网在线免费观看| 99草在线视频| 亚洲成年网站在线观看| 黄视频在线播放| 欧美巨大黑人极品精男| 亚洲人体视频| 成人在线国产精品| 思热99re视热频这里只精品| 亚洲色图自拍| 99亚洲一区二区| 九九热99视频| 91在线一区二区三区| 国产麻豆a毛片| 天天影视色香欲综合网老头| 中文字幕乱码中文字幕| 亚洲成人免费在线视频| 北岛玲日韩精品一区二区三区| 久99久在线视频| 在线观看精品| 国产精品国产三级国产专区53| 精品国产一区二区三区小蝌蚪| 国产911在线观看| 全国精品久久少妇| 日本不卡视频一区| 亚洲天堂网中文字| 无码人妻精品一区二区三区蜜桃91 | www.五月婷婷| 在线视频欧美性高潮| h片视频在线观看| 国产中文日韩欧美| 国产精品一区二区99| 东北少妇不带套对白| 久久99热这里只有精品| 人妻少妇精品视频一区二区三区 | 视色,视色影院,视色影库,视色网| 一区二区三区四区五区精品视频| 福利视频999| 欧美激情在线一区二区| 欧美福利视频一区二区| 日韩一区二区电影| 男人的天堂在线视频免费观看| 欧美在线视频网| 国内精品麻豆美女在线播放视频| 色乱码一区二区三区熟女| 日韩影院在线观看| 女同毛片一区二区三区| 亚洲国产精品久久人人爱| 99国产精品久久久久99打野战| 在线观看日韩欧美| 欧洲一区二区三区精品| 久久综合福利| 99精品热视频只有精品10| 美女久久久久久久久| 一区二区三区在线看| jizz中国女人| 欧美成人午夜激情在线| 99精品视频在线免费播放| 亚洲乱码一区二区三区| 男女男精品视频| 变态另类ts人妖一区二区| 91豆麻精品91久久久久久| 深夜福利在线观看直播| 26uuu国产精品视频| 校花撩起jk露出白色内裤国产精品| 欧美综合在线播放| 波多野结衣在线一区| 日韩欧美一区二区一幕| 亚洲精品久久久久中文字幕二区| 国产天堂在线播放视频| av电影成人| 一区二区亚洲| 狠狠人妻久久久久久综合蜜桃| 欧美日韩色婷婷| 浮生影视网在线观看免费| 国产精品久久av| 99精品全国免费观看视频软件| www.五月天色| 亚洲一区影音先锋| 无码精品视频一区二区三区| 91高清视频免费| 欧美中文字幕一区二区| 国产乱码一区二区三区四区| 亚洲精品视频一区二区| 亚洲精品无码久久久| 国内外成人免费激情在线视频网站| 欧美日韩精品一区二区三区在线观看| 131美女爱做视频| 久久九九全国免费| 亚洲综合一区中| 欧美日韩电影在线观看| 精品精品国产三级a∨在线| 欧美亚洲另类色图| 国产欧美精品一区二区色综合 | 国产一区二区毛片| 久久久久久福利| 亚洲精品一区在线观看香蕉| 成人免费网站www网站高清| 中文字幕免费高| 不卡的av网站| 国产精品日产欧美久久久久| 国产大片中文字幕| 亚洲视频在线免费看| 日韩午夜电影免费看| 国产一区二区三区在线免费| 99精品国产91久久久久久| 中文字幕在线观看视频免费| 欧美成人一区在线| 五月综合久久| 99九九精品视频| 欧美性猛交xxxx免费看| 拍真实国产伦偷精品| 国产一区不卡在线观看| 美女免费视频一区| 男女啊啊啊视频| 久久精品国产免费观看| 欧美日韩一区二区三区四区不卡 | 不卡的av网站| 亚洲综合一区中| 欧美孕妇毛茸茸xxxx| 综合久久婷婷| 五月婷六月丁香| 亚洲国产精品网站| 国产精品亚洲欧美日韩一区在线| 欧美v在线观看|