核心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 能夠使用統一的介...