1 #include "camsys_marvin.h"
3 static const char miscdev_name[] = CAMSYS_MARVIN_DEVNAME;
6 static int camsys_mrv_iomux_cb(camsys_extdev_t *extdev,void *ptr)
8 unsigned int cif_vol_sel;
10 if (extdev->dev_cfg & CAMSYS_DEVCFG_FLASHLIGHT) {
11 iomux_set(ISP_FLASH_TRIG);
12 if (extdev->fl.fl.io != 0xffffffff) {
13 iomux_set(ISP_FL_TRIG);
17 if (extdev->dev_cfg & CAMSYS_DEVCFG_PREFLASHLIGHT) {
18 iomux_set(ISP_PRELIGHT_TRIG);
21 if (extdev->dev_cfg & CAMSYS_DEVCFG_SHUTTER) {
22 iomux_set(ISP_SHUTTER_OPEN);
23 iomux_set(ISP_SHUTTER_TRIG);
26 iomux_set(CIF0_CLKOUT);
29 struct pinctrl *pinctrl;
30 struct pinctrl_state *state;
32 char state_str[20] = {0};
34 struct device *dev = &(extdev->pdev->dev);
36 if (extdev->phy.type == CamSys_Phy_Cif) {
37 if ((extdev->phy.info.cif.fmt >= CamSys_Fmt_Raw_8b)&& (extdev->phy.info.cif.fmt <= CamSys_Fmt_Raw_12b)) {
39 strcpy(state_str,"isp_dvp8bit");
43 if ((extdev->phy.info.cif.fmt >= CamSys_Fmt_Raw_10b)&& (extdev->phy.info.cif.fmt <= CamSys_Fmt_Raw_12b)) {
44 strcpy(state_str,"isp_dvp10bit");
47 if (extdev->phy.info.cif.fmt == CamSys_Fmt_Raw_12b) {
48 strcpy(state_str,"isp_dvp12bit");
52 strcpy(state_str,"default");
57 pinctrl = devm_pinctrl_get(dev);
58 if (IS_ERR(pinctrl)) {
59 camsys_err("%s:Get pinctrl failed!\n",__func__);
62 state = pinctrl_lookup_state(pinctrl,
65 dev_err(dev, "%s:could not get %s pinstate\n",__func__,state_str);
70 retval = pinctrl_select_state(pinctrl, state);
73 "%s:could not set %s pins\n",__func__,state_str);
80 if (extdev->phy.type == CamSys_Phy_Cif) {
83 if (!IS_ERR_OR_NULL(extdev->dovdd.ldo)) {
84 if (extdev->dovdd.max_uv >= 25000000) {
85 __raw_writel(((1<<1)|(1<<(1+16))),RK30_GRF_BASE+0x018c);
87 __raw_writel((1<<(1+16)),RK30_GRF_BASE+0x018c);
90 __raw_writel(((1<<1)|(1<<(1+16))),RK30_GRF_BASE+0x018c);
93 __raw_writel(((1<<1)|(1<<(1+16))),RK_GRF_VIRT+0x018c);
97 __raw_writel(0xffffffff, RK_GRF_VIRT+0x01dc);
103 static int camsys_mrv_reset_cb(void *ptr)
105 camsys_dev_t *camsys_dev = (camsys_dev_t*)ptr;
106 #if 0 //do nothing ,zyc
107 cru_set_soft_reset(SOFT_RST_ISP,true);
109 cru_set_soft_reset(SOFT_RST_ISP,false);
111 camsys_trace(1, "%s soft reset\n",dev_name(camsys_dev->miscdev.this_device));
115 static int camsys_mrv_clkin_cb(void *ptr, unsigned int on)
117 camsys_dev_t *camsys_dev = (camsys_dev_t*)ptr;
118 camsys_mrv_clk_t *clk = (camsys_mrv_clk_t*)camsys_dev->clk;
120 spin_lock(&clk->lock);
121 if (on && !clk->in_on) {
122 clk_enable(clk->pd_isp);
123 clk_enable(clk->aclk_isp);
124 clk_enable(clk->hclk_isp);
125 clk_enable(clk->isp);
126 clk_enable(clk->isp_jpe);
127 clk_enable(clk->pclkin_isp);
131 camsys_trace(1, "%s clock in turn on",dev_name(camsys_dev->miscdev.this_device));
132 camsys_mrv_reset_cb(ptr);
134 } else if (!on && clk->in_on) {
135 clk_disable(clk->pd_isp);
136 clk_disable(clk->aclk_isp);
137 clk_disable(clk->hclk_isp);
138 clk_disable(clk->isp);
139 clk_disable(clk->isp_jpe);
140 clk_disable(clk->pclkin_isp);
142 camsys_trace(1, "%s clock in turn off",dev_name(camsys_dev->miscdev.this_device));
144 spin_unlock(&clk->lock);
148 static int camsys_mrv_clkout_cb(void *ptr, unsigned int on)
150 camsys_dev_t *camsys_dev = (camsys_dev_t*)ptr;
151 camsys_mrv_clk_t *clk = (camsys_mrv_clk_t*)camsys_dev->clk;
152 struct clk *cif_clk_out_div;
154 spin_lock(&clk->lock);
155 if (on && (clk->out_on != on)) {
156 clk_enable(clk->cif_clk_out);
157 clk_set_rate(clk->cif_clk_out,on);
160 camsys_trace(1, "%s clock out(rate: %dHz) turn on",dev_name(camsys_dev->miscdev.this_device),
162 } else if (!on && clk->out_on) {
163 cif_clk_out_div = clk_get(NULL, "cif0_out_div");
164 if(IS_ERR_OR_NULL(cif_clk_out_div)) {
165 cif_clk_out_div = clk_get(NULL, "cif_out_div");
168 if(!IS_ERR_OR_NULL(cif_clk_out_div)) {
169 clk_set_parent(clk->cif_clk_out, cif_clk_out_div);
170 clk_put(cif_clk_out_div);
172 camsys_warn("%s clock out may be not off!", dev_name(camsys_dev->miscdev.this_device));
174 clk_disable(clk->cif_clk_out);
177 camsys_trace(1, "%s clock out turn off",dev_name(camsys_dev->miscdev.this_device));
179 spin_unlock(&clk->lock);
183 static irqreturn_t camsys_mrv_irq(int irq, void *data)
185 camsys_dev_t *camsys_dev = (camsys_dev_t*)data;
186 camsys_irqstas_t *irqsta;
187 camsys_irqpool_t *irqpool;
188 unsigned int isp_mis,mipi_mis,mi_mis,*mis;
190 isp_mis = __raw_readl((void volatile *)(camsys_dev->devmems.registermem->vir_base + MRV_ISP_MIS));
191 mipi_mis = __raw_readl((void volatile *)(camsys_dev->devmems.registermem->vir_base + MRV_MIPI_MIS));
192 mi_mis = __raw_readl((void volatile *)(camsys_dev->devmems.registermem->vir_base + MRV_MI_MIS));
194 __raw_writel(isp_mis, (void volatile *)(camsys_dev->devmems.registermem->vir_base + MRV_ISP_ICR));
195 __raw_writel(mipi_mis, (void volatile *)(camsys_dev->devmems.registermem->vir_base + MRV_MIPI_ICR));
196 __raw_writel(mi_mis, (void volatile *)(camsys_dev->devmems.registermem->vir_base + MRV_MI_ICR));
198 spin_lock(&camsys_dev->irq.lock);
199 if (!list_empty(&camsys_dev->irq.irq_pool)) {
200 list_for_each_entry(irqpool, &camsys_dev->irq.irq_pool, list) {
201 if (irqpool->pid != 0) {
223 camsys_trace(2,"Thread(pid:%d) irqpool mis(%d) is invalidate",irqpool->pid,irqpool->mis);
229 spin_lock(&irqpool->lock);
230 if (!list_empty(&irqpool->deactive)) {
231 irqsta = list_first_entry(&irqpool->deactive, camsys_irqstas_t, list);
232 irqsta->sta.mis = *mis;
233 list_del_init(&irqsta->list);
234 list_add_tail(&irqsta->list,&irqpool->active);
235 wake_up(&irqpool->done);
237 spin_unlock(&irqpool->lock);
243 spin_unlock(&camsys_dev->irq.lock);
247 static int camsys_mrv_remove_cb(struct platform_device *pdev)
249 camsys_dev_t *camsys_dev = platform_get_drvdata(pdev);
250 camsys_mrv_clk_t *mrv_clk=NULL;
252 if (camsys_dev->clk != NULL) {
254 mrv_clk = (camsys_mrv_clk_t*)camsys_dev->clk;
256 camsys_mrv_clkout_cb(mrv_clk,0);
258 camsys_mrv_clkin_cb(mrv_clk,0);
260 if (!IS_ERR_OR_NULL(mrv_clk->pd_isp)) {
261 clk_put(mrv_clk->pd_isp);
263 if (!IS_ERR_OR_NULL(mrv_clk->aclk_isp)) {
264 clk_put(mrv_clk->aclk_isp);
266 if (!IS_ERR_OR_NULL(mrv_clk->hclk_isp)) {
267 clk_put(mrv_clk->hclk_isp);
269 if (!IS_ERR_OR_NULL(mrv_clk->isp)) {
270 clk_put(mrv_clk->isp);
272 if (!IS_ERR_OR_NULL(mrv_clk->isp_jpe)) {
273 clk_put(mrv_clk->isp_jpe);
275 if (!IS_ERR_OR_NULL(mrv_clk->pclkin_isp)) {
276 clk_put(mrv_clk->pclkin_isp);
278 if (!IS_ERR_OR_NULL(mrv_clk->cif_clk_out)) {
279 clk_put(mrv_clk->cif_clk_out);
288 int camsys_mrv_probe_cb(struct platform_device *pdev, camsys_dev_t *camsys_dev)
291 camsys_mrv_clk_t *mrv_clk=NULL;
292 //struct clk *clk_parent;
294 err = request_irq(camsys_dev->irq.irq_id, camsys_mrv_irq, 0, CAMSYS_MARVIN_IRQNAME,camsys_dev);
296 camsys_err("request irq for %s failed",CAMSYS_MARVIN_IRQNAME);
301 mrv_clk = kzalloc(sizeof(camsys_mrv_clk_t),GFP_KERNEL);
302 if (mrv_clk == NULL) {
303 camsys_err("Allocate camsys_mrv_clk_t failed!");
308 // mrv_clk->pd_isp = devm_clk_get(&pdev->dev, "pd_isp");
309 mrv_clk->pd_isp = NULL;
310 mrv_clk->aclk_isp = devm_clk_get(&pdev->dev, "aclk_isp");
311 mrv_clk->hclk_isp = devm_clk_get(&pdev->dev, "hclk_isp");
312 mrv_clk->isp = devm_clk_get(&pdev->dev, "clk_isp");
313 mrv_clk->isp_jpe = devm_clk_get(&pdev->dev, "clk_isp_jpe");
314 mrv_clk->pclkin_isp = devm_clk_get(&pdev->dev, "pclkin_isp");
315 mrv_clk->cif_clk_out = devm_clk_get(&pdev->dev, "clk_vipout");
316 if (/*IS_ERR_OR_NULL(mrv_clk->pd_isp) ||*/ IS_ERR_OR_NULL(mrv_clk->aclk_isp) || IS_ERR_OR_NULL(mrv_clk->hclk_isp) ||
317 IS_ERR_OR_NULL(mrv_clk->isp) || IS_ERR_OR_NULL(mrv_clk->isp_jpe) || IS_ERR_OR_NULL(mrv_clk->pclkin_isp) ||
318 IS_ERR_OR_NULL(mrv_clk->cif_clk_out)) {
319 camsys_err("Get %s clock resouce failed!\n",miscdev_name);
324 clk_set_rate(mrv_clk->isp,320000000);
325 clk_set_rate(mrv_clk->isp_jpe,320000000);
327 spin_lock_init(&mrv_clk->lock);
329 mrv_clk->in_on = false;
332 camsys_dev->clk = (void*)mrv_clk;
333 camsys_dev->clkin_cb = camsys_mrv_clkin_cb;
334 camsys_dev->clkout_cb = camsys_mrv_clkout_cb;
335 camsys_dev->reset_cb = camsys_mrv_reset_cb;
336 camsys_dev->iomux = camsys_mrv_iomux_cb;
338 camsys_dev->miscdev.minor = MISC_DYNAMIC_MINOR;
339 camsys_dev->miscdev.name = miscdev_name;
340 camsys_dev->miscdev.nodename = miscdev_name;
341 camsys_dev->miscdev.fops = &camsys_fops;
343 err = misc_register(&camsys_dev->miscdev);
345 camsys_err("misc register %s failed!",miscdev_name);
346 goto misc_register_failed;
350 camsys_dev->dev_id = CAMSYS_DEVID_MARVIN;
351 camsys_dev->platform_remove = camsys_mrv_remove_cb;
354 misc_register_failed:
355 if (!IS_ERR_OR_NULL(camsys_dev->miscdev.this_device)) {
356 misc_deregister(&camsys_dev->miscdev);
360 if (mrv_clk != NULL) {
361 if (!IS_ERR_OR_NULL(mrv_clk->pd_isp)) {
362 clk_put(mrv_clk->pd_isp);
364 if (!IS_ERR_OR_NULL(mrv_clk->aclk_isp)) {
365 clk_put(mrv_clk->aclk_isp);
367 if (!IS_ERR_OR_NULL(mrv_clk->hclk_isp)) {
368 clk_put(mrv_clk->hclk_isp);
370 if (!IS_ERR_OR_NULL(mrv_clk->isp)) {
371 clk_put(mrv_clk->isp);
373 if (!IS_ERR_OR_NULL(mrv_clk->isp_jpe)) {
374 clk_put(mrv_clk->isp_jpe);
376 if (!IS_ERR_OR_NULL(mrv_clk->pclkin_isp)) {
377 clk_put(mrv_clk->pclkin_isp);
379 if (!IS_ERR_OR_NULL(mrv_clk->cif_clk_out)) {
380 clk_put(mrv_clk->cif_clk_out);
390 EXPORT_SYMBOL_GPL(camsys_mrv_probe_cb);