背景:
延续上一篇写的从app控制gpio电平,想从app通过framework--jni--driver来控制ldo,也就是pm8909_l8这种电源脚。
代码:
diff --git a/kernel/drivers/misc/chaoDriver/gpio_control.c b/kernel/drivers/misc/chaoDriver/gpio_control.c
index a93f6c1..df33b71 100755
--- a/kernel/drivers/misc/chaoDriver/gpio_control.c
+++ b/kernel/drivers/misc/chaoDriver/gpio_control.c
@@ -33,6 +33,7 @@
#include <linux/delay.h>
#include <linux/of_gpio.h>
#include <linux/spi/spi.h>
+#include <linux/regulator/consumer.h>
#ifdef CONFIG_COMPAT
#include <linux/compat.h>
@@ -183,12 +184,49 @@ int gpio_control_get_gpio_info(struct platform_device *pdev)
return 0;
}
-static int gpio_control_probe(struct platform_device *dev)
+static int gpio_parse_dt(struct device *dev,struct chao_gpio_pdata *pdata)
+{
+ int ret = 0;
+ pdata->avdd = regulator_get(dev, "vdd_ana");
+ if (IS_ERR(pdata->avdd)) {
+ ret = PTR_ERR(pdata->avdd);
+ pdata->avdd=NULL;
+ printk(KERN_ALERT "chao Regulator get 2.8V failed avdd\n");
+ return ret;
+ }
+
+
//这里有一个问题
//ret = regulator_set_voltage(pdata->avdd,2850000,2850000);
+ ret = regulator_set_voltage(pdata->avdd,2800000,2900000);
+ if (ret) {
+ regulator_put(pdata->avdd);
+ pdata->avdd = NULL;
+ printk(KERN_ALERT "chao Regulator set 2.8V failed avdd\n");
+ return ret;
+ }
+
+ printk(KERN_ALERT "chao gpio_parse_dt success\n");
+
+ return ret;
+}
+
+static int gpio_control_probe(struct platform_device *pdev)
{
int ret = 0;
struct pinctrl *pinctrl;
-
+
+ struct chao_gpio_pdata *pdata;
+
+ pdata = devm_kzalloc(&pdev->dev, sizeof(struct chao_gpio_pdata), GFP_KERNEL);
+ if (!pdata) {
+ dev_err(&pdev->dev,"Failed to allocate memory for pdata\n");
+ return -ENOMEM;
+ }
+
+ printk(KERN_ALERT "qyc before parse dt\n");
+ ret = gpio_parse_dt(&pdev->dev,pdata);
+ printk(KERN_ALERT "qyc after parse dt\n");
+
if (alloc_chrdev_region(&gpio_devno, 0, 1, GPIO_DEVNAME)) {
goto err_allocate_chrdev;
}
@@ -206,7 +244,7 @@ static int gpio_control_probe(struct platform_device *dev)
goto err_add_cdev;
}
- printk(KERN_ALERT "chao probe before class create \n");
+ printk(KERN_ALERT "qyc probe before class create \n");
gpio_class = class_create(THIS_MODULE, LKK_CLASS);
if (IS_ERR(gpio_class)) {
goto err_create_class;
@@ -219,16 +257,23 @@ static int gpio_control_probe(struct platform_device *dev)
device_create_file(gpio_device, &dev_attr_gpio_pin);
- printk(KERN_ALERT "chao probe before get dtsi gpio\n");
+ printk(KERN_ALERT "qyc probe before get dtsi gpio\n");
//gpio control fun
- gpio_control_get_gpio_info(dev); //init pinctrl from dtsi
+ gpio_control_get_gpio_info(pdev); //init pinctrl from dtsi
//printk(KERN_ALERT "chao probe pull 8 start\n");
//pinctrl_select_state(gpio_pin_ctrl.pinGpioCtrl, gpio_pin_ctrl.cst0_output1);
//printk(KERN_ALERT "chao probe pull 8 end\n");
+
- printk(KERN_ALERT "chao probe success\n");
+ ret = regulator_enable(pdata->avdd);
+ if(ret) {
+ printk(KERN_ALERT "qyc can not enable avdd 2.8v: %d", ret);
+ return ret;
+ }
+
+ printk(KERN_ALERT "qyc probe success\n");
return 0;
err_create_device:
中间碰到了一个问题:
开机logp跑到7秒左右,不跑了(电流恒定,不进android),看了下log,驱动正常跑的,没任何错误。



这种问题就没法了,只能逐渐删减代码.
1.先把驱动里的关于vdd_ana-supply的parse_dt函数屏蔽,结果机器正常启动。
说明原驱动OK.
2.仍然解析vdd_ana-supply,但是把parse_dt里面的regulator_set_voltage函数屏蔽掉。结果机器正常启动。
说明解析vdd_ana-supply没问题,是设置L8电导致的。
3.L8的电压范围是2.8V 到 2.9V,源驱动程序设置最小和最大均为2.85v,现在把最小设置为2.8,把最大设置为2.9V。结果正常开机。
-----------
这就确认了问题:
解析dtsi中电源节点正常,但是如果regulator_set_voltage里面参数的最小和最大值不合理,会导致机器起不来。
(暂不清楚,为什么最小和最大设置成一样,都为2.85 V会导致该问题 ?? 按道理应该可以 )
验证:
就比较简单,在probe结尾
regulator_enable(pdata->avdd);
------
量了下电压,有2.896 V。
到时候把这个写在ioctl里面,就可以在app中控制电压了。
----------
end ~