File Index
Files and directories
Sign in
FILE

videocc-sa8775p.c

File preview with syntax highlighting.

linux-6.19.14/drivers/clk/qcom/videocc-sa8775p.c C
  1// SPDX-License-Identifier: GPL-2.0-only
  2/*
  3 * Copyright (c) 2024, Qualcomm Innovation Center, Inc. All rights reserved.
  4 */
  5
  6#include <linux/clk-provider.h>
  7#include <linux/module.h>
  8#include <linux/mod_devicetable.h>
  9#include <linux/of.h>
 10#include <linux/platform_device.h>
 11#include <linux/pm_runtime.h>
 12#include <linux/regmap.h>
 13
 14#include <dt-bindings/clock/qcom,sa8775p-videocc.h>
 15
 16#include "clk-alpha-pll.h"
 17#include "clk-branch.h"
 18#include "clk-pll.h"
 19#include "clk-rcg.h"
 20#include "clk-regmap.h"
 21#include "clk-regmap-divider.h"
 22#include "clk-regmap-mux.h"
 23#include "common.h"
 24#include "gdsc.h"
 25#include "reset.h"
 26
 27enum {
 28	DT_IFACE,
 29	DT_BI_TCXO,
 30	DT_BI_TCXO_AO,
 31	DT_SLEEP_CLK,
 32};
 33
 34enum {
 35	P_BI_TCXO,
 36	P_BI_TCXO_AO,
 37	P_SLEEP_CLK,
 38	P_VIDEO_PLL0_OUT_MAIN,
 39	P_VIDEO_PLL1_OUT_MAIN,
 40};
 41
 42static const struct pll_vco lucid_evo_vco[] = {
 43	{ 249600000, 2020000000, 0 },
 44};
 45
 46static const struct alpha_pll_config video_pll0_config = {
 47	.l = 0x39,
 48	.alpha = 0x3000,
 49	.config_ctl_val = 0x20485699,
 50	.config_ctl_hi_val = 0x00182261,
 51	.config_ctl_hi1_val = 0x32aa299c,
 52	.user_ctl_val = 0x00000000,
 53	.user_ctl_hi_val = 0x00400805,
 54};
 55
 56static struct clk_alpha_pll video_pll0 = {
 57	.offset = 0x0,
 58	.vco_table = lucid_evo_vco,
 59	.num_vco = ARRAY_SIZE(lucid_evo_vco),
 60	.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_LUCID_EVO],
 61	.clkr = {
 62		.hw.init = &(const struct clk_init_data) {
 63			.name = "video_pll0",
 64			.parent_data = &(const struct clk_parent_data) {
 65				.index = DT_BI_TCXO,
 66			},
 67			.num_parents = 1,
 68			.ops = &clk_alpha_pll_lucid_evo_ops,
 69		},
 70	},
 71};
 72
 73static const struct alpha_pll_config video_pll1_config = {
 74	.l = 0x39,
 75	.alpha = 0x3000,
 76	.config_ctl_val = 0x20485699,
 77	.config_ctl_hi_val = 0x00182261,
 78	.config_ctl_hi1_val = 0x32aa299c,
 79	.user_ctl_val = 0x00000000,
 80	.user_ctl_hi_val = 0x00400805,
 81};
 82
 83static struct clk_alpha_pll video_pll1 = {
 84	.offset = 0x1000,
 85	.vco_table = lucid_evo_vco,
 86	.num_vco = ARRAY_SIZE(lucid_evo_vco),
 87	.regs = clk_alpha_pll_regs[CLK_ALPHA_PLL_TYPE_LUCID_EVO],
 88	.clkr = {
 89		.hw.init = &(const struct clk_init_data) {
 90			.name = "video_pll1",
 91			.parent_data = &(const struct clk_parent_data) {
 92				.index = DT_BI_TCXO,
 93			},
 94			.num_parents = 1,
 95			.ops = &clk_alpha_pll_lucid_evo_ops,
 96		},
 97	},
 98};
 99
