🚀 这篇博客主要分享给从事手机研发显示屏(LCD/LCM)调试的同仁们,如果你对LCD的基础时序很陌生,不烦来看看我分享的这部分内容对你有没有帮助?如有帮助,还请顺手点赞、收藏或转发,原创不易,确实手都敲废了~,OK废话不说了,接下来开始上干货!👇

概述

什么是时序?我个人的理解,既是特定事件所发生的必要时间顺序,对于某些底层器件,它们的功能性引脚例如电压引脚、复位引脚需要遵循特定的时间顺序去进行响应拉高或拉低一定的时间才能够保障IC芯片正常工作。对于LCD的基础属性来说,LCD时序主要关注上电、唤醒、睡眠、下电四个部分的时序,对于这四个部分的时序我们经常测量的引脚有:vsp、vsn、LCD reset、TP reset、mipi dtp0这几个引脚,如果需要同步关注TP的时序的话,还需要加上SPI或者I2C引脚和TP中断引脚。

 

时序观测方法

首先我们要学会如何去观看时序,下面我们以集创家的某颗IC上电时序图来讲解一下上电时序怎么去看,如下图"集创上电时序图":

像这种时序规格图,我们在观看的时候要秉着1个规则去看,即先左后右

我们先从左边看,一开始所有引脚都是拉低状态,但是也许实际测量的波形图有时候会看到在拉低状态前有些是半拉高状态,就是介于拉低与拉高之间的一种状态。这种状态通常情况下是硬件平台的初始状态,并不影响实际波形图,如果非要介意的话可以去咨询一下平台去把引脚的默认pull状态改一改,懒人也可以在控制引脚前强制把对应引脚拉低一段时间后再去配置时序。不扯远了,我们以上图的时序图来理清一下:

1、首先是IOVCC拉高,IOVCC上电后给LCD IC供电,然后这个时候可以TP reset拉高,如果是开机阶段的话其实可以不管TP reset的状态,但是如果是唤醒的话TP reset需要拉高

2、接着VSP开始拉高。//iovcc主要是给LCD IC供电、vsp/vsn主要给偏压IC供电,其实主要是给panel逻辑电路下的液晶供电。

3、RESET_N也就是LCD reset拉高,这里需要注意一下,别看看是虚线,其实虚线也需要响应具体动作的,那为什么不搞成实线呢??

4、RESET_N拉高了之后,VSN才拉高,别看这个地方VSN的线条是往下拉,要注意VSN本身的属性,对于LCD来说液晶是需要±电压交流电来驱动的,VSN其实是一个负极电压,所以它往下拉其实就是拉高的动作,emm如果还是不理解的话,想想小学负数的运算口诀:负负得正??等VSN拉高了之后RESET_N才拉低,拉低之后再次拉高,当最后一次拉高动作起来之后,基本上这颗IC就能够正常工作了

5、MIPI的时序其实有更复杂的时序,由于这个地方只是初略的要求配置一下mipi的动作,所以我们就不讲复杂的了,但看它这个时序图上的要求,其实也就四个部分,分别是 initial code (下初始化代码)、Sleep out(11指令)、Display on(29指令)和Video packet(显示数据包)。这个地方拉高的位置其实可以就是dsi和dphy上电的位置。

6、再往下就是I2C/SPI的时序动作,可以看到在对应Display on的时候会下发一条command给TP FW,告知TP固件要Ready工作了,一般其实就是这个时候TP驱动走唤醒流程

7、最后就是TP_RESET_N的动作了,就是TP reset的时序图,要求一直拉高状态(至少要保证在VSP/VSN之前是处于拉高状态),但是要注意这个地方不绝对哈,因为如果是刚开机的时候也这么搞的话会有个风险,因为一般情况下刚开机的时候是先跑LCD的驱动,那这个时候去操作TP的reset脚的话要注意资源的释放,否则等进入到kernel后TP驱动申请不到TP reset的话,TP驱动就无法正常加载!

看完上面时序图,我们再看看其中的每一条时序动作的规格,因为对于时序来说并不只是单看这些波形图的顺序动作,还要看它们的时间延时,具体其实上面时序图就已经标出来了,比如其中的T1 、T2、Ton1、Ton3等等,这些时间要求其实就是我们需要在驱动中配置的时序规格,具体来看一下详细规格:

我这里从这些规格当中选取几个实际测量的波形图供大家看看,如下图T1的规格,要求最低0.1ms也就是100us,然后我们实际测量出来是120us也就是0.12ms,这是满足T1的时序规格的。

