Exemple #1
0
static int ts72xx_wdt_settimeout(struct watchdog_device *wdd, unsigned int to)
{
	struct ts72xx_wdt_priv *priv = watchdog_get_drvdata(wdd);

	if (to == 1) {
		priv->regval = TS72XX_WDT_CTRL_1SEC;
	} else if (to == 2) {
		priv->regval = TS72XX_WDT_CTRL_2SEC;
	} else if (to <= 4) {
		priv->regval = TS72XX_WDT_CTRL_4SEC;
		to = 4;
	} else {
		priv->regval = TS72XX_WDT_CTRL_8SEC;
		if (to <= 8)
			to = 8;
	}

	wdd->timeout = to;

	if (watchdog_active(wdd)) {
		ts72xx_wdt_stop(wdd);
		ts72xx_wdt_start(wdd);
	}

	return 0;
}
Exemple #2
0
static int ts72xx_wdt_release(struct inode *inode, struct file *file)
{
	struct ts72xx_wdt *wdt = file->private_data;

	if (mutex_lock_interruptible(&wdt->lock))
		return -ERESTARTSYS;

	if ((wdt->flags & TS72XX_WDT_EXPECT_CLOSE_FLAG) != 0) {
		ts72xx_wdt_stop(wdt);
	} else {
		dev_warn(&wdt->pdev->dev,
			 "TS-72XX WDT device closed unexpectly. "
			 "Watchdog timer will not stop!\n");
		/*
		 * Kick it one more time, to give userland some time
		 * to recover (for example, respawning the kicker
		 * daemon).
		 */
		ts72xx_wdt_kick(wdt);
	}

	wdt->flags = 0;

	mutex_unlock(&wdt->lock);
	return 0;
}
Exemple #3
0
static int ts72xx_wdt_probe(struct platform_device *pdev)
{
	struct ts72xx_wdt *wdt;
	struct resource *r1, *r2;
	int error = 0;

	wdt = devm_kzalloc(&pdev->dev, sizeof(struct ts72xx_wdt), GFP_KERNEL);
	if (!wdt) {
		dev_err(&pdev->dev, "failed to allocate memory\n");
		return -ENOMEM;
	}

	r1 = platform_get_resource(pdev, IORESOURCE_MEM, 0);
	if (!r1) {
		dev_err(&pdev->dev, "failed to get memory resource\n");
		return -ENODEV;
	}

	wdt->control_reg = devm_ioremap_resource(&pdev->dev, r1);
	if (IS_ERR(wdt->control_reg))
		return PTR_ERR(wdt->control_reg);

	r2 = platform_get_resource(pdev, IORESOURCE_MEM, 1);
	if (!r2) {
		dev_err(&pdev->dev, "failed to get memory resource\n");
		return -ENODEV;
	}

	wdt->feed_reg = devm_ioremap_resource(&pdev->dev, r2);
	if (IS_ERR(wdt->feed_reg))
		return PTR_ERR(wdt->feed_reg);

	platform_set_drvdata(pdev, wdt);
	ts72xx_wdt_pdev = pdev;
	wdt->pdev = pdev;
	mutex_init(&wdt->lock);

	/* make sure that the watchdog is disabled */
	ts72xx_wdt_stop(wdt);

	error = misc_register(&ts72xx_wdt_miscdev);
	if (error) {
		dev_err(&pdev->dev, "failed to register miscdev\n");
		return error;
	}

	dev_info(&pdev->dev, "TS-72xx Watchdog driver\n");

	return 0;
}
Exemple #4
0
static int ts72xx_wdt_probe(struct platform_device *pdev)
{
	struct ts72xx_wdt *wdt;
	struct resource *r1, *r2;
	int error = 0;

	wdt = kzalloc(sizeof(struct ts72xx_wdt), GFP_KERNEL);
	if (!wdt) {
		dev_err(&pdev->dev, "failed to allocate memory\n");
		return -ENOMEM;
	}

	r1 = platform_get_resource(pdev, IORESOURCE_MEM, 0);
	if (!r1) {
		dev_err(&pdev->dev, "failed to get memory resource\n");
		error = -ENODEV;
		goto fail;
	}

	r1 = request_mem_region(r1->start, resource_size(r1), pdev->name);
	if (!r1) {
		dev_err(&pdev->dev, "cannot request memory region\n");
		error = -EBUSY;
		goto fail;
	}

	wdt->control_reg = ioremap(r1->start, resource_size(r1));
	if (!wdt->control_reg) {
		dev_err(&pdev->dev, "failed to map memory\n");
		error = -ENODEV;
		goto fail_free_control;
	}

	r2 = platform_get_resource(pdev, IORESOURCE_MEM, 1);
	if (!r2) {
		dev_err(&pdev->dev, "failed to get memory resource\n");
		error = -ENODEV;
		goto fail_unmap_control;
	}

	r2 = request_mem_region(r2->start, resource_size(r2), pdev->name);
	if (!r2) {
		dev_err(&pdev->dev, "cannot request memory region\n");
		error = -EBUSY;
		goto fail_unmap_control;
	}

	wdt->feed_reg = ioremap(r2->start, resource_size(r2));
	if (!wdt->feed_reg) {
		dev_err(&pdev->dev, "failed to map memory\n");
		error = -ENODEV;
		goto fail_free_feed;
	}

	platform_set_drvdata(pdev, wdt);
	ts72xx_wdt_pdev = pdev;
	wdt->pdev = pdev;
	mutex_init(&wdt->lock);

	/* make sure that the watchdog is disabled */
	ts72xx_wdt_stop(wdt);

	error = misc_register(&ts72xx_wdt_miscdev);
	if (error) {
		dev_err(&pdev->dev, "failed to register miscdev\n");
		goto fail_unmap_feed;
	}

	dev_info(&pdev->dev, "TS-72xx Watchdog driver\n");

	return 0;

fail_unmap_feed:
	platform_set_drvdata(pdev, NULL);
	iounmap(wdt->feed_reg);
fail_free_feed:
	release_mem_region(r2->start, resource_size(r2));
fail_unmap_control:
	iounmap(wdt->control_reg);
fail_free_control:
	release_mem_region(r1->start, resource_size(r1));
fail:
	kfree(wdt);
	return error;
}
Exemple #5
0
static long ts72xx_wdt_ioctl(struct file *file, unsigned int cmd,
			     unsigned long arg)
{
	struct ts72xx_wdt *wdt = file->private_data;
	void __user *argp = (void __user *)arg;
	int __user *p = (int __user *)argp;
	int error = 0;

	if (mutex_lock_interruptible(&wdt->lock))
		return -ERESTARTSYS;

	switch (cmd) {
	case WDIOC_GETSUPPORT:
		error = copy_to_user(argp, &winfo, sizeof(winfo));
		break;

	case WDIOC_GETSTATUS:
	case WDIOC_GETBOOTSTATUS:
		error = put_user(0, p);
		break;

	case WDIOC_KEEPALIVE:
		ts72xx_wdt_kick(wdt);
		break;

	case WDIOC_SETOPTIONS: {
		int options;

		if (get_user(options, p)) {
			error = -EFAULT;
			break;
		}

		error = -EINVAL;

		if ((options & WDIOS_DISABLECARD) != 0) {
			ts72xx_wdt_stop(wdt);
			error = 0;
		}
		if ((options & WDIOS_ENABLECARD) != 0) {
			ts72xx_wdt_start(wdt);
			error = 0;
		}

		break;
	}

	case WDIOC_SETTIMEOUT: {
		int new_timeout;

		if (get_user(new_timeout, p)) {
			error = -EFAULT;
		} else {
			int regval;

			regval = timeout_to_regval(new_timeout);
			if (regval < 0) {
				error = -EINVAL;
			} else {
				ts72xx_wdt_stop(wdt);
				wdt->regval = regval;
				ts72xx_wdt_start(wdt);
			}
		}
		if (error)
			break;

		/*FALLTHROUGH*/
	}

	case WDIOC_GETTIMEOUT:
		if (put_user(regval_to_timeout(wdt->regval), p))
			error = -EFAULT;
		break;

	default:
		error = -ENOTTY;
		break;
	}

	mutex_unlock(&wdt->lock);
	return error;
}