Skip to content

Commit

Permalink
mfd: arizona: Support Cirrus Logic CS47L24 and WM1831
Browse files Browse the repository at this point in the history
This patch adds the regmap configuration tables and
core MFD handling for the CS47L24 and WM1831 codecs.

Note that compared to the other Arizona codecs, these devices
do not have an LDO1 or micsupp regulators, extcon driver, or
the DCVDD isolation control.

Signed-off-by: Richard Fitzgerald <rf@opensource.wolfsonmicro.com>
Signed-off-by: Lee Jones <lee.jones@linaro.org>
  • Loading branch information
Richard Fitzgerald authored and Lee Jones committed Dec 4, 2015
1 parent 9a65a6d commit ea1f333
Show file tree
Hide file tree
Showing 8 changed files with 1,753 additions and 25 deletions.
18 changes: 12 additions & 6 deletions drivers/mfd/Kconfig
Expand Up @@ -1370,24 +1370,30 @@ config MFD_ARIZONA
bool

config MFD_ARIZONA_I2C
tristate "Wolfson Microelectronics Arizona platform with I2C"
tristate "Cirrus Logic/Wolfson Microelectronics Arizona platform with I2C"
select MFD_ARIZONA
select MFD_CORE
select REGMAP_I2C
depends on I2C
help
Support for the Wolfson Microelectronics Arizona platform audio SoC
core functionality controlled via I2C.
Support for the Cirrus Logic/Wolfson Microelectronics Arizona platform
audio SoC core functionality controlled via I2C.

config MFD_ARIZONA_SPI
tristate "Wolfson Microelectronics Arizona platform with SPI"
tristate "Cirrus Logic/Wolfson Microelectronics Arizona platform with SPI"
select MFD_ARIZONA
select MFD_CORE
select REGMAP_SPI
depends on SPI_MASTER
help
Support for the Wolfson Microelectronics Arizona platform audio SoC
core functionality controlled via I2C.
Support for the Cirrus Logic/Wolfson Microelectronics Arizona platform
audio SoC core functionality controlled via I2C.

config MFD_CS47L24
bool "Cirrus Logic CS47L24 and WM1831"
depends on MFD_ARIZONA
help
Support for Cirrus Logic CS47L24 and WM1831 low power audio SoC

config MFD_WM5102
bool "Wolfson Microelectronics WM5102"
Expand Down
3 changes: 3 additions & 0 deletions drivers/mfd/Makefile
Expand Up @@ -51,6 +51,9 @@ endif
ifeq ($(CONFIG_MFD_WM8998),y)
obj-$(CONFIG_MFD_ARIZONA) += wm8998-tables.o
endif
ifeq ($(CONFIG_MFD_CS47L24),y)
obj-$(CONFIG_MFD_ARIZONA) += cs47l24-tables.o
endif
obj-$(CONFIG_MFD_WM8400) += wm8400-core.o
wm831x-objs := wm831x-core.o wm831x-irq.o wm831x-otp.o
wm831x-objs += wm831x-auxadc.o
Expand Down
74 changes: 68 additions & 6 deletions drivers/mfd/arizona-core.c
Expand Up @@ -598,6 +598,12 @@ static int arizona_runtime_resume(struct device *dev)
goto err;
}
break;
case WM1831:
case CS47L24:
ret = arizona_wait_for_boot(arizona);
if (ret != 0)
goto err;
break;
default:
ret = arizona_wait_for_boot(arizona);
if (ret != 0)
Expand Down Expand Up @@ -682,6 +688,9 @@ static int arizona_runtime_suspend(struct device *dev)
}
}
break;
case WM1831:
case CS47L24:
break;
default:
jd_active = arizona_is_jack_det_active(arizona);
if (jd_active < 0)
Expand Down Expand Up @@ -862,6 +871,8 @@ const struct of_device_id arizona_of_match[] = {
{ .compatible = "wlf,wm8997", .data = (void *)WM8997 },
{ .compatible = "wlf,wm8998", .data = (void *)WM8998 },
{ .compatible = "wlf,wm1814", .data = (void *)WM1814 },
{ .compatible = "wlf,wm1831", .data = (void *)WM1831 },
{ .compatible = "cirrus,cs47l24", .data = (void *)CS47L24 },
{},
};
EXPORT_SYMBOL_GPL(arizona_of_match);
Expand Down Expand Up @@ -919,6 +930,23 @@ static const struct mfd_cell wm5110_devs[] = {
},
};