如下图T2的规格,VSP的上升沿时长要求最低0.1ms,实际测量出是500us也就是0.5ms,也是满足T2的时序规格

再来看看T4的规格,Power ready to last high-pulse of RESET_N指的就是所有power都上电了后到最后一次LCD reset拉高之间的延时,怎么看power都上电了呢?这里的power其实就是三power:iovcc vsp vsn,最先上电的是iovcc,然后是vsp,最后是vsn,所以vsn上电后基本上三power都ready好了,这里T4要求最低间隔10ms,然后这里实际测量出是90ms,符合时序规格。

再来看下一个,T5的时序规格,要求的是iovcc到mipi上电的时序规格,测mipi的时候只需测量mipi的dtp0引脚就可以测出其mipi动作的波形图了,这里实际测量出是1.78s,时序规格最低0ms,符合时序规格

再来看一个T7-1的时序规格,这里指的是LCD reset到下初始化代码之间的间隔延时,OTP其实就是烧录到LCD内部的一些代码,可能会包含一些例如Flicker、gamma等setting code。如果AP端没有写这部分代码的话,就会使用OTP里面的代码,可以理解成在屏亮的时候会优先使用OTP里面的initial code,如果AP端也有部分initial code的话就会覆盖到OTP中对应的部分initial code,AP指的就是软件这边的一端。这个时序规格就是要找到下初始化代码位置,对应的位置就是mipi 11指令前面(这里就是第二个箭头指的位置,这里有一条指令,由于测量间距所以被y轴线覆盖住了可以参考下面T9的波形图,旁边那条粗一点的指令线是11指令,因为初始化代码里面11前面还配了几个寄存器指令,所以粗了些),下图的波形图1号通道标签备注错了,VDD1V8是mipi DTP0的引脚,纠正一下。另外可能有些同仁会疑问这个波形里面不是有很多个LCD reset拉高的位置吗?为什么是最后一次拉高呢?其实需要结合上面的时序图来判定是测哪个LCD reset high到OTP位置。

接着再看一下T9的时序规格,Sleep-out指令到video packet间 的延时,Sleep out对应的就是11指令,Display on指令对应的就是29指令,video packet其实就是指mipi收到的数据显示指令,对应的波形图就是mipi中密密麻麻的波形图,因为一张图像是无数条指令整合而成的数据,一般在收到video packet的时候mipi都已经进入了high speed的模式了,此时传输数据的速率非常快且密集。T9要求的时序规格是典型120ms左右,我们实际测量是154ms,故也是符合时序规格的。

以上就是从上电时序当中选取的部分时序图和时序规格,在实际测量和观测的时候如果遇上不知道怎么测量对标可以参考时序图和部分特殊指令(11/29;28/10)。 

接下来再看一下集创下电时序图,左边是下电部分,右边是上电部分,主要看左边部分:

还是按照先左后右的规则去看这个时序图:

1、首先是mipi的动作,先跑Display off(28指令)和Sleep in(10)指令,然后进入lp模式最后下拉。

2、I2C/SPI在mipi进入Sleep in模式后也会由TP驱动去给TP FW下发进入睡眠模式(tp suspend)。

3、LCD reset和TP reset都相继下拉,使IC退出工作模式,这里可以看到有虚线,意思是按照虚线的时序走可以,按照实线的时序走也可以。

4、VSN下拉,至于为何看到它的脉冲是个上升沿前文有过大概解释,这里看能不能理解,不清楚的话可以请教一下硬件的同事。

5、VSP下拉,然后VDDD下拉,如果是四power的话就会有个VDDD电压,但是我所使用的工程没有用到所以我就不展开解释了。

6、最后IOVCC下拉,IC停止工作。 

接下来再看一下下电的时序规格:

这里面观测方法和前面的差不多,就抽选一个稍微特殊一点的时序简单讲一下。

比如T12的时序规格,要求进睡眠到LCD reset拉低之间的延时最低100ms,Sleep in(10指令)和Display off(28指令)都有比较明显的特征(一般就是mipi的最后两条指令),如下波形图实测有误差,右边的y轴线应该右移到途中红框里面LCD reset下拉位置,差不多也是120ms左右,满足最低100ms的时序要求

再看一下唤醒时序图和唤醒时序规格,其实很多情况下唤醒时序和上电时序有大部分雷同之处,具体观测方法和测量方法类似。

