//gpio_request申请gpio口

int gpio_request(unsigned gpio, const char *label)
{
struct gpio_desc *desc;
struct gpio_chip *chip;
int status = -EINVAL;
unsigned long flags; spin_lock_irqsave(&gpio_lock, flags); // gpio_lock是自旋锁,上锁,保存FLAG在flags变量
if (!gpio_is_valid(gpio))
goto done;
desc = &gpio_desc[gpio];
chip = desc->chip;
if (chip == NULL)
goto done; if (!try_module_get(chip->owner)) // 该函数用于增加模块使用计数;若返回为0,表示调用失败,希望使用的模块没有被加载或正在被卸载中 goto done; /* NOTE: gpio_request() can be called in early boot,
* before IRQs are enabled, for non-sleeping (SOC) GPIOs.
*/ if (test_and_set_bit(FLAG_REQUESTED, &desc->flags) == ) { // 原子操作,将flags的第FLAG_REQUESTED位置1,并返回其原值
desc_set_label(desc, label ? : "?");// 如果原来的值是0, 执行desc_set_label, 对desc->chip.label赋值,如果label有定义,直接用定义,比如上面的“temporary”,否则用“?”
status = 0;
} else {
status = -EBUSY;
module_put(chip->owner); // 该函数用于减少模块使用计数goto done;
} if (chip->request) {// chip->request在linux初始化时是没有指向的 /* chip->request may sleep */
spin_unlock_irqrestore(&gpio_lock, flags);// 如果chip->request不为0, 解锁,因为后面调用的chip->request有可能睡眠
status = chip->request(chip, gpio - chip->base);
spin_lock_irqsave(&gpio_lock, flags); if (status < ) {
desc_set_label(desc, NULL);
module_put(chip->owner);
clear_bit(FLAG_REQUESTED, &desc->flags);
}
} done:
if (status)
pr_debug("gpio_request: gpio-%d (%s) status %d\n",
gpio, label ? : "?", status);
spin_unlock_irqrestore(&gpio_lock, flags);
return status;
}
EXPORT_SYMBOL_GPL(gpio_request); void gpio_free(unsigned gpio)
{
unsigned long flags;
struct gpio_desc *desc;
struct gpio_chip *chip; might_sleep(); if (!gpio_is_valid(gpio)) {
WARN_ON(extra_checks);
return;
} gpio_unexport(gpio); spin_lock_irqsave(&gpio_lock, flags); desc = &gpio_desc[gpio];
chip = desc->chip;
if (chip && test_bit(FLAG_REQUESTED, &desc->flags)) {
if (chip->free) {
spin_unlock_irqrestore(&gpio_lock, flags);
might_sleep_if(extra_checks && chip->can_sleep);
chip->free(chip, gpio - chip->base);
spin_lock_irqsave(&gpio_lock, flags);
}
desc_set_label(desc, NULL);
module_put(desc->chip->owner);
clear_bit(FLAG_ACTIVE_LOW, &desc->flags);
clear_bit(FLAG_REQUESTED, &desc->flags);
} else
WARN_ON(extra_checks); spin_unlock_irqrestore(&gpio_lock, flags);
}
EXPORT_SYMBOL_GPL(gpio_free);

