Пример #1
0
static int __init tegra_gmi_char_probe(struct platform_device *pdev)
{
	int err = -ENODEV;
	struct tegra_nor_chip_parms *plat = pdev->dev.platform_data;
	struct device *dev = &pdev->dev;

	if (!plat) {
		pr_err("%s: no platform device info\n", __func__);
		return -EINVAL;
	}
	info = devm_kzalloc(dev, sizeof(struct tegra_gmi_char_info),
			    GFP_KERNEL);
	if (!info)
		return -ENOMEM;
	info->base = ((void __iomem *)IO_APB_VIRT +
				(TEGRA_SNOR_BASE - IO_APB_PHYS));
	info->plat = plat;
	info->dev = dev;

#ifdef CONFIG_TEGRA_GMI_ACCESS_CONTROL
	info->gmiLockHandle = register_gmi_device(DRV_NAME, 0);
	info->request_gmi_access = request_gmi_access;
	info->release_gmi_access = release_gmi_access;
	info->gmiLockHandle =	register_gmi_device(DRV_NAME, 0);
#else
	info->gmiLockHandle = NULL;
	info->request_gmi_access = NULL;
	info->release_gmi_access = NULL;
#endif

	/* Clock setting */
	info->clk = clk_get_sys("tegra-nor", NULL);
	if (IS_ERR(info->clk)) {
		pr_err("%s: can't get clock\n", __func__);
		return PTR_ERR(info->clk);
	}

	err = clk_prepare_enable(info->clk);
	if (err != 0) {
		pr_err("%s: can't enable clock\n", __func__);
		return err;
	}

	err = tegra_gmi_char_prepare_regs(info);

	if (err) {
		dev_err(dev, "Error initializing reg values\n");
		return err;
	}

	// write init config
	snor_tegra_writel(info, info->init_config, TEGRA_SNOR_CONFIG_REG);
	snor_tegra_writel(info, info->timing1_read, TEGRA_SNOR_TIMING1_REG);
	snor_tegra_writel(info, info->timing0_read, TEGRA_SNOR_TIMING0_REG);

	platform_set_drvdata(pdev, info);

	info->gmi_class = class_create(THIS_MODULE, DRV_NAME);

	if (IS_ERR(info->gmi_class)) {
		err = PTR_ERR(info->gmi_class);
		return err;
	}

	err = alloc_chrdev_region(&info->gmi_dev_t, 0, 1, DRV_NAME);

	if (err < 0) {
		class_destroy(info->gmi_class);
		pr_err("%s: failed to allocate device region\n", DRV_NAME);
		return err;
	}

	cdev_init(&info->gmi_cdev, &gmichar_fops);
	err = cdev_add(&info->gmi_cdev, info->gmi_dev_t, 1);

	if (err)
		return err;

	info->gmi_device = device_create(info->gmi_class, NULL,
					info->gmi_dev_t, info, DRV_NAME);

	if (IS_ERR(info->gmi_device)) {
		pr_err("device create failed for %s\n", DRV_NAME);
		cdev_del(&info->gmi_cdev);
		goto fail;
	}

	return 0;
fail:
	pr_err("Tegra GMI CHAR probe failed\n");
	return err;
}
Пример #2
0
static int __devinit tegra_gmi_pca_probe(struct platform_device *pdev)
{
	int err = 0, err_gpio = 0;
	int err_int = 0;
	struct tegra_nor_chip_parms *plat = pdev->dev.platform_data;
	struct cs_info *csinfo = &plat->csinfo;
	struct gpio_state *state = &csinfo->gpio_cs;
	struct device *dev = &pdev->dev;
	struct resource *res;

	if (!plat) {
		pr_err("%s: no platform device info\n", __func__);
		err = -EINVAL;
		goto fail;
	}
	info = devm_kzalloc(dev, sizeof(struct tegra_gmi_pca_info),
				GFP_KERNEL);
	if (!info) {
		err = -ENOMEM;
	goto fail;
	}

	info->base = ((void __iomem *)IO_APB_VIRT +
			(TEGRA_SNOR_BASE - IO_APB_PHYS));
	info->plat = plat;
	info->dev = dev;

	/* Intialise the SNOR controller before probe */
	err = tegra_gmi_controller_init(info);
	if (err) {
		dev_err(dev, "Error initializing controller\n");
		goto fail;
	}
	platform_set_drvdata(pdev, info);

	init_waitqueue_head(&pca_wait);

	err_gpio = gpio_request(state[0].gpio_num, state[0].label);
	gpio_direction_output(state[0].gpio_num, 0);

	res = platform_get_resource(pdev, IORESOURCE_IO, 0);
	if (!res) {
		dev_err(dev, "GPIO %d can't be used as interrupt\n",
							res->start);
		return -ENODEV;
	}

	err_int = gpio_request(res->start, NULL);
	gpio_direction_output(res->start, 0);
	irq = gpio_to_irq(res->start);
	info->gpio_num = res->start;

	if (irq <= 0) {
		printk(KERN_ALERT "GPIO %d can't be used as interrupt"
							, res->start);
		goto fail;
	}

	if (irq > -1) {
		if (request_irq(irq, pca_handler, IRQF_TRIGGER_FALLING,
				"i2c-pca-gmi", &pca_gmi_ops) < 0) {
			dev_err(dev, "Request irq%d failed\n", irq);
			goto fail;
		}
	}

#ifdef CONFIG_TEGRA_GMI_ACCESS_CONTROL
	info->gmiFmLockHandle = register_gmi_device("gmi-i2c-pca", 0);
#endif

	pca_gmi_data.i2c_clock = clock;
	pca_gmi_request_access(NULL);

	if (i2c_pca_add_bus(&pca_gmi_ops) < 0) {
		pca_gmi_release_access(NULL);
		dev_err(dev, "Failed to add i2c bus\n");
		goto out_irq;
	}

	pca_gmi_release_access(NULL);

	return 0;

out_irq:
	if (irq > -1)
		free_irq(irq, &pca_gmi_ops);

fail:
	pr_err("Tegra GMI PCA probe failed\n");
	return err;
}