需要注意一下就是看下是否支持手势功能(LPWG),如果支持的话就需要注意进手势模式后看下是否要求vsp/vsn/LCD reset不下拉,这个具体还是需要driver去找位置配置一下,下面放一个进手势的时序图和规格表:

这里就是要求LCD进睡眠后需要至少100ms后由TP驱动给TP FW下发进手势模式的指令,这个其实很好配置,掌握好Sleep in指令到tp suspend之间的时间即可,可以测量SPI的mosi引脚到mipi 10指令之间的延时看下是否满足时序规格。

以上就是关于基础时序的观测方法介绍,接下来简单梳理一下时序流程。

时序流程梳理

我这边通常使用到的平台主要是MTK和展锐,就以AndroidS下MT6765平台和展锐SC9863A平台的流程大致讲下基础时序是如何调用的,不同平台会有一点点差异,具体的还是以大家手上的为准,以下内容仅供参考!首先讲下MTK的上电时序:

MTK上电流程

首先是primary_display.c这个文件中会去判断有没有跑过lcm的probe函数,如果没有就会去跑probe函数disp_lcm_probe(),然后跑lcm的init函数disp_lcm_init().

disp_lcm_probe函数中有一个for循环,它会去把配置的lcm driver文件一个一个获取到,然后进行上电(lcm_drv->init_power),跑上电时序和匹配id,如果成功了就会给变量isLCMFound置1,表示会使用这个lcm驱动。如果有兼容情况的话,上电时序只能一个一个的跑,那么实际测量的时候发现配置的时序和实际波形可能有一部分是另外一个屏的上电时序,这个是正常的,只要最后面跑的时序是正常配置的时序即可,因为从流程上讲毕竟是先上电再读id,没办法先区分id再去跑对应时序的。

跑完probe后就会跑disp_lcm_init,这里面lcm_drv->init()就是跑屏的initial code,会把initial code push到屏里面去,让屏跑起来,但是有点不理解为什么这个函数里面还会再跑一次lcm_drv->init_power()?莫非是跑probe到这里有哪个地方会出现掉电的情况?

mtk中跑BootLoader阶段大致的流程是这样:1 、2、3、4、5、6

MTK睡眠唤醒流程

然后唤醒流程基本上就是在kernel里面去跑了,大致流程是这样:1、resume_power;2、resume;

睡眠流程大致是这样:1、suspend;2、suspend_power。需强调注意是否有手势功能,有的话睡眠时序要考虑2路电和reset变化。

可是有没有发现没有下发sleep in指令?所以在suspend函数中要记得配置sleep in指令。

展锐上电流程

展锐的上电流程大致和mtk差不多的方法,在for循环里面去获取dtsi里面的属性内容和节点信息,然后调用ops->power去跑上电时序

ops->power的接口函数实际上是这个地方的panel_power函数:

panel_power里面会根据形参来控制是上电还是下电

当然不同终端可能会有自己的客制化代码和框架,像我这边对接的某音业务,他们是把控制上下电时序进行了另外的封装,是用一个叫bias_voltage_set_vol函数去控制偏压IC然后再管控vsp/vsn上电和下电。

展锐睡眠唤醒流程

展锐的睡眠流程主要会走sprd_dsi_encoder_disable函数中的drm_panel_disable和drm_panel_unprepare,其实就是走的sprd_panel_disable和sprd_panel_unprepare:

展锐的唤醒流程主要会走sprd_dsi_encoder_enable函数中的drm_panel_prepare和drm_panel_enable,其实就是走的sprd_panel_prepare和sprd_panel_enable:

这里额外拓展一下ESD recovery中其实就是走的这里的睡眠和唤醒流程:

  

时序配置方法

其实看懂了上面的驱动流程之后基本上就知道在哪个位置去配置时序了,不过可能还是有部分同仁不是很清楚,所以大致讲一下吧

MTK上电时序配置

上电时序是在开机启动的时候去跑,mtk架构上是把它安排在BootLoader里面,我们需要关注的就是关于vsp/vsn和reset这三个脚怎么去拉高或拉低,前面上电流程里有提到上电时序其实是在lcm_drv->init_power里面去配置,lcm_drv->init_power其实就是对应的客制化lcm文件中的init_power()函数,也就是这里:

  

需要在这里操作vsp/vsn的拉高拉低,在需要加延时的位置去加延时:

 

