static int drv2667_init(struct drv2667_data *haptics) { int error; /* Set default haptic frequency to 195Hz on Page 1*/ haptics->frequency = 195; haptics->page = DRV2667_PAGE_1; error = regmap_register_patch(haptics->regmap, drv2667_init_regs, ARRAY_SIZE(drv2667_init_regs)); if (error) { dev_err(&haptics->client->dev, "Failed to write init registers: %d\n", error); return error; } error = regmap_write(haptics->regmap, DRV2667_PAGE, haptics->page); if (error) { dev_err(&haptics->client->dev, "Failed to set page: %d\n", error); goto error_out; } error = drv2667_set_waveform_freq(haptics); if (error) goto error_page; error = regmap_register_patch(haptics->regmap, drv2667_page1_init, ARRAY_SIZE(drv2667_page1_init)); if (error) { dev_err(&haptics->client->dev, "Failed to write page registers: %d\n", error); return error; } error = regmap_write(haptics->regmap, DRV2667_PAGE, DRV2667_PAGE_0); return error; error_page: regmap_write(haptics->regmap, DRV2667_PAGE, DRV2667_PAGE_0); error_out: return error; }
static int tscs42xx_i2c_probe(struct i2c_client *i2c, const struct i2c_device_id *id) { struct tscs42xx *tscs42xx; int ret = 0; tscs42xx = devm_kzalloc(&i2c->dev, sizeof(*tscs42xx), GFP_KERNEL); if (!tscs42xx) { ret = -ENOMEM; dev_err(&i2c->dev, "Failed to allocate memory for data (%d)\n", ret); return ret; } i2c_set_clientdata(i2c, tscs42xx); tscs42xx->dev = &i2c->dev; tscs42xx->regmap = devm_regmap_init_i2c(i2c, &tscs42xx_regmap); if (IS_ERR(tscs42xx->regmap)) { ret = PTR_ERR(tscs42xx->regmap); dev_err(tscs42xx->dev, "Failed to allocate regmap (%d)\n", ret); return ret; } init_coeff_ram_cache(tscs42xx); ret = part_is_valid(tscs42xx); if (ret <= 0) { dev_err(tscs42xx->dev, "No valid part (%d)\n", ret); ret = -ENODEV; return ret; } ret = regmap_write(tscs42xx->regmap, R_RESET, RV_RESET_ENABLE); if (ret < 0) { dev_err(tscs42xx->dev, "Failed to reset device (%d)\n", ret); return ret; } ret = regmap_register_patch(tscs42xx->regmap, tscs42xx_patch, ARRAY_SIZE(tscs42xx_patch)); if (ret < 0) { dev_err(tscs42xx->dev, "Failed to apply patch (%d)\n", ret); return ret; } mutex_init(&tscs42xx->audio_params_lock); mutex_init(&tscs42xx->coeff_ram_lock); mutex_init(&tscs42xx->pll_lock); ret = snd_soc_register_codec(tscs42xx->dev, &soc_codec_dev_tscs42xx, &tscs42xx_dai, 1); if (ret) { dev_err(tscs42xx->dev, "Failed to register codec (%d)\n", ret); return ret; } return 0; }
static int rt5616_i2c_probe(struct i2c_client *i2c, const struct i2c_device_id *id) { struct rt5616_priv *rt5616; unsigned int val; int ret; rt5616 = devm_kzalloc(&i2c->dev, sizeof(struct rt5616_priv), GFP_KERNEL); if (rt5616 == NULL) return -ENOMEM; i2c_set_clientdata(i2c, rt5616); rt5616->regmap = devm_regmap_init_i2c(i2c, &rt5616_regmap); if (IS_ERR(rt5616->regmap)) { ret = PTR_ERR(rt5616->regmap); dev_err(&i2c->dev, "Failed to allocate register map: %d\n", ret); return ret; } regmap_read(rt5616->regmap, RT5616_DEVICE_ID, &val); if (val != 0x6281) { dev_err(&i2c->dev, "Device with ID register %#x is not rt5616\n", val); return -ENODEV; } regmap_write(rt5616->regmap, RT5616_RESET, 0); regmap_update_bits(rt5616->regmap, RT5616_PWR_ANLG1, RT5616_PWR_VREF1 | RT5616_PWR_MB | RT5616_PWR_BG | RT5616_PWR_VREF2, RT5616_PWR_VREF1 | RT5616_PWR_MB | RT5616_PWR_BG | RT5616_PWR_VREF2); mdelay(10); regmap_update_bits(rt5616->regmap, RT5616_PWR_ANLG1, RT5616_PWR_FV1 | RT5616_PWR_FV2, RT5616_PWR_FV1 | RT5616_PWR_FV2); ret = regmap_register_patch(rt5616->regmap, init_list, ARRAY_SIZE(init_list)); if (ret != 0) dev_warn(&i2c->dev, "Failed to apply regmap patch: %d\n", ret); regmap_update_bits(rt5616->regmap, RT5616_PWR_ANLG1, RT5616_PWR_LDO_DVO_MASK, RT5616_PWR_LDO_DVO_1_2V); return snd_soc_register_codec(&i2c->dev, &soc_codec_dev_rt5616, rt5616_dai, ARRAY_SIZE(rt5616_dai)); }
static int cs42l52_i2c_probe(struct i2c_client *i2c_client, const struct i2c_device_id *id) { struct cs42l52_private *cs42l52; int ret; unsigned int devid = 0; unsigned int reg; cs42l52 = devm_kzalloc(&i2c_client->dev, sizeof(struct cs42l52_private), GFP_KERNEL); if (cs42l52 == NULL) return -ENOMEM; cs42l52->dev = &i2c_client->dev; cs42l52->regmap = devm_regmap_init_i2c(i2c_client, &cs42l52_regmap); if (IS_ERR(cs42l52->regmap)) { ret = PTR_ERR(cs42l52->regmap); dev_err(&i2c_client->dev, "regmap_init() failed: %d\n", ret); return ret; } i2c_set_clientdata(i2c_client, cs42l52); if (dev_get_platdata(&i2c_client->dev)) memcpy(&cs42l52->pdata, dev_get_platdata(&i2c_client->dev), sizeof(cs42l52->pdata)); ret = regmap_register_patch(cs42l52->regmap, cs42l52_threshold_patch, ARRAY_SIZE(cs42l52_threshold_patch)); if (ret != 0) dev_warn(cs42l52->dev, "Failed to apply regmap patch: %d\n", ret); ret = regmap_read(cs42l52->regmap, CS42L52_CHIP, ®); devid = reg & CS42L52_CHIP_ID_MASK; if (devid != CS42L52_CHIP_ID) { ret = -ENODEV; dev_err(&i2c_client->dev, "CS42L52 Device ID (%X). Expected %X\n", devid, CS42L52_CHIP_ID); return ret; } regcache_cache_only(cs42l52->regmap, true); ret = snd_soc_register_codec(&i2c_client->dev, &soc_codec_dev_cs42l52, &cs42l52_dai, 1); if (ret < 0) return ret; return 0; }
static int cs35l32_i2c_probe(struct i2c_client *i2c_client, const struct i2c_device_id *id) { struct cs35l32_private *cs35l32; struct cs35l32_platform_data *pdata = dev_get_platdata(&i2c_client->dev); int ret, i; unsigned int devid = 0; unsigned int reg; cs35l32 = devm_kzalloc(&i2c_client->dev, sizeof(struct cs35l32_private), GFP_KERNEL); if (!cs35l32) { dev_err(&i2c_client->dev, "could not allocate codec\n"); return -ENOMEM; } i2c_set_clientdata(i2c_client, cs35l32); cs35l32->regmap = devm_regmap_init_i2c(i2c_client, &cs35l32_regmap); if (IS_ERR(cs35l32->regmap)) { ret = PTR_ERR(cs35l32->regmap); dev_err(&i2c_client->dev, "regmap_init() failed: %d\n", ret); return ret; } if (pdata) { cs35l32->pdata = *pdata; } else { pdata = devm_kzalloc(&i2c_client->dev, sizeof(struct cs35l32_platform_data), GFP_KERNEL); if (!pdata) { dev_err(&i2c_client->dev, "could not allocate pdata\n"); return -ENOMEM; } if (i2c_client->dev.of_node) { ret = cs35l32_handle_of_data(i2c_client, &cs35l32->pdata); if (ret != 0) return ret; } } for (i = 0; i < ARRAY_SIZE(cs35l32->supplies); i++) cs35l32->supplies[i].supply = cs35l32_supply_names[i]; ret = devm_regulator_bulk_get(&i2c_client->dev, ARRAY_SIZE(cs35l32->supplies), cs35l32->supplies); if (ret != 0) { dev_err(&i2c_client->dev, "Failed to request supplies: %d\n", ret); return ret; } ret = regulator_bulk_enable(ARRAY_SIZE(cs35l32->supplies), cs35l32->supplies); if (ret != 0) { dev_err(&i2c_client->dev, "Failed to enable supplies: %d\n", ret); return ret; } /* Reset the Device */ cs35l32->reset_gpio = devm_gpiod_get(&i2c_client->dev, "reset-gpios"); if (IS_ERR(cs35l32->reset_gpio)) { ret = PTR_ERR(cs35l32->reset_gpio); if (ret != -ENOENT && ret != -ENOSYS) return ret; cs35l32->reset_gpio = NULL; } else { ret = gpiod_direction_output(cs35l32->reset_gpio, 0); if (ret) return ret; gpiod_set_value_cansleep(cs35l32->reset_gpio, 1); } /* initialize codec */ ret = regmap_read(cs35l32->regmap, CS35L32_DEVID_AB, ®); devid = (reg & 0xFF) << 12; ret = regmap_read(cs35l32->regmap, CS35L32_DEVID_CD, ®); devid |= (reg & 0xFF) << 4; ret = regmap_read(cs35l32->regmap, CS35L32_DEVID_E, ®); devid |= (reg & 0xF0) >> 4; if (devid != CS35L32_CHIP_ID) { ret = -ENODEV; dev_err(&i2c_client->dev, "CS35L32 Device ID (%X). Expected %X\n", devid, CS35L32_CHIP_ID); return ret; } ret = regmap_read(cs35l32->regmap, CS35L32_REV_ID, ®); if (ret < 0) { dev_err(&i2c_client->dev, "Get Revision ID failed\n"); return ret; } ret = regmap_register_patch(cs35l32->regmap, cs35l32_monitor_patch, ARRAY_SIZE(cs35l32_monitor_patch)); if (ret < 0) { dev_err(&i2c_client->dev, "Failed to apply errata patch\n"); return ret; } dev_info(&i2c_client->dev, "Cirrus Logic CS35L32, Revision: %02X\n", reg & 0xFF); /* Setup VBOOST Management */ if (cs35l32->pdata.boost_mng) regmap_update_bits(cs35l32->regmap, CS35L32_AUDIO_LED_MNGR, CS35L32_BOOST_MASK, cs35l32->pdata.boost_mng); /* Setup ADSP Format Config */ if (cs35l32->pdata.sdout_share) regmap_update_bits(cs35l32->regmap, CS35L32_ADSP_CTL, CS35L32_ADSP_SHARE_MASK, cs35l32->pdata.sdout_share << 3); /* Setup ADSP Data Configuration */ if (cs35l32->pdata.sdout_datacfg) regmap_update_bits(cs35l32->regmap, CS35L32_ADSP_CTL, CS35L32_ADSP_DATACFG_MASK, cs35l32->pdata.sdout_datacfg << 4); /* Setup Low Battery Recovery */ if (cs35l32->pdata.batt_recov) regmap_update_bits(cs35l32->regmap, CS35L32_BATT_THRESHOLD, CS35L32_BATT_REC_MASK, cs35l32->pdata.batt_recov << 1); /* Setup Low Battery Threshold */ if (cs35l32->pdata.batt_thresh) regmap_update_bits(cs35l32->regmap, CS35L32_BATT_THRESHOLD, CS35L32_BATT_THRESH_MASK, cs35l32->pdata.batt_thresh << 4); /* Power down the AMP */ regmap_update_bits(cs35l32->regmap, CS35L32_PWRCTL1, CS35L32_PDN_AMP, CS35L32_PDN_AMP); /* Clear MCLK Error Bit since we don't have the clock yet */ ret = regmap_read(cs35l32->regmap, CS35L32_INT_STATUS_1, ®); ret = snd_soc_register_codec(&i2c_client->dev, &soc_codec_dev_cs35l32, cs35l32_dai, ARRAY_SIZE(cs35l32_dai)); if (ret < 0) goto err_disable; return 0; err_disable: regulator_bulk_disable(ARRAY_SIZE(cs35l32->supplies), cs35l32->supplies); return ret; }
static int wm8993_i2c_probe(struct i2c_client *i2c, const struct i2c_device_id *id) { struct wm8993_priv *wm8993; unsigned int reg; int ret, i; wm8993 = devm_kzalloc(&i2c->dev, sizeof(struct wm8993_priv), GFP_KERNEL); if (wm8993 == NULL) return -ENOMEM; wm8993->dev = &i2c->dev; init_completion(&wm8993->fll_lock); wm8993->regmap = devm_regmap_init_i2c(i2c, &wm8993_regmap); if (IS_ERR(wm8993->regmap)) { ret = PTR_ERR(wm8993->regmap); dev_err(&i2c->dev, "Failed to allocate regmap: %d\n", ret); return ret; } i2c_set_clientdata(i2c, wm8993); for (i = 0; i < ARRAY_SIZE(wm8993->supplies); i++) wm8993->supplies[i].supply = wm8993_supply_names[i]; ret = devm_regulator_bulk_get(&i2c->dev, ARRAY_SIZE(wm8993->supplies), wm8993->supplies); if (ret != 0) { dev_err(&i2c->dev, "Failed to request supplies: %d\n", ret); return ret; } ret = regulator_bulk_enable(ARRAY_SIZE(wm8993->supplies), wm8993->supplies); if (ret != 0) { dev_err(&i2c->dev, "Failed to enable supplies: %d\n", ret); return ret; } ret = regmap_read(wm8993->regmap, WM8993_SOFTWARE_RESET, ®); if (ret != 0) { dev_err(&i2c->dev, "Failed to read chip ID: %d\n", ret); goto err_enable; } if (reg != 0x8993) { dev_err(&i2c->dev, "Invalid ID register value %x\n", reg); ret = -EINVAL; goto err_enable; } ret = regmap_write(wm8993->regmap, WM8993_SOFTWARE_RESET, 0xffff); if (ret != 0) goto err_enable; ret = regmap_register_patch(wm8993->regmap, wm8993_regmap_patch, ARRAY_SIZE(wm8993_regmap_patch)); if (ret != 0) dev_warn(wm8993->dev, "Failed to apply regmap patch: %d\n", ret); if (i2c->irq) { /* Put GPIO1 into interrupt mode (only GPIO1 can output IRQ) */ ret = regmap_update_bits(wm8993->regmap, WM8993_GPIO1, WM8993_GPIO1_PD | WM8993_GPIO1_SEL_MASK, 7); if (ret != 0) goto err_enable; ret = request_threaded_irq(i2c->irq, NULL, wm8993_irq, IRQF_TRIGGER_HIGH | IRQF_ONESHOT, "wm8993", wm8993); if (ret != 0) goto err_enable; } regulator_bulk_disable(ARRAY_SIZE(wm8993->supplies), wm8993->supplies); regcache_cache_only(wm8993->regmap, true); ret = snd_soc_register_codec(&i2c->dev, &soc_codec_dev_wm8993, &wm8993_dai, 1); if (ret != 0) { dev_err(&i2c->dev, "Failed to register CODEC: %d\n", ret); goto err_irq; } return 0; err_irq: if (i2c->irq) free_irq(i2c->irq, wm8993); err_enable: regulator_bulk_disable(ARRAY_SIZE(wm8993->supplies), wm8993->supplies); return ret; }
/* * Instantiate the generic non-control parts of the device. */ static int wm8994_device_init(struct wm8994 *wm8994, int irq) { struct wm8994_pdata *pdata; struct regmap_config *regmap_config; const struct reg_default *regmap_patch = NULL; const char *devname; int ret, i, patch_regs = 0; int pulls = 0; if (dev_get_platdata(wm8994->dev)) { pdata = dev_get_platdata(wm8994->dev); wm8994->pdata = *pdata; } pdata = &wm8994->pdata; ret = wm8994_set_pdata_from_of(wm8994); if (ret != 0) return ret; dev_set_drvdata(wm8994->dev, wm8994); /* Add the on-chip regulators first for bootstrapping */ ret = mfd_add_devices(wm8994->dev, -1, wm8994_regulator_devs, ARRAY_SIZE(wm8994_regulator_devs), NULL, 0, NULL); if (ret != 0) { dev_err(wm8994->dev, "Failed to add children: %d\n", ret); goto err; } switch (wm8994->type) { case WM1811: wm8994->num_supplies = ARRAY_SIZE(wm1811_main_supplies); break; case WM8994: wm8994->num_supplies = ARRAY_SIZE(wm8994_main_supplies); break; case WM8958: wm8994->num_supplies = ARRAY_SIZE(wm8958_main_supplies); break; default: BUG(); goto err; } wm8994->supplies = devm_kzalloc(wm8994->dev, sizeof(struct regulator_bulk_data) * wm8994->num_supplies, GFP_KERNEL); if (!wm8994->supplies) { ret = -ENOMEM; goto err; } switch (wm8994->type) { case WM1811: for (i = 0; i < ARRAY_SIZE(wm1811_main_supplies); i++) wm8994->supplies[i].supply = wm1811_main_supplies[i]; break; case WM8994: for (i = 0; i < ARRAY_SIZE(wm8994_main_supplies); i++) wm8994->supplies[i].supply = wm8994_main_supplies[i]; break; case WM8958: for (i = 0; i < ARRAY_SIZE(wm8958_main_supplies); i++) wm8994->supplies[i].supply = wm8958_main_supplies[i]; break; default: BUG(); goto err; } ret = devm_regulator_bulk_get(wm8994->dev, wm8994->num_supplies, wm8994->supplies); if (ret != 0) { dev_err(wm8994->dev, "Failed to get supplies: %d\n", ret); goto err; } ret = regulator_bulk_enable(wm8994->num_supplies, wm8994->supplies); if (ret != 0) { dev_err(wm8994->dev, "Failed to enable supplies: %d\n", ret); goto err; } ret = wm8994_reg_read(wm8994, WM8994_SOFTWARE_RESET); if (ret < 0) { dev_err(wm8994->dev, "Failed to read ID register\n"); goto err_enable; } switch (ret) { case 0x1811: devname = "WM1811"; if (wm8994->type != WM1811) dev_warn(wm8994->dev, "Device registered as type %d\n", wm8994->type); wm8994->type = WM1811; break; case 0x8994: devname = "WM8994"; if (wm8994->type != WM8994) dev_warn(wm8994->dev, "Device registered as type %d\n", wm8994->type); wm8994->type = WM8994; break; case 0x8958: devname = "WM8958"; if (wm8994->type != WM8958) dev_warn(wm8994->dev, "Device registered as type %d\n", wm8994->type); wm8994->type = WM8958; break; default: dev_err(wm8994->dev, "Device is not a WM8994, ID is %x\n", ret); ret = -EINVAL; goto err_enable; } ret = wm8994_reg_read(wm8994, WM8994_CHIP_REVISION); if (ret < 0) { dev_err(wm8994->dev, "Failed to read revision register: %d\n", ret); goto err_enable; } wm8994->revision = ret & WM8994_CHIP_REV_MASK; wm8994->cust_id = (ret & WM8994_CUST_ID_MASK) >> WM8994_CUST_ID_SHIFT; switch (wm8994->type) { case WM8994: switch (wm8994->revision) { case 0: case 1: dev_warn(wm8994->dev, "revision %c not fully supported\n", 'A' + wm8994->revision); break; case 2: case 3: default: regmap_patch = wm8994_revc_patch; patch_regs = ARRAY_SIZE(wm8994_revc_patch); break; } break; case WM8958: switch (wm8994->revision) { case 0: regmap_patch = wm8958_reva_patch; patch_regs = ARRAY_SIZE(wm8958_reva_patch); break; default: break; } break; case WM1811: /* Revision C did not change the relevant layer */ if (wm8994->revision > 1) wm8994->revision++; regmap_patch = wm1811_reva_patch; patch_regs = ARRAY_SIZE(wm1811_reva_patch); break; default: break; } dev_info(wm8994->dev, "%s revision %c CUST_ID %02x\n", devname, 'A' + wm8994->revision, wm8994->cust_id); switch (wm8994->type) { case WM1811: regmap_config = &wm1811_regmap_config; break; case WM8994: regmap_config = &wm8994_regmap_config; break; case WM8958: regmap_config = &wm8958_regmap_config; break; default: dev_err(wm8994->dev, "Unknown device type %d\n", wm8994->type); return -EINVAL; } ret = regmap_reinit_cache(wm8994->regmap, regmap_config); if (ret != 0) { dev_err(wm8994->dev, "Failed to reinit register cache: %d\n", ret); return ret; } /* Explicitly put the device into reset in case regulators * don't get disabled in order to ensure we know the device * state. */ ret = wm8994_reg_write(wm8994, WM8994_SOFTWARE_RESET, wm8994_reg_read(wm8994, WM8994_SOFTWARE_RESET)); if (ret != 0) { dev_err(wm8994->dev, "Failed to reset device: %d\n", ret); return ret; } if (regmap_patch) { ret = regmap_register_patch(wm8994->regmap, regmap_patch, patch_regs); if (ret != 0) { dev_err(wm8994->dev, "Failed to register patch: %d\n", ret); goto err; } } wm8994->irq_base = pdata->irq_base; wm8994->gpio_base = pdata->gpio_base; /* GPIO configuration is only applied if it's non-zero */ for (i = 0; i < ARRAY_SIZE(pdata->gpio_defaults); i++) { if (pdata->gpio_defaults[i]) { wm8994_set_bits(wm8994, WM8994_GPIO_1 + i, 0xffff, pdata->gpio_defaults[i]); } } wm8994->ldo_ena_always_driven = pdata->ldo_ena_always_driven; if (pdata->spkmode_pu) pulls |= WM8994_SPKMODE_PU; /* Disable unneeded pulls */ wm8994_set_bits(wm8994, WM8994_PULL_CONTROL_2, WM8994_LDO1ENA_PD | WM8994_LDO2ENA_PD | WM8994_SPKMODE_PU | WM8994_CSNADDR_PD, pulls); /* In some system designs where the regulators are not in use, * we can achieve a small reduction in leakage currents by * floating LDO outputs. This bit makes no difference if the * LDOs are enabled, it only affects cases where the LDOs were * in operation and are then disabled. */ for (i = 0; i < WM8994_NUM_LDO_REGS; i++) { if (wm8994_ldo_in_use(pdata, i)) wm8994_set_bits(wm8994, WM8994_LDO_1 + i, WM8994_LDO1_DISCH, WM8994_LDO1_DISCH); else wm8994_set_bits(wm8994, WM8994_LDO_1 + i, WM8994_LDO1_DISCH, 0); } wm8994_irq_init(wm8994); ret = mfd_add_devices(wm8994->dev, -1, wm8994_devs, ARRAY_SIZE(wm8994_devs), NULL, 0, NULL); if (ret != 0) { dev_err(wm8994->dev, "Failed to add children: %d\n", ret); goto err_irq; } pm_runtime_enable(wm8994->dev); pm_runtime_idle(wm8994->dev); return 0; err_irq: wm8994_irq_exit(wm8994); err_enable: regulator_bulk_disable(wm8994->num_supplies, wm8994->supplies); err: mfd_remove_devices(wm8994->dev); return ret; }
static int cs35l32_i2c_probe(struct i2c_client *i2c_client, const struct i2c_device_id *id) { struct cs35l32_private *cs35l32; struct device_node *np = i2c_client->dev.of_node; u32 val32; int ret; unsigned int devid = 0; unsigned int reg; cs35l32 = devm_kzalloc(&i2c_client->dev, sizeof(struct cs35l32_private), GFP_KERNEL); if (!cs35l32) { dev_err(&i2c_client->dev, "could not allocate codec\n"); return -ENOMEM; } i2c_set_clientdata(i2c_client, cs35l32); cs35l32->regmap = devm_regmap_init_i2c(i2c_client, &cs35l32_regmap); if (IS_ERR(cs35l32->regmap)) { ret = PTR_ERR(cs35l32->regmap); dev_err(&i2c_client->dev, "regmap_init() failed: %d\n", ret); return ret; } if (of_property_read_u32(np, "cs35l32,boost-mng", &val32) >= 0) cs35l32->pdata.boost_mng = val32; if (of_property_read_u32(np, "cs35l32,sdout-datacfg", &val32) >= 0) cs35l32->pdata.sdout_datacfg = val32; if (of_property_read_u32(np, "cs35l32,sdout-share", &val32) >= 0) cs35l32->pdata.sdout_share = val32; cs35l32->pdata.gpio_nreset = of_get_named_gpio_flags(np, "cs35l32,gpio-nreset", 0, NULL); ret = gpio_request(cs35l32->pdata.gpio_nreset, "cs35l32 reset"); if (ret < 0) { dev_err(&i2c_client->dev, "failed to request the gpio %d\n", cs35l32->pdata.gpio_nreset); return ret; } /*bring the chip out of reset*/ gpio_direction_output(cs35l32->pdata.gpio_nreset, 0); msleep(20); gpio_set_value_cansleep(cs35l32->pdata.gpio_nreset, 1); msleep(20); ret = regmap_register_patch(cs35l32->regmap, cs35l32_monitor_patch, ARRAY_SIZE(cs35l32_monitor_patch)); if (ret < 0) { dev_err(&i2c_client->dev, "failed to register regmap(try again : 0x40)\n"); i2c_client->addr = 0x40; ret = regmap_register_patch(cs35l32->regmap, cs35l32_monitor_patch, ARRAY_SIZE(cs35l32_monitor_patch)); if (ret < 0) dev_err(&i2c_client->dev, "failed to register regmap retry again\n"); } /* initialize codec */ ret = regmap_read(cs35l32->regmap, CS35L32_DEVID_AB, ®); devid = (reg & 0xFF) << 12; ret = regmap_read(cs35l32->regmap, CS35L32_DEVID_CD, ®); devid |= (reg & 0xFF) << 4; ret = regmap_read(cs35l32->regmap, CS35L32_DEVID_E, ®); devid |= (reg & 0xF0) >> 4; if ((devid != CS35L32_CHIP_ID) && (devid != CS35L32_CHIP_ID_VZW)) { ret = -ENODEV; dev_err(&i2c_client->dev, "CS35L32 Device ID (%X). Expected %X\n", devid, CS35L32_CHIP_ID); return ret; } ret = regmap_read(cs35l32->regmap, CS35L32_REV_ID, ®); if (ret < 0) { dev_err(&i2c_client->dev, "Get Revision ID failed\n"); return ret;; } dev_info(&i2c_client->dev, "Cirrus Logic CS35L32, Revision: %02X\n", reg & 0xFF); regcache_cache_only(cs35l32->regmap, false); ret = snd_soc_register_codec(&i2c_client->dev, &soc_codec_dev_cs35l32, cs35l32_dai, ARRAY_SIZE(cs35l32_dai)); if (ret < 0) return ret; return 0; }
static int cs42l52_i2c_probe(struct i2c_client *i2c_client, const struct i2c_device_id *id) { struct cs42l52_private *cs42l52; struct cs42l52_platform_data *pdata = dev_get_platdata(&i2c_client->dev); int ret; unsigned int devid = 0; unsigned int reg; u32 val32; cs42l52 = devm_kzalloc(&i2c_client->dev, sizeof(struct cs42l52_private), GFP_KERNEL); if (cs42l52 == NULL) return -ENOMEM; cs42l52->dev = &i2c_client->dev; cs42l52->regmap = devm_regmap_init_i2c(i2c_client, &cs42l52_regmap); if (IS_ERR(cs42l52->regmap)) { ret = PTR_ERR(cs42l52->regmap); dev_err(&i2c_client->dev, "regmap_init() failed: %d\n", ret); return ret; } if (pdata) { cs42l52->pdata = *pdata; } else { pdata = devm_kzalloc(&i2c_client->dev, sizeof(struct cs42l52_platform_data), GFP_KERNEL); if (!pdata) { dev_err(&i2c_client->dev, "could not allocate pdata\n"); return -ENOMEM; } if (i2c_client->dev.of_node) { if (of_property_read_bool(i2c_client->dev.of_node, "cirrus,mica-differential-cfg")) pdata->mica_diff_cfg = true; if (of_property_read_bool(i2c_client->dev.of_node, "cirrus,micb-differential-cfg")) pdata->micb_diff_cfg = true; if (of_property_read_u32(i2c_client->dev.of_node, "cirrus,micbias-lvl", &val32) >= 0) pdata->micbias_lvl = val32; if (of_property_read_u32(i2c_client->dev.of_node, "cirrus,chgfreq-divisor", &val32) >= 0) pdata->chgfreq = val32; pdata->reset_gpio = of_get_named_gpio(i2c_client->dev.of_node, "cirrus,reset-gpio", 0); } cs42l52->pdata = *pdata; } if (cs42l52->pdata.reset_gpio) { ret = devm_gpio_request_one(&i2c_client->dev, cs42l52->pdata.reset_gpio, GPIOF_OUT_INIT_HIGH, "CS42L52 /RST"); if (ret < 0) { dev_err(&i2c_client->dev, "Failed to request /RST %d: %d\n", cs42l52->pdata.reset_gpio, ret); return ret; } gpio_set_value_cansleep(cs42l52->pdata.reset_gpio, 0); gpio_set_value_cansleep(cs42l52->pdata.reset_gpio, 1); } i2c_set_clientdata(i2c_client, cs42l52); ret = regmap_register_patch(cs42l52->regmap, cs42l52_threshold_patch, ARRAY_SIZE(cs42l52_threshold_patch)); if (ret != 0) dev_warn(cs42l52->dev, "Failed to apply regmap patch: %d\n", ret); ret = regmap_read(cs42l52->regmap, CS42L52_CHIP, ®); devid = reg & CS42L52_CHIP_ID_MASK; if (devid != CS42L52_CHIP_ID) { ret = -ENODEV; dev_err(&i2c_client->dev, "CS42L52 Device ID (%X). Expected %X\n", devid, CS42L52_CHIP_ID); return ret; } dev_info(&i2c_client->dev, "Cirrus Logic CS42L52, Revision: %02X\n", reg & CS42L52_CHIP_REV_MASK); /* Set Platform Data */ if (cs42l52->pdata.mica_diff_cfg) regmap_update_bits(cs42l52->regmap, CS42L52_MICA_CTL, CS42L52_MIC_CTL_TYPE_MASK, cs42l52->pdata.mica_diff_cfg << CS42L52_MIC_CTL_TYPE_SHIFT); if (cs42l52->pdata.micb_diff_cfg) regmap_update_bits(cs42l52->regmap, CS42L52_MICB_CTL, CS42L52_MIC_CTL_TYPE_MASK, cs42l52->pdata.micb_diff_cfg << CS42L52_MIC_CTL_TYPE_SHIFT); if (cs42l52->pdata.chgfreq) regmap_update_bits(cs42l52->regmap, CS42L52_CHARGE_PUMP, CS42L52_CHARGE_PUMP_MASK, cs42l52->pdata.chgfreq << CS42L52_CHARGE_PUMP_SHIFT); if (cs42l52->pdata.micbias_lvl) regmap_update_bits(cs42l52->regmap, CS42L52_IFACE_CTL2, CS42L52_IFACE_CTL2_BIAS_LVL, cs42l52->pdata.micbias_lvl); ret = snd_soc_register_codec(&i2c_client->dev, &soc_codec_dev_cs42l52, &cs42l52_dai, 1); if (ret < 0) return ret; return 0; }
static int cs35l33_i2c_probe(struct i2c_client *i2c_client, const struct i2c_device_id *id) { struct cs35l33_private *cs35l33; struct cs35l33_pdata *pdata = dev_get_platdata(&i2c_client->dev); int ret, devid, i; unsigned int reg; cs35l33 = devm_kzalloc(&i2c_client->dev, sizeof(struct cs35l33_private), GFP_KERNEL); if (!cs35l33) return -ENOMEM; i2c_set_clientdata(i2c_client, cs35l33); cs35l33->regmap = devm_regmap_init_i2c(i2c_client, &cs35l33_regmap); if (IS_ERR(cs35l33->regmap)) { ret = PTR_ERR(cs35l33->regmap); dev_err(&i2c_client->dev, "regmap_init() failed: %d\n", ret); return ret; } regcache_cache_only(cs35l33->regmap, true); for (i = 0; i < ARRAY_SIZE(cs35l33_core_supplies); i++) cs35l33->core_supplies[i].supply = cs35l33_core_supplies[i]; cs35l33->num_core_supplies = ARRAY_SIZE(cs35l33_core_supplies); ret = devm_regulator_bulk_get(&i2c_client->dev, cs35l33->num_core_supplies, cs35l33->core_supplies); if (ret != 0) { dev_err(&i2c_client->dev, "Failed to request core supplies: %d\n", ret); return ret; } if (pdata) { cs35l33->pdata = *pdata; } else { cs35l33_of_get_pdata(&i2c_client->dev, cs35l33); pdata = &cs35l33->pdata; } ret = devm_request_threaded_irq(&i2c_client->dev, i2c_client->irq, NULL, cs35l33_irq_thread, IRQF_ONESHOT | IRQF_TRIGGER_LOW, "cs35l33", cs35l33); if (ret != 0) dev_warn(&i2c_client->dev, "Failed to request IRQ: %d\n", ret); /* We could issue !RST or skip it based on AMP topology */ cs35l33->reset_gpio = devm_gpiod_get_optional(&i2c_client->dev, "reset-gpios", GPIOD_OUT_HIGH); if (IS_ERR(cs35l33->reset_gpio)) { dev_err(&i2c_client->dev, "%s ERROR: Can't get reset GPIO\n", __func__); return PTR_ERR(cs35l33->reset_gpio); } ret = regulator_bulk_enable(cs35l33->num_core_supplies, cs35l33->core_supplies); if (ret != 0) { dev_err(&i2c_client->dev, "Failed to enable core supplies: %d\n", ret); return ret; } gpiod_set_value_cansleep(cs35l33->reset_gpio, 1); msleep(CS35L33_BOOT_DELAY); regcache_cache_only(cs35l33->regmap, false); /* initialize codec */ ret = regmap_read(cs35l33->regmap, CS35L33_DEVID_AB, ®); devid = (reg & 0xFF) << 12; ret = regmap_read(cs35l33->regmap, CS35L33_DEVID_CD, ®); devid |= (reg & 0xFF) << 4; ret = regmap_read(cs35l33->regmap, CS35L33_DEVID_E, ®); devid |= (reg & 0xF0) >> 4; if (devid != CS35L33_CHIP_ID) { dev_err(&i2c_client->dev, "CS35L33 Device ID (%X). Expected ID %X\n", devid, CS35L33_CHIP_ID); goto err_enable; } ret = regmap_read(cs35l33->regmap, CS35L33_REV_ID, ®); if (ret < 0) { dev_err(&i2c_client->dev, "Get Revision ID failed\n"); goto err_enable; } dev_info(&i2c_client->dev, "Cirrus Logic CS35L33, Revision: %02X\n", reg & 0xFF); ret = regmap_register_patch(cs35l33->regmap, cs35l33_patch, ARRAY_SIZE(cs35l33_patch)); if (ret < 0) { dev_err(&i2c_client->dev, "Error in applying regmap patch: %d\n", ret); goto err_enable; } /* disable mclk and tdm */ regmap_update_bits(cs35l33->regmap, CS35L33_CLK_CTL, CS35L33_MCLKDIS | CS35L33_SDOUT_3ST_TDM, CS35L33_MCLKDIS | CS35L33_SDOUT_3ST_TDM); pm_runtime_set_autosuspend_delay(&i2c_client->dev, 100); pm_runtime_use_autosuspend(&i2c_client->dev); pm_runtime_set_active(&i2c_client->dev); pm_runtime_enable(&i2c_client->dev); ret = devm_snd_soc_register_component(&i2c_client->dev, &soc_component_dev_cs35l33, &cs35l33_dai, 1); if (ret < 0) { dev_err(&i2c_client->dev, "%s: Register component failed\n", __func__); goto err_enable; } return 0; err_enable: regulator_bulk_disable(cs35l33->num_core_supplies, cs35l33->core_supplies); return ret; }
static int twl6040_probe(struct i2c_client *client, const struct i2c_device_id *id) { struct device_node *node = client->dev.of_node; struct twl6040 *twl6040; struct mfd_cell *cell = NULL; int irq, ret, children = 0; if (!node) { dev_err(&client->dev, "of node is missing\n"); return -EINVAL; } /* In order to operate correctly we need valid interrupt config */ if (!client->irq) { dev_err(&client->dev, "Invalid IRQ configuration\n"); return -EINVAL; } twl6040 = devm_kzalloc(&client->dev, sizeof(struct twl6040), GFP_KERNEL); if (!twl6040) return -ENOMEM; twl6040->regmap = devm_regmap_init_i2c(client, &twl6040_regmap_config); if (IS_ERR(twl6040->regmap)) return PTR_ERR(twl6040->regmap); i2c_set_clientdata(client, twl6040); twl6040->clk32k = devm_clk_get(&client->dev, "clk32k"); if (IS_ERR(twl6040->clk32k)) { if (PTR_ERR(twl6040->clk32k) == -EPROBE_DEFER) return -EPROBE_DEFER; dev_dbg(&client->dev, "clk32k is not handled\n"); twl6040->clk32k = NULL; } twl6040->mclk = devm_clk_get(&client->dev, "mclk"); if (IS_ERR(twl6040->mclk)) { if (PTR_ERR(twl6040->mclk) == -EPROBE_DEFER) return -EPROBE_DEFER; dev_dbg(&client->dev, "mclk is not handled\n"); twl6040->mclk = NULL; } twl6040->supplies[0].supply = "vio"; twl6040->supplies[1].supply = "v2v1"; ret = devm_regulator_bulk_get(&client->dev, TWL6040_NUM_SUPPLIES, twl6040->supplies); if (ret != 0) { dev_err(&client->dev, "Failed to get supplies: %d\n", ret); return ret; } ret = regulator_bulk_enable(TWL6040_NUM_SUPPLIES, twl6040->supplies); if (ret != 0) { dev_err(&client->dev, "Failed to enable supplies: %d\n", ret); return ret; } twl6040->dev = &client->dev; twl6040->irq = client->irq; mutex_init(&twl6040->mutex); init_completion(&twl6040->ready); regmap_register_patch(twl6040->regmap, twl6040_patch, ARRAY_SIZE(twl6040_patch)); twl6040->rev = twl6040_reg_read(twl6040, TWL6040_REG_ASICREV); if (twl6040->rev < 0) { dev_err(&client->dev, "Failed to read revision register: %d\n", twl6040->rev); ret = twl6040->rev; goto gpio_err; } /* ERRATA: Automatic power-up is not possible in ES1.0 */ if (twl6040_get_revid(twl6040) > TWL6040_REV_ES1_0) twl6040->audpwron = of_get_named_gpio(node, "ti,audpwron-gpio", 0); else twl6040->audpwron = -EINVAL; if (gpio_is_valid(twl6040->audpwron)) { ret = devm_gpio_request_one(&client->dev, twl6040->audpwron, GPIOF_OUT_INIT_LOW, "audpwron"); if (ret) goto gpio_err; /* Clear any pending interrupt */ twl6040_reg_read(twl6040, TWL6040_REG_INTID); } ret = regmap_add_irq_chip(twl6040->regmap, twl6040->irq, IRQF_ONESHOT, 0, &twl6040_irq_chip, &twl6040->irq_data); if (ret < 0) goto gpio_err; twl6040->irq_ready = regmap_irq_get_virq(twl6040->irq_data, TWL6040_IRQ_READY); twl6040->irq_th = regmap_irq_get_virq(twl6040->irq_data, TWL6040_IRQ_TH); ret = devm_request_threaded_irq(twl6040->dev, twl6040->irq_ready, NULL, twl6040_readyint_handler, IRQF_ONESHOT, "twl6040_irq_ready", twl6040); if (ret) { dev_err(twl6040->dev, "READY IRQ request failed: %d\n", ret); goto readyirq_err; } ret = devm_request_threaded_irq(twl6040->dev, twl6040->irq_th, NULL, twl6040_thint_handler, IRQF_ONESHOT, "twl6040_irq_th", twl6040); if (ret) { dev_err(twl6040->dev, "Thermal IRQ request failed: %d\n", ret); goto readyirq_err; } /* * The main functionality of twl6040 to provide audio on OMAP4+ systems. * We can add the ASoC codec child whenever this driver has been loaded. */ irq = regmap_irq_get_virq(twl6040->irq_data, TWL6040_IRQ_PLUG); cell = &twl6040->cells[children]; cell->name = "twl6040-codec"; twl6040_codec_rsrc[0].start = irq; twl6040_codec_rsrc[0].end = irq; cell->resources = twl6040_codec_rsrc; cell->num_resources = ARRAY_SIZE(twl6040_codec_rsrc); children++; /* Vibra input driver support */ if (twl6040_has_vibra(node)) { irq = regmap_irq_get_virq(twl6040->irq_data, TWL6040_IRQ_VIB); cell = &twl6040->cells[children]; cell->name = "twl6040-vibra"; twl6040_vibra_rsrc[0].start = irq; twl6040_vibra_rsrc[0].end = irq; cell->resources = twl6040_vibra_rsrc; cell->num_resources = ARRAY_SIZE(twl6040_vibra_rsrc); children++; } /* GPO support */ cell = &twl6040->cells[children]; cell->name = "twl6040-gpo"; children++; /* PDM clock support */ cell = &twl6040->cells[children]; cell->name = "twl6040-pdmclk"; children++; /* The chip is powered down so mark regmap to cache only and dirty */ regcache_cache_only(twl6040->regmap, true); regcache_mark_dirty(twl6040->regmap); ret = mfd_add_devices(&client->dev, -1, twl6040->cells, children, NULL, 0, NULL); if (ret) goto readyirq_err; return 0; readyirq_err: regmap_del_irq_chip(twl6040->irq, twl6040->irq_data); gpio_err: regulator_bulk_disable(TWL6040_NUM_SUPPLIES, twl6040->supplies); return ret; }
static __devinit int wm8994_device_init(struct wm8994 *wm8994, int irq) { struct wm8994_pdata *pdata = wm8994->dev->platform_data; struct regmap_config *regmap_config; const struct reg_default *regmap_patch = NULL; const char *devname; int ret, i, patch_regs; int pulls = 0; dev_set_drvdata(wm8994->dev, wm8994); ret = mfd_add_devices(wm8994->dev, -1, wm8994_regulator_devs, ARRAY_SIZE(wm8994_regulator_devs), NULL, 0); if (ret != 0) { dev_err(wm8994->dev, "Failed to add children: %d\n", ret); goto err; } switch (wm8994->type) { case WM1811: wm8994->num_supplies = ARRAY_SIZE(wm1811_main_supplies); break; case WM8994: wm8994->num_supplies = ARRAY_SIZE(wm8994_main_supplies); break; case WM8958: wm8994->num_supplies = ARRAY_SIZE(wm8958_main_supplies); break; default: BUG(); goto err; } wm8994->supplies = devm_kzalloc(wm8994->dev, sizeof(struct regulator_bulk_data) * wm8994->num_supplies, GFP_KERNEL); if (!wm8994->supplies) { ret = -ENOMEM; goto err; } switch (wm8994->type) { case WM1811: for (i = 0; i < ARRAY_SIZE(wm1811_main_supplies); i++) wm8994->supplies[i].supply = wm1811_main_supplies[i]; break; case WM8994: for (i = 0; i < ARRAY_SIZE(wm8994_main_supplies); i++) wm8994->supplies[i].supply = wm8994_main_supplies[i]; break; case WM8958: for (i = 0; i < ARRAY_SIZE(wm8958_main_supplies); i++) wm8994->supplies[i].supply = wm8958_main_supplies[i]; break; default: BUG(); goto err; } ret = regulator_bulk_get(wm8994->dev, wm8994->num_supplies, wm8994->supplies); if (ret != 0) { dev_err(wm8994->dev, "Failed to get supplies: %d\n", ret); goto err; } ret = regulator_bulk_enable(wm8994->num_supplies, wm8994->supplies); if (ret != 0) { dev_err(wm8994->dev, "Failed to enable supplies: %d\n", ret); goto err_get; } ret = wm8994_reg_read(wm8994, WM8994_SOFTWARE_RESET); if (ret < 0) { dev_err(wm8994->dev, "Failed to read ID register\n"); goto err_enable; } switch (ret) { case 0x1811: devname = "WM1811"; if (wm8994->type != WM1811) dev_warn(wm8994->dev, "Device registered as type %d\n", wm8994->type); wm8994->type = WM1811; break; case 0x8994: devname = "WM8994"; if (wm8994->type != WM8994) dev_warn(wm8994->dev, "Device registered as type %d\n", wm8994->type); wm8994->type = WM8994; break; case 0x8958: devname = "WM8958"; if (wm8994->type != WM8958) dev_warn(wm8994->dev, "Device registered as type %d\n", wm8994->type); wm8994->type = WM8958; break; default: dev_err(wm8994->dev, "Device is not a WM8994, ID is %x\n", ret); ret = -EINVAL; goto err_enable; } ret = wm8994_reg_read(wm8994, WM8994_CHIP_REVISION); if (ret < 0) { dev_err(wm8994->dev, "Failed to read revision register: %d\n", ret); goto err_enable; } wm8994->revision = ret; switch (wm8994->type) { case WM8994: switch (wm8994->revision) { case 0: case 1: dev_warn(wm8994->dev, "revision %c not fully supported\n", 'A' + wm8994->revision); break; case 2: case 3: regmap_patch = wm8994_revc_patch; patch_regs = ARRAY_SIZE(wm8994_revc_patch); break; default: break; } break; case WM8958: switch (wm8994->revision) { case 0: regmap_patch = wm8958_reva_patch; patch_regs = ARRAY_SIZE(wm8958_reva_patch); break; default: break; } break; case WM1811: if (wm8994->revision > 1) wm8994->revision++; switch (wm8994->revision) { case 0: case 1: case 2: case 3: case 4: regmap_patch = wm1811_reva_patch; patch_regs = ARRAY_SIZE(wm1811_reva_patch); break; default: break; } break; default: break; } dev_info(wm8994->dev, "%s revision %c\n", devname, 'A' + wm8994->revision); switch (wm8994->type) { case WM1811: regmap_config = &wm1811_regmap_config; break; case WM8994: regmap_config = &wm8994_regmap_config; break; case WM8958: regmap_config = &wm8958_regmap_config; break; default: dev_err(wm8994->dev, "Unknown device type %d\n", wm8994->type); return -EINVAL; } ret = regmap_reinit_cache(wm8994->regmap, regmap_config); if (ret != 0) { dev_err(wm8994->dev, "Failed to reinit register cache: %d\n", ret); return ret; } if (regmap_patch) { ret = regmap_register_patch(wm8994->regmap, regmap_patch, patch_regs); if (ret != 0) { dev_err(wm8994->dev, "Failed to register patch: %d\n", ret); goto err; } } if (pdata) { wm8994->irq_base = pdata->irq_base; wm8994->gpio_base = pdata->gpio_base; for (i = 0; i < ARRAY_SIZE(pdata->gpio_defaults); i++) { if (pdata->gpio_defaults[i]) { wm8994_set_bits(wm8994, WM8994_GPIO_1 + i, 0xffff, pdata->gpio_defaults[i]); } } wm8994->ldo_ena_always_driven = pdata->ldo_ena_always_driven; if (pdata->spkmode_pu) pulls |= WM8994_SPKMODE_PU; } wm8994_set_bits(wm8994, WM8994_PULL_CONTROL_2, WM8994_LDO1ENA_PD | WM8994_LDO2ENA_PD | WM8994_SPKMODE_PU | WM8994_CSNADDR_PD, pulls); for (i = 0; i < WM8994_NUM_LDO_REGS; i++) { if (wm8994_ldo_in_use(pdata, i)) wm8994_set_bits(wm8994, WM8994_LDO_1 + i, WM8994_LDO1_DISCH, WM8994_LDO1_DISCH); else wm8994_set_bits(wm8994, WM8994_LDO_1 + i, WM8994_LDO1_DISCH, 0); } wm8994_irq_init(wm8994); ret = mfd_add_devices(wm8994->dev, -1, wm8994_devs, ARRAY_SIZE(wm8994_devs), NULL, 0); if (ret != 0) { dev_err(wm8994->dev, "Failed to add children: %d\n", ret); goto err_irq; } pm_runtime_enable(wm8994->dev); pm_runtime_idle(wm8994->dev); return 0; err_irq: wm8994_irq_exit(wm8994); err_enable: regulator_bulk_disable(wm8994->num_supplies, wm8994->supplies); err_get: regulator_bulk_free(wm8994->num_supplies, wm8994->supplies); err: mfd_remove_devices(wm8994->dev); return ret; }