1 /*
2  * Copyright (c) 2020-2022 Huawei Device Co., Ltd.
3  *
4  * HDF is dual licensed: you can use it either under the terms of
5  * the GPL, or the BSD license, at your option.
6  * See the LICENSE file in the root of this repository for complete details.
7  */
8 
9 #include "ili9881c_boe.h"
10 #include "gpio_if.h"
11 #include "hdf_bl.h"
12 #include "hdf_disp.h"
13 #include "osal.h"
14 
15 /* panel on command payload */
16 static uint8_t g_payLoad0[] = { 0xFF, 0x98, 0x81, 0x03 };
17 static uint8_t g_payLoad1[] = { 0x01, 0x00 };
18 static uint8_t g_payLoad2[] = { 0x02, 0x00 };
19 static uint8_t g_payLoad3[] = { 0x03, 0x73 };
20 static uint8_t g_payLoad4[] = { 0x04, 0x00 };
21 static uint8_t g_payLoad5[] = { 0x05, 0x00 };
22 static uint8_t g_payLoad6[] = { 0x06, 0x08 };
23 static uint8_t g_payLoad7[] = { 0x07, 0x00 };
24 static uint8_t g_payLoad8[] = { 0x08, 0x00 };
25 static uint8_t g_payLoad9[] = { 0x09, 0x00 };
26 static uint8_t g_payLoad10[] = { 0x0A, 0x01 };
27 static uint8_t g_payLoad11[] = { 0x0B, 0x01 };
28 static uint8_t g_payLoad12[] = { 0x0C, 0x00 };
29 static uint8_t g_payLoad13[] = { 0x0D, 0x01 };
30 static uint8_t g_payLoad14[] = { 0x0E, 0x01 };
31 static uint8_t g_payLoad15[] = { 0x0F, 0x00 };
32 static uint8_t g_payLoad16[] = { 0x10, 0x00 };
33 static uint8_t g_payLoad17[] = { 0x11, 0x00 };
34 static uint8_t g_payLoad18[] = { 0x12, 0x00 };
35 static uint8_t g_payLoad19[] = { 0x13, 0x1F };
36 static uint8_t g_payLoad20[] = { 0x14, 0x1F };
37 static uint8_t g_payLoad21[] = { 0x15, 0x00 };
38 static uint8_t g_payLoad22[] = { 0x16, 0x00 };
39 static uint8_t g_payLoad23[] = { 0x17, 0x00 };
40 static uint8_t g_payLoad24[] = { 0x18, 0x00 };
41 static uint8_t g_payLoad25[] = { 0x19, 0x00 };
42 static uint8_t g_payLoad26[] = { 0x1A, 0x00 };
43 static uint8_t g_payLoad27[] = { 0x1B, 0x00 };
44 static uint8_t g_payLoad28[] = { 0x1C, 0x00 };
45 static uint8_t g_payLoad29[] = { 0x1D, 0x00 };
46 static uint8_t g_payLoad30[] = { 0x1E, 0x40 };
47 static uint8_t g_payLoad31[] = { 0x1F, 0xC0 };
48 static uint8_t g_payLoad32[] = { 0x20, 0x06 };
49 static uint8_t g_payLoad33[] = { 0x21, 0x01 };
50 static uint8_t g_payLoad34[] = { 0x22, 0x06 };
51 static uint8_t g_payLoad35[] = { 0x23, 0x01 };
52 static uint8_t g_payLoad36[] = { 0x24, 0x88 };
53 static uint8_t g_payLoad37[] = { 0x25, 0x88 };
54 static uint8_t g_payLoad38[] = { 0x26, 0x00 };
55 static uint8_t g_payLoad39[] = { 0x27, 0x00 };
56 static uint8_t g_payLoad40[] = { 0x28, 0x3B };
57 static uint8_t g_payLoad41[] = { 0x29, 0x03 };
58 static uint8_t g_payLoad42[] = { 0x2A, 0x00 };
59 static uint8_t g_payLoad43[] = { 0x2B, 0x00 };
60 static uint8_t g_payLoad44[] = { 0x2C, 0x00 };
61 static uint8_t g_payLoad45[] = { 0x2D, 0x00 };
62 static uint8_t g_payLoad46[] = { 0x2E, 0x00 };
63 static uint8_t g_payLoad47[] = { 0x2F, 0x00 };
64 static uint8_t g_payLoad48[] = { 0x30, 0x00 };
65 static uint8_t g_payLoad49[] = { 0x31, 0x00 };
66 static uint8_t g_payLoad50[] = { 0x32, 0x00 };
67 static uint8_t g_payLoad51[] = { 0x33, 0x00 };
68 static uint8_t g_payLoad52[] = { 0x34, 0x00 };
69 static uint8_t g_payLoad53[] = { 0x35, 0x00 };
70 static uint8_t g_payLoad54[] = { 0x36, 0x00 };
71 static uint8_t g_payLoad55[] = { 0x37, 0x00 };
72 static uint8_t g_payLoad56[] = { 0x38, 0x00 };
73 static uint8_t g_payLoad57[] = { 0x39, 0x00 };
74 static uint8_t g_payLoad58[] = { 0x3A, 0x00 };
75 static uint8_t g_payLoad59[] = { 0x3B, 0x00 };
76 static uint8_t g_payLoad60[] = { 0x3C, 0x00 };
77 static uint8_t g_payLoad61[] = { 0x3D, 0x00 };
78 static uint8_t g_payLoad62[] = { 0x3E, 0x00 };
79 static uint8_t g_payLoad63[] = { 0x3F, 0x00 };
80 static uint8_t g_payLoad64[] = { 0x40, 0x00 };
81 static uint8_t g_payLoad65[] = { 0x41, 0x00 };
82 static uint8_t g_payLoad66[] = { 0x42, 0x00 };
83 static uint8_t g_payLoad67[] = { 0x43, 0x00 };
84 static uint8_t g_payLoad68[] = { 0x44, 0x00 };
85 static uint8_t g_payLoad69[] = { 0x50, 0x01 };
86 static uint8_t g_payLoad70[] = { 0x51, 0x23 };
87 static uint8_t g_payLoad71[] = { 0x52, 0x45 };
88 static uint8_t g_payLoad72[] = { 0x53, 0x67 };
89 static uint8_t g_payLoad73[] = { 0x54, 0x89 };
90 static uint8_t g_payLoad74[] = { 0x55, 0xAB };
91 static uint8_t g_payLoad75[] = { 0x56, 0x01 };
92 static uint8_t g_payLoad76[] = { 0x57, 0x23 };
93 static uint8_t g_payLoad77[] = { 0x58, 0x45 };
94 static uint8_t g_payLoad78[] = { 0x59, 0x67 };
95 static uint8_t g_payLoad79[] = { 0x5A, 0x89 };
96 static uint8_t g_payLoad80[] = { 0x5B, 0xAB };
97 static uint8_t g_payLoad81[] = { 0x5C, 0xCD };
98 static uint8_t g_payLoad82[] = { 0x5D, 0xEF };
99 static uint8_t g_payLoad83[] = { 0x5E, 0x00 };
100 static uint8_t g_payLoad84[] = { 0x5F, 0x01 };
101 static uint8_t g_payLoad85[] = { 0x60, 0x01 };
102 static uint8_t g_payLoad86[] = { 0x61, 0x06 };
103 static uint8_t g_payLoad87[] = { 0x62, 0x06 };
104 static uint8_t g_payLoad88[] = { 0x63, 0x07 };
105 static uint8_t g_payLoad89[] = { 0x64, 0x07 };
106 static uint8_t g_payLoad90[] = { 0x65, 0x00 };
107 static uint8_t g_payLoad91[] = { 0x66, 0x00 };
108 static uint8_t g_payLoad92[] = { 0x67, 0x02 };
109 static uint8_t g_payLoad93[] = { 0x68, 0x02 };
110 static uint8_t g_payLoad94[] = { 0x69, 0x05 };
111 static uint8_t g_payLoad95[] = { 0x6A, 0x05 };
112 static uint8_t g_payLoad96[] = { 0x6B, 0x02 };
113 static uint8_t g_payLoad97[] = { 0x6C, 0x0D };
114 static uint8_t g_payLoad98[] = { 0x6D, 0x0D };
115 static uint8_t g_payLoad99[] = { 0x6E, 0x0C };
116 static uint8_t g_payLoad100[] = { 0x6F, 0x0C };
117 static uint8_t g_payLoad101[] = { 0x70, 0x0F };
118 static uint8_t g_payLoad102[] = { 0x71, 0x0F };
119 static uint8_t g_payLoad103[] = { 0x72, 0x0E };
120 static uint8_t g_payLoad104[] = { 0x73, 0x0E };
121 static uint8_t g_payLoad105[] = { 0x74, 0x02 };
122 static uint8_t g_payLoad106[] = { 0x75, 0x01 };
123 static uint8_t g_payLoad107[] = { 0x76, 0x01 };
124 static uint8_t g_payLoad108[] = { 0x77, 0x06 };
125 static uint8_t g_payLoad109[] = { 0x78, 0x06 };
126 static uint8_t g_payLoad110[] = { 0x79, 0x07 };
127 static uint8_t g_payLoad111[] = { 0x7A, 0x07 };
128 static uint8_t g_payLoad112[] = { 0x7B, 0x00 };
129 static uint8_t g_payLoad113[] = { 0x7C, 0x00 };
130 static uint8_t g_payLoad114[] = { 0x7D, 0x02 };
131 static uint8_t g_payLoad115[] = { 0x7E, 0x02 };
132 static uint8_t g_payLoad116[] = { 0x7F, 0x05 };
133 static uint8_t g_payLoad117[] = { 0x80, 0x05 };
134 static uint8_t g_payLoad118[] = { 0x81, 0x02 };
135 static uint8_t g_payLoad119[] = { 0x82, 0x0D };
136 static uint8_t g_payLoad120[] = { 0x83, 0x0D };
137 static uint8_t g_payLoad121[] = { 0x84, 0x0C };
138 static uint8_t g_payLoad122[] = { 0x85, 0x0C };
139 static uint8_t g_payLoad123[] = { 0x86, 0x0F };
140 static uint8_t g_payLoad124[] = { 0x87, 0x0F };
141 static uint8_t g_payLoad125[] = { 0x88, 0x0E };
142 static uint8_t g_payLoad126[] = { 0x89, 0x0E };
143 static uint8_t g_payLoad127[] = { 0x8A, 0x02 };
144 static uint8_t g_payLoad128[] = { 0xFF, 0x98, 0x81, 0x04 };
145 static uint8_t g_payLoad129[] = { 0x6C, 0x15 };
146 static uint8_t g_payLoad130[] = { 0x6E, 0x2A };
147 static uint8_t g_payLoad131[] = { 0x6F, 0x33 };
148 static uint8_t g_payLoad132[] = { 0x8D, 0x1B };
149 static uint8_t g_payLoad133[] = { 0x87, 0xBA };
150 static uint8_t g_payLoad134[] = { 0x3A, 0x24 };
151 static uint8_t g_payLoad135[] = { 0x26, 0x76 };
152 static uint8_t g_payLoad136[] = { 0xB2, 0xD1 };
153 static uint8_t g_payLoad137[] = { 0xFF, 0x98, 0x81, 0x01 };
154 static uint8_t g_payLoad138[] = { 0x22, 0x0A };
155 static uint8_t g_payLoad139[] = { 0x31, 0x00 };
156 static uint8_t g_payLoad140[] = { 0x43, 0x66 };
157 static uint8_t g_payLoad141[] = { 0x53, 0x40 };
158 static uint8_t g_payLoad142[] = { 0x50, 0x87 };
159 static uint8_t g_payLoad143[] = { 0x51, 0x82 };
160 static uint8_t g_payLoad144[] = { 0x60, 0x15 };
161 static uint8_t g_payLoad145[] = { 0x61, 0x01 };
162 static uint8_t g_payLoad146[] = { 0x62, 0x0C };
163 static uint8_t g_payLoad147[] = { 0x63, 0x00 };
164 static uint8_t g_payLoad148[] = { 0xA0, 0x00 };
165 static uint8_t g_payLoad149[] = { 0xA1, 0x13 };
166 static uint8_t g_payLoad150[] = { 0xA2, 0x23 };
167 static uint8_t g_payLoad151[] = { 0xA3, 0x14 };
168 static uint8_t g_payLoad152[] = { 0xA4, 0x16 };
169 static uint8_t g_payLoad153[] = { 0xA5, 0x29 };
170 static uint8_t g_payLoad154[] = { 0xA6, 0x1E };
171 static uint8_t g_payLoad155[] = { 0xA7, 0x1D };
172 static uint8_t g_payLoad156[] = { 0xA8, 0x86 };
173 static uint8_t g_payLoad157[] = { 0xA9, 0x1E };
174 static uint8_t g_payLoad158[] = { 0xAA, 0x29 };
175 static uint8_t g_payLoad159[] = { 0xAB, 0x74 };
176 static uint8_t g_payLoad160[] = { 0xAC, 0x19 };
177 static uint8_t g_payLoad161[] = { 0xAD, 0x17 };
178 static uint8_t g_payLoad162[] = { 0xAE, 0x4B };
179 static uint8_t g_payLoad163[] = { 0xAF, 0x20 };
180 static uint8_t g_payLoad164[] = { 0xB0, 0x26 };
181 static uint8_t g_payLoad165[] = { 0xB1, 0x4C };
182 static uint8_t g_payLoad166[] = { 0xB2, 0x5D };
183 static uint8_t g_payLoad167[] = { 0xB3, 0x3F };
184 static uint8_t g_payLoad168[] = { 0xC0, 0x00 };
185 static uint8_t g_payLoad169[] = { 0xC1, 0x13 };
186 static uint8_t g_payLoad170[] = { 0xC2, 0x23 };
187 static uint8_t g_payLoad171[] = { 0xC3, 0x14 };
188 static uint8_t g_payLoad172[] = { 0xC4, 0x16 };
189 static uint8_t g_payLoad173[] = { 0xC5, 0x29 };
190 static uint8_t g_payLoad174[] = { 0xC6, 0x1E };
191 static uint8_t g_payLoad175[] = { 0xC7, 0x1D };
192 static uint8_t g_payLoad176[] = { 0xC8, 0x86 };
193 static uint8_t g_payLoad177[] = { 0xC9, 0x1E };
194 static uint8_t g_payLoad178[] = { 0xCA, 0x29 };
195 static uint8_t g_payLoad179[] = { 0xCB, 0x74 };
196 static uint8_t g_payLoad180[] = { 0xCC, 0x19 };
197 static uint8_t g_payLoad181[] = { 0xCD, 0x17 };
198 static uint8_t g_payLoad182[] = { 0xCE, 0x4B };
199 static uint8_t g_payLoad183[] = { 0xCF, 0x20 };
200 static uint8_t g_payLoad184[] = { 0xD0, 0x26 };
201 static uint8_t g_payLoad185[] = { 0xD1, 0x4C };
202 static uint8_t g_payLoad186[] = { 0xD2, 0x5D };
203 static uint8_t g_payLoad187[] = { 0xD3, 0x3F };
204 static uint8_t g_payLoad188[] = { 0xFF, 0x98, 0x81, 0x00 };
205 static uint8_t g_payLoad189[] = { 0x11, 0x00 };
206 static uint8_t g_payLoad190[] = { 0x29, 0x00 };
207 static uint8_t g_payLoad191[] = { 0x35, 0x00 };
208 
209 static struct DsiCmdDesc g_panelOnCode[] = {
210     { 0x39, 0x00, sizeof(g_payLoad0), g_payLoad0 },
211     { 0x23, 0x00, sizeof(g_payLoad1), g_payLoad1 },
212     { 0x23, 0x00, sizeof(g_payLoad2), g_payLoad2 },
213     { 0x23, 0x00, sizeof(g_payLoad3), g_payLoad3 },
214     { 0x23, 0x00, sizeof(g_payLoad4), g_payLoad4 },
215     { 0x23, 0x00, sizeof(g_payLoad5), g_payLoad5 },
216     { 0x23, 0x00, sizeof(g_payLoad6), g_payLoad6 },
217     { 0x23, 0x00, sizeof(g_payLoad7), g_payLoad7 },
218     { 0x23, 0x00, sizeof(g_payLoad8), g_payLoad8 },
219     { 0x23, 0x00, sizeof(g_payLoad9), g_payLoad9 },
220     { 0x23, 0x00, sizeof(g_payLoad10), g_payLoad10 },
221     { 0x23, 0x00, sizeof(g_payLoad11), g_payLoad11 },
222     { 0x23, 0x00, sizeof(g_payLoad12), g_payLoad12 },
223     { 0x23, 0x00, sizeof(g_payLoad13), g_payLoad13 },
224     { 0x23, 0x00, sizeof(g_payLoad14), g_payLoad14 },
225     { 0x23, 0x00, sizeof(g_payLoad15), g_payLoad15 },
226     { 0x23, 0x00, sizeof(g_payLoad16), g_payLoad16 },
227     { 0x23, 0x00, sizeof(g_payLoad17), g_payLoad17 },
228     { 0x23, 0x00, sizeof(g_payLoad18), g_payLoad18 },
229     { 0x23, 0x00, sizeof(g_payLoad19), g_payLoad19 },
230     { 0x23, 0x00, sizeof(g_payLoad20), g_payLoad20 },
231     { 0x23, 0x00, sizeof(g_payLoad21), g_payLoad21 },
232     { 0x23, 0x00, sizeof(g_payLoad22), g_payLoad22 },
233     { 0x23, 0x00, sizeof(g_payLoad23), g_payLoad23 },
234     { 0x23, 0x00, sizeof(g_payLoad24), g_payLoad24 },
235     { 0x23, 0x00, sizeof(g_payLoad25), g_payLoad25 },
236     { 0x23, 0x00, sizeof(g_payLoad26), g_payLoad26 },
237     { 0x23, 0x00, sizeof(g_payLoad27), g_payLoad27 },
238     { 0x23, 0x00, sizeof(g_payLoad28), g_payLoad28 },
239     { 0x23, 0x00, sizeof(g_payLoad29), g_payLoad29 },
240     { 0x23, 0x00, sizeof(g_payLoad30), g_payLoad30 },
241     { 0x23, 0x00, sizeof(g_payLoad31), g_payLoad31 },
242     { 0x23, 0x00, sizeof(g_payLoad32), g_payLoad32 },
243     { 0x23, 0x00, sizeof(g_payLoad33), g_payLoad33 },
244     { 0x23, 0x00, sizeof(g_payLoad34), g_payLoad34 },
245     { 0x23, 0x00, sizeof(g_payLoad35), g_payLoad35 },
246     { 0x23, 0x00, sizeof(g_payLoad36), g_payLoad36 },
247     { 0x23, 0x00, sizeof(g_payLoad37), g_payLoad37 },
248     { 0x23, 0x00, sizeof(g_payLoad38), g_payLoad38 },
249     { 0x23, 0x00, sizeof(g_payLoad39), g_payLoad39 },
250     { 0x23, 0x00, sizeof(g_payLoad40), g_payLoad40 },
251     { 0x23, 0x00, sizeof(g_payLoad41), g_payLoad41 },
252     { 0x23, 0x00, sizeof(g_payLoad42), g_payLoad42 },
253     { 0x23, 0x00, sizeof(g_payLoad43), g_payLoad43 },
254     { 0x23, 0x00, sizeof(g_payLoad44), g_payLoad44 },
255     { 0x23, 0x00, sizeof(g_payLoad45), g_payLoad45 },
256     { 0x23, 0x00, sizeof(g_payLoad46), g_payLoad46 },
257     { 0x23, 0x00, sizeof(g_payLoad47), g_payLoad47 },
258     { 0x23, 0x00, sizeof(g_payLoad48), g_payLoad48 },
259     { 0x23, 0x00, sizeof(g_payLoad49), g_payLoad49 },
260     { 0x23, 0x00, sizeof(g_payLoad50), g_payLoad50 },
261     { 0x23, 0x00, sizeof(g_payLoad51), g_payLoad51 },
262     { 0x23, 0x00, sizeof(g_payLoad52), g_payLoad52 },
263     { 0x23, 0x00, sizeof(g_payLoad53), g_payLoad53 },
264     { 0x23, 0x00, sizeof(g_payLoad54), g_payLoad54 },
265     { 0x23, 0x00, sizeof(g_payLoad55), g_payLoad55 },
266     { 0x23, 0x00, sizeof(g_payLoad56), g_payLoad56 },
267     { 0x23, 0x00, sizeof(g_payLoad57), g_payLoad57 },
268     { 0x23, 0x00, sizeof(g_payLoad58), g_payLoad58 },
269     { 0x23, 0x00, sizeof(g_payLoad59), g_payLoad59 },
270     { 0x23, 0x00, sizeof(g_payLoad60), g_payLoad60 },
271     { 0x23, 0x00, sizeof(g_payLoad61), g_payLoad61 },
272     { 0x23, 0x00, sizeof(g_payLoad62), g_payLoad62 },
273     { 0x23, 0x00, sizeof(g_payLoad63), g_payLoad63 },
274     { 0x23, 0x00, sizeof(g_payLoad64), g_payLoad64 },
275     { 0x23, 0x00, sizeof(g_payLoad65), g_payLoad65 },
276     { 0x23, 0x00, sizeof(g_payLoad66), g_payLoad66 },
277     { 0x23, 0x00, sizeof(g_payLoad67), g_payLoad67 },
278     { 0x23, 0x00, sizeof(g_payLoad68), g_payLoad68 },
279     { 0x23, 0x00, sizeof(g_payLoad69), g_payLoad69 },
280     { 0x23, 0x00, sizeof(g_payLoad70), g_payLoad70 },
281     { 0x23, 0x00, sizeof(g_payLoad71), g_payLoad71 },
282     { 0x23, 0x00, sizeof(g_payLoad72), g_payLoad72 },
283     { 0x23, 0x00, sizeof(g_payLoad73), g_payLoad73 },
284     { 0x23, 0x00, sizeof(g_payLoad74), g_payLoad74 },
285     { 0x23, 0x00, sizeof(g_payLoad75), g_payLoad75 },
286     { 0x23, 0x00, sizeof(g_payLoad76), g_payLoad76 },
287     { 0x23, 0x00, sizeof(g_payLoad77), g_payLoad77 },
288     { 0x23, 0x00, sizeof(g_payLoad78), g_payLoad78 },
289     { 0x23, 0x00, sizeof(g_payLoad79), g_payLoad79 },
290     { 0x23, 0x00, sizeof(g_payLoad80), g_payLoad80 },
291     { 0x23, 0x00, sizeof(g_payLoad81), g_payLoad81 },
292     { 0x23, 0x00, sizeof(g_payLoad82), g_payLoad82 },
293     { 0x23, 0x00, sizeof(g_payLoad83), g_payLoad83 },
294     { 0x23, 0x00, sizeof(g_payLoad84), g_payLoad84 },
295     { 0x23, 0x00, sizeof(g_payLoad85), g_payLoad85 },
296     { 0x23, 0x00, sizeof(g_payLoad86), g_payLoad86 },
297     { 0x23, 0x00, sizeof(g_payLoad87), g_payLoad87 },
298     { 0x23, 0x00, sizeof(g_payLoad88), g_payLoad88 },
299     { 0x23, 0x00, sizeof(g_payLoad89), g_payLoad89 },
300     { 0x23, 0x00, sizeof(g_payLoad90), g_payLoad90 },
301     { 0x23, 0x00, sizeof(g_payLoad91), g_payLoad91 },
302     { 0x23, 0x00, sizeof(g_payLoad92), g_payLoad92 },
303     { 0x23, 0x00, sizeof(g_payLoad93), g_payLoad93 },
304     { 0x23, 0x00, sizeof(g_payLoad94), g_payLoad94 },
305     { 0x23, 0x00, sizeof(g_payLoad95), g_payLoad95 },
306     { 0x23, 0x00, sizeof(g_payLoad96), g_payLoad96 },
307     { 0x23, 0x00, sizeof(g_payLoad97), g_payLoad97 },
308     { 0x23, 0x00, sizeof(g_payLoad98), g_payLoad98 },
309     { 0x23, 0x00, sizeof(g_payLoad99), g_payLoad99 },
310     { 0x23, 0x00, sizeof(g_payLoad100), g_payLoad100 },
311     { 0x23, 0x00, sizeof(g_payLoad101), g_payLoad101 },
312     { 0x23, 0x00, sizeof(g_payLoad102), g_payLoad102 },
313     { 0x23, 0x00, sizeof(g_payLoad103), g_payLoad103 },
314     { 0x23, 0x00, sizeof(g_payLoad104), g_payLoad104 },
315     { 0x23, 0x00, sizeof(g_payLoad105), g_payLoad105 },
316     { 0x23, 0x00, sizeof(g_payLoad106), g_payLoad106 },
317     { 0x23, 0x00, sizeof(g_payLoad107), g_payLoad107 },
318     { 0x23, 0x00, sizeof(g_payLoad108), g_payLoad108 },
319     { 0x23, 0x00, sizeof(g_payLoad109), g_payLoad109 },
320     { 0x23, 0x00, sizeof(g_payLoad110), g_payLoad110 },
321     { 0x23, 0x00, sizeof(g_payLoad111), g_payLoad111 },
322     { 0x23, 0x00, sizeof(g_payLoad112), g_payLoad112 },
323     { 0x23, 0x00, sizeof(g_payLoad113), g_payLoad113 },
324     { 0x23, 0x00, sizeof(g_payLoad114), g_payLoad114 },
325     { 0x23, 0x00, sizeof(g_payLoad115), g_payLoad115 },
326     { 0x23, 0x00, sizeof(g_payLoad116), g_payLoad116 },
327     { 0x23, 0x00, sizeof(g_payLoad117), g_payLoad117 },
328     { 0x23, 0x00, sizeof(g_payLoad118), g_payLoad118 },
329     { 0x23, 0x00, sizeof(g_payLoad119), g_payLoad119 },
330     { 0x23, 0x00, sizeof(g_payLoad120), g_payLoad120 },
331     { 0x23, 0x00, sizeof(g_payLoad121), g_payLoad121 },
332     { 0x23, 0x00, sizeof(g_payLoad122), g_payLoad122 },
333     { 0x23, 0x00, sizeof(g_payLoad123), g_payLoad123 },
334     { 0x23, 0x00, sizeof(g_payLoad124), g_payLoad124 },
335     { 0x23, 0x00, sizeof(g_payLoad125), g_payLoad125 },
336     { 0x23, 0x00, sizeof(g_payLoad126), g_payLoad126 },
337     { 0x23, 0x00, sizeof(g_payLoad127), g_payLoad127 },
338     { 0x39, 0x00, sizeof(g_payLoad128), g_payLoad128 },
339     { 0x23, 0x00, sizeof(g_payLoad129), g_payLoad129 },
340     { 0x23, 0x00, sizeof(g_payLoad130), g_payLoad130 },
341     { 0x23, 0x00, sizeof(g_payLoad131), g_payLoad131 },
342     { 0x23, 0x00, sizeof(g_payLoad132), g_payLoad132 },
343     { 0x23, 0x00, sizeof(g_payLoad133), g_payLoad133 },
344     { 0x23, 0x00, sizeof(g_payLoad134), g_payLoad134 },
345     { 0x23, 0x00, sizeof(g_payLoad135), g_payLoad135 },
346     { 0x23, 0x00, sizeof(g_payLoad136), g_payLoad136 },
347     { 0x39, 0x00, sizeof(g_payLoad137), g_payLoad137 },
348     { 0x23, 0x00, sizeof(g_payLoad138), g_payLoad138 },
349     { 0x23, 0x00, sizeof(g_payLoad139), g_payLoad139 },
350     { 0x23, 0x00, sizeof(g_payLoad140), g_payLoad140 },
351     { 0x23, 0x00, sizeof(g_payLoad141), g_payLoad141 },
352     { 0x23, 0x00, sizeof(g_payLoad142), g_payLoad142 },
353     { 0x23, 0x00, sizeof(g_payLoad143), g_payLoad143 },
354     { 0x23, 0x00, sizeof(g_payLoad144), g_payLoad144 },
355     { 0x23, 0x00, sizeof(g_payLoad145), g_payLoad145 },
356     { 0x23, 0x00, sizeof(g_payLoad146), g_payLoad146 },
357     { 0x23, 0x00, sizeof(g_payLoad147), g_payLoad147 },
358     { 0x23, 0x00, sizeof(g_payLoad148), g_payLoad148 },
359     { 0x23, 0x00, sizeof(g_payLoad149), g_payLoad149 },
360     { 0x23, 0x00, sizeof(g_payLoad150), g_payLoad150 },
361     { 0x23, 0x00, sizeof(g_payLoad151), g_payLoad151 },
362     { 0x23, 0x00, sizeof(g_payLoad152), g_payLoad152 },
363     { 0x23, 0x00, sizeof(g_payLoad153), g_payLoad153 },
364     { 0x23, 0x00, sizeof(g_payLoad154), g_payLoad154 },
365     { 0x23, 0x00, sizeof(g_payLoad155), g_payLoad155 },
366     { 0x23, 0x00, sizeof(g_payLoad156), g_payLoad156 },
367     { 0x23, 0x00, sizeof(g_payLoad157), g_payLoad157 },
368     { 0x23, 0x00, sizeof(g_payLoad158), g_payLoad158 },
369     { 0x23, 0x00, sizeof(g_payLoad159), g_payLoad159 },
370     { 0x23, 0x00, sizeof(g_payLoad160), g_payLoad160 },
371     { 0x23, 0x00, sizeof(g_payLoad161), g_payLoad161 },
372     { 0x23, 0x00, sizeof(g_payLoad162), g_payLoad162 },
373     { 0x23, 0x00, sizeof(g_payLoad163), g_payLoad163 },
374     { 0x23, 0x00, sizeof(g_payLoad164), g_payLoad164 },
375     { 0x23, 0x00, sizeof(g_payLoad165), g_payLoad165 },
376     { 0x23, 0x00, sizeof(g_payLoad166), g_payLoad166 },
377     { 0x23, 0x00, sizeof(g_payLoad167), g_payLoad167 },
378     { 0x23, 0x00, sizeof(g_payLoad168), g_payLoad168 },
379     { 0x23, 0x00, sizeof(g_payLoad169), g_payLoad169 },
380     { 0x23, 0x00, sizeof(g_payLoad170), g_payLoad170 },
381     { 0x23, 0x00, sizeof(g_payLoad171), g_payLoad171 },
382     { 0x23, 0x00, sizeof(g_payLoad172), g_payLoad172 },
383     { 0x23, 0x00, sizeof(g_payLoad173), g_payLoad173 },
384     { 0x23, 0x00, sizeof(g_payLoad174), g_payLoad174 },
385     { 0x23, 0x00, sizeof(g_payLoad175), g_payLoad175 },
386     { 0x23, 0x00, sizeof(g_payLoad176), g_payLoad176 },
387     { 0x23, 0x00, sizeof(g_payLoad177), g_payLoad177 },
388     { 0x23, 0x00, sizeof(g_payLoad178), g_payLoad178 },
389     { 0x23, 0x00, sizeof(g_payLoad179), g_payLoad179 },
390     { 0x23, 0x00, sizeof(g_payLoad180), g_payLoad180 },
391     { 0x23, 0x00, sizeof(g_payLoad181), g_payLoad181 },
392     { 0x23, 0x00, sizeof(g_payLoad182), g_payLoad182 },
393     { 0x23, 0x00, sizeof(g_payLoad183), g_payLoad183 },
394     { 0x23, 0x00, sizeof(g_payLoad184), g_payLoad184 },
395     { 0x23, 0x00, sizeof(g_payLoad185), g_payLoad185 },
396     { 0x23, 0x00, sizeof(g_payLoad186), g_payLoad186 },
397     { 0x23, 0x00, sizeof(g_payLoad187), g_payLoad187 },
398     { 0x39, 0x00, sizeof(g_payLoad188), g_payLoad188 },
399     { 0x23, 0x78, sizeof(g_payLoad189), g_payLoad189 },
400     { 0x23, 0x0A, sizeof(g_payLoad190), g_payLoad190 },
401     { 0x23, 0x00, sizeof(g_payLoad191), g_payLoad191 },
402 };
403 
404 /* panel off command payload */
405 static uint8_t g_offpayLoad0[] = { 0x11 };
406 static uint8_t g_offpayLoad1[] = { 0x29 };
407 
408 static struct DsiCmdDesc g_panelOffCode[] = {
409     { 0x13, 0x0A, sizeof(g_offpayLoad0), g_offpayLoad0 },
410     { 0x13, 0x78, sizeof(g_offpayLoad1), g_offpayLoad1 },
411 };
412 
413 #define SET_GPIO_DELAY_5MS   5
414 #define ILI9881C_MIPI_DATA_LANES   4
415 
Ili9881cBoeSendCmds(struct mipi_dsi_device * dsi,const struct DsiCmdDesc * cmds,int size)416 static int Ili9881cBoeSendCmds(struct mipi_dsi_device *dsi,
417     const struct DsiCmdDesc *cmds, int size)
418 {
419     int32_t i;
420 
421     if (dsi == NULL) {
422         return -EINVAL;
423     }
424 
425     for (i = 0; i < size; i++) {
426         mipi_dsi_generic_write(dsi, cmds[i].payload, cmds[i].dataLen);
427         if (cmds[i].delay) {
428             OsalMSleep(cmds[i].delay);
429         }
430     }
431     return HDF_SUCCESS;
432 }
433 
ToIli9881cBoeDev(const struct PanelData * panel)434 static struct Ili9881cBoeDev *ToIli9881cBoeDev(const struct PanelData *panel)
435 {
436     return (struct Ili9881cBoeDev *)panel->object->priv;
437 }
438 
SetGpioState(uint16_t gpio,uint16_t dir,uint16_t level,uint32_t delay)439 static SetGpioState(uint16_t gpio, uint16_t dir, uint16_t level, uint32_t delay)
440 {
441     int32_t ret;
442 
443     ret = GpioSetDir(gpio, dir);
444     if (ret != HDF_SUCCESS) {
445         HDF_LOGE("%s GpioSetDir failed, ret:%d", __func__, ret);
446         return HDF_FAILURE;
447     }
448     ret = GpioWrite(gpio, level);
449     if (ret != HDF_SUCCESS) {
450         HDF_LOGE("%s GpioWrite failed, ret:%d", __func__, ret);
451         return HDF_FAILURE;
452     }
453     OsalMSleep(delay);
454     return HDF_SUCCESS;
455 }
456 
Ili9881cBoePrepare(const struct Ili9881cBoeDev * ili9881cBoeDev)457 static int32_t Ili9881cBoePrepare(const struct Ili9881cBoeDev *ili9881cBoeDev)
458 {
459     int32_t i;
460     int32_t ret;
461     int32_t items;
462     struct GpioTiming *timing = NULL;
463 
464     HDF_LOGI("%s()", __func__);
465     ret = regulator_enable(ili9881cBoeDev->supply);
466     if (ret < 0) {
467         HDF_LOGE("regulator_enable failed");
468     }
469     ret = SetGpioState(ili9881cBoeDev->avddGpio, GPIO_DIR_OUT, GPIO_VAL_HIGH, SET_GPIO_DELAY_5MS); /* delay 5ms */
470     if (ret != HDF_SUCCESS) {
471         HDF_LOGE("%s SetGpioState failed, gpio:%d", __func__, ili9881cBoeDev->avddGpio);
472         return HDF_FAILURE;
473     }
474     ret = SetGpioState(ili9881cBoeDev->aveeGpio, GPIO_DIR_OUT, GPIO_VAL_HIGH, SET_GPIO_DELAY_5MS);
475     if (ret != HDF_SUCCESS) {
476         HDF_LOGE("%s SetGpioState failed, gpio:%d", __func__, ili9881cBoeDev->aveeGpio);
477         return HDF_FAILURE;
478     }
479     ret = SetGpioState(ili9881cBoeDev->vghlGpio, GPIO_DIR_OUT, GPIO_VAL_HIGH, SET_GPIO_DELAY_5MS);
480     if (ret != HDF_SUCCESS) {
481         HDF_LOGE("%s SetGpioState failed, gpio:%d", __func__, ili9881cBoeDev->vghlGpio);
482         return HDF_FAILURE;
483     }
484     ret = SetGpioState(ili9881cBoeDev->tsrstGpio, GPIO_DIR_OUT, GPIO_VAL_HIGH, SET_GPIO_DELAY_5MS);
485     if (ret != HDF_SUCCESS) {
486         HDF_LOGE("%s SetGpioState failed, gpio:%d", __func__, ili9881cBoeDev->tsrstGpio);
487         return HDF_FAILURE;
488     }
489     ret = GpioSetDir(ili9881cBoeDev->resetGpio, GPIO_DIR_OUT);
490     if (ret != HDF_SUCCESS) {
491         HDF_LOGE("GpioSetDir failed, ret:%d", ret);
492         return HDF_FAILURE;
493     }
494     items = ili9881cBoeDev->rstOnSeq.items;
495     timing = ili9881cBoeDev->rstOnSeq.timing;
496     for (i = 0; i < items; i++) {
497         GpioWrite(ili9881cBoeDev->resetGpio, timing[i].level);
498         OsalMSleep(timing[i].delay);
499     }
500     return HDF_SUCCESS;
501 }
502 
Ili9881cBoeUnprepare(const struct Ili9881cBoeDev * ili9881cBoeDev)503 static int32_t Ili9881cBoeUnprepare(const struct Ili9881cBoeDev *ili9881cBoeDev)
504 {
505     int32_t i;
506     int32_t ret;
507     int32_t items;
508     struct GpioTiming *timing = NULL;
509 
510     HDF_LOGI("%s()", __func__);
511     ret = SetGpioState(ili9881cBoeDev->avddGpio, GPIO_DIR_OUT, GPIO_VAL_LOW, SET_GPIO_DELAY_5MS); /* delay 5ms */
512     if (ret != HDF_SUCCESS) {
513         HDF_LOGE("%s SetGpioState failed, gpio:%d", __func__, ili9881cBoeDev->avddGpio);
514         return HDF_FAILURE;
515     }
516     ret = SetGpioState(ili9881cBoeDev->aveeGpio, GPIO_DIR_OUT, GPIO_VAL_LOW, SET_GPIO_DELAY_5MS);
517     if (ret != HDF_SUCCESS) {
518         HDF_LOGE("%s SetGpioState failed, gpio:%d", __func__, ili9881cBoeDev->aveeGpio);
519         return HDF_FAILURE;
520     }
521     ret = SetGpioState(ili9881cBoeDev->vghlGpio, GPIO_DIR_OUT, GPIO_VAL_LOW, SET_GPIO_DELAY_5MS);
522     if (ret != HDF_SUCCESS) {
523         HDF_LOGE("%s SetGpioState failed, gpio:%d", __func__, ili9881cBoeDev->vghlGpio);
524         return HDF_FAILURE;
525     }
526     ret = SetGpioState(ili9881cBoeDev->tsrstGpio, GPIO_DIR_OUT, GPIO_VAL_LOW, SET_GPIO_DELAY_5MS);
527     if (ret != HDF_SUCCESS) {
528         HDF_LOGE("%s SetGpioState failed, gpio:%d", __func__, ili9881cBoeDev->tsrstGpio);
529         return HDF_FAILURE;
530     }
531     ret = GpioSetDir(ili9881cBoeDev->resetGpio, GPIO_DIR_OUT);
532     if (ret != HDF_SUCCESS) {
533         HDF_LOGE("GpioSetDir failed, ret:%d", ret);
534         return HDF_FAILURE;
535     }
536     items = ili9881cBoeDev->rstOffSeq.items;
537     timing = ili9881cBoeDev->rstOffSeq.timing;
538     for (i = 0; i < items; i++) {
539         GpioWrite(ili9881cBoeDev->resetGpio, timing[i].level);
540         OsalMSleep(timing[i].delay);
541     }
542     regulator_disable(ili9881cBoeDev->supply);
543     return HDF_SUCCESS;
544 }
545 
Ili9881cBoeOn(struct PanelData * panel)546 static int32_t Ili9881cBoeOn(struct PanelData *panel)
547 {
548     int32_t ret;
549     struct Ili9881cBoeDev *ili9881cBoeDev = NULL;
550 
551     HDF_LOGI("%s()", __func__);
552     ili9881cBoeDev = ToIli9881cBoeDev(panel);
553     ret = Ili9881cBoePrepare(ili9881cBoeDev);
554     if (ret != HDF_SUCCESS) {
555         HDF_LOGE("%s Ili9881cBoePrepare failed", __func__);
556         return HDF_FAILURE;
557     }
558     ret = Ili9881cBoeSendCmds(ili9881cBoeDev->dsiDev, g_panelOnCode,
559                               sizeof(g_panelOnCode) / sizeof(g_panelOnCode[0]));
560     if (ret != HDF_SUCCESS) {
561         HDF_LOGE("%s Ili9881cBoeSendCmds failed", __func__);
562         return HDF_FAILURE;
563     }
564     return HDF_SUCCESS;
565 }
566 
Ili9881cBoeOff(struct PanelData * panel)567 static int32_t Ili9881cBoeOff(struct PanelData *panel)
568 {
569     int32_t ret;
570     struct Ili9881cBoeDev *ili9881cBoeDev = NULL;
571 
572     ili9881cBoeDev = ToIli9881cBoeDev(panel);
573     HDF_LOGI(" %s line = %d", __func__, __LINE__);
574     ret = Ili9881cBoeSendCmds(ili9881cBoeDev->dsiDev, g_panelOffCode,
575                               sizeof(g_panelOffCode) / sizeof(g_panelOffCode[0]));
576     if (ret != HDF_SUCCESS) {
577         HDF_LOGE("%s Ili9881cBoeSendCmds failed", __func__);
578         return HDF_FAILURE;
579     }
580     ret = Ili9881cBoeUnprepare(ili9881cBoeDev);
581     if (ret != HDF_SUCCESS) {
582         HDF_LOGE("%s Ili9881cBoeUnprepare failed", __func__);
583         return HDF_FAILURE;
584     }
585     return HDF_SUCCESS;
586 }
587 
Ili9881cBoeInit(struct PanelData * panel)588 static int32_t Ili9881cBoeInit(struct PanelData *panel)
589 {
590     return 0;
591 }
592 
593 #define BLK_PWM_INDEX             2
594 #define PWM_MAX_PERIOD            40000
595 /* backlight setting */
596 #define MIN_LEVEL                 0
597 #define MAX_LEVEL                 255
598 #define DEFAULT_LEVEL             127
599 
600 static struct PanelInfo g_panelInfo = {
601     .width = 800,           /* width */
602     .height = 1280,         /* height */
603     .hbp = 80,              /* horizontal back porch */
604     .hfp = 80,              /* horizontal front porch */
605     .hsw = 20,              /* horizontal sync width */
606     .vbp = 12,              /* vertical back porch */
607     .vfp = 20,              /* vertical front porch */
608     .vsw = 4,               /* vertical sync width */
609     .clockFreq = 76800000,  /* clock */
610     .pWidth = 150,          /* physical width */
611     .pHeight = 240,         /* physical height */
612     .blk = { BLK_PWM, MIN_LEVEL, MAX_LEVEL, DEFAULT_LEVEL },
613 };
614 
615 static struct GpioTiming g_rstOnSeq[] = {
616     {1, 5},   /* high, delay 5ms */
617     {0, 20},  /* low, delay 20ms */
618     {1, 30},  /* high, delay 30ms */
619 };
620 
621 static struct GpioTiming g_rstOffSeq = {0, 10}; /* low, delay 10ms */
622 
Ili9881cBoeResInit(struct Ili9881cBoeDev * ili9881cBoeDev)623 static void Ili9881cBoeResInit(struct Ili9881cBoeDev *ili9881cBoeDev)
624 {
625     ili9881cBoeDev->avddGpio = AVDD_GPIO;
626     ili9881cBoeDev->aveeGpio = AVEE_GPIO;
627     ili9881cBoeDev->vghlGpio = VGHL_GPIO;
628     ili9881cBoeDev->tsrstGpio = TSRST_GPIO;
629     ili9881cBoeDev->resetGpio = RESET_GPIO;
630     ili9881cBoeDev->rstOnSeq.items = sizeof(g_rstOnSeq) / sizeof(struct GpioTiming);
631     ili9881cBoeDev->rstOnSeq.timing = g_rstOnSeq;
632     ili9881cBoeDev->rstOffSeq.items = 1; /* number of reset off sequence */
633     ili9881cBoeDev->rstOffSeq.timing = &g_rstOffSeq;
634     ili9881cBoeDev->dsiDev->lanes = ILI9881C_MIPI_DATA_LANES; /* number of active data lanes */
635     ili9881cBoeDev->dsiDev->format = MIPI_DSI_FMT_RGB888; /* pixel format for video mode */
636     ili9881cBoeDev->dsiDev->mode_flags = (MIPI_DSI_MODE_VIDEO \
637                                         | MIPI_DSI_MODE_VIDEO_BURST); /* DSI operation mode related flags */
638     ili9881cBoeDev->panel.info = &g_panelInfo;
639     ili9881cBoeDev->panel.init = Ili9881cBoeInit;
640     ili9881cBoeDev->panel.on = Ili9881cBoeOn;
641     ili9881cBoeDev->panel.off = Ili9881cBoeOff;
642     ili9881cBoeDev->panel.priv = ili9881cBoeDev->dsiDev;
643 }
644 
Ili9881cBoeEntryInit(struct HdfDeviceObject * object)645 int32_t Ili9881cBoeEntryInit(struct HdfDeviceObject *object)
646 {
647     struct device_node *panelNode = NULL;
648     struct Ili9881cBoeDev *ili9881cBoeDev = NULL;
649 
650     ili9881cBoeDev = (struct Ili9881cBoeDev *)OsalMemCalloc(sizeof(struct Ili9881cBoeDev));
651     if (ili9881cBoeDev == NULL) {
652         HDF_LOGE("%s ili9881cBoeDev malloc fail", __func__);
653         return HDF_FAILURE;
654     }
655     panelNode = of_find_compatible_node(NULL, NULL, "sprd,generic-mipi-panel");
656     if (panelNode == NULL) {
657         HDF_LOGE("%s of_find_compatible_node fail", __func__);
658         goto FAIL;
659     }
660     ili9881cBoeDev->dsiDev = of_find_mipi_dsi_device_by_node(panelNode);
661     if (ili9881cBoeDev->dsiDev == NULL) {
662         HDF_LOGE("%s of_find_mipi_dsi_device_by_node fail", __func__);
663         goto FAIL;
664     }
665     ili9881cBoeDev->supply = devm_regulator_get(&ili9881cBoeDev->dsiDev->dev, "power");
666     if (ili9881cBoeDev->supply == NULL) {
667         HDF_LOGE("Get regulator fail");
668         goto FAIL;
669     }
670     Ili9881cBoeResInit(ili9881cBoeDev);
671     ili9881cBoeDev->panel.blDev = GetBacklightDev("hdf_pwm");
672     if (ili9881cBoeDev->panel.blDev == NULL) {
673         HDF_LOGE("%s GetBacklightDev fail", __func__);
674         goto FAIL;
675     }
676     ili9881cBoeDev->panel.object = object;
677     object->priv = ili9881cBoeDev;
678     if (RegisterPanel(&ili9881cBoeDev->panel) == HDF_SUCCESS) {
679         HDF_LOGI("%s success", __func__);
680         return HDF_SUCCESS;
681     }
682 
683 FAIL:
684     OsalMemFree(ili9881cBoeDev);
685     return HDF_FAILURE;
686 }
687 
688 struct HdfDriverEntry g_ili9881cBoeDevEntry = {
689     .moduleVersion = 1,
690     .moduleName = "LCD_ILI9881CBOE",
691     .Init = Ili9881cBoeEntryInit,
692 };
693 
694 HDF_INIT(g_ili9881cBoeDevEntry);
695