如果要操作reset的话,可以在lcm_init里面去配置LCD reset的拉高拉低:

 

MTK睡眠时序配置

MTK的睡眠时序主要是在kernel里面去配置,因为BootLoader基本上不涉及睡眠唤醒。

所以我们需要在kernel中的lcm客制化文件中去配置睡眠时序,睡眠时序主要涉及关背光、进睡眠、vsp/vsn下电和reset拉低。建议的话可以把这四个部分拆分开,前面进睡眠流程有讲过,主要是先跑suspend然后再跑suspend_power,所以可以把关背光、进睡眠的时序放在suspend中,vsp/vsn下电时序和reset下电时序放在suspend_power当中,如果有手势功能的话需要注意是否vsp/vsn和reset不拉低!

MTK唤醒时序配置

MTK的唤醒时序也主要是在kernel里面去配置

唤醒的流程主要先跑resume_power然后跑resume,这里涉及出睡眠、开背光、vsp/vsn上电和reset拉高,同上面差不多,也是建议分开各放各的时序,比如可以把出睡眠、开背光时序放在resume里面(我这里11和29指令都放在initial code里面了),vsp/vsn上电和reset拉高放在resume_power。

展锐上电时序配置

参考前面的上电流程,原生代码的话直接在panel_power里面去配置vsp/vsn就可以了,这里avdd就是对应vsp,avee就是对应vsn,性质差不多,都是给偏压IC和LCD IC供电的。客制化代码的话需要去参考各自的框架去处理了,不同终端也许框架有差异。

如果要操作reset的话就需要在dtsi里面去配置节点属性的信息了,展锐关于拉reset的方法和MTK的有差异,展锐这边会在dtsi里面把拉reset的动作和延时封装在sprd,reset-on-sequence里面,然后传到power_on_seq.timing里面去,在panel_power里面去用一个for循环调用。

展锐睡眠时序配置

展锐的进睡眠时序主要是用sprd_panel_unprepare函数来处理的,如果要操作vsp/vsn的话就在这个函数里面去操作就可以了,如果要操作reset的话需要在dtsi文件里面去修改sprd,reset-off-sequence节点属性,至于关背光和进睡眠时序则是在sprd_panel_disable()函数中。

展锐唤醒时序配置

展锐的唤醒时序主要是sprd_panel_prepare()函数来处理的,配置方法和上面的睡眠时序配置方法差不多,而出睡眠和开背光时序则是在sprd_panel_enable()函数

常见问题

1、分不清11 29 和10 28的位置:

11:出睡眠,即 sleep out   的指令
10:进睡眠,即 sleep in    的指令
28:关背光,即 display off 的指令
29:开背光,即 displap on  的指令
所以通常亮屏的顺序是11 29,也就是先出睡眠再开启背光,中间要留足够的时间保证背光亮
起来之前已经有显示图像显示出来了,否则唤醒的时候就会有白帧或黑帧。
灭屏的顺序就需要反过来,即 28 10 ,先关背光再进睡眠,中间的时间不宜太长,否则用户
会注意到屏幕虽然背光灭了但是还有显示图像。

2、11 29 也算是初始化代码的一部分,有时候看时序时找不到initial code位置的时候可以借鉴11 29 的特殊延时来判断initial code的大致位置。

3、mipi的high speed特征图就是看到mipi的密密麻麻的信号指令。

4、展锐平台兼容上电时序时,复杂的时序dtsi可以优先放在前面,简单的时序放后面,就是让复杂的时序先跑,然后跑简单一点的时序。

5、展锐平台,上电时序位置不要轻易操作tp reset脚,如果要操作,完了之后需要及时释放资源,否则会影响tp驱动加载找不到tp reset

6、IC规格书中直接搜power on就能搜索到时序位置:power on/off sequence

💯以上就是个人的一个全部知识共享,🙈这里面肯定有很多不足甚至是错误理解的地方,希望同仁们在看到了之后及时在评论区中点评指正,避免误导他人😂。也欢迎同行的朋友们私信交流技术上的问题,希望能够互帮互助,如果这边文章对您有帮助,也请点赞收藏或转发!至此,感谢!

Logo

开放原子开发者工作坊旨在鼓励更多人参与开源活动,与志同道合的开发者们相互交流开发经验、分享开发心得、获取前沿技术趋势。工作坊有多种形式的开发者活动,如meetup、训练营等,主打技术交流,干货满满,真诚地邀请各位开发者共同参与!

更多推荐