static int
qpnp_pon_input_dispatch(struct qpnp_pon *pon, u32 pon_type)
{
	int rc;
	struct qpnp_pon_config *cfg = NULL;
	u8 pon_rt_sts = 0, pon_rt_bit = 0;

	cfg = qpnp_get_cfg(pon, pon_type);
	if (!cfg)
		return -EINVAL;

	/* Check if key reporting is supported */
	if (!cfg->key_code)
		return 0;

	/* check the RT status to get the current status of the line */
	rc = spmi_ext_register_readl(pon->spmi->ctrl, pon->spmi->sid,
				QPNP_PON_RT_STS(pon->base), &pon_rt_sts, 1);
	if (rc) {
		dev_err(&pon->spmi->dev, "Unable to read PON RT status\n");
		return rc;
	}

	switch (cfg->pon_type) {
	case PON_KPDPWR:
		pon_rt_bit = QPNP_PON_KPDPWR_N_SET;
		break;
	case PON_RESIN:
		pon_rt_bit = QPNP_PON_RESIN_N_SET;
		break;
	case PON_CBLPWR:
		pon_rt_bit = QPNP_PON_CBLPWR_N_SET;
		break;
	default:
		return -EINVAL;
	}

	input_report_key(pon->pon_input, cfg->key_code,
					(pon_rt_sts & pon_rt_bit));
	input_sync(pon->pon_input);

	if((cfg->key_code == 116) && (pon_rt_sts & pon_rt_bit)){
		pon->powerkey_state = 1;
	}else if((cfg->key_code == 116) && !(pon_rt_sts & pon_rt_bit)){
		pon->powerkey_state = 0;
	}
#if CONFIG_SEC_DEBUG
	sec_debug_check_crash_key(cfg->key_code, pon->powerkey_state);
#endif
#if defined(CONFIG_MACH_MONTBLANC)
	check_pkey_press=pon->powerkey_state;
#endif
	return 0;
}
Beispiel #2
0
static void bark_work_func(struct work_struct *work)
{
	int rc;
	u8 pon_rt_sts = 0;
	struct qpnp_pon_config *cfg;
	struct qpnp_pon *pon =
		container_of(work, struct qpnp_pon, bark_work.work);

	/* enable reset */
	rc = qpnp_pon_masked_write(pon, QPNP_PON_RESIN_S2_CNTL(pon->base),
				QPNP_PON_S2_CNTL_EN, QPNP_PON_S2_CNTL_EN);
	if (rc) {
		dev_err(&pon->spmi->dev, "Unable to configure S2 enable\n");
		goto err_return;
	}
	/* bark RT status update delay */
	msleep(100);
	/* read the bark RT status */
	rc = spmi_ext_register_readl(pon->spmi->ctrl, pon->spmi->sid,
				QPNP_PON_RT_STS(pon->base), &pon_rt_sts, 1);
	if (rc) {
		dev_err(&pon->spmi->dev, "Unable to read PON RT status\n");
		goto err_return;
	}

	if (!(pon_rt_sts & QPNP_PON_RESIN_BARK_N_SET)) {
		cfg = qpnp_get_cfg(pon, PON_RESIN);
		if (!cfg) {
			dev_err(&pon->spmi->dev, "Invalid config pointer\n");
			goto err_return;
		}
		/* report the key event and enable the bark IRQ */
		input_report_key(pon->pon_input, cfg->key_code, 0);
		input_sync(pon->pon_input);
		enable_irq(cfg->bark_irq);
	} else {
		/* disable reset */
		rc = qpnp_pon_masked_write(pon,
				QPNP_PON_RESIN_S2_CNTL(pon->base),
				QPNP_PON_S2_CNTL_EN, 0);
		if (rc) {
			dev_err(&pon->spmi->dev,
				"Unable to configure S2 enable\n");
			goto err_return;
		}
		/* re-arm the work */
		schedule_delayed_work(&pon->bark_work, QPNP_KEY_STATUS_DELAY);
	}

err_return:
	return;
}
Beispiel #3
0
static void forcecrash_timeout(unsigned long data)
{
	u8 pon_rt_sts = 0, rt_bit = QPNP_PON_KPDPWR_N_SET;
	int rc;

	rc = spmi_ext_register_readl(gspmi->ctrl, gspmi->sid,
			QPNP_PON_RT_STS(base), &pon_rt_sts, 1);
	if (rc)
		dev_err(dev, "Unable to read PON RT status\n");

	dev_info(dev, "status %d\n", pon_rt_sts & rt_bit);
	if (pon_rt_sts & rt_bit)
		panic("Force crash triggered!!!\n");
	else {
		del_timer(&forcecrash_timer);
		wake_unlock(&wakelock);
	}
}