mirror of
https://github.com/linux-msm/laptops-kernel.git
synced 2026-08-13 14:19:53 -07:00
Merge branch 'topic/asoc' into for-linus
This commit is contained in:
commit
bb14eb0da7
186 files changed
+15231
-3461
No files matched your search
@@ -530,6 +530,7 @@ S: Maintained
|
||||
F: drivers/infiniband/hw/amso1100/
|
||||
|
||||
ANALOG DEVICES INC ASOC CODEC DRIVERS
|
||||
M: Lars-Peter Clausen <lars@metafoo.de>
|
||||
L: device-drivers-devel@blackfin.uclinux.org
|
||||
L: alsa-devel@alsa-project.org (moderated for non-subscribers)
|
||||
W: http://wiki.analog.com/
|
||||
@@ -7199,6 +7200,7 @@ T: git git://opensource.wolfsonmicro.com/linux-2.6-audioplus
|
||||
W: http://opensource.wolfsonmicro.com/content/linux-drivers-wolfson-devices
|
||||
S: Supported
|
||||
F: Documentation/hwmon/wm83??
|
||||
F: arch/arm/mach-s3c64xx/mach-crag6410*
|
||||
F: drivers/leds/leds-wm83*.c
|
||||
F: drivers/input/misc/wm831x-on.c
|
||||
F: drivers/input/touchscreen/wm831x-ts.c
|
||||
|
||||
@@ -900,7 +900,6 @@ static struct twl4030_platform_data rx51_twldata __initdata = {
|
||||
};
|
||||
|
||||
static struct tpa6130a2_platform_data rx51_tpa6130a2_data __initdata_or_module = {
|
||||
.id = TPA6130A2,
|
||||
.power_gpio = 98,
|
||||
};
|
||||
|
||||
|
||||
@@ -330,6 +330,38 @@ static void omap_init_audio(void)
|
||||
static inline void omap_init_audio(void) {}
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_SND_OMAP_SOC_MCPDM) || \
|
||||
defined(CONFIG_SND_OMAP_SOC_MCPDM_MODULE)
|
||||
|
||||
static struct omap_device_pm_latency omap_mcpdm_latency[] = {
|
||||
{
|
||||
.deactivate_func = omap_device_idle_hwmods,
|
||||
.activate_func = omap_device_enable_hwmods,
|
||||
.flags = OMAP_DEVICE_LATENCY_AUTO_ADJUST,
|
||||
},
|
||||
};
|
||||
|
||||
static void omap_init_mcpdm(void)
|
||||
{
|
||||
struct omap_hwmod *oh;
|
||||
struct omap_device *od;
|
||||
|
||||
oh = omap_hwmod_lookup("mcpdm");
|
||||
if (!oh) {
|
||||
printk(KERN_ERR "Could not look up mcpdm hw_mod\n");
|
||||
return;
|
||||
}
|
||||
|
||||
od = omap_device_build("omap-mcpdm", -1, oh, NULL, 0,
|
||||
omap_mcpdm_latency,
|
||||
ARRAY_SIZE(omap_mcpdm_latency), 0);
|
||||
if (IS_ERR(od))
|
||||
printk(KERN_ERR "Could not build omap_device for omap-mcpdm-dai\n");
|
||||
}
|
||||
#else
|
||||
static inline void omap_init_mcpdm(void) {}
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_SPI_OMAP24XX) || defined(CONFIG_SPI_OMAP24XX_MODULE)
|
||||
|
||||
#include <plat/mcspi.h>
|
||||
@@ -683,6 +715,7 @@ static int __init omap2_init_devices(void)
|
||||
* in alphabetical order so they're easier to sort through.
|
||||
*/
|
||||
omap_init_audio();
|
||||
omap_init_mcpdm();
|
||||
omap_init_camera();
|
||||
omap_init_mbox();
|
||||
omap_init_mcspi();
|
||||
|
||||
@@ -5430,7 +5430,7 @@ static __initdata struct omap_hwmod *omap44xx_hwmods[] = {
|
||||
&omap44xx_mcbsp4_hwmod,
|
||||
|
||||
/* mcpdm class */
|
||||
/* &omap44xx_mcpdm_hwmod, */
|
||||
&omap44xx_mcpdm_hwmod,
|
||||
|
||||
/* mcspi class */
|
||||
&omap44xx_mcspi1_hwmod,
|
||||
|
||||
@@ -74,41 +74,6 @@ void omap_mcbsp_register_board_cfg(struct resource *res, int res_count,
|
||||
|
||||
/*-------------------------------------------------------------------------*/
|
||||
|
||||
#if defined(CONFIG_SND_OMAP_SOC_MCPDM) || \
|
||||
defined(CONFIG_SND_OMAP_SOC_MCPDM_MODULE)
|
||||
|
||||
static struct resource mcpdm_resources[] = {
|
||||
{
|
||||
.name = "mcpdm_mem",
|
||||
.start = OMAP44XX_MCPDM_BASE,
|
||||
.end = OMAP44XX_MCPDM_BASE + SZ_4K,
|
||||
.flags = IORESOURCE_MEM,
|
||||
},
|
||||
{
|
||||
.name = "mcpdm_irq",
|
||||
.start = OMAP44XX_IRQ_MCPDM,
|
||||
.end = OMAP44XX_IRQ_MCPDM,
|
||||
.flags = IORESOURCE_IRQ,
|
||||
},
|
||||
};
|
||||
|
||||
static struct platform_device omap_mcpdm_device = {
|
||||
.name = "omap-mcpdm",
|
||||
.id = -1,
|
||||
.num_resources = ARRAY_SIZE(mcpdm_resources),
|
||||
.resource = mcpdm_resources,
|
||||
};
|
||||
|
||||
static void omap_init_mcpdm(void)
|
||||
{
|
||||
(void) platform_device_register(&omap_mcpdm_device);
|
||||
}
|
||||
#else
|
||||
static inline void omap_init_mcpdm(void) {}
|
||||
#endif
|
||||
|
||||
/*-------------------------------------------------------------------------*/
|
||||
|
||||
#if defined(CONFIG_MMC_OMAP) || defined(CONFIG_MMC_OMAP_MODULE) || \
|
||||
defined(CONFIG_MMC_OMAP_HS) || defined(CONFIG_MMC_OMAP_HS_MODULE)
|
||||
|
||||
@@ -291,7 +256,6 @@ static int __init omap_init_devices(void)
|
||||
* in alphabetical order so they're easier to sort through.
|
||||
*/
|
||||
omap_init_rng();
|
||||
omap_init_mcpdm();
|
||||
omap_init_uwire();
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -74,12 +74,12 @@ static irqreturn_t twl6040_vib_irq_handler(int irq, void *data)
|
||||
if (status & TWL6040_VIBLOCDET) {
|
||||
dev_warn(info->dev, "Left Vibrator overcurrent detected\n");
|
||||
twl6040_clear_bits(twl6040, TWL6040_REG_VIBCTLL,
|
||||
TWL6040_VIBENAL);
|
||||
TWL6040_VIBENA);
|
||||
}
|
||||
if (status & TWL6040_VIBROCDET) {
|
||||
dev_warn(info->dev, "Right Vibrator overcurrent detected\n");
|
||||
twl6040_clear_bits(twl6040, TWL6040_REG_VIBCTLR,
|
||||
TWL6040_VIBENAR);
|
||||
TWL6040_VIBENA);
|
||||
}
|
||||
|
||||
return IRQ_HANDLED;
|
||||
@@ -104,16 +104,16 @@ static void twl6040_vibra_enable(struct vibra_info *info)
|
||||
* overcurrent detection
|
||||
*/
|
||||
twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLL,
|
||||
TWL6040_VIBENAL | TWL6040_VIBCTRLL);
|
||||
TWL6040_VIBENA | TWL6040_VIBCTRL);
|
||||
twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLR,
|
||||
TWL6040_VIBENAR | TWL6040_VIBCTRLR);
|
||||
TWL6040_VIBENA | TWL6040_VIBCTRL);
|
||||
usleep_range(3000, 3500);
|
||||
}
|
||||
|
||||
twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLL,
|
||||
TWL6040_VIBENAL);
|
||||
TWL6040_VIBENA);
|
||||
twl6040_reg_write(twl6040, TWL6040_REG_VIBCTLR,
|
||||
TWL6040_VIBENAR);
|
||||
TWL6040_VIBENA);
|
||||
|
||||
info->enabled = true;
|
||||
}
|
||||
@@ -201,6 +201,13 @@ static int vibra_play(struct input_dev *input, void *data,
|
||||
struct vibra_info *info = input_get_drvdata(input);
|
||||
int ret;
|
||||
|
||||
/* Do not allow effect, while the routing is set to use audio */
|
||||
ret = twl6040_get_vibralr_status(info->twl6040);
|
||||
if (ret & TWL6040_VIBSEL) {
|
||||
dev_info(&input->dev, "Vibra is configured for audio\n");
|
||||
return -EBUSY;
|
||||
}
|
||||
|
||||
info->weak_speed = effect->u.rumble.weak_magnitude;
|
||||
info->strong_speed = effect->u.rumble.strong_magnitude;
|
||||
info->direction = effect->direction < EFFECT_DIR_180_DEG ? 1 : -1;
|
||||
|
||||
@@ -34,16 +34,24 @@
|
||||
#include <linux/mfd/core.h>
|
||||
#include <linux/mfd/twl6040.h>
|
||||
|
||||
#define VIBRACTRL_MEMBER(reg) ((reg == TWL6040_REG_VIBCTLL) ? 0 : 1)
|
||||
|
||||
int twl6040_reg_read(struct twl6040 *twl6040, unsigned int reg)
|
||||
{
|
||||
int ret;
|
||||
u8 val = 0;
|
||||
|
||||
mutex_lock(&twl6040->io_mutex);
|
||||
ret = twl_i2c_read_u8(TWL_MODULE_AUDIO_VOICE, &val, reg);
|
||||
if (ret < 0) {
|
||||
mutex_unlock(&twl6040->io_mutex);
|
||||
return ret;
|
||||
/* Vibra control registers from cache */
|
||||
if (unlikely(reg == TWL6040_REG_VIBCTLL ||
|
||||
reg == TWL6040_REG_VIBCTLR)) {
|
||||
val = twl6040->vibra_ctrl_cache[VIBRACTRL_MEMBER(reg)];
|
||||
} else {
|
||||
ret = twl_i2c_read_u8(TWL_MODULE_AUDIO_VOICE, &val, reg);
|
||||
if (ret < 0) {
|
||||
mutex_unlock(&twl6040->io_mutex);
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
mutex_unlock(&twl6040->io_mutex);
|
||||
|
||||
@@ -57,6 +65,9 @@ int twl6040_reg_write(struct twl6040 *twl6040, unsigned int reg, u8 val)
|
||||
|
||||
mutex_lock(&twl6040->io_mutex);
|
||||
ret = twl_i2c_write_u8(TWL_MODULE_AUDIO_VOICE, val, reg);
|
||||
/* Cache the vibra control registers */
|
||||
if (reg == TWL6040_REG_VIBCTLL || reg == TWL6040_REG_VIBCTLR)
|
||||
twl6040->vibra_ctrl_cache[VIBRACTRL_MEMBER(reg)] = val;
|
||||
mutex_unlock(&twl6040->io_mutex);
|
||||
|
||||
return ret;
|
||||
@@ -433,6 +444,18 @@ unsigned int twl6040_get_sysclk(struct twl6040 *twl6040)
|
||||
}
|
||||
EXPORT_SYMBOL(twl6040_get_sysclk);
|
||||
|
||||
/* Get the combined status of the vibra control register */
|
||||
int twl6040_get_vibralr_status(struct twl6040 *twl6040)
|
||||
{
|
||||
u8 status;
|
||||
|
||||
status = twl6040->vibra_ctrl_cache[0] | twl6040->vibra_ctrl_cache[1];
|
||||
status &= (TWL6040_VIBENA | TWL6040_VIBSEL);
|
||||
|
||||
return status;
|
||||
}
|
||||
EXPORT_SYMBOL(twl6040_get_vibralr_status);
|
||||
|
||||
static struct resource twl6040_vibra_rsrc[] = {
|
||||
{
|
||||
.flags = IORESOURCE_IRQ,
|
||||
|
||||
@@ -243,6 +243,18 @@ static struct mfd_cell wm8994_devs[] = {
|
||||
* and should be handled via the standard regulator API supply
|
||||
* management.
|
||||
*/
|
||||
static const char *wm1811_main_supplies[] = {
|
||||
"DBVDD1",
|
||||
"DBVDD2",
|
||||
"DBVDD3",
|
||||
"DCVDD",
|
||||
"AVDD1",
|
||||
"AVDD2",
|
||||
"CPVDD",
|
||||
"SPKVDD1",
|
||||
"SPKVDD2",
|
||||
};
|
||||
|
||||
static const char *wm8994_main_supplies[] = {
|
||||
"DBVDD",
|
||||
"DCVDD",
|
||||
@@ -401,6 +413,9 @@ static int wm8994_device_init(struct wm8994 *wm8994, int irq)
|
||||
}
|
||||
|
||||
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;
|
||||
@@ -421,6 +436,10 @@ static int wm8994_device_init(struct wm8994 *wm8994, int irq)
|
||||
}
|
||||
|
||||
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];
|
||||
@@ -454,6 +473,13 @@ static int wm8994_device_init(struct wm8994 *wm8994, int irq)
|
||||
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)
|
||||
@@ -651,6 +677,7 @@ static int wm8994_i2c_remove(struct i2c_client *i2c)
|
||||
}
|
||||
|
||||
static const struct i2c_device_id wm8994_i2c_id[] = {
|
||||
{ "wm1811", WM1811 },
|
||||
{ "wm8994", WM8994 },
|
||||
{ "wm8958", WM8958 },
|
||||
{ }
|
||||
|
||||
@@ -1599,13 +1599,18 @@ static void regulator_disable_work(struct work_struct *work)
|
||||
int regulator_disable_deferred(struct regulator *regulator, int ms)
|
||||
{
|
||||
struct regulator_dev *rdev = regulator->rdev;
|
||||
int ret;
|
||||
|
||||
mutex_lock(&rdev->mutex);
|
||||
rdev->deferred_disables++;
|
||||
mutex_unlock(&rdev->mutex);
|
||||
|
||||
return schedule_delayed_work(&rdev->disable_work,
|
||||
msecs_to_jiffies(ms));
|
||||
ret = schedule_delayed_work(&rdev->disable_work,
|
||||
msecs_to_jiffies(ms));
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(regulator_disable_deferred);
|
||||
|
||||
|
||||
@@ -140,6 +140,14 @@ static int wm8994_ldo2_list_voltage(struct regulator_dev *rdev,
|
||||
return (selector * 100000) + 900000;
|
||||
case WM8958:
|
||||
return (selector * 100000) + 1000000;
|
||||
case WM1811:
|
||||
switch (selector) {
|
||||
case 0:
|
||||
return -EINVAL;
|
||||
default:
|
||||
return (selector * 100000) + 950000;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
return -EINVAL;
|
||||
}
|
||||
@@ -170,6 +178,11 @@ static int wm8994_ldo2_set_voltage(struct regulator_dev *rdev,
|
||||
case WM8958:
|
||||
selector = (min_uV - 1000000) / 100000;
|
||||
break;
|
||||
case WM1811:
|
||||
selector = (min_uV - 950000) / 100000;
|
||||
if (selector == 0)
|
||||
selector = 1;
|
||||
break;
|
||||
default:
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
+15
-23
@@ -68,8 +68,6 @@
|
||||
#define TWL6040_REG_ACCCTL 0x2D
|
||||
#define TWL6040_REG_STATUS 0x2E
|
||||
|
||||
#define TWL6040_CACHEREGNUM (TWL6040_REG_STATUS + 1)
|
||||
|
||||
/* INTID (0x03) fields */
|
||||
|
||||
#define TWL6040_THINT 0x01
|
||||
@@ -122,34 +120,24 @@
|
||||
#define TWL6040_LPLLFIN 0x08
|
||||
#define TWL6040_HPLLSEL 0x10
|
||||
|
||||
/* HSLCTL (0x10) fields */
|
||||
/* HSLCTL/R (0x10/0x11) fields */
|
||||
|
||||
#define TWL6040_HSDACMODEL 0x02
|
||||
#define TWL6040_HSDRVMODEL 0x08
|
||||
#define TWL6040_HSDACENA (1 << 0)
|
||||
#define TWL6040_HSDACMODE (1 << 1)
|
||||
#define TWL6040_HSDRVMODE (1 << 3)
|
||||
|
||||
/* HSRCTL (0x11) fields */
|
||||
/* VIBCTLL/R (0x18/0x1A) fields */
|
||||
|
||||
#define TWL6040_HSDACMODER 0x02
|
||||
#define TWL6040_HSDRVMODER 0x08
|
||||
#define TWL6040_VIBENA (1 << 0)
|
||||
#define TWL6040_VIBSEL (1 << 1)
|
||||
#define TWL6040_VIBCTRL (1 << 2)
|
||||
#define TWL6040_VIBCTRL_P (1 << 3)
|
||||
#define TWL6040_VIBCTRL_N (1 << 4)
|
||||
|
||||
/* VIBCTLL (0x18) fields */
|
||||
|
||||
#define TWL6040_VIBENAL 0x01
|
||||
#define TWL6040_VIBCTRLL 0x04
|
||||
#define TWL6040_VIBCTRLLP 0x08
|
||||
#define TWL6040_VIBCTRLLN 0x10
|
||||
|
||||
/* VIBDATL (0x19) fields */
|
||||
/* VIBDATL/R (0x19/0x1B) fields */
|
||||
|
||||
#define TWL6040_VIBDAT_MAX 0x64
|
||||
|
||||
/* VIBCTLR (0x1A) fields */
|
||||
|
||||
#define TWL6040_VIBENAR 0x01
|
||||
#define TWL6040_VIBCTRLR 0x04
|
||||
#define TWL6040_VIBCTRLRP 0x08
|
||||
#define TWL6040_VIBCTRLRN 0x10
|
||||
|
||||
/* GPOCTL (0x1E) fields */
|
||||
|
||||
#define TWL6040_GPO1 0x01
|
||||
@@ -197,6 +185,7 @@ struct twl6040 {
|
||||
int audpwron;
|
||||
int power_count;
|
||||
int rev;
|
||||
u8 vibra_ctrl_cache[2];
|
||||
|
||||
int pll;
|
||||
unsigned int sysclk;
|
||||
@@ -221,10 +210,13 @@ int twl6040_get_pll(struct twl6040 *twl6040);
|
||||
unsigned int twl6040_get_sysclk(struct twl6040 *twl6040);
|
||||
int twl6040_irq_init(struct twl6040 *twl6040);
|
||||
void twl6040_irq_exit(struct twl6040 *twl6040);
|
||||
/* Get the combined status of the vibra control register */
|
||||
int twl6040_get_vibralr_status(struct twl6040 *twl6040);
|
||||
|
||||
static inline int twl6040_get_revid(struct twl6040 *twl6040)
|
||||
{
|
||||
return twl6040->rev;
|
||||
}
|
||||
|
||||
|
||||
#endif /* End of __TWL6040_CODEC_H__ */
|
||||
@@ -20,6 +20,7 @@
|
||||
enum wm8994_type {
|
||||
WM8994 = 0,
|
||||
WM8958 = 1,
|
||||
WM1811 = 2,
|
||||
};
|
||||
|
||||
struct regulator_dev;
|
||||
|
||||
@@ -2069,6 +2069,10 @@
|
||||
/*
|
||||
* R96 (0x60) - Analogue HP (1)
|
||||
*/
|
||||
#define WM1811_HPOUT1_ATTN 0x0100 /* HPOUT1_ATTN */
|
||||
#define WM1811_HPOUT1_ATTN_MASK 0x0100 /* HPOUT1_ATTN */
|
||||
#define WM1811_HPOUT1_ATTN_SHIFT 8 /* HPOUT1_ATTN */
|
||||
#define WM1811_HPOUT1_ATTN_WIDTH 1 /* HPOUT1_ATTN */
|
||||
#define WM8994_HPOUT1L_RMV_SHORT 0x0080 /* HPOUT1L_RMV_SHORT */
|
||||
#define WM8994_HPOUT1L_RMV_SHORT_MASK 0x0080 /* HPOUT1L_RMV_SHORT */
|
||||
#define WM8994_HPOUT1L_RMV_SHORT_SHIFT 7 /* HPOUT1L_RMV_SHORT */
|
||||
|
||||
+20
-17
@@ -24,13 +24,13 @@ struct snd_pcm_substream;
|
||||
* Describes the physical PCM data formating and clocking. Add new formats
|
||||
* to the end.
|
||||
*/
|
||||
#define SND_SOC_DAIFMT_I2S 0 /* I2S mode */
|
||||
#define SND_SOC_DAIFMT_RIGHT_J 1 /* Right Justified mode */
|
||||
#define SND_SOC_DAIFMT_LEFT_J 2 /* Left Justified mode */
|
||||
#define SND_SOC_DAIFMT_DSP_A 3 /* L data MSB after FRM LRC */
|
||||
#define SND_SOC_DAIFMT_DSP_B 4 /* L data MSB during FRM LRC */
|
||||
#define SND_SOC_DAIFMT_AC97 5 /* AC97 */
|
||||
#define SND_SOC_DAIFMT_PDM 6 /* Pulse density modulation */
|
||||
#define SND_SOC_DAIFMT_I2S 1 /* I2S mode */
|
||||
#define SND_SOC_DAIFMT_RIGHT_J 2 /* Right Justified mode */
|
||||
#define SND_SOC_DAIFMT_LEFT_J 3 /* Left Justified mode */
|
||||
#define SND_SOC_DAIFMT_DSP_A 4 /* L data MSB after FRM LRC */
|
||||
#define SND_SOC_DAIFMT_DSP_B 5 /* L data MSB during FRM LRC */
|
||||
#define SND_SOC_DAIFMT_AC97 6 /* AC97 */
|
||||
#define SND_SOC_DAIFMT_PDM 7 /* Pulse density modulation */
|
||||
|
||||
/* left and right justified also known as MSB and LSB respectively */
|
||||
#define SND_SOC_DAIFMT_MSB SND_SOC_DAIFMT_LEFT_J
|
||||
@@ -42,8 +42,8 @@ struct snd_pcm_substream;
|
||||
* DAI bit clocks can be be gated (disabled) when the DAI is not
|
||||
* sending or receiving PCM data in a frame. This can be used to save power.
|
||||
*/
|
||||
#define SND_SOC_DAIFMT_CONT (0 << 4) /* continuous clock */
|
||||
#define SND_SOC_DAIFMT_GATED (1 << 4) /* clock is gated */
|
||||
#define SND_SOC_DAIFMT_CONT (1 << 4) /* continuous clock */
|
||||
#define SND_SOC_DAIFMT_GATED (2 << 4) /* clock is gated */
|
||||
|
||||
/*
|
||||
* DAI hardware signal inversions.
|
||||
@@ -51,10 +51,10 @@ struct snd_pcm_substream;
|
||||
* Specifies whether the DAI can also support inverted clocks for the specified
|
||||
* format.
|
||||
*/
|
||||
#define SND_SOC_DAIFMT_NB_NF (0 << 8) /* normal bit clock + frame */
|
||||
#define SND_SOC_DAIFMT_NB_IF (1 << 8) /* normal BCLK + inv FRM */
|
||||
#define SND_SOC_DAIFMT_IB_NF (2 << 8) /* invert BCLK + nor FRM */
|
||||
#define SND_SOC_DAIFMT_IB_IF (3 << 8) /* invert BCLK + FRM */
|
||||
#define SND_SOC_DAIFMT_NB_NF (1 << 8) /* normal bit clock + frame */
|
||||
#define SND_SOC_DAIFMT_NB_IF (2 << 8) /* normal BCLK + inv FRM */
|
||||
#define SND_SOC_DAIFMT_IB_NF (3 << 8) /* invert BCLK + nor FRM */
|
||||
#define SND_SOC_DAIFMT_IB_IF (4 << 8) /* invert BCLK + FRM */
|
||||
|
||||
/*
|
||||
* DAI hardware clock masters.
|
||||
@@ -63,10 +63,10 @@ struct snd_pcm_substream;
|
||||
* i.e. if the codec is clk and FRM master then the interface is
|
||||
* clk and frame slave.
|
||||
*/
|
||||
#define SND_SOC_DAIFMT_CBM_CFM (0 << 12) /* codec clk & FRM master */
|
||||
#define SND_SOC_DAIFMT_CBS_CFM (1 << 12) /* codec clk slave & FRM master */
|
||||
#define SND_SOC_DAIFMT_CBM_CFS (2 << 12) /* codec clk master & frame slave */
|
||||
#define SND_SOC_DAIFMT_CBS_CFS (3 << 12) /* codec clk & FRM slave */
|
||||
#define SND_SOC_DAIFMT_CBM_CFM (1 << 12) /* codec clk & FRM master */
|
||||
#define SND_SOC_DAIFMT_CBS_CFM (2 << 12) /* codec clk slave & FRM master */
|
||||
#define SND_SOC_DAIFMT_CBM_CFS (3 << 12) /* codec clk master & frame slave */
|
||||
#define SND_SOC_DAIFMT_CBS_CFS (4 << 12) /* codec clk & FRM slave */
|
||||
|
||||
#define SND_SOC_DAIFMT_FORMAT_MASK 0x000f
|
||||
#define SND_SOC_DAIFMT_CLOCK_MASK 0x00f0
|
||||
@@ -242,6 +242,9 @@ struct snd_soc_dai {
|
||||
void *playback_dma_data;
|
||||
void *capture_dma_data;
|
||||
|
||||
/* Symmetry data - only valid if symmetry is being enforced */
|
||||
unsigned int rate;
|
||||
|
||||
/* parent platform/codec */
|
||||
union {
|
||||
struct snd_soc_platform *platform;
|
||||
|
||||
@@ -381,6 +381,9 @@ int snd_soc_dapm_force_enable_pin(struct snd_soc_dapm_context *dapm,
|
||||
int snd_soc_dapm_ignore_suspend(struct snd_soc_dapm_context *dapm,
|
||||
const char *pin);
|
||||
|
||||
/* Mostly internal - should not normally be used */
|
||||
void dapm_mark_dirty(struct snd_soc_dapm_widget *w, const char *reason);
|
||||
|
||||
/* dapm widget types */
|
||||
enum snd_soc_dapm_type {
|
||||
snd_soc_dapm_input = 0, /* input pin */
|
||||
@@ -473,6 +476,8 @@ struct snd_soc_dapm_widget {
|
||||
unsigned char ext:1; /* has external widgets */
|
||||
unsigned char force:1; /* force state */
|
||||
unsigned char ignore_suspend:1; /* kept enabled over suspend */
|
||||
unsigned char new_power:1; /* power from this run */
|
||||
unsigned char power_checked:1; /* power checked this run */
|
||||
int subseq; /* sort within widget type */
|
||||
|
||||
int (*power_check)(struct snd_soc_dapm_widget *w);
|
||||
@@ -492,6 +497,9 @@ struct snd_soc_dapm_widget {
|
||||
|
||||
/* used during DAPM updates */
|
||||
struct list_head power_list;
|
||||
struct list_head dirty;
|
||||
int inputs;
|
||||
int outputs;
|
||||
};
|
||||
|
||||
struct snd_soc_dapm_update {
|
||||
@@ -537,4 +545,10 @@ struct snd_soc_dapm_widget_list {
|
||||
struct snd_soc_dapm_widget *widgets[0];
|
||||
};
|
||||
|
||||
struct snd_soc_dapm_stats {
|
||||
int power_checks;
|
||||
int path_checks;
|
||||
int neighbour_checks;
|
||||
};
|
||||
|
||||
#endif
|
||||
+51
-40
@@ -28,13 +28,20 @@
|
||||
/*
|
||||
* Convenience kcontrol builders
|
||||
*/
|
||||
#define SOC_SINGLE_VALUE(xreg, xshift, xmax, xinvert) \
|
||||
#define SOC_DOUBLE_VALUE(xreg, shift_left, shift_right, xmax, xinvert) \
|
||||
((unsigned long)&(struct soc_mixer_control) \
|
||||
{.reg = xreg, .shift = xshift, .rshift = xshift, .max = xmax, \
|
||||
.platform_max = xmax, .invert = xinvert})
|
||||
{.reg = xreg, .rreg = xreg, .shift = shift_left, \
|
||||
.rshift = shift_right, .max = xmax, .platform_max = xmax, \
|
||||
.invert = xinvert})
|
||||
#define SOC_SINGLE_VALUE(xreg, xshift, xmax, xinvert) \
|
||||
SOC_DOUBLE_VALUE(xreg, xshift, xshift, xmax, xinvert)
|
||||
#define SOC_SINGLE_VALUE_EXT(xreg, xmax, xinvert) \
|
||||
((unsigned long)&(struct soc_mixer_control) \
|
||||
{.reg = xreg, .max = xmax, .platform_max = xmax, .invert = xinvert})
|
||||
#define SOC_DOUBLE_R_VALUE(xlreg, xrreg, xshift, xmax, xinvert) \
|
||||
((unsigned long)&(struct soc_mixer_control) \
|
||||
{.reg = xlreg, .rreg = xrreg, .shift = xshift, .rshift = xshift, \
|
||||
.max = xmax, .platform_max = xmax, .invert = xinvert})
|
||||
#define SOC_SINGLE(xname, reg, shift, max, invert) \
|
||||
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \
|
||||
.info = snd_soc_info_volsw, .get = snd_soc_get_volsw,\
|
||||
@@ -48,40 +55,36 @@
|
||||
.info = snd_soc_info_volsw, .get = snd_soc_get_volsw,\
|
||||
.put = snd_soc_put_volsw, \
|
||||
.private_value = SOC_SINGLE_VALUE(reg, shift, max, invert) }
|
||||
#define SOC_DOUBLE(xname, xreg, shift_left, shift_right, xmax, xinvert) \
|
||||
#define SOC_DOUBLE(xname, reg, shift_left, shift_right, max, invert) \
|
||||
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = (xname),\
|
||||
.info = snd_soc_info_volsw, .get = snd_soc_get_volsw, \
|
||||
.put = snd_soc_put_volsw, \
|
||||
.private_value = (unsigned long)&(struct soc_mixer_control) \
|
||||
{.reg = xreg, .shift = shift_left, .rshift = shift_right, \
|
||||
.max = xmax, .platform_max = xmax, .invert = xinvert} }
|
||||
.private_value = SOC_DOUBLE_VALUE(reg, shift_left, shift_right, \
|
||||
max, invert) }
|
||||
#define SOC_DOUBLE_R(xname, reg_left, reg_right, xshift, xmax, xinvert) \
|
||||
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = (xname), \
|
||||
.info = snd_soc_info_volsw_2r, \
|
||||
.get = snd_soc_get_volsw_2r, .put = snd_soc_put_volsw_2r, \
|
||||
.private_value = (unsigned long)&(struct soc_mixer_control) \
|
||||
{.reg = reg_left, .rreg = reg_right, .shift = xshift, \
|
||||
.max = xmax, .platform_max = xmax, .invert = xinvert} }
|
||||
#define SOC_DOUBLE_TLV(xname, xreg, shift_left, shift_right, xmax, xinvert, tlv_array) \
|
||||
.info = snd_soc_info_volsw, \
|
||||
.get = snd_soc_get_volsw, .put = snd_soc_put_volsw, \
|
||||
.private_value = SOC_DOUBLE_R_VALUE(reg_left, reg_right, xshift, \
|
||||
xmax, xinvert) }
|
||||
#define SOC_DOUBLE_TLV(xname, reg, shift_left, shift_right, max, invert, tlv_array) \
|
||||
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = (xname),\
|
||||
.access = SNDRV_CTL_ELEM_ACCESS_TLV_READ |\
|
||||
SNDRV_CTL_ELEM_ACCESS_READWRITE,\
|
||||
.tlv.p = (tlv_array), \
|
||||
.info = snd_soc_info_volsw, .get = snd_soc_get_volsw, \
|
||||
.put = snd_soc_put_volsw, \
|
||||
.private_value = (unsigned long)&(struct soc_mixer_control) \
|
||||
{.reg = xreg, .shift = shift_left, .rshift = shift_right,\
|
||||
.max = xmax, .platform_max = xmax, .invert = xinvert} }
|
||||
.private_value = SOC_DOUBLE_VALUE(reg, shift_left, shift_right, \
|
||||
max, invert) }
|
||||
#define SOC_DOUBLE_R_TLV(xname, reg_left, reg_right, xshift, xmax, xinvert, tlv_array) \
|
||||
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = (xname),\
|
||||
.access = SNDRV_CTL_ELEM_ACCESS_TLV_READ |\
|
||||
SNDRV_CTL_ELEM_ACCESS_READWRITE,\
|
||||
.tlv.p = (tlv_array), \
|
||||
.info = snd_soc_info_volsw_2r, \
|
||||
.get = snd_soc_get_volsw_2r, .put = snd_soc_put_volsw_2r, \
|
||||
.private_value = (unsigned long)&(struct soc_mixer_control) \
|
||||
{.reg = reg_left, .rreg = reg_right, .shift = xshift, \
|
||||
.max = xmax, .platform_max = xmax, .invert = xinvert} }
|
||||
.info = snd_soc_info_volsw, \
|
||||
.get = snd_soc_get_volsw, .put = snd_soc_put_volsw, \
|
||||
.private_value = SOC_DOUBLE_R_VALUE(reg_left, reg_right, xshift, \
|
||||
xmax, xinvert) }
|
||||
#define SOC_DOUBLE_S8_TLV(xname, xreg, xmin, xmax, tlv_array) \
|
||||
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = (xname), \
|
||||
.access = SNDRV_CTL_ELEM_ACCESS_TLV_READ | \
|
||||
@@ -121,14 +124,13 @@
|
||||
.info = snd_soc_info_volsw, \
|
||||
.get = xhandler_get, .put = xhandler_put, \
|
||||
.private_value = SOC_SINGLE_VALUE(xreg, xshift, xmax, xinvert) }
|
||||
#define SOC_DOUBLE_EXT(xname, xreg, shift_left, shift_right, xmax, xinvert,\
|
||||
#define SOC_DOUBLE_EXT(xname, reg, shift_left, shift_right, max, invert,\
|
||||
xhandler_get, xhandler_put) \
|
||||
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = (xname),\
|
||||
.info = snd_soc_info_volsw, \
|
||||
.get = xhandler_get, .put = xhandler_put, \
|
||||
.private_value = (unsigned long)&(struct soc_mixer_control) \
|
||||
{.reg = xreg, .shift = shift_left, .rshift = shift_right, \
|
||||
.max = xmax, .platform_max = xmax, .invert = xinvert} }
|
||||
.private_value = \
|
||||
SOC_DOUBLE_VALUE(reg, shift_left, shift_right, max, invert) }
|
||||
#define SOC_SINGLE_EXT_TLV(xname, xreg, xshift, xmax, xinvert,\
|
||||
xhandler_get, xhandler_put, tlv_array) \
|
||||
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \
|
||||
@@ -146,20 +148,18 @@
|
||||
.tlv.p = (tlv_array), \
|
||||
.info = snd_soc_info_volsw, \
|
||||
.get = xhandler_get, .put = xhandler_put, \
|
||||
.private_value = (unsigned long)&(struct soc_mixer_control) \
|
||||
{.reg = xreg, .shift = shift_left, .rshift = shift_right, \
|
||||
.max = xmax, .platform_max = xmax, .invert = xinvert} }
|
||||
.private_value = SOC_DOUBLE_VALUE(xreg, shift_left, shift_right, \
|
||||
xmax, xinvert) }
|
||||
#define SOC_DOUBLE_R_EXT_TLV(xname, reg_left, reg_right, xshift, xmax, xinvert,\
|
||||
xhandler_get, xhandler_put, tlv_array) \
|
||||
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = (xname), \
|
||||
.access = SNDRV_CTL_ELEM_ACCESS_TLV_READ | \
|
||||
SNDRV_CTL_ELEM_ACCESS_READWRITE, \
|
||||
.tlv.p = (tlv_array), \
|
||||
.info = snd_soc_info_volsw_2r, \
|
||||
.info = snd_soc_info_volsw, \
|
||||
.get = xhandler_get, .put = xhandler_put, \
|
||||
.private_value = (unsigned long)&(struct soc_mixer_control) \
|
||||
{.reg = reg_left, .rreg = reg_right, .shift = xshift, \
|
||||
.max = xmax, .platform_max = xmax, .invert = xinvert} }
|
||||
.private_value = SOC_DOUBLE_R_VALUE(reg_left, reg_right, xshift, \
|
||||
xmax, xinvert) }
|
||||
#define SOC_SINGLE_BOOL_EXT(xname, xdata, xhandler_get, xhandler_put) \
|
||||
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \
|
||||
.info = snd_soc_info_bool_ext, \
|
||||
@@ -393,12 +393,8 @@ int snd_soc_get_volsw(struct snd_kcontrol *kcontrol,
|
||||
struct snd_ctl_elem_value *ucontrol);
|
||||
int snd_soc_put_volsw(struct snd_kcontrol *kcontrol,
|
||||
struct snd_ctl_elem_value *ucontrol);
|
||||
int snd_soc_info_volsw_2r(struct snd_kcontrol *kcontrol,
|
||||
struct snd_ctl_elem_info *uinfo);
|
||||
int snd_soc_get_volsw_2r(struct snd_kcontrol *kcontrol,
|
||||
struct snd_ctl_elem_value *ucontrol);
|
||||
int snd_soc_put_volsw_2r(struct snd_kcontrol *kcontrol,
|
||||
struct snd_ctl_elem_value *ucontrol);
|
||||
#define snd_soc_get_volsw_2r snd_soc_get_volsw
|
||||
#define snd_soc_put_volsw_2r snd_soc_put_volsw
|
||||
int snd_soc_info_volsw_s8(struct snd_kcontrol *kcontrol,
|
||||
struct snd_ctl_elem_info *uinfo);
|
||||
int snd_soc_get_volsw_s8(struct snd_kcontrol *kcontrol,
|
||||
@@ -582,6 +578,7 @@ struct snd_soc_codec {
|
||||
|
||||
/* dapm */
|
||||
struct snd_soc_dapm_context dapm;
|
||||
unsigned int ignore_pmdown_time:1; /* pmdown_time is ignored at stop */
|
||||
|
||||
#ifdef CONFIG_DEBUG_FS
|
||||
struct dentry *debugfs_codec_root;
|
||||
@@ -713,6 +710,8 @@ struct snd_soc_dai_link {
|
||||
const char *cpu_dai_name;
|
||||
const char *codec_dai_name;
|
||||
|
||||
unsigned int dai_fmt; /* format to set on init */
|
||||
|
||||
/* Keep DAI active over suspend */
|
||||
unsigned int ignore_suspend:1;
|
||||
|
||||
@@ -825,9 +824,11 @@ struct snd_soc_card {
|
||||
struct list_head widgets;
|
||||
struct list_head paths;
|
||||
struct list_head dapm_list;
|
||||
struct list_head dapm_dirty;
|
||||
|
||||
/* Generic DAPM context for the card */
|
||||
struct snd_soc_dapm_context dapm;
|
||||
struct snd_soc_dapm_stats dapm_stats;
|
||||
|
||||
#ifdef CONFIG_DEBUG_FS
|
||||
struct dentry *debugfs_card_root;
|
||||
@@ -850,8 +851,6 @@ struct snd_soc_pcm_runtime {
|
||||
unsigned int complete:1;
|
||||
unsigned int dev_registered:1;
|
||||
|
||||
/* Symmetry data - only valid if symmetry is being enforced */
|
||||
unsigned int rate;
|
||||
long pmdown_time;
|
||||
|
||||
/* runtime devices */
|
||||
@@ -946,6 +945,18 @@ static inline void snd_soc_initialize_card_lists(struct snd_soc_card *card)
|
||||
INIT_LIST_HEAD(&card->dapm_list);
|
||||
}
|
||||
|
||||
static inline bool snd_soc_volsw_is_stereo(struct soc_mixer_control *mc)
|
||||
{
|
||||
if (mc->reg == mc->rreg && mc->shift == mc->rshift)
|
||||
return 0;
|
||||
/*
|
||||
* mc->reg == mc->rreg && mc->shift != mc->rshift, or
|
||||
* mc->reg != mc->rreg means that the control is
|
||||
* stereo (bits in one register or in two registers)
|
||||
*/
|
||||
return 1;
|
||||
}
|
||||
|
||||
int snd_soc_util_init(void);
|
||||
void snd_soc_util_exit(void);
|
||||
|
||||
|
||||
@@ -23,13 +23,7 @@
|
||||
#ifndef TPA6130A2_PLAT_H
|
||||
#define TPA6130A2_PLAT_H
|
||||
|
||||
enum tpa_model {
|
||||
TPA6130A2,
|
||||
TPA6140A2,
|
||||
};
|
||||
|
||||
struct tpa6130a2_platform_data {
|
||||
enum tpa_model id;
|
||||
int power_gpio;
|
||||
};
|
||||
|
||||
|
||||
@@ -0,0 +1,27 @@
|
||||
/*
|
||||
* linux/sound/wm1250-ev1.h - Platform data for WM1250-EV1
|
||||
*
|
||||
* Copyright 2011 Wolfson Microelectronics. PLC.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
#ifndef __LINUX_SND_WM1250_EV1_H
|
||||
#define __LINUX_SND_WM1250_EV1_H
|
||||
|
||||
#define WM1250_EV1_NUM_GPIOS 5
|
||||
|
||||
#define WM1250_EV1_GPIO_CLK_ENA 0
|
||||
#define WM1250_EV1_GPIO_CLK_SEL0 1
|
||||
#define WM1250_EV1_GPIO_CLK_SEL1 2
|
||||
#define WM1250_EV1_GPIO_OSR 3
|
||||
#define WM1250_EV1_GPIO_MASTER 4
|
||||
|
||||
|
||||
struct wm1250_ev1_pdata {
|
||||
int gpios[WM1250_EV1_NUM_GPIOS];
|
||||
};
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,59 @@
|
||||
/*
|
||||
* linux/sound/wm5100.h -- Platform data for WM5100
|
||||
*
|
||||
* Copyright 2011 Wolfson Microelectronics. PLC.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
#ifndef __LINUX_SND_WM5100_H
|
||||
#define __LINUX_SND_WM5100_H
|
||||
|
||||
enum wm5100_in_mode {
|
||||
WM5100_IN_SE = 0,
|
||||
WM5100_IN_DIFF = 1,
|
||||
WM5100_IN_DMIC = 2,
|
||||
};
|
||||
|
||||
enum wm5100_dmic_sup {
|
||||
WM5100_DMIC_SUP_MICVDD = 0,
|
||||
WM5100_DMIC_SUP_MICBIAS1 = 1,
|
||||
WM5100_DMIC_SUP_MICBIAS2 = 2,
|
||||
WM5100_DMIC_SUP_MICBIAS3 = 3,
|
||||
};
|
||||
|
||||
enum wm5100_micdet_bias {
|
||||
WM5100_MICDET_MICBIAS1 = 0,
|
||||
WM5100_MICDET_MICBIAS2 = 1,
|
||||
WM5100_MICDET_MICBIAS3 = 2,
|
||||
};
|
||||
|
||||
struct wm5100_jack_mode {
|
||||
enum wm5100_micdet_bias bias;
|
||||
int hp_pol;
|
||||
int micd_src;
|
||||
};
|
||||
|
||||
#define WM5100_GPIO_SET 0x10000
|
||||
|
||||
struct wm5100_pdata {
|
||||
int reset; /** GPIO controlling /RESET, if any */
|
||||
int ldo_ena; /** GPIO controlling LODENA, if any */
|
||||
int hp_pol; /** GPIO controlling headset polarity, if any */
|
||||
int irq_flags;
|
||||
int gpio_base;
|
||||
|
||||
struct wm5100_jack_mode jack_modes[2];
|
||||
|
||||
/* Input pin mode selection */
|
||||
enum wm5100_in_mode in_mode[4];
|
||||
|
||||
/* DMIC supply selection */
|
||||
enum wm5100_dmic_sup dmic_sup[4];
|
||||
|
||||
int gpio_defaults[6];
|
||||
};
|
||||
|
||||
#endif
|
||||
@@ -216,6 +216,31 @@ DEFINE_EVENT(snd_soc_dapm_widget, snd_soc_dapm_widget_event_done,
|
||||
|
||||
);
|
||||
|
||||
TRACE_EVENT(snd_soc_dapm_walk_done,
|
||||
|
||||
TP_PROTO(struct snd_soc_card *card),
|
||||
|
||||
TP_ARGS(card),
|
||||
|
||||
TP_STRUCT__entry(
|
||||
__string( name, card->name )
|
||||
__field( int, power_checks )
|
||||
__field( int, path_checks )
|
||||
__field( int, neighbour_checks )
|
||||
),
|
||||
|
||||
TP_fast_assign(
|
||||
__assign_str(name, card->name);
|
||||
__entry->power_checks = card->dapm_stats.power_checks;
|
||||
__entry->path_checks = card->dapm_stats.path_checks;
|
||||
__entry->neighbour_checks = card->dapm_stats.neighbour_checks;
|
||||
),
|
||||
|
||||
TP_printk("%s: checks %d power, %d path, %d neighbour",
|
||||
__get_str(name), (int)__entry->power_checks,
|
||||
(int)__entry->path_checks, (int)__entry->neighbour_checks)
|
||||
);
|
||||
|
||||
TRACE_EVENT(snd_soc_jack_irq,
|
||||
|
||||
TP_PROTO(const char *name),
|
||||
|
||||
Loaded 20 of 186 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user