static const char * const cs47l24_supplies[] = {
"MICVDD",
"CPVDD",
"SPKVDD",
};

static const struct mfd_cell cs47l24_devs[] = {
{ .name = "arizona-gpio" },
{ .name = "arizona-haptics" },
{ .name = "arizona-pwm" },
{
.name = "cs47l24-codec",
.parent_supplies = cs47l24_supplies,
.num_parent_supplies = ARRAY_SIZE(cs47l24_supplies),
},
};

static const char * const wm8997_supplies[] = {
"MICVDD",
"DBVDD2",
Expand Down Expand Up @@ -963,7 +991,7 @@ static const struct mfd_cell wm8998_devs[] = {
int arizona_dev_init(struct arizona *arizona)
{
struct device *dev = arizona->dev;
const char *type_name;
const char *type_name = NULL;
unsigned int reg, val, mask;
int (*apply_patch)(struct arizona *) = NULL;
const struct mfd_cell *subdevs = NULL;
Expand All @@ -987,6 +1015,8 @@ int arizona_dev_init(struct arizona *arizona)
case WM8997:
case WM8998:
case WM1814:
case WM1831:
case CS47L24:
for (i = 0; i < ARRAY_SIZE(wm5102_core_supplies); i++)
arizona->core_supplies[i].supply
= wm5102_core_supplies[i];
Expand All @@ -1001,11 +1031,18 @@ int arizona_dev_init(struct arizona *arizona)
/* Mark DCVDD as external, LDO1 driver will clear if internal */
arizona->external_dcvdd = true;

ret = mfd_add_devices(arizona->dev, -1, early_devs,
ARRAY_SIZE(early_devs), NULL, 0, NULL);
if (ret != 0) {
dev_err(dev, "Failed to add early children: %d\n", ret);
return ret;
switch (arizona->type) {
case WM1831:
case CS47L24:
break; /* No LDO1 regulator */
default:
ret = mfd_add_devices(arizona->dev, -1, early_devs,
ARRAY_SIZE(early_devs), NULL, 0, NULL);
if (ret != 0) {
dev_err(dev, "Failed to add early children: %d\n", ret);
return ret;
}
break;
}

ret = devm_regulator_bulk_get(dev, arizona->num_core_supplies,
Expand Down Expand Up @@ -1069,6 +1106,7 @@ int arizona_dev_init(struct arizona *arizona)
case 0x5102:
case 0x5110:
case 0x6349:
case 0x6363:
case 0x8997:
break;
default:
Expand Down Expand Up @@ -1167,6 +1205,30 @@ int arizona_dev_init(struct arizona *arizona)
n_subdevs = ARRAY_SIZE(wm5110_devs);
}
break;
case 0x6363:
if (IS_ENABLED(CONFIG_MFD_CS47L24)) {
switch (arizona->type) {
case CS47L24:
type_name = "CS47L24";
break;

case WM1831:
type_name = "WM1831";
break;

default:
dev_warn(arizona->dev,
"CS47L24 registered as %d\n",
arizona->type);
arizona->type = CS47L24;
break;
}

apply_patch = cs47l24_patch;
subdevs = cs47l24_devs;
n_subdevs = ARRAY_SIZE(cs47l24_devs);
}
break;
case 0x8997:
if (IS_ENABLED(CONFIG_MFD_WM8997)) {
type_name = "WM8997";
Expand Down
40 changes: 27 additions & 13 deletions drivers/mfd/arizona-irq.c
Expand Up @@ -30,11 +30,13 @@ static int arizona_map_irq(struct arizona *arizona, int irq)
{
int ret;

ret = regmap_irq_get_virq(arizona->aod_irq_chip, irq);
if (ret < 0)
ret = regmap_irq_get_virq(arizona->irq_chip, irq);
if (arizona->aod_irq_chip) {
ret = regmap_irq_get_virq(arizona->aod_irq_chip, irq);
if (ret >= 0)
return ret;
}

return ret;
return regmap_irq_get_virq(arizona->irq_chip, irq);
}

int arizona_request_irq(struct arizona *arizona, int irq, char *name,
Expand Down Expand Up @@ -107,8 +109,8 @@ static irqreturn_t arizona_irq_thread(int irq, void *data)
do {
poll = false;

/* Always handle the AoD domain */
handle_nested_irq(irq_find_mapping(arizona->virq, 0));
if (arizona->aod_irq_chip)
handle_nested_irq(irq_find_mapping(arizona->virq, 0));

/*
* Check if one of the main interrupts is asserted and only
Expand Down Expand Up @@ -219,6 +221,15 @@ int arizona_irq_init(struct arizona *arizona)
arizona->ctrlif_error = false;
break;
#endif
#ifdef CONFIG_MFD_CS47L24
case WM1831:
case CS47L24:
aod = NULL;
irq = &cs47l24_irq;

arizona->ctrlif_error = false;
break;
#endif
#ifdef CONFIG_MFD_WM8997
case WM8997:
aod = &wm8997_aod;
Expand Down Expand Up @@ -291,13 +302,16 @@ int arizona_irq_init(struct arizona *arizona)
goto err;
}

ret = regmap_add_irq_chip(arizona->regmap,
irq_create_mapping(arizona->virq, 0),
IRQF_ONESHOT, 0, aod,
&arizona->aod_irq_chip);
if (ret != 0) {
dev_err(arizona->dev, "Failed to add AOD IRQs: %d\n", ret);
goto err_domain;
if (aod) {
ret = regmap_add_irq_chip(arizona->regmap,
irq_create_mapping(arizona->virq, 0),
IRQF_ONESHOT, 0, aod,
&arizona->aod_irq_chip);
if (ret != 0) {
dev_err(arizona->dev,
"Failed to add AOD IRQs: %d\n", ret);
goto err_domain;
}
}

ret = regmap_add_irq_chip(arizona->regmap,
Expand Down
7 changes: 7 additions & 0 deletions drivers/mfd/arizona-spi.c
Expand Up @@ -46,6 +46,11 @@ static int arizona_spi_probe(struct spi_device *spi)
if (IS_ENABLED(CONFIG_MFD_WM5110))
regmap_config = &wm5110_spi_regmap;
break;
case WM1831:
case CS47L24:
if (IS_ENABLED(CONFIG_MFD_CS47L24))
regmap_config = &cs47l24_spi_regmap;
break;
default:
dev_err(&spi->dev, "Unknown device type %ld\n", type);
return -EINVAL;
Expand Down Expand Up @@ -89,6 +94,8 @@ static const struct spi_device_id arizona_spi_ids[] = {
{ "wm5102", WM5102 },
{ "wm5110", WM5110 },
{ "wm8280", WM8280 },
{ "wm1831", WM1831 },
{ "cs47l24", CS47L24 },
{ },
};
MODULE_DEVICE_TABLE(spi, arizona_spi_ids);
Expand Down
4 changes: 4 additions & 0 deletions drivers/mfd/arizona.h
Expand Up @@ -25,6 +25,8 @@ extern const struct regmap_config wm5102_spi_regmap;
extern const struct regmap_config wm5110_i2c_regmap;
extern const struct regmap_config wm5110_spi_regmap;

extern const struct regmap_config cs47l24_spi_regmap;

extern const struct regmap_config wm8997_i2c_regmap;

extern const struct regmap_config wm8998_i2c_regmap;
Expand All @@ -40,6 +42,8 @@ extern const struct regmap_irq_chip wm5110_aod;
extern const struct regmap_irq_chip wm5110_irq;
extern const struct regmap_irq_chip wm5110_revd_irq;

extern const struct regmap_irq_chip cs47l24_irq;

extern const struct regmap_irq_chip wm8997_aod;
extern const struct regmap_irq_chip wm8997_irq;

Expand Down

0 comments on commit ea1f333

Please sign in to comment.