100static const struct parent_map video_cc_parent_map_0_ao[] = {
101	{ P_BI_TCXO_AO, 0 },
102};
103
104static const struct clk_parent_data video_cc_parent_data_0_ao[] = {
105	{ .index = DT_BI_TCXO_AO },
106};
107
108static const struct parent_map video_cc_parent_map_1[] = {
109	{ P_BI_TCXO, 0 },
110	{ P_VIDEO_PLL0_OUT_MAIN, 1 },
111};
112
113static const struct clk_parent_data video_cc_parent_data_1[] = {
114	{ .index = DT_BI_TCXO },
115	{ .hw = &video_pll0.clkr.hw },
116};
117
118static const struct parent_map video_cc_parent_map_2[] = {
119	{ P_BI_TCXO, 0 },
120	{ P_VIDEO_PLL1_OUT_MAIN, 1 },
121};
122
123static const struct clk_parent_data video_cc_parent_data_2[] = {
124	{ .index = DT_BI_TCXO },
125	{ .hw = &video_pll1.clkr.hw },
126};
127
128static const struct parent_map video_cc_parent_map_3[] = {
129	{ P_SLEEP_CLK, 0 },
130};
131
132static const struct clk_parent_data video_cc_parent_data_3[] = {
133	{ .index = DT_SLEEP_CLK },
134};
135
136static const struct freq_tbl ftbl_video_cc_ahb_clk_src[] = {
137	F(19200000, P_BI_TCXO_AO, 1, 0, 0),
138	{ }
139};
140
141static struct clk_rcg2 video_cc_ahb_clk_src = {
142	.cmd_rcgr = 0x8030,
143	.mnd_width = 0,
144	.hid_width = 5,
145	.parent_map = video_cc_parent_map_0_ao,
146	.freq_tbl = ftbl_video_cc_ahb_clk_src,
147	.clkr.hw.init = &(const struct clk_init_data) {
148		.name = "video_cc_ahb_clk_src",
149		.parent_data = video_cc_parent_data_0_ao,
150		.num_parents = ARRAY_SIZE(video_cc_parent_data_0_ao),
151		.flags = CLK_SET_RATE_PARENT,
152		.ops = &clk_rcg2_shared_ops,
153	},
154};
155
156static const struct freq_tbl ftbl_video_cc_mvs0_clk_src[] = {
157	F(1098000000, P_VIDEO_PLL0_OUT_MAIN, 1, 0, 0),
158	F(1332000000, P_VIDEO_PLL0_OUT_MAIN, 1, 0, 0),
159	F(1599000000, P_VIDEO_PLL0_OUT_MAIN, 1, 0, 0),
160	F(1680000000, P_VIDEO_PLL0_OUT_MAIN, 1, 0, 0),
161	{ }
162};
163
164static struct clk_rcg2 video_cc_mvs0_clk_src = {
165	.cmd_rcgr = 0x8000,
166	.mnd_width = 0,
167	.hid_width = 5,
168	.parent_map = video_cc_parent_map_1,
169	.freq_tbl = ftbl_video_cc_mvs0_clk_src,
170	.clkr.hw.init = &(const struct clk_init_data) {
171		.name = "video_cc_mvs0_clk_src",
172		.parent_data = video_cc_parent_data_1,
173		.num_parents = ARRAY_SIZE(video_cc_parent_data_1),
174		.flags = CLK_SET_RATE_PARENT,
175		.ops = &clk_rcg2_shared_ops,
176	},
177};
178
179static const struct freq_tbl ftbl_video_cc_mvs1_clk_src[] = {
180	F(1098000000, P_VIDEO_PLL1_OUT_MAIN, 1, 0, 0),
181	F(1332000000, P_VIDEO_PLL1_OUT_MAIN, 1, 0, 0),
182	F(1600000000, P_VIDEO_PLL1_OUT_MAIN, 1, 0, 0),
183	F(1800000000, P_VIDEO_PLL1_OUT_MAIN, 1, 0, 0),
184	{ }
185};
186
187static struct clk_rcg2 video_cc_mvs1_clk_src = {
188	.cmd_rcgr = 0x8018,
189	.mnd_width = 0,
190	.hid_width = 5,
191	.parent_map = video_cc_parent_map_2,
192	.freq_tbl = ftbl_video_cc_mvs1_clk_src,
193	.clkr.hw.init = &(const struct clk_init_data) {
194		.name = "video_cc_mvs1_clk_src",
195		.parent_data = video_cc_parent_data_2,
196		.num_parents = ARRAY_SIZE(video_cc_parent_data_2),
197		.flags = CLK_SET_RATE_PARENT,
198		.ops = &clk_rcg2_shared_ops,
199	},
200};
201
202static const struct freq_tbl ftbl_video_cc_sleep_clk_src[] = {
203	F(32000, P_SLEEP_CLK, 1, 0, 0),
204	{ }
205};
206
207static struct clk_rcg2 video_cc_sleep_clk_src = {
208	.cmd_rcgr = 0x812c,
209	.mnd_width = 0,
210	.hid_width = 5,
211	.parent_map = video_cc_parent_map_3,
212	.freq_tbl = ftbl_video_cc_sleep_clk_src,
213	.clkr.hw.init = &(const struct clk_init_data) {
214		.name = "video_cc_sleep_clk_src",
215		.parent_data = video_cc_parent_data_3,
216		.num_parents = ARRAY_SIZE(video_cc_parent_data_3),
217		.flags = CLK_SET_RATE_PARENT,
218		.ops = &clk_rcg2_shared_ops,
219	},
220};
221
222static struct clk_rcg2 video_cc_xo_clk_src = {
223	.cmd_rcgr = 0x8110,
224	.mnd_width = 0,
225	.hid_width = 5,
226	.parent_map = video_cc_parent_map_0_ao,
227	.freq_tbl = ftbl_video_cc_ahb_clk_src,
228	.clkr.hw.init = &(const struct clk_init_data) {
229		.name = "video_cc_xo_clk_src",
230		.parent_data = video_cc_parent_data_0_ao,
231		.num_parents = ARRAY_SIZE(video_cc_parent_data_0_ao),
232		.flags = CLK_SET_RATE_PARENT,
233		.ops = &clk_rcg2_shared_ops,
234	},
235};
236
237static struct clk_regmap_div video_cc_mvs0_div_clk_src = {
238	.reg = 0x80b8,
239	.shift = 0,
240	.width = 4,
241	.clkr.hw.init = &(const struct clk_init_data) {
242		.name = "video_cc_mvs0_div_clk_src",
243		.parent_hws = (const struct clk_hw*[]) {
244			&video_cc_mvs0_clk_src.clkr.hw,
245		},
246		.num_parents = 1,
247		.flags = CLK_SET_RATE_PARENT,
248		.ops = &clk_regmap_div_ro_ops,
249	},
250};
251
252static struct clk_regmap_div video_cc_mvs0c_div2_div_clk_src = {
253	.reg = 0x806c,
254	.shift = 0,
255	.width = 4,
256	.clkr.hw.init = &(const struct clk_init_data) {
257		.name = "video_cc_mvs0c_div2_div_clk_src",
258		.parent_hws = (const struct clk_hw*[]) {
259			&video_cc_mvs0_clk_src.clkr.hw,
260		},
261		.num_parents = 1,
262		.flags = CLK_SET_RATE_PARENT,
263		.ops = &clk_regmap_div_ro_ops,
264	},
265};
266
267static struct clk_regmap_div video_cc_mvs1_div_clk_src = {
268	.reg = 0x80dc,
269	.shift = 0,
270	.width = 4,
271	.clkr.hw.init = &(const struct clk_init_data) {
272		.name = "video_cc_mvs1_div_clk_src",
273		.parent_hws = (const struct clk_hw*[]) {
274			&video_cc_mvs1_clk_src.clkr.hw,
275		},
276		.num_parents = 1,
277		.flags = CLK_SET_RATE_PARENT,
278		.ops = &clk_regmap_div_ro_ops,
279	},
280};
281
282static struct clk_regmap_div video_cc_mvs1c_div2_div_clk_src = {
283	.reg = 0x8094,
284	.shift = 0,
285	.width = 4,
286	.clkr.hw.init = &(const struct clk_init_data) {
287		.name = "video_cc_mvs1c_div2_div_clk_src",
288		.parent_hws = (const struct clk_hw*[]) {
289			&video_cc_mvs1_clk_src.clkr.hw,
290		},
291		.num_parents = 1,
292		.flags = CLK_SET_RATE_PARENT,
293		.ops = &clk_regmap_div_ro_ops,
294	},
295};
296
297static struct clk_regmap_div video_cc_sm_div_clk_src = {
298	.reg = 0x8108,
299	.shift = 0,
300	.width = 4,
301	.clkr.hw.init = &(const struct clk_init_data) {
302		.name = "video_cc_sm_div_clk_src",
303		.ops = &clk_regmap_div_ro_ops,
304	},
305};
306
307static struct clk_branch video_cc_mvs0_clk = {
308	.halt_reg = 0x80b0,
309	.halt_check = BRANCH_HALT_VOTED,
310	.hwcg_reg = 0x80b0,
311	.hwcg_bit = 1,
312	.clkr = {
313		.enable_reg = 0x80b0,
314		.enable_mask = BIT(0),
315		.hw.init = &(const struct clk_init_data) {
316			.name = "video_cc_mvs0_clk",
317			.parent_hws = (const struct clk_hw*[]) {
318				&video_cc_mvs0_div_clk_src.clkr.hw,
319			},
320			.num_parents = 1,
321			.flags = CLK_SET_RATE_PARENT,
322			.ops = &clk_branch2_ops,
323		},
324	},
325};
326
327static struct clk_branch video_cc_mvs0c_clk = {
328	.halt_reg = 0x8064,
329	.halt_check = BRANCH_HALT,
330	.clkr = {
331		.enable_reg = 0x8064,
332		.enable_mask = BIT(0),
333		.hw.init = &(const struct clk_init_data) {
334			.name = "video_cc_mvs0c_clk",
335			.parent_hws = (const struct clk_hw*[]) {
336				&video_cc_mvs0c_div2_div_clk_src.clkr.hw,
337			},
338			.num_parents = 1,
339			.flags = CLK_SET_RATE_PARENT,
340			.ops = &clk_branch2_ops,
341		},
342	},
343};
344
345static struct clk_branch video_cc_mvs1_clk = {
346	.halt_reg = 0x80d4,
347	.halt_check = BRANCH_HALT_VOTED,
348	.hwcg_reg = 0x80d4,
349	.hwcg_bit = 1,
350	.clkr = {
351		.enable_reg = 0x80d4,
352		.enable_mask = BIT(0),
353		.hw.init = &(const struct clk_init_data) {
354			.name = "video_cc_mvs1_clk",
355			.parent_hws = (const struct clk_hw*[]) {
356				&video_cc_mvs1_div_clk_src.clkr.hw,
357			},
358			.num_parents = 1,
359			.flags = CLK_SET_RATE_PARENT,
360			.ops = &clk_branch2_ops,
361		},
362	},
363};
364
365static struct clk_branch video_cc_mvs1c_clk = {
366	.halt_reg = 0x808c,
367	.halt_check = BRANCH_HALT,
368	.clkr = {
369		.enable_reg = 0x808c,
370		.enable_mask = BIT(0),
371		.hw.init = &(const struct clk_init_data) {
372			.name = "video_cc_mvs1c_clk",
373			.parent_hws = (const struct clk_hw*[]) {
374				&video_cc_mvs1c_div2_div_clk_src.clkr.hw,
375			},
376			.num_parents = 1,
377			.flags = CLK_SET_RATE_PARENT,
378			.ops = &clk_branch2_ops,
379		},
380	},
381};
382
383static struct clk_branch video_cc_pll_lock_monitor_clk = {
384	.halt_reg = 0x9000,
385	.halt_check = BRANCH_HALT,
386	.clkr = {
387		.enable_reg = 0x9000,
388		.enable_mask = BIT(0),
389		.hw.init = &(const struct clk_init_data) {
390			.name = "video_cc_pll_lock_monitor_clk",
391			.parent_hws = (const struct clk_hw*[]) {
392				&video_cc_xo_clk_src.clkr.hw,
393			},
394			.num_parents = 1,
395			.flags = CLK_SET_RATE_PARENT,
396			.ops = &clk_branch2_ops,
397		},
398	},
399};
400
401static struct clk_branch video_cc_sm_obs_clk = {
402	.halt_reg = 0x810c,
403	.halt_check = BRANCH_HALT_SKIP,
404	.clkr = {
405		.enable_reg = 0x810c,
406		.enable_mask = BIT(0),
407		.hw.init = &(const struct clk_init_data) {
408			.name = "video_cc_sm_obs_clk",
409			.parent_hws = (const struct clk_hw*[]) {
410				&video_cc_sm_div_clk_src.clkr.hw,
411			},
412			.num_parents = 1,
413			.flags = CLK_SET_RATE_PARENT,
414			.ops = &clk_branch2_ops,
415		},
416	},
417};
418
419static struct gdsc video_cc_mvs0c_gdsc = {
420	.gdscr = 0x804c,
421	.en_rest_wait_val = 0x2,
422	.en_few_wait_val = 0x2,
423	.clk_dis_wait_val = 0x6,
424	.pd = {
425		.name = "video_cc_mvs0c_gdsc",
426	},
427	.pwrsts = PWRSTS_OFF_ON,
428	.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
429};
430
431static struct gdsc video_cc_mvs0_gdsc = {
432	.gdscr = 0x809c,
433	.en_rest_wait_val = 0x2,
434	.en_few_wait_val = 0x2,
435	.clk_dis_wait_val = 0x6,
436	.pd = {
437		.name = "video_cc_mvs0_gdsc",
438	},
439	.pwrsts = PWRSTS_OFF_ON,
440	.parent = &video_cc_mvs0c_gdsc.pd,
441	.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR | HW_CTRL_TRIGGER,
442};
443
444static struct gdsc video_cc_mvs1c_gdsc = {
445	.gdscr = 0x8074,
446	.en_rest_wait_val = 0x2,
447	.en_few_wait_val = 0x2,
448	.clk_dis_wait_val = 0x6,
449	.pd = {
450		.name = "video_cc_mvs1c_gdsc",
451	},
452	.pwrsts = PWRSTS_OFF_ON,
453	.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR,
454};
455
456static struct gdsc video_cc_mvs1_gdsc = {
457	.gdscr = 0x80c0,
458	.en_rest_wait_val = 0x2,
459	.en_few_wait_val = 0x2,
460	.clk_dis_wait_val = 0x6,
461	.pd = {
462		.name = "video_cc_mvs1_gdsc",
463	},
464	.pwrsts = PWRSTS_OFF_ON,
465	.parent = &video_cc_mvs1c_gdsc.pd,
466	.flags = RETAIN_FF_ENABLE | POLL_CFG_GDSCR | HW_CTRL_TRIGGER,
467};
468
469static struct clk_regmap *video_cc_sa8775p_clocks[] = {
470	[VIDEO_CC_AHB_CLK_SRC] = &video_cc_ahb_clk_src.clkr,
471	[VIDEO_CC_MVS0_CLK] = &video_cc_mvs0_clk.clkr,
472	[VIDEO_CC_MVS0_CLK_SRC] = &video_cc_mvs0_clk_src.clkr,
473	[VIDEO_CC_MVS0_DIV_CLK_SRC] = &video_cc_mvs0_div_clk_src.clkr,
474	[VIDEO_CC_MVS0C_CLK] = &video_cc_mvs0c_clk.clkr,
475	[VIDEO_CC_MVS0C_DIV2_DIV_CLK_SRC] = &video_cc_mvs0c_div2_div_clk_src.clkr,
476	[VIDEO_CC_MVS1_CLK] = &video_cc_mvs1_clk.clkr,
477	[VIDEO_CC_MVS1_CLK_SRC] = &video_cc_mvs1_clk_src.clkr,
478	[VIDEO_CC_MVS1_DIV_CLK_SRC] = &video_cc_mvs1_div_clk_src.clkr,
479	[VIDEO_CC_MVS1C_CLK] = &video_cc_mvs1c_clk.clkr,
480	[VIDEO_CC_MVS1C_DIV2_DIV_CLK_SRC] = &video_cc_mvs1c_div2_div_clk_src.clkr,
481	[VIDEO_CC_PLL_LOCK_MONITOR_CLK] = &video_cc_pll_lock_monitor_clk.clkr,
482	[VIDEO_CC_SLEEP_CLK_SRC] = &video_cc_sleep_clk_src.clkr,
483	[VIDEO_CC_SM_DIV_CLK_SRC] = &video_cc_sm_div_clk_src.clkr,
484	[VIDEO_CC_SM_OBS_CLK] = &video_cc_sm_obs_clk.clkr,
485	[VIDEO_CC_XO_CLK_SRC] = &video_cc_xo_clk_src.clkr,
486	[VIDEO_PLL0] = &video_pll0.clkr,
487	[VIDEO_PLL1] = &video_pll1.clkr,
488};
489
490static struct gdsc *video_cc_sa8775p_gdscs[] = {
491	[VIDEO_CC_MVS0_GDSC] = &video_cc_mvs0_gdsc,
492	[VIDEO_CC_MVS0C_GDSC] = &video_cc_mvs0c_gdsc,
493	[VIDEO_CC_MVS1_GDSC] = &video_cc_mvs1_gdsc,
494	[VIDEO_CC_MVS1C_GDSC] = &video_cc_mvs1c_gdsc,
495};
496
497static const struct qcom_reset_map video_cc_sa8775p_resets[] = {
498	[VIDEO_CC_INTERFACE_BCR] = { 0x80e8 },
499	[VIDEO_CC_MVS0_BCR] = { 0x8098 },
500	[VIDEO_CC_MVS0C_CLK_ARES] = { 0x8064, 2 },
501	[VIDEO_CC_MVS0C_BCR] = { 0x8048 },
502	[VIDEO_CC_MVS1_BCR] = { 0x80bc },
503	[VIDEO_CC_MVS1C_CLK_ARES] = { 0x808c, 2 },
504	[VIDEO_CC_MVS1C_BCR] = { 0x8070 },
505};
506
507static const struct regmap_config video_cc_sa8775p_regmap_config = {
508	.reg_bits = 32,
509	.reg_stride = 4,
510	.val_bits = 32,
511	.max_register = 0xb000,
512	.fast_io = true,
513};
514
515static const struct qcom_cc_desc video_cc_sa8775p_desc = {
516	.config = &video_cc_sa8775p_regmap_config,
517	.clks = video_cc_sa8775p_clocks,
518	.num_clks = ARRAY_SIZE(video_cc_sa8775p_clocks),
519	.resets = video_cc_sa8775p_resets,
520	.num_resets = ARRAY_SIZE(video_cc_sa8775p_resets),
521	.gdscs = video_cc_sa8775p_gdscs,
522	.num_gdscs = ARRAY_SIZE(video_cc_sa8775p_gdscs),
523};
524
525static const struct of_device_id video_cc_sa8775p_match_table[] = {
526	{ .compatible = "qcom,qcs8300-videocc" },
527	{ .compatible = "qcom,sa8775p-videocc" },
528	{ }
529};
530MODULE_DEVICE_TABLE(of, video_cc_sa8775p_match_table);
531
532static int video_cc_sa8775p_probe(struct platform_device *pdev)
533{
534	struct regmap *regmap;
535	int ret;
536
537	ret = devm_pm_runtime_enable(&pdev->dev);
538	if (ret)
539		return ret;
540
541	ret = pm_runtime_resume_and_get(&pdev->dev);
542	if (ret)
543		return ret;
544
545	regmap = qcom_cc_map(pdev, &video_cc_sa8775p_desc);
546	if (IS_ERR(regmap)) {
547		pm_runtime_put(&pdev->dev);
548		return PTR_ERR(regmap);
549	}
550
551	clk_lucid_evo_pll_configure(&video_pll0, regmap, &video_pll0_config);
552	clk_lucid_evo_pll_configure(&video_pll1, regmap, &video_pll1_config);
553
554	/*
555	 * Set mvs0c clock divider to div-3 to make the mvs0 and
556	 * mvs0c clocks to run at the same frequency on QCS8300
557	 */
558	if (of_device_is_compatible(pdev->dev.of_node, "qcom,qcs8300-videocc"))
559		regmap_write(regmap, video_cc_mvs0c_div2_div_clk_src.reg, 2);
560
561	/* Keep some clocks always enabled */
562	qcom_branch_set_clk_en(regmap, 0x80ec); /* VIDEO_CC_AHB_CLK */
563	qcom_branch_set_clk_en(regmap, 0x8144); /* VIDEO_CC_SLEEP_CLK */
564	qcom_branch_set_clk_en(regmap, 0x8128); /* VIDEO_CC_XO_CLK */
565
566	ret = qcom_cc_really_probe(&pdev->dev, &video_cc_sa8775p_desc, regmap);
567
568	pm_runtime_put(&pdev->dev);
569
570	return ret;
571}
572
573static struct platform_driver video_cc_sa8775p_driver = {
574	.probe = video_cc_sa8775p_probe,
575	.driver = {
576		.name = "videocc-sa8775p",
577		.of_match_table = video_cc_sa8775p_match_table,
578	},
579};
580
581module_platform_driver(video_cc_sa8775p_driver);
582
583MODULE_DESCRIPTION("QTI VIDEOCC SA8775P Driver");
584MODULE_LICENSE("GPL");
~/ Read-only file preview.