static int imx6ul_tsc_probe()

in touchscreen/imx6ul_tsc.c [373:513]


static int imx6ul_tsc_probe(struct platform_device *pdev)
{
	struct device_node *np = pdev->dev.of_node;
	struct imx6ul_tsc *tsc;
	struct input_dev *input_dev;
	int err;
	int tsc_irq;
	int adc_irq;
	u32 average_samples;

	tsc = devm_kzalloc(&pdev->dev, sizeof(*tsc), GFP_KERNEL);
	if (!tsc)
		return -ENOMEM;

	input_dev = devm_input_allocate_device(&pdev->dev);
	if (!input_dev)
		return -ENOMEM;

	input_dev->name = "iMX6UL Touchscreen Controller";
	input_dev->id.bustype = BUS_HOST;

	input_dev->open = imx6ul_tsc_open;
	input_dev->close = imx6ul_tsc_close;

	input_set_capability(input_dev, EV_KEY, BTN_TOUCH);
	input_set_abs_params(input_dev, ABS_X, 0, 0xFFF, 0, 0);
	input_set_abs_params(input_dev, ABS_Y, 0, 0xFFF, 0, 0);

	input_set_drvdata(input_dev, tsc);

	tsc->dev = &pdev->dev;
	tsc->input = input_dev;
	init_completion(&tsc->completion);

	tsc->xnur_gpio = devm_gpiod_get(&pdev->dev, "xnur", GPIOD_IN);
	if (IS_ERR(tsc->xnur_gpio)) {
		err = PTR_ERR(tsc->xnur_gpio);
		dev_err(&pdev->dev,
			"failed to request GPIO tsc_X- (xnur): %d\n", err);
		return err;
	}

	tsc->tsc_regs = devm_platform_ioremap_resource(pdev, 0);
	if (IS_ERR(tsc->tsc_regs)) {
		err = PTR_ERR(tsc->tsc_regs);
		dev_err(&pdev->dev, "failed to remap tsc memory: %d\n", err);
		return err;
	}

	tsc->adc_regs = devm_platform_ioremap_resource(pdev, 1);
	if (IS_ERR(tsc->adc_regs)) {
		err = PTR_ERR(tsc->adc_regs);
		dev_err(&pdev->dev, "failed to remap adc memory: %d\n", err);
		return err;
	}

	tsc->tsc_clk = devm_clk_get(&pdev->dev, "tsc");
	if (IS_ERR(tsc->tsc_clk)) {
		err = PTR_ERR(tsc->tsc_clk);
		dev_err(&pdev->dev, "failed getting tsc clock: %d\n", err);
		return err;
	}

	tsc->adc_clk = devm_clk_get(&pdev->dev, "adc");
	if (IS_ERR(tsc->adc_clk)) {
		err = PTR_ERR(tsc->adc_clk);
		dev_err(&pdev->dev, "failed getting adc clock: %d\n", err);
		return err;
	}

	tsc_irq = platform_get_irq(pdev, 0);
	if (tsc_irq < 0)
		return tsc_irq;

	adc_irq = platform_get_irq(pdev, 1);
	if (adc_irq < 0)
		return adc_irq;

	err = devm_request_threaded_irq(tsc->dev, tsc_irq,
					NULL, tsc_irq_fn, IRQF_ONESHOT,
					dev_name(&pdev->dev), tsc);
	if (err) {
		dev_err(&pdev->dev,
			"failed requesting tsc irq %d: %d\n",
			tsc_irq, err);
		return err;
	}

	err = devm_request_irq(tsc->dev, adc_irq, adc_irq_fn, 0,
				dev_name(&pdev->dev), tsc);
	if (err) {
		dev_err(&pdev->dev,
			"failed requesting adc irq %d: %d\n",
			adc_irq, err);
		return err;
	}

	err = of_property_read_u32(np, "measure-delay-time",
				   &tsc->measure_delay_time);
	if (err)
		tsc->measure_delay_time = 0xffff;

	err = of_property_read_u32(np, "pre-charge-time",
				   &tsc->pre_charge_time);
	if (err)
		tsc->pre_charge_time = 0xfff;

	err = of_property_read_u32(np, "touchscreen-average-samples",
				   &average_samples);
	if (err)
		average_samples = 1;

	switch (average_samples) {
	case 1:
		tsc->average_enable = false;
		tsc->average_select = 0; /* value unused; initialize anyway */
		break;
	case 4:
	case 8:
	case 16:
	case 32:
		tsc->average_enable = true;
		tsc->average_select = ilog2(average_samples) - 2;
		break;
	default:
		dev_err(&pdev->dev,
			"touchscreen-average-samples (%u) must be 1, 4, 8, 16 or 32\n",
			average_samples);
		return -EINVAL;
	}

	err = input_register_device(tsc->input);
	if (err) {
		dev_err(&pdev->dev,
			"failed to register input device: %d\n", err);
		return err;
	}

	platform_set_drvdata(pdev, tsc);
	return 0;
}