问题:针对GPIO的MUX的功能,RK平台的配置有些区别于高通平台,高通的平台中即便是“default”的状态也是需要在Driver中去设置的,但是RK平台针对“default”的状态是不需要在Driver中去配置,而是由平台统一的实现了。
DTS:
&dsi {
compatible = "rockchip,rk3399-dsi";
enable-gpios = <&gpio1 0 GPIO_ACTIVE_HIGH>;
reset-gpios = <&gpio1 2 GPIO_ACTIVE_LOW>;
standby-gpios = <&gpio1 1 GPIO_ACTIVE_LOW>;
pinctrl-names = "default";
pinctrl-0 = <&bridge_gpio>;
....
&pinctrl {
backlight {
pwm_en_gpio: pwm-en-gpio {
rockchip,pins = <4 24 RK_FUNC_GPIO &pcfg_pull_up>;
};
};
dsi {
bridge_gpio: bridge-gpio {
rockchip,pins =
<1 0 RK_FUNC_GPIO &pcfg_pull_none>,
<1 1 RK_FUNC_GPIO &pcfg_pull_none>,
<1 2 RK_FUNC_GPIO &pcfg_pull_none>;
};
};
};
只需要如上的配置即可,驱动中我们完全不用再去管了。
BUT,WHY?之前一直对这个功能很疑惑,既然驱动中没有去做配置,那么平台是在哪个地方完成的呢?其实就是在设备和驱动Match成功后,在触发probe之前。如下:
[ 1.400918] [<ffffff800808a564>] dump_backtrace+0x0/0x1ec
[ 1.400929] [<ffffff800808a764>] show_stack+0x14/0x1c
[ 1.400941] [<ffffff80083a13b8>] dump_stack+0x94/0xb4
[ 1.400952] [<ffffff80083dfaf0>] rockchip_set_mux+0x21c/0x324
[ 1.400962] [<ffffff80083e0418>] rockchip_pmx_set+0x94/0xf0
[ 1.400972] [<ffffff80083db2a8>] pinmux_enable_setting+0x1b8/0x248
[ 1.400984] [<ffffff80083d8668>] pinctrl_commit_state+0x78/0x120
[ 1.400995] [<ffffff80083d872c>] pinctrl_select_state+0x1c/0x2c
[ 1.401007] [<ffffff8008519c64>] pinctrl_bind_pins+0xa4/0x11c
[ 1.401020] [<ffffff80084f8490>] driver_probe_device+0x90/0x2ac
[ 1.401029] [<ffffff80084f8710>] __driver_attach+0x64/0x90
[ 1.401038] [<ffffff80084f75cc>] bus_for_each_dev+0x80/0xb0
[ 1.401047] [<ffffff80084f805c>] driver_attach+0x20/0x28
[ 1.401056] [<ffffff80084f7c14>] bus_add_driver+0xe8/0x1e4
[ 1.401066] [<ffffff80084f92c4>] driver_register+0x94/0xe0
[ 1.401076] [<ffffff80084fa200>] __platform_driver_register+0x48/0x50
[ 1.401086] [<ffffff800908cb30>] rockchip_dsi_driver_init+0x18/0x20
[ 1.401095] [<ffffff80080839f0>] do_one_initcall+0x178/0x194
[ 1.401105] [<ffffff8009060ddc>] kernel_init_freeable+0x1a4/0x25c
[ 1.401117] [<ffffff8008b1b3b0>] kernel_init+0x10/0xf8
[ 1.401126] [<ffffff80080832a0>] ret_from_fork+0x10/0x30
通过上面的堆栈打印,可以充分的说明这个问题。
really_probe
->pinctrl_bind_pins
->devm_pinctrl_get
->pinctrl_lookup_state(dev->pins->p,PINCTRL_STATE_DEFAULT) //"default"
->pinctrl_lookup_state(dev->pins->p,PINCTRL_STATE_INIT) //"init"
->pinctrl_select_state(dev->pins->p,dev->pins->init_state/default_state)
->pinctrl_init_done
如上所示,如果init状态存在则初始化为init,否则初始化为default.