/** * wm8350_reg_lock() * * The WM8350 has a hardware lock which can be used to prevent writes to * some registers (generally those which can cause particularly serious * problems if misused). This function enables that lock. * * @wm8350: pointer to local driver data structure
*/ int wm8350_reg_lock(struct wm8350 *wm8350)
{ int ret;
mutex_lock(®_lock_mutex);
ldbg(__func__);
ret = wm8350_reg_write(wm8350, WM8350_SECURITY, WM8350_LOCK_KEY); if (ret)
dev_err(wm8350->dev, "lock failed\n");
wm8350->unlocked = false;
mutex_unlock(®_lock_mutex);
return ret;
}
EXPORT_SYMBOL_GPL(wm8350_reg_lock);
/** * wm8350_reg_unlock() * * The WM8350 has a hardware lock which can be used to prevent writes to * some registers (generally those which can cause particularly serious * problems if misused). This function disables that lock so updates * can be performed. For maximum safety this should be done only when * required. * * @wm8350: pointer to local driver data structure
*/ int wm8350_reg_unlock(struct wm8350 *wm8350)
{ int ret;
mutex_lock(®_lock_mutex);
ldbg(__func__);
ret = wm8350_reg_write(wm8350, WM8350_SECURITY, WM8350_UNLOCK_KEY); if (ret)
dev_err(wm8350->dev, "unlock failed\n");
/* If a late IRQ left the completion signalled then consume
* the completion. */
try_wait_for_completion(&wm8350->auxadc_done);
/* We ignore the result of the completion and just check for a * conversion result, allowing us to soldier on if the IRQ
* infrastructure is not set up for the chip. */
wait_for_completion_timeout(&wm8350->auxadc_done, msecs_to_jiffies(5));
/* * Register a client device. This is non-fatal since there is no need to * fail the entire device init due to a single platform device failing.
*/ staticvoid wm8350_client_dev_register(struct wm8350 *wm8350, constchar *name, struct platform_device **pdev)
{ int ret;
*pdev = platform_device_alloc(name, -1); if (*pdev == NULL) {
dev_err(wm8350->dev, "Failed to allocate %s\n", name); return;
}
(*pdev)->dev.parent = wm8350->dev;
platform_set_drvdata(*pdev, wm8350);
ret = platform_device_add(*pdev); if (ret != 0) {
dev_err(wm8350->dev, "Failed to register %s: %d\n", name, ret);
platform_device_put(*pdev);
*pdev = NULL;
}
}
int wm8350_device_init(struct wm8350 *wm8350, int irq, struct wm8350_platform_data *pdata)
{ int ret; unsignedint id1, id2, mask_rev; unsignedint cust_id, mode, chip_rev;
dev_set_drvdata(wm8350->dev, wm8350);
/* get WM8350 revision and config mode */
ret = regmap_read(wm8350->regmap, WM8350_RESET_ID, &id1); if (ret != 0) {
dev_err(wm8350->dev, "Failed to read ID: %d\n", ret); goto err;
}
ret = regmap_read(wm8350->regmap, WM8350_ID, &id2); if (ret != 0) {
dev_err(wm8350->dev, "Failed to read ID: %d\n", ret); goto err;
}
ret = regmap_read(wm8350->regmap, WM8350_REVISION, &mask_rev); if (ret != 0) {
dev_err(wm8350->dev, "Failed to read revision: %d\n", ret); goto err;
}
if (id1 != 0x6143) {
dev_err(wm8350->dev, "Device with ID %x is not a WM8350\n", id1);
ret = -ENODEV; goto err;
}
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.