linux核心GPIO程式設計說明

2021-08-11 14:11:31 字數 3860 閱讀 5375

核心gpio程式設計說明

參考資料:

從官方資料來看,linux核心中的gpio介面目前有新舊兩個版本,新的版本的介面是descriptor-based的,而舊的是integer-based的。舊的介面已出於相容性的考慮仍被支援,但已不再建議使用。網上目前大多gpio程式設計說明都是舊的版本,所以這篇說明就以介紹新的介面版本為主。

1.驅動首先需要包含標頭檔案:

#include

2.呼叫gpio裝置所需函式,函式返回描述符或錯誤碼

struct gpio_desc *gpiod_get(struct device *dev, const char *con_id,

enum gpiod_flags flags)

如果裝置需要使用多個gpio,則需在函式中新增index引數:

struct gpio_desc *gpiod_get_index(struct device *dev,

const char *con_id, unsigned int idx,

enum gpiod_flags flags)

其中gpiod_flag控制初始化模式,有以下幾種:

* gpiod_asis or 0 不進行初始化

* gpiod_in 將gpio初始化為input模式

* gpiod_out_low 將gpio初始化為低電平output

* gpiod_out_high 將gpio初始化為高電平output

也可以用以下兩個函式呼叫可用gpio。當沒有gpio呼叫成功時,返回null

struct gpio_desc *gpiod_get_optional(struct device *dev,

const char *con_id,

enum gpiod_flags flags)

struct gpio_desc *gpiod_get_index_optional(struct device *dev,

const char *con_id,

unsigned int index,

enum gpiod_flags flags)

或者在獲取多個gpio時只要呼叫乙個函式即可:

struct gpio_descs *gpiod_get_array(struct device *dev,

const char *con_id,

enum gpiod_flags flags)

該函式返回結構體gpi_descs:

struct gpio_descs

3. 釋放乙個gpio使用函式:

void gpiod_put(struct gpio_desc *desc)

或者釋放多個gpio使用

void gpiod_put_array(struct gpio_descs *descs)

在呼叫這些函式後,被釋放的描述符不可再被使用。

4.gpio的設定

呼叫以下函式來的設定gpio的方向:

int gpiod_direction_input(struct gpio_desc *desc)

int gpiod_direction_output(struct gpio_desc *desc, int value)

獲取當前方向:

int gpiod_get_direction(const struct gpio_desc *desc)

函式返回gpiof_dir_in/gpiof_dir_out

5.gpio的訪問

gpio的訪問可通過主存的讀寫指令完成,這種操作不需要sleep,所以在內部硬中斷時也可以被呼叫,安全性較高。使用以下函式來進行該原子訪問操作:

int gpiod_get_value(const struct gpio_desc *desc);

void gpiod_set_value(struct gpio_desc *desc, int value);

另一種gpio裝置訪問必須使用訊息匯流排如i2c或spi,這種操作需要在佇列中等待,所以不再能在irq中被呼叫:

int gpiod_get_value_cansleep(const struct gpio_desc *desc)

void gpiod_set_value_cansleep(struct gpio_desc *desc, int value)

分辨此類gpio裝置:

int gpiod_cansleep(const struct gpio_desc *desc)

6.輸出訊號

有些裝置採用低電平有效的方式輸出邏輯訊號。此時低電平輸出1,高電平輸出0。此時可以通過訪問raw_value的方式來訪問實際電路上的值,與邏輯處理無關:

int gpiod_get_raw_value(const struct gpio_desc *desc)

void gpiod_set_raw_value(struct gpio_desc *desc, int value)

int gpiod_get_raw_value_cansleep(const struct gpio_desc *desc)

void gpiod_set_raw_value_cansleep(struct gpio_desc *desc, int value)

int gpiod_direction_output_raw(struct gpio_desc *desc, int value)

邏輯關係彙總如下: 

function (example) active-low property physical line 

gpiod_set_raw_value(desc, 0); don』t care low 

gpiod_set_raw_value(desc, 1); don』t care high 

gpiod_set_value(desc, 0); default (active-high) low 

gpiod_set_value(desc, 1); default (active-high) high 

gpiod_set_value(desc, 0); active-low high 

gpiod_set_value(desc, 1); active-low low

可以使用如下函式判斷乙個裝置是否是低電平有效的裝置。

int gpiod_is_active_low(const struct gpio_desc *desc)

可以通過以下函式對一組gpio進行輸出設定:

void gpiod_set_array_value(unsigned int array_size,

struct gpio_desc **desc_array,

int *value_array)

void gpiod_set_raw_array_value(unsigned int array_size,

struct gpio_desc **desc_array,

int *value_array)

void gpiod_set_array_value_cansleep(unsigned int array_size,

struct gpio_desc **desc_array,

int *value_array)

void gpiod_set_raw_array_value_cansleep(unsigned int array_size,

struct gpio_desc **desc_array,

int *value_array)

7.對映到irqs

int gpiod_to_irq(const struct gpio_desc *desc)

8.gpio和acpi

在acpi系統上,gpio裝置在gpioio()/gpioint()從_crs中獲得的資源列表中被描述,這些資源不能在系統gpio中被使用。

linux核心 GPIO口程式設計入門

1.api介面 請求gpio口 int gpio request unsigned gpio,const char label 釋放gpio口 void gpio free unsigned gpio 判斷gpio索引號是否有效 gpio口是否存在 int gpio is valid int num...

Linux核心驅動GPIO的使用

linux核心中gpio 是最簡單 最常用的資源 和 interrupt dma,timer一樣 驅動程式,應用程式都能夠通過相應的介面使用gpio,gpio使用0 max int之間的整數標識,不能使用負數,gpio與 硬體體系密切相關的 不過linux 有乙個框架 處理gpio 能夠使用統一的介...

Linux核心驅動GPIO的使用

linux核心中gpio 是最簡單 最常用的資源 和 interrupt dma,timer一樣 驅動程式,應用程式都能夠通過相應的介面使用gpio,gpio使用0 max int之間的整數標識,不能使用負數,gpio與 硬體體系密切相關的 不過linux 有乙個框架 處理gpio 能夠使用統一的介...