diff options
author | Takashi Iwai <tiwai@suse.de> | 2013-08-23 08:12:22 -0400 |
---|---|---|
committer | Takashi Iwai <tiwai@suse.de> | 2013-08-23 08:12:22 -0400 |
commit | 68538bf2bce557c3b5fe8c59b034d45352500db1 (patch) | |
tree | a84b68990cadcbfc277acc7b7f2b75716750e203 /sound/soc/soc-core.c | |
parent | a8cc20999799a94929a56393ff39b32245e33d64 (diff) | |
parent | 43bcb402f84fe459102120b4e2d28d7117f16cd0 (diff) |
Merge tag 'asoc-v3.12' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/sound into for-next
ASoC: Updates for v3.12
- DAPM is now mandatory for CODEC drivers in order to avoid the repeated
regressions in the special cases for non-DAPM CODECs and make it
easier to integrate with other components on boards. All existing
drivers have had some level of DAPM support added.
- A lot of cleanups in DAPM plus support for maintaining controls in a
specific state while a DAPM widget all contributed by Lars-Peter Clausen.
- Core helpers for bitbanged AC'97 reset from Markus Pargmann.
- New drivers and support for Analog Devices ADAU1702 and ADAU1401(a),
Asahi Kasei Microdevices AK4554, Atmel AT91ASM9x5 and WM8904 based
machines, Freescale S/PDIF and SSI AC'97, Renesas R-Car SoCs, Samsung
Exynos5420 SoCs, Texas Instruments PCM1681 and PCM1792A and Wolfson
Microelectronics WM8997.
- Support for building drivers that can support it cross-platform for
compile test.
Diffstat (limited to 'sound/soc/soc-core.c')
-rw-r--r-- | sound/soc/soc-core.c | 240 |
1 files changed, 182 insertions, 58 deletions
diff --git a/sound/soc/soc-core.c b/sound/soc/soc-core.c index 88daa649fc06..5471940dc0f7 100644 --- a/sound/soc/soc-core.c +++ b/sound/soc/soc-core.c | |||
@@ -30,9 +30,12 @@ | |||
30 | #include <linux/bitops.h> | 30 | #include <linux/bitops.h> |
31 | #include <linux/debugfs.h> | 31 | #include <linux/debugfs.h> |
32 | #include <linux/platform_device.h> | 32 | #include <linux/platform_device.h> |
33 | #include <linux/pinctrl/consumer.h> | ||
33 | #include <linux/ctype.h> | 34 | #include <linux/ctype.h> |
34 | #include <linux/slab.h> | 35 | #include <linux/slab.h> |
35 | #include <linux/of.h> | 36 | #include <linux/of.h> |
37 | #include <linux/gpio.h> | ||
38 | #include <linux/of_gpio.h> | ||
36 | #include <sound/ac97_codec.h> | 39 | #include <sound/ac97_codec.h> |
37 | #include <sound/core.h> | 40 | #include <sound/core.h> |
38 | #include <sound/jack.h> | 41 | #include <sound/jack.h> |
@@ -47,8 +50,6 @@ | |||
47 | 50 | ||
48 | #define NAME_SIZE 32 | 51 | #define NAME_SIZE 32 |
49 | 52 | ||
50 | static DECLARE_WAIT_QUEUE_HEAD(soc_pm_waitq); | ||
51 | |||
52 | #ifdef CONFIG_DEBUG_FS | 53 | #ifdef CONFIG_DEBUG_FS |
53 | struct dentry *snd_soc_debugfs_root; | 54 | struct dentry *snd_soc_debugfs_root; |
54 | EXPORT_SYMBOL_GPL(snd_soc_debugfs_root); | 55 | EXPORT_SYMBOL_GPL(snd_soc_debugfs_root); |
@@ -69,6 +70,16 @@ static int pmdown_time = 5000; | |||
69 | module_param(pmdown_time, int, 0); | 70 | module_param(pmdown_time, int, 0); |
70 | MODULE_PARM_DESC(pmdown_time, "DAPM stream powerdown time (msecs)"); | 71 | MODULE_PARM_DESC(pmdown_time, "DAPM stream powerdown time (msecs)"); |
71 | 72 | ||
73 | struct snd_ac97_reset_cfg { | ||
74 | struct pinctrl *pctl; | ||
75 | struct pinctrl_state *pstate_reset; | ||
76 | struct pinctrl_state *pstate_warm_reset; | ||
77 | struct pinctrl_state *pstate_run; | ||
78 | int gpio_sdata; | ||
79 | int gpio_sync; | ||
80 | int gpio_reset; | ||
81 | }; | ||
82 | |||
72 | /* returns the minimum number of bytes needed to represent | 83 | /* returns the minimum number of bytes needed to represent |
73 | * a particular given value */ | 84 | * a particular given value */ |
74 | static int min_bytes_needed(unsigned long val) | 85 | static int min_bytes_needed(unsigned long val) |
@@ -532,6 +543,15 @@ static int soc_ac97_dev_register(struct snd_soc_codec *codec) | |||
532 | } | 543 | } |
533 | #endif | 544 | #endif |
534 | 545 | ||
546 | static void codec2codec_close_delayed_work(struct work_struct *work) | ||
547 | { | ||
548 | /* Currently nothing to do for c2c links | ||
549 | * Since c2c links are internal nodes in the DAPM graph and | ||
550 | * don't interface with the outside world or application layer | ||
551 | * we don't have to do any special handling on close. | ||
552 | */ | ||
553 | } | ||
554 | |||
535 | #ifdef CONFIG_PM_SLEEP | 555 | #ifdef CONFIG_PM_SLEEP |
536 | /* powers down audio subsystem for suspend */ | 556 | /* powers down audio subsystem for suspend */ |
537 | int snd_soc_suspend(struct device *dev) | 557 | int snd_soc_suspend(struct device *dev) |
@@ -1430,6 +1450,9 @@ static int soc_probe_link_dais(struct snd_soc_card *card, int num, int order) | |||
1430 | return ret; | 1450 | return ret; |
1431 | } | 1451 | } |
1432 | } else { | 1452 | } else { |
1453 | INIT_DELAYED_WORK(&rtd->delayed_work, | ||
1454 | codec2codec_close_delayed_work); | ||
1455 | |||
1433 | /* link the DAI widgets */ | 1456 | /* link the DAI widgets */ |
1434 | play_w = codec_dai->playback_widget; | 1457 | play_w = codec_dai->playback_widget; |
1435 | capture_w = cpu_dai->capture_widget; | 1458 | capture_w = cpu_dai->capture_widget; |
@@ -2082,6 +2105,117 @@ int snd_soc_new_ac97_codec(struct snd_soc_codec *codec, | |||
2082 | } | 2105 | } |
2083 | EXPORT_SYMBOL_GPL(snd_soc_new_ac97_codec); | 2106 | EXPORT_SYMBOL_GPL(snd_soc_new_ac97_codec); |
2084 | 2107 | ||
2108 | static struct snd_ac97_reset_cfg snd_ac97_rst_cfg; | ||
2109 | |||
2110 | static void snd_soc_ac97_warm_reset(struct snd_ac97 *ac97) | ||
2111 | { | ||
2112 | struct pinctrl *pctl = snd_ac97_rst_cfg.pctl; | ||
2113 | |||
2114 | pinctrl_select_state(pctl, snd_ac97_rst_cfg.pstate_warm_reset); | ||
2115 | |||
2116 | gpio_direction_output(snd_ac97_rst_cfg.gpio_sync, 1); | ||
2117 | |||
2118 | udelay(10); | ||
2119 | |||
2120 | gpio_direction_output(snd_ac97_rst_cfg.gpio_sync, 0); | ||
2121 | |||
2122 | pinctrl_select_state(pctl, snd_ac97_rst_cfg.pstate_run); | ||
2123 | msleep(2); | ||
2124 | } | ||
2125 | |||
2126 | static void snd_soc_ac97_reset(struct snd_ac97 *ac97) | ||
2127 | { | ||
2128 | struct pinctrl *pctl = snd_ac97_rst_cfg.pctl; | ||
2129 | |||
2130 | pinctrl_select_state(pctl, snd_ac97_rst_cfg.pstate_reset); | ||
2131 | |||
2132 | gpio_direction_output(snd_ac97_rst_cfg.gpio_sync, 0); | ||
2133 | gpio_direction_output(snd_ac97_rst_cfg.gpio_sdata, 0); | ||
2134 | gpio_direction_output(snd_ac97_rst_cfg.gpio_reset, 0); | ||
2135 | |||
2136 | udelay(10); | ||
2137 | |||
2138 | gpio_direction_output(snd_ac97_rst_cfg.gpio_reset, 1); | ||
2139 | |||
2140 | pinctrl_select_state(pctl, snd_ac97_rst_cfg.pstate_run); | ||
2141 | msleep(2); | ||
2142 | } | ||
2143 | |||
2144 | static int snd_soc_ac97_parse_pinctl(struct device *dev, | ||
2145 | struct snd_ac97_reset_cfg *cfg) | ||
2146 | { | ||
2147 | struct pinctrl *p; | ||
2148 | struct pinctrl_state *state; | ||
2149 | int gpio; | ||
2150 | int ret; | ||
2151 | |||
2152 | p = devm_pinctrl_get(dev); | ||
2153 | if (IS_ERR(p)) { | ||
2154 | dev_err(dev, "Failed to get pinctrl\n"); | ||
2155 | return PTR_RET(p); | ||
2156 | } | ||
2157 | cfg->pctl = p; | ||
2158 | |||
2159 | state = pinctrl_lookup_state(p, "ac97-reset"); | ||
2160 | if (IS_ERR(state)) { | ||
2161 | dev_err(dev, "Can't find pinctrl state ac97-reset\n"); | ||
2162 | return PTR_RET(state); | ||
2163 | } | ||
2164 | cfg->pstate_reset = state; | ||
2165 | |||
2166 | state = pinctrl_lookup_state(p, "ac97-warm-reset"); | ||
2167 | if (IS_ERR(state)) { | ||
2168 | dev_err(dev, "Can't find pinctrl state ac97-warm-reset\n"); | ||
2169 | return PTR_RET(state); | ||
2170 | } | ||
2171 | cfg->pstate_warm_reset = state; | ||
2172 | |||
2173 | state = pinctrl_lookup_state(p, "ac97-running"); | ||
2174 | if (IS_ERR(state)) { | ||
2175 | dev_err(dev, "Can't find pinctrl state ac97-running\n"); | ||
2176 | return PTR_RET(state); | ||
2177 | } | ||
2178 | cfg->pstate_run = state; | ||
2179 | |||
2180 | gpio = of_get_named_gpio(dev->of_node, "ac97-gpios", 0); | ||
2181 | if (gpio < 0) { | ||
2182 | dev_err(dev, "Can't find ac97-sync gpio\n"); | ||
2183 | return gpio; | ||
2184 | } | ||
2185 | ret = devm_gpio_request(dev, gpio, "AC97 link sync"); | ||
2186 | if (ret) { | ||
2187 | dev_err(dev, "Failed requesting ac97-sync gpio\n"); | ||
2188 | return ret; | ||
2189 | } | ||
2190 | cfg->gpio_sync = gpio; | ||
2191 | |||
2192 | gpio = of_get_named_gpio(dev->of_node, "ac97-gpios", 1); | ||
2193 | if (gpio < 0) { | ||
2194 | dev_err(dev, "Can't find ac97-sdata gpio %d\n", gpio); | ||
2195 | return gpio; | ||
2196 | } | ||
2197 | ret = devm_gpio_request(dev, gpio, "AC97 link sdata"); | ||
2198 | if (ret) { | ||
2199 | dev_err(dev, "Failed requesting ac97-sdata gpio\n"); | ||
2200 | return ret; | ||
2201 | } | ||
2202 | cfg->gpio_sdata = gpio; | ||
2203 | |||
2204 | gpio = of_get_named_gpio(dev->of_node, "ac97-gpios", 2); | ||
2205 | if (gpio < 0) { | ||
2206 | dev_err(dev, "Can't find ac97-reset gpio\n"); | ||
2207 | return gpio; | ||
2208 | } | ||
2209 | ret = devm_gpio_request(dev, gpio, "AC97 link reset"); | ||
2210 | if (ret) { | ||
2211 | dev_err(dev, "Failed requesting ac97-reset gpio\n"); | ||
2212 | return ret; | ||
2213 | } | ||
2214 | cfg->gpio_reset = gpio; | ||
2215 | |||
2216 | return 0; | ||
2217 | } | ||
2218 | |||
2085 | struct snd_ac97_bus_ops *soc_ac97_ops; | 2219 | struct snd_ac97_bus_ops *soc_ac97_ops; |
2086 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | 2220 | EXPORT_SYMBOL_GPL(soc_ac97_ops); |
2087 | 2221 | ||
@@ -2100,6 +2234,35 @@ int snd_soc_set_ac97_ops(struct snd_ac97_bus_ops *ops) | |||
2100 | EXPORT_SYMBOL_GPL(snd_soc_set_ac97_ops); | 2234 | EXPORT_SYMBOL_GPL(snd_soc_set_ac97_ops); |
2101 | 2235 | ||
2102 | /** | 2236 | /** |
2237 | * snd_soc_set_ac97_ops_of_reset - Set ac97 ops with generic ac97 reset functions | ||
2238 | * | ||
2239 | * This function sets the reset and warm_reset properties of ops and parses | ||
2240 | * the device node of pdev to get pinctrl states and gpio numbers to use. | ||
2241 | */ | ||
2242 | int snd_soc_set_ac97_ops_of_reset(struct snd_ac97_bus_ops *ops, | ||
2243 | struct platform_device *pdev) | ||
2244 | { | ||
2245 | struct device *dev = &pdev->dev; | ||
2246 | struct snd_ac97_reset_cfg cfg; | ||
2247 | int ret; | ||
2248 | |||
2249 | ret = snd_soc_ac97_parse_pinctl(dev, &cfg); | ||
2250 | if (ret) | ||
2251 | return ret; | ||
2252 | |||
2253 | ret = snd_soc_set_ac97_ops(ops); | ||
2254 | if (ret) | ||
2255 | return ret; | ||
2256 | |||
2257 | ops->warm_reset = snd_soc_ac97_warm_reset; | ||
2258 | ops->reset = snd_soc_ac97_reset; | ||
2259 | |||
2260 | snd_ac97_rst_cfg = cfg; | ||
2261 | return 0; | ||
2262 | } | ||
2263 | EXPORT_SYMBOL_GPL(snd_soc_set_ac97_ops_of_reset); | ||
2264 | |||
2265 | /** | ||
2103 | * snd_soc_free_ac97_codec - free AC97 codec device | 2266 | * snd_soc_free_ac97_codec - free AC97 codec device |
2104 | * @codec: audio codec | 2267 | * @codec: audio codec |
2105 | * | 2268 | * |
@@ -2301,6 +2464,22 @@ static int snd_soc_add_controls(struct snd_card *card, struct device *dev, | |||
2301 | return 0; | 2464 | return 0; |
2302 | } | 2465 | } |
2303 | 2466 | ||
2467 | struct snd_kcontrol *snd_soc_card_get_kcontrol(struct snd_soc_card *soc_card, | ||
2468 | const char *name) | ||
2469 | { | ||
2470 | struct snd_card *card = soc_card->snd_card; | ||
2471 | struct snd_kcontrol *kctl; | ||
2472 | |||
2473 | if (unlikely(!name)) | ||
2474 | return NULL; | ||
2475 | |||
2476 | list_for_each_entry(kctl, &card->controls, list) | ||
2477 | if (!strncmp(kctl->id.name, name, sizeof(kctl->id.name))) | ||
2478 | return kctl; | ||
2479 | return NULL; | ||
2480 | } | ||
2481 | EXPORT_SYMBOL_GPL(snd_soc_card_get_kcontrol); | ||
2482 | |||
2304 | /** | 2483 | /** |
2305 | * snd_soc_add_codec_controls - add an array of controls to a codec. | 2484 | * snd_soc_add_codec_controls - add an array of controls to a codec. |
2306 | * Convenience function to add a list of controls. Many codecs were | 2485 | * Convenience function to add a list of controls. Many codecs were |
@@ -2543,59 +2722,6 @@ int snd_soc_put_value_enum_double(struct snd_kcontrol *kcontrol, | |||
2543 | EXPORT_SYMBOL_GPL(snd_soc_put_value_enum_double); | 2722 | EXPORT_SYMBOL_GPL(snd_soc_put_value_enum_double); |
2544 | 2723 | ||
2545 | /** | 2724 | /** |
2546 | * snd_soc_info_enum_ext - external enumerated single mixer info callback | ||
2547 | * @kcontrol: mixer control | ||
2548 | * @uinfo: control element information | ||
2549 | * | ||
2550 | * Callback to provide information about an external enumerated | ||
2551 | * single mixer. | ||
2552 | * | ||
2553 | * Returns 0 for success. | ||
2554 | */ | ||
2555 | int snd_soc_info_enum_ext(struct snd_kcontrol *kcontrol, | ||
2556 | struct snd_ctl_elem_info *uinfo) | ||
2557 | { | ||
2558 | struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; | ||
2559 | |||
2560 | uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED; | ||
2561 | uinfo->count = 1; | ||
2562 | uinfo->value.enumerated.items = e->max; | ||
2563 | |||
2564 | if (uinfo->value.enumerated.item > e->max - 1) | ||
2565 | uinfo->value.enumerated.item = e->max - 1; | ||
2566 | strcpy(uinfo->value.enumerated.name, | ||
2567 | e->texts[uinfo->value.enumerated.item]); | ||
2568 | return 0; | ||
2569 | } | ||
2570 | EXPORT_SYMBOL_GPL(snd_soc_info_enum_ext); | ||
2571 | |||
2572 | /** | ||
2573 | * snd_soc_info_volsw_ext - external single mixer info callback | ||
2574 | * @kcontrol: mixer control | ||
2575 | * @uinfo: control element information | ||
2576 | * | ||
2577 | * Callback to provide information about a single external mixer control. | ||
2578 | * | ||
2579 | * Returns 0 for success. | ||
2580 | */ | ||
2581 | int snd_soc_info_volsw_ext(struct snd_kcontrol *kcontrol, | ||
2582 | struct snd_ctl_elem_info *uinfo) | ||
2583 | { | ||
2584 | int max = kcontrol->private_value; | ||
2585 | |||
2586 | if (max == 1 && !strstr(kcontrol->id.name, " Volume")) | ||
2587 | uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN; | ||
2588 | else | ||
2589 | uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER; | ||
2590 | |||
2591 | uinfo->count = 1; | ||
2592 | uinfo->value.integer.min = 0; | ||
2593 | uinfo->value.integer.max = max; | ||
2594 | return 0; | ||
2595 | } | ||
2596 | EXPORT_SYMBOL_GPL(snd_soc_info_volsw_ext); | ||
2597 | |||
2598 | /** | ||
2599 | * snd_soc_info_volsw - single mixer info callback | 2725 | * snd_soc_info_volsw - single mixer info callback |
2600 | * @kcontrol: mixer control | 2726 | * @kcontrol: mixer control |
2601 | * @uinfo: control element information | 2727 | * @uinfo: control element information |
@@ -3910,10 +4036,8 @@ int snd_soc_add_platform(struct device *dev, struct snd_soc_platform *platform, | |||
3910 | { | 4036 | { |
3911 | /* create platform component name */ | 4037 | /* create platform component name */ |
3912 | platform->name = fmt_single_name(dev, &platform->id); | 4038 | platform->name = fmt_single_name(dev, &platform->id); |
3913 | if (platform->name == NULL) { | 4039 | if (platform->name == NULL) |
3914 | kfree(platform); | ||
3915 | return -ENOMEM; | 4040 | return -ENOMEM; |
3916 | } | ||
3917 | 4041 | ||
3918 | platform->dev = dev; | 4042 | platform->dev = dev; |
3919 | platform->driver = platform_drv; | 4043 | platform->driver = platform_drv; |