Linux下GPIO驱动(四) ----gpio_request();gpio_free();的更多相关文章

  1. 很好的linux下GPIO驱动详解文章

    原文地址  http://blog.csdn.net/llxmedici/article/details/6282372 打算跟着友善之臂的<mini2440 linux移植开发指南>来做 ...

  2. Linux下GPIO驱动(三) ----gpio_desc()的分析

    上篇最后提出的疑问是结构体gpio_chip中的成员函数set等是怎么实现的,在回答之前先介绍下gpio_desc这个结构体. 如上图所示,右上方部分为GPIO驱动对其它驱动提供的GPIO操作接口,其 ...

  3. Linux下GPIO驱动(一) ----一个简单的LED驱动

    /******************************* * *杂项设备驱动:miscdevice *majior=10; * * *****************************/ ...

  4. Linux下GPIO驱动

    编写驱动程序,首先要了解是什么类型的设备.linux下的设备分为三类,分别为:字符设备,块设备和网络设备.字符设备类型是根据是否以字符流为数据的交换方式,大部分设备都是字符设备,如键盘,串口等,块设备 ...

  5. Linux下GPIO驱动(五) ----misc_register();

    // struct miscdevice { int minor; const char *name; const struct file_operations *fops; struct list_ ...

  6. Linux下GPIO驱动(二) ----s3c_gpio_cfgpin();gpio_set_value();

    首先来看s3c_gpio_cfgpin(); int s3c_gpio_cfgpin(unsigned int pin, unsigned int config) { struct s3c_gpio_ ...

  7. 飞思卡尔imx6开发板Linux下GPIO驱动

    控制GPIO_1_28的输出: #define MY_BOMB_GPIO       IMX_GPIO_NR(1, 28) 配置为输出方式: gpio_direction_output (MY_BOM ...

  8. Linux 下wifi 驱动开发(四)—— USB接口WiFi驱动浅析

    源: Linux 下wifi 驱动开发(四)—— USB接口WiFi驱动浅析

  9. 调试exynos4412—ARM嵌入式Linux—LEDS/GPIO驱动之一

    /** ****************************************************************************** * @author    暴走的小 ...

随机推荐

  1. typedef和typename关键字

    .类型说明typedef 类型说明的格式为: typedef 类型 定义名; 类型说明只定义了一个数据类型的新名字而不是定义一种新的数据类型.定义名表示这个类型的新名字. 例如: 用下面语句定义整型数 ...

  2. mysql 源码调试方法

     http://blog.itpub.net/29254281/viewspace-1847415/ 其中吕海波老师分享的内容是 <调试Oracle二三例:调试技术在日常运维中的应用>其中 ...

  3. [JavaScript]转--如何让JS代码高大上

    原文出处:http://www.cnblogs.com/wenber/p/3630373.html 1,创造简短的写法 你可以这么写: 1 var slice = Array.prototype.sl ...

  4. What is a heap?--reference

    A heap is a partially sorted binary tree. Although a heap is not completely in order, it conforms to ...

  5. 学习jQuery后的部分总结

    1.remove和empty <div id="div1"> <ul id="ul1"> <li>嘿嘿</li> ...

  6. 如何真正免费运营推广APP应用

    随着移动终端的迅速普及,各类APP如雨后春笋般涌现出来,但是真正的运营成功的产品却寥寥无几. 从瓜分渠道资源到抢占用户的过程中,很多同行都明显的感觉到,渠道平台所带来的量日益减少,但是刊例价格却一再攀 ...

  7. fstat - 读取文件相关信息

    #fstat读取到的信息 ["dev"]=> int(16777220) ["ino"]=> int(66880002) ["mode&q ...

  8. html select用法总结

    本文将介绍select 原生的常用方法,这些都是经过测试,兼容ie6到ie10,及chrome,火狐等,也就是说大部分浏览器都兼容.如果大家发现有不兼容的情况,可以跟我留言. 我们对基本的用法了如指掌 ...

  9. FPGA设计—UVM验证篇 Hello world

    这里就不赘述UVM为何物了,做了半年多的FPGA设计验证工作,按需求一直是用VHDL编写测试程序,最近看了几天UVM验证方法学的书,感觉这是一种很好的验证工具,现在开始UVM的学习,于是准备用Mode ...

  10. android之模拟器访问外网设置

    一.确定adb可用 1.1 确认adb环境变量 1.2 命令行cmd 执行adb shell启动模拟器的命令行 二.DNS确认 2.1 确定DNS是否为电脑的DNS 2.2 修改DNS地址 三.效果图