Regulator framework

来源:互联网 发布:淘宝 睿智表行 编辑:程序博客网 时间:2024/04/28 12:24


1 General description

Voltage Regulator & current regulator 电压调节器和电流调节器

Linux中,regulator framework提供标准的API区控制regulator设备。这样做的目的是动态的调节电源的使用,以达到节能。

1.1 Regulator

电压或电流调节器,分类

1.2 Power domain

连接在同一个输出源上的设备在同一个domain里,这个输出源叫做一个power domain。常见的输出源有switchregulator

下面的图片中有三个power domain

Domain1switch 1consumer Dconsumer E

Domain2switch 2consumer Bconsumer C

Domain3consumer A

它们之间的supply 关系:domain 1--> domain 2--> domain 3

 

1.3 constraints

Constraint用来定义电压电流的设置来保护设备,分为三个等级:

l regulator level: 限定regulator的电压与电源的使用范围

l Domain level:   限定power domain的电压与电流的使用范围

l Consumer leve: 限定consumer的电压与电流的使用范围

如果有一个LCD backlight driver申请将电流从5ma调至10ma,那么要依次查看下面几个电流的限制,全部通过时才能申请到电流值:

ü Consumer:查找LCDbrightness table,看10ma是否在table

ü Power Domain:电流的大小是否在power domain的当前状态下的电流限制范围内

ü Regulator:是否超过regulator的参数限制

 

2 Framework

Regulator framework主要有一下几个部分组成:

l Consumer driver interface

consumer使用framework提供APIgetput regulatorgetset voltage & currentlimitmodeenabledisable。通过这下接口,consumerdriver就可以完全控制device所连接的regulator

l Regulator interface

Regulator drivercore注册regulator即其操作方法

l Machine

Machine specific code为每个regulator创建voltage/currentdomain,并提供电压电流限制来防止过压或过流

l Userspace interface

Framework通过sysfsuserspace提供一些电源使用的情况

2.1 provider device driver

A provider that is usually a PMIC may contain one or more regulators.All of these regulators are defined in a global static match table whose data strcture is of_regulator_match.Example of match table for PF3000:

static struct of_regulator_match pfuze3000_matches[] = {

        { .name = "sw1a",       },

        { .name = "sw1b",       },

        { .name = "sw2",        },

        { .name = "sw3",        },

        { .name = "swbst",      },

        { .name = "vsnvs",      },

        { .name = "vrefddr",    },

        { .name = "vldo1",      },

        { .name = "vldo2",      },

        { .name = "vccsd",      },

        { .name = "v33",        },

        { .name = "vldo3",      },

        { .name = "vldo4",      },

};  

This table just list all the regulators that a privider can provide,that doesn’t mean all these regulator will be used.

During the procedure of probe for the provider, every component of the match table will be compared with all the regulators that are actually used by name.And all matches will be initialized according to device node. function “of_regulator_match” is respomsible for this process. After this, all the information from device node for regulators actually used are described in match table.

 

Each regulator registered with the core is described with a struct regulator_desc and regulator_config. Struct regulator_desc contains the non-varing parts of the regulator description and struct regulator_config contains the run time variable parts of the reguletor description.

 

The regulator_desc structure for every regulator is declared in a static table,but the struct regulator_config for every regulator is initilized at run time,and information in match table will copyed to it.

 

After registerred, struct regulator_dev defines a registerred regualtor class device.

The defination of these structures are defined in “include/linux/regulator/driver.h”

 

Normally,a static array of this structure is define,each one describes a reguletor in provide which may be a PMIC. Take PF3000 as an example,all of its regulators are declared in pfuze3000_regulators[].

When you write a regulator driver,you may follow three steps:

Get device node of “regulators”

 

struct of_regulator_match 对应一个regulator nodekernel中通常以一个静态的table定义provider里所有的regulator node。如,pfuze3000_matches[],这个table用来和DTS中的regulator节点进行match,并将mathnode所有信息解析到这个table中的对应record

 

Provider(以PMIC为例)通常包括多个regulator,它在DTS表现为regulators节点的一个子节点。其中,regulators节点为’/’节点的子节点。

reg_sensor: regulator@4 {

                        compatible = "regulator-fixed";

                        reg = <4>;

                        regulator-name = "sensor-supply";

                        regulator-min-microvolt = <3300000>;

                        regulator-max-microvolt = <3300000>;

                        gpio = <&gpio2 31 0>;

                        startup-delay-us = <500>;

                        enable-active-high;

                };

其中,reg_sensor是该regulator的标号,用来被consumer引用。

PMIC,通常以platform device方式注册到内核,它的probe方法必然包括以下几部分:

1) 调用of_regulator_match,初始化match[i]->init_data->constraint的相关域,这起始解释解析regulators下的所有regulator节点

2) 初始化config的相关域,config中的init_data域直接从match_table中获得

3) Descriptors,通常也是静态定义的table

4) 调用struct regulator_dev *devm_regulator_register(struct device *dev,

                                  const struct regulator_desc *regulator_desc,

                                  const struct regulator_config *config)

根据descriptorconfig注册regulator

2.2 consumer device driver

1Regulator consumerDTS中的描述:

consumernode中以xxx-supply=<®ulator-lable>表示其consumeregulator。而这里xxx表示这个regulator的在consumer driver中的id

(以mag3110为例):

        mag3110@0e {

                compatible = "fsl,mag3110";

                reg = <0x0e>;

                position = <2>;

                vdd-supply = <®_sensor>;

                vddio-supply = <®_sensor>;

                interrupt-parent = <&gpio3>;

                interrupts = <16 1>;

        };

其中idvddvddiosupply都是reg_sensor指向的这个regulator

2、regulator consumer driverprobe方法:

Regulator consumerprobe过程第一步当然是给device上电了,这就需要使能它所连接的regulator

vdd = devm_regulator_get(&client->dev, "vdd");

regulator_enable(vdd);

然后在进行consumerdevice自己的probe操作了。

 

 

Device register of provider

 

 

Consumer get source

 

 

 


0 0
原创粉丝点击