调试记录:rk3368 接触摸屏后进recovery无显示

soc:rk3368

Android:6.0

现象:接触摸屏后进recovery无显示,进Android系统正常;不接触摸屏正常显示recovery UI。

串口信息:

locale is [(null)]
stage is []
reason is [(null)]
cannot find/open a drm device: No such file or directory
fb0 reports (possibly inaccurate):
  vi.bits_per_pixel = 16
  vi.red.offset   =  11   .length =   5
  vi.green.offset =   5   .length =   6
  vi.blue.offset  =   0   .length =   5
  fi.line_length = 2048
framebuffer: 0 (1024 x 600) double_buffer 1

跟踪recovery代码发现打开fb正常,但阻塞在fbdev_blank里面的ioctl没有出来:

static void fbdev_blank(minui_backend* backend __unused, bool blank)
{
    int ret;

    ret = ioctl(fb_fd, FBIOBLANK, blank ? FB_BLANK_POWERDOWN : FB_BLANK_UNBLANK);
    if (ret < 0)
        perror("ioctl(): blank");
}

最后经过问题排查,将原因锁定到触摸屏驱动drivers/input/touchscreen/gt9xx。在resume和suspend中操作regulator时卡在wile循环中没有出来。所有导致kernel的驱动没有完整跑完,fb的ioctl也就没有返回。将触摸屏驱动resume和suspend代码修改一下解决。

-       regulator_tp = regulator_get(NULL,"vcc_tp");
-       if(regulator_tp ==NULL)
-       {
-               printk("!!!!%s:%d:get regulator_tp failed\n",__func__,__LINE__);
-               return 0;
-       }
-       while(regulator_is_enabled(regulator_tp))
-       {
-               reg = regulator_disable(regulator_tp);
-               msleep(10);
-       }
-       regulator_put(regulator_tp);
+
+       reg = regulator_disable(ts->tp_regulator);
+       if (reg < 0)
+               GTP_ERROR("failed to disable tp regulator\n");
        msleep(20);
        return 0;

为什么触摸屏和显示有关联呢?因为tp驱动的suspend与resume与fb关联在一起了。当fb BLANK时会回调tp的resume或者suspend.

    ts->tp.tp_resume = goodix_ts_early_resume;
    ts->tp.tp_suspend = goodix_ts_early_suspend;
    tp_register_fb(&ts->tp);
static inline int fb_notifier_callback(struct notifier_block *self,
				unsigned long action, void *data)
{
	struct tp_device *tp;
	struct fb_event *event = data;
	int blank_mode = *((int *)event->data);
	int ret = 0;

	tp = container_of(self, struct tp_device, fb_notif);

	//printk("%s.....lin=%d tp->status=%x,blank_mode=%x\n",__func__,__LINE__,tp->status,blank_mode);

	mutex_lock(&tp->ops_lock);

	if (action == FB_EARLY_EVENT_BLANK) {
		switch (blank_mode) {
		case FB_BLANK_UNBLANK:
			break;
		default:
			ret = tp->tp_suspend(tp);
			break;
		}
	}
	else if (action == FB_EVENT_BLANK) {
		switch (blank_mode) {
		case FB_BLANK_UNBLANK:
			tp->tp_resume(tp);
			break;
		default:
			break;
		}
	}
	mutex_unlock(&tp->ops_lock);

	if (ret < 0)
	{
		printk("TP_notifier_callback error action=%x,blank_mode=%x\n",(int)action,blank_mode);
		return ret;
	}

	return NOTIFY_OK;
}

static inline int tp_register_fb(struct tp_device *tp)
{
	memset(&tp->fb_notif, 0, sizeof(tp->fb_notif));
	tp->fb_notif.notifier_call = fb_notifier_callback;
	mutex_init(&tp->ops_lock);

	return fb_register_client(&tp->fb_notif);
}


猜你喜欢

转载自blog.csdn.net/dpppppp/article/details/80620340