From b4b48e8df95f24d4e75e9fc07690bb8bc6416974 Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Wed, 3 Jun 2009 20:43:29 +0100 Subject: [PATCH] --- yaml --- r: 148347 b: refs/heads/master c: 872c78202c58d26596e25743791ee81a7d24abad h: refs/heads/master i: 148345: 32cd9b572baab3f4c2bf7e705d16675e498a9792 148343: 19ce2dbffba5c54f2bb064d5cc26d0693ac064f1 v: v3 --- [refs] | 2 +- trunk/Documentation/hwmon/sysfs-interface | 6 - trunk/Documentation/sound/alsa/soc/dapm.txt | 1 - trunk/MAINTAINERS | 17 +- trunk/Makefile | 4 +- trunk/arch/arm/include/asm/assembler.h | 13 - trunk/arch/arm/include/asm/atomic.h | 61 +- trunk/arch/arm/include/asm/cache.h | 16 - trunk/arch/arm/include/asm/page.h | 7 + trunk/arch/arm/include/asm/system.h | 176 -- trunk/arch/arm/kernel/elf.c | 9 - trunk/arch/arm/kernel/entry-armv.S | 5 +- trunk/arch/arm/lib/bitops.h | 2 - .../arm/mach-gemini/include/mach/hardware.h | 3 +- trunk/arch/arm/mach-kirkwood/common.c | 8 +- trunk/arch/arm/mach-kirkwood/ts219-setup.c | 6 +- trunk/arch/arm/mach-loki/common.c | 6 - .../arm/mach-mmp/include/mach/mfp-pxa168.h | 5 - .../arm/mach-mmp/include/mach/mfp-pxa910.h | 5 - trunk/arch/arm/mach-mmp/include/mach/mfp.h | 9 +- trunk/arch/arm/mach-mmp/time.c | 2 +- trunk/arch/arm/mach-mv78xx0/common.c | 16 +- trunk/arch/arm/mach-mx2/clock_imx21.c | 2 +- trunk/arch/arm/mach-mx2/clock_imx27.c | 2 +- trunk/arch/arm/mach-mx3/clock-imx35.c | 2 +- trunk/arch/arm/mach-mx3/clock.c | 2 +- trunk/arch/arm/mach-orion5x/common.c | 5 +- trunk/arch/arm/mach-pxa/devices.c | 5 +- trunk/arch/arm/mach-pxa/ezx.c | 36 +- trunk/arch/arm/mach-pxa/imote2.c | 2 +- trunk/arch/arm/mach-pxa/include/mach/reset.h | 5 +- trunk/arch/arm/mach-pxa/mfp-pxa2xx.c | 6 - trunk/arch/arm/mach-pxa/palmld.c | 2 - trunk/arch/arm/mach-pxa/palmt5.c | 1 - trunk/arch/arm/mach-pxa/palmtx.c | 1 - trunk/arch/arm/mach-pxa/reset.c | 4 +- trunk/arch/arm/mach-pxa/spitz.c | 8 +- trunk/arch/arm/mach-pxa/tosa.c | 2 +- trunk/arch/arm/mm/proc-v7.S | 36 +- trunk/arch/arm/tools/mach-types | 131 +- trunk/arch/mips/Kconfig | 5 +- trunk/arch/mips/include/asm/cpu-info.h | 4 +- trunk/arch/mips/include/asm/delay.h | 92 +- trunk/arch/mips/include/asm/ioctl.h | 4 - trunk/arch/mips/kernel/proc.c | 2 +- trunk/arch/mips/lib/Makefile | 4 +- trunk/arch/mips/lib/delay.c | 56 - trunk/arch/mips/sibyte/cfe/setup.c | 8 +- trunk/arch/powerpc/configs/pmac32_defconfig | 278 +-- trunk/arch/powerpc/include/asm/mpc52xx_psc.h | 11 - trunk/arch/sparc/include/asm/elf_64.h | 5 +- trunk/arch/sparc/lib/csum_copy_from_user.S | 2 +- trunk/arch/sparc/lib/csum_copy_to_user.S | 2 +- .../x86/kernel/cpu/cpufreq/acpi-cpufreq.c | 6 +- .../arch/x86/kernel/cpu/cpufreq/powernow-k7.c | 2 +- .../arch/x86/kernel/cpu/cpufreq/powernow-k8.c | 15 +- .../kernel/cpu/cpufreq/speedstep-centrino.c | 2 +- trunk/arch/x86/kernel/cpu/mcheck/mce_64.c | 2 +- trunk/arch/x86/kernel/tlb_uv.c | 2 +- trunk/arch/x86/lguest/Makefile | 1 - trunk/arch/x86/lguest/boot.c | 17 +- trunk/arch/x86/pci/mmconfig-shared.c | 6 +- trunk/block/bsg.c | 3 - trunk/crypto/ahash.c | 7 +- trunk/drivers/acpi/pci_bind.c | 24 +- trunk/drivers/acpi/processor_core.c | 2 +- trunk/drivers/acpi/processor_idle.c | 8 +- trunk/drivers/acpi/processor_perflib.c | 12 +- trunk/drivers/acpi/processor_throttling.c | 2 +- trunk/drivers/acpi/video.c | 18 +- trunk/drivers/ata/ahci.c | 72 - trunk/drivers/ata/ata_piix.c | 9 - trunk/drivers/ata/pata_ali.c | 17 +- trunk/drivers/ata/pata_efar.c | 17 +- trunk/drivers/ata/pata_legacy.c | 2 - trunk/drivers/ata/pata_netcell.c | 13 +- trunk/drivers/char/mem.c | 3 - trunk/drivers/char/mxser.c | 2 +- trunk/drivers/cpufreq/cpufreq.c | 2 +- trunk/drivers/dma/fsldma.c | 71 +- trunk/drivers/dma/ioat_dma.c | 2 +- trunk/drivers/gpu/drm/Kconfig | 14 +- trunk/drivers/gpu/drm/drm_crtc.c | 7 +- trunk/drivers/gpu/drm/drm_crtc_helper.c | 109 +- trunk/drivers/gpu/drm/drm_edid.c | 5 - trunk/drivers/gpu/drm/drm_irq.c | 8 +- trunk/drivers/gpu/drm/drm_sysfs.c | 7 +- trunk/drivers/gpu/drm/i915/i915_dma.c | 12 +- trunk/drivers/gpu/drm/i915/i915_gem.c | 3 + trunk/drivers/gpu/drm/i915/intel_crt.c | 6 +- trunk/drivers/gpu/drm/i915/intel_dvo.c | 1 - trunk/drivers/gpu/drm/i915/intel_hdmi.c | 1 - trunk/drivers/gpu/drm/i915/intel_lvds.c | 8 +- trunk/drivers/gpu/drm/i915/intel_sdvo.c | 1 - trunk/drivers/gpu/drm/i915/intel_tv.c | 1 - trunk/drivers/gpu/drm/radeon/radeon_cp.c | 4 +- trunk/drivers/gpu/drm/radeon/radeon_drv.h | 5 +- trunk/drivers/hwmon/lm78.c | 2 +- trunk/drivers/ide/ide-pci-generic.c | 11 - trunk/drivers/ide/pdc202xx_old.c | 22 +- trunk/drivers/idle/i7300_idle.c | 6 +- trunk/drivers/md/raid5.c | 28 +- trunk/drivers/media/video/ivtv/ivtv-queue.c | 3 +- trunk/drivers/mmc/host/mvsdio.c | 35 - trunk/drivers/mmc/host/mxcmmc.c | 47 +- trunk/drivers/mmc/host/omap.c | 2 +- trunk/drivers/mmc/host/omap_hsmmc.c | 2 +- trunk/drivers/mmc/host/sdhci-of.c | 9 +- trunk/drivers/mtd/nand/davinci_nand.c | 7 +- trunk/drivers/net/3c509.c | 4 - trunk/drivers/net/atl1e/atl1e_main.c | 1 - trunk/drivers/net/atlx/atl1.c | 6 - trunk/drivers/net/atlx/atlx.h | 6 + trunk/drivers/net/bfin_mac.c | 29 +- trunk/drivers/net/cxgb3/adapter.h | 4 +- trunk/drivers/net/cxgb3/cxgb3_main.c | 8 +- trunk/drivers/net/cxgb3/sge.c | 11 +- trunk/drivers/net/cxgb3/t3_hw.c | 5 - trunk/drivers/net/e1000/e1000_main.c | 5 +- trunk/drivers/net/forcedeth.c | 15 +- trunk/drivers/net/gianfar.h | 2 +- trunk/drivers/net/mac8390.c | 2 +- trunk/drivers/net/mlx4/en_tx.c | 8 +- trunk/drivers/net/r8169.c | 11 +- trunk/drivers/net/wireless/Kconfig | 1 - trunk/drivers/net/wireless/at76c50x-usb.c | 12 +- .../net/wireless/rtl818x/rtl8187_dev.c | 2 - trunk/drivers/parport/share.c | 13 +- trunk/drivers/pci/hotplug/acpiphp.h | 1 + trunk/drivers/pci/hotplug/acpiphp_glue.c | 63 +- trunk/drivers/pci/probe.c | 2 - trunk/drivers/serial/imx.c | 2 - trunk/drivers/ssb/embedded.c | 1 - trunk/firmware/cis/.gitignore | 1 - trunk/fs/autofs4/waitq.c | 22 +- trunk/fs/btrfs/extent-tree.c | 51 +- trunk/fs/btrfs/volumes.c | 1 - trunk/fs/buffer.c | 2 - trunk/fs/inode.c | 32 +- trunk/fs/jbd/commit.c | 6 +- trunk/fs/nilfs2/cpfile.c | 6 +- trunk/fs/xfs/linux-2.6/kmem.h | 2 +- trunk/fs/xfs/xfs_dfrag.c | 8 +- trunk/fs/xfs/xfs_fsops.c | 2 +- trunk/include/drm/drm_crtc.h | 3 - trunk/include/drm/drm_crtc_helper.h | 2 - trunk/include/linux/amba/serial.h | 1 - trunk/include/linux/auto_fs.h | 3 +- trunk/include/linux/cpumask.h | 15 - trunk/include/linux/i7300_idle.h | 20 +- trunk/include/linux/net_dropmon.h | 1 - .../linux/netfilter/nf_conntrack_tcp.h | 4 - trunk/include/linux/parport.h | 4 - trunk/include/linux/tracehook.h | 11 +- trunk/include/sound/core.h | 10 + trunk/include/sound/driver.h | 1 + trunk/include/sound/soc-dai.h | 30 +- trunk/include/sound/soc-dapm.h | 24 +- trunk/include/sound/soc.h | 34 +- trunk/include/sound/wm9081.h | 25 - trunk/ipc/shm.c | 7 +- trunk/kernel/async.c | 15 +- trunk/kernel/fork.c | 2 +- trunk/kernel/ptrace.c | 2 - trunk/kernel/sched_cpupri.c | 2 +- trunk/kernel/sched_rt.c | 2 +- trunk/kernel/smp.c | 2 +- trunk/lib/cpumask.c | 12 - trunk/net/bluetooth/hci_sysfs.c | 6 + trunk/net/netfilter/nf_conntrack_proto_dccp.c | 4 - trunk/net/netfilter/nf_conntrack_proto_tcp.c | 18 - trunk/net/netfilter/nfnetlink_log.c | 6 - trunk/net/netfilter/xt_hashlimit.c | 2 +- trunk/net/sched/cls_api.c | 23 +- trunk/net/sched/cls_cgroup.c | 25 +- trunk/sound/aoa/fabrics/layout.c | 8 +- trunk/sound/aoa/soundbus/i2sbus/core.c | 8 +- trunk/sound/core/init.c | 31 +- trunk/sound/pci/au88x0/au88x0_core.c | 10 +- trunk/sound/pci/ca0106/ca0106_mixer.c | 10 +- trunk/sound/soc/Kconfig | 2 - trunk/sound/soc/Makefile | 2 - trunk/sound/soc/atmel/Kconfig | 8 - trunk/sound/soc/atmel/Makefile | 1 - trunk/sound/soc/atmel/playpaq_wm8510.c | 2 +- trunk/sound/soc/atmel/snd-soc-afeb9260.c | 203 --- trunk/sound/soc/blackfin/bf5xx-ac97.c | 9 - trunk/sound/soc/blackfin/bf5xx-sport.c | 4 +- trunk/sound/soc/codecs/Kconfig | 24 - trunk/sound/soc/codecs/Makefile | 12 - trunk/sound/soc/codecs/ac97.c | 4 +- trunk/sound/soc/codecs/ad1980.c | 4 +- trunk/sound/soc/codecs/cs4270.c | 105 +- trunk/sound/soc/codecs/spdif_transciever.c | 71 - trunk/sound/soc/codecs/spdif_transciever.h | 17 - trunk/sound/soc/codecs/ssm2602.c | 33 +- trunk/sound/soc/codecs/stac9766.c | 463 ----- trunk/sound/soc/codecs/stac9766.h | 21 - trunk/sound/soc/codecs/tlv320aic23.c | 16 +- trunk/sound/soc/codecs/twl4030.c | 1116 +++--------- trunk/sound/soc/codecs/twl4030.h | 43 +- trunk/sound/soc/codecs/uda134x.c | 4 +- trunk/sound/soc/codecs/wm8350.c | 2 +- trunk/sound/soc/codecs/wm8350.h | 1 - trunk/sound/soc/codecs/wm8400.c | 8 +- trunk/sound/soc/codecs/wm8510.c | 2 +- trunk/sound/soc/codecs/wm8580.c | 4 +- trunk/sound/soc/codecs/wm8731.c | 4 +- trunk/sound/soc/codecs/wm8753.c | 6 +- trunk/sound/soc/codecs/wm8900.c | 6 +- trunk/sound/soc/codecs/wm8903.c | 119 +- trunk/sound/soc/codecs/wm8940.c | 955 ---------- trunk/sound/soc/codecs/wm8940.h | 104 -- trunk/sound/soc/codecs/wm8960.c | 969 ----------- trunk/sound/soc/codecs/wm8960.h | 127 -- trunk/sound/soc/codecs/wm8988.c | 1097 ------------ trunk/sound/soc/codecs/wm8988.h | 60 - trunk/sound/soc/codecs/wm8990.c | 2 +- trunk/sound/soc/codecs/wm9081.c | 1534 ----------------- trunk/sound/soc/codecs/wm9081.h | 787 --------- trunk/sound/soc/codecs/wm9705.c | 4 +- trunk/sound/soc/codecs/wm9712.c | 8 +- trunk/sound/soc/codecs/wm9713.c | 48 +- trunk/sound/soc/fsl/Kconfig | 32 +- trunk/sound/soc/fsl/Makefile | 7 - trunk/sound/soc/fsl/efika-audio-fabric.c | 90 - trunk/sound/soc/fsl/fsl_ssi.c | 11 +- trunk/sound/soc/fsl/mpc5200_dma.c | 564 ------ trunk/sound/soc/fsl/mpc5200_dma.h | 80 - trunk/sound/soc/fsl/mpc5200_psc_ac97.c | 329 ---- trunk/sound/soc/fsl/mpc5200_psc_ac97.h | 15 - trunk/sound/soc/fsl/mpc5200_psc_i2s.c | 754 +++++++- trunk/sound/soc/fsl/mpc5200_psc_i2s.h | 12 - trunk/sound/soc/fsl/pcm030-audio-fabric.c | 90 - trunk/sound/soc/omap/Kconfig | 8 - trunk/sound/soc/omap/Makefile | 2 - trunk/sound/soc/omap/n810.c | 7 +- trunk/sound/soc/omap/omap-mcbsp.c | 43 +- trunk/sound/soc/omap/omap-pcm.c | 9 +- trunk/sound/soc/omap/omap2evm.c | 2 +- trunk/sound/soc/omap/omap3beagle.c | 28 +- trunk/sound/soc/omap/omap3evm.c | 147 -- trunk/sound/soc/omap/omap3pandora.c | 4 +- trunk/sound/soc/omap/overo.c | 2 +- trunk/sound/soc/omap/sdp3430.c | 94 +- trunk/sound/soc/pxa/Kconfig | 13 +- trunk/sound/soc/pxa/Makefile | 2 - trunk/sound/soc/pxa/em-x270.c | 9 +- trunk/sound/soc/pxa/imote2.c | 114 -- trunk/sound/soc/pxa/magician.c | 13 +- trunk/sound/soc/pxa/pxa-ssp.c | 218 ++- trunk/sound/soc/pxa/pxa2xx-i2s.c | 39 +- trunk/sound/soc/s3c24xx/s3c-i2s-v2.c | 91 +- trunk/sound/soc/s3c24xx/s3c2412-i2s.c | 2 +- trunk/sound/soc/s3c24xx/s3c64xx-i2s.c | 157 +- trunk/sound/soc/s3c24xx/s3c64xx-i2s.h | 6 +- trunk/sound/soc/s6000/Kconfig | 19 - trunk/sound/soc/s6000/Makefile | 11 - trunk/sound/soc/s6000/s6000-i2s.c | 629 ------- trunk/sound/soc/s6000/s6000-i2s.h | 25 - trunk/sound/soc/s6000/s6000-pcm.c | 497 ------ trunk/sound/soc/s6000/s6000-pcm.h | 35 - trunk/sound/soc/s6000/s6105-ipcam.c | 244 --- trunk/sound/soc/sh/ssi.c | 2 +- trunk/sound/soc/soc-core.c | 165 +- trunk/sound/soc/soc-dapm.c | 427 ++--- trunk/sound/soc/txx9/Kconfig | 29 - trunk/sound/soc/txx9/Makefile | 11 - trunk/sound/soc/txx9/txx9aclc-ac97.c | 255 --- trunk/sound/soc/txx9/txx9aclc-generic.c | 98 -- trunk/sound/soc/txx9/txx9aclc.c | 430 ----- trunk/sound/soc/txx9/txx9aclc.h | 83 - trunk/sound/usb/caiaq/audio.c | 88 +- trunk/sound/usb/caiaq/device.c | 108 +- trunk/sound/usb/caiaq/device.h | 1 + trunk/sound/usb/caiaq/midi.c | 24 +- trunk/virt/kvm/kvm_main.c | 3 +- 277 files changed, 2444 insertions(+), 14284 deletions(-) delete mode 100644 trunk/arch/mips/lib/delay.c delete mode 100644 trunk/firmware/cis/.gitignore create mode 100644 trunk/include/sound/driver.h delete mode 100644 trunk/include/sound/wm9081.h delete mode 100644 trunk/sound/soc/atmel/snd-soc-afeb9260.c delete mode 100644 trunk/sound/soc/codecs/spdif_transciever.c delete mode 100644 trunk/sound/soc/codecs/spdif_transciever.h delete mode 100644 trunk/sound/soc/codecs/stac9766.c delete mode 100644 trunk/sound/soc/codecs/stac9766.h delete mode 100644 trunk/sound/soc/codecs/wm8940.c delete mode 100644 trunk/sound/soc/codecs/wm8940.h delete mode 100644 trunk/sound/soc/codecs/wm8960.c delete mode 100644 trunk/sound/soc/codecs/wm8960.h delete mode 100644 trunk/sound/soc/codecs/wm8988.c delete mode 100644 trunk/sound/soc/codecs/wm8988.h delete mode 100644 trunk/sound/soc/codecs/wm9081.c delete mode 100644 trunk/sound/soc/codecs/wm9081.h delete mode 100644 trunk/sound/soc/fsl/efika-audio-fabric.c delete mode 100644 trunk/sound/soc/fsl/mpc5200_dma.c delete mode 100644 trunk/sound/soc/fsl/mpc5200_dma.h delete mode 100644 trunk/sound/soc/fsl/mpc5200_psc_ac97.c delete mode 100644 trunk/sound/soc/fsl/mpc5200_psc_ac97.h delete mode 100644 trunk/sound/soc/fsl/mpc5200_psc_i2s.h delete mode 100644 trunk/sound/soc/fsl/pcm030-audio-fabric.c delete mode 100644 trunk/sound/soc/omap/omap3evm.c delete mode 100644 trunk/sound/soc/pxa/imote2.c delete mode 100644 trunk/sound/soc/s6000/Kconfig delete mode 100644 trunk/sound/soc/s6000/Makefile delete mode 100644 trunk/sound/soc/s6000/s6000-i2s.c delete mode 100644 trunk/sound/soc/s6000/s6000-i2s.h delete mode 100644 trunk/sound/soc/s6000/s6000-pcm.c delete mode 100644 trunk/sound/soc/s6000/s6000-pcm.h delete mode 100644 trunk/sound/soc/s6000/s6105-ipcam.c delete mode 100644 trunk/sound/soc/txx9/Kconfig delete mode 100644 trunk/sound/soc/txx9/Makefile delete mode 100644 trunk/sound/soc/txx9/txx9aclc-ac97.c delete mode 100644 trunk/sound/soc/txx9/txx9aclc-generic.c delete mode 100644 trunk/sound/soc/txx9/txx9aclc.c delete mode 100644 trunk/sound/soc/txx9/txx9aclc.h diff --git a/[refs] b/[refs] index 604113f5341e..89469d493aa0 100644 --- a/[refs] +++ b/[refs] @@ -1,2 +1,2 @@ --- -refs/heads/master: d108728ea24a766335ae22f10bfaf41f248fb70e +refs/heads/master: 872c78202c58d26596e25743791ee81a7d24abad diff --git a/trunk/Documentation/hwmon/sysfs-interface b/trunk/Documentation/hwmon/sysfs-interface index 004ee161721e..2f10ce6a879f 100644 --- a/trunk/Documentation/hwmon/sysfs-interface +++ b/trunk/Documentation/hwmon/sysfs-interface @@ -150,11 +150,6 @@ fan[1-*]_min Fan minimum value Unit: revolution/min (RPM) RW -fan[1-*]_max Fan maximum value - Unit: revolution/min (RPM) - Only rarely supported by the hardware. - RW - fan[1-*]_input Fan input value. Unit: revolution/min (RPM) RO @@ -395,7 +390,6 @@ OR in[0-*]_min_alarm in[0-*]_max_alarm fan[1-*]_min_alarm -fan[1-*]_max_alarm temp[1-*]_min_alarm temp[1-*]_max_alarm temp[1-*]_crit_alarm diff --git a/trunk/Documentation/sound/alsa/soc/dapm.txt b/trunk/Documentation/sound/alsa/soc/dapm.txt index 9ac842be9b4f..9e6763264a2e 100644 --- a/trunk/Documentation/sound/alsa/soc/dapm.txt +++ b/trunk/Documentation/sound/alsa/soc/dapm.txt @@ -62,7 +62,6 @@ Audio DAPM widgets fall into a number of types:- o Mic - Mic (and optional Jack) o Line - Line Input/Output (and optional Jack) o Speaker - Speaker - o Supply - Power or clock supply widget used by other widgets. o Pre - Special PRE widget (exec before all others) o Post - Special POST widget (exec after all others) diff --git a/trunk/MAINTAINERS b/trunk/MAINTAINERS index e8cb115e33b8..41c6605feb0a 100644 --- a/trunk/MAINTAINERS +++ b/trunk/MAINTAINERS @@ -624,7 +624,6 @@ M: paulius.zaleckas@teltonika.lt L: linux-arm-kernel@lists.arm.linux.org.uk (subscribers-only) T: git git://gitorious.org/linux-gemini/mainline.git S: Maintained -F: arch/arm/mach-gemini/ ARM/EBSA110 MACHINE SUPPORT P: Russell King @@ -651,7 +650,6 @@ P: Paulius Zaleckas M: paulius.zaleckas@teltonika.lt L: linux-arm-kernel@lists.arm.linux.org.uk (subscribers-only) S: Maintained -F: arch/arm/mm/*-fa* ARM/FOOTBRIDGE ARCHITECTURE P: Russell King @@ -1542,13 +1540,6 @@ W: http://www.fi.muni.cz/~kas/cosa/ S: Maintained F: drivers/net/wan/cosa* -CPMAC ETHERNET DRIVER -P: Florian Fainelli -M: florian@openwrt.org -L: netdev@vger.kernel.org -S: Maintained -F: drivers/net/cpmac.c - CPU FREQUENCY DRIVERS P: Dave Jones M: davej@redhat.com @@ -2258,7 +2249,7 @@ P: Li Yang M: leoli@freescale.com P: Zhang Wei M: zw@zh-kernel.org -L: linuxppc-dev@ozlabs.org +L: linuxppc-embedded@ozlabs.org L: linux-kernel@vger.kernel.org S: Maintained F: drivers/dma/fsldma.* @@ -4574,8 +4565,7 @@ F: drivers/pcmcia/pxa2xx* F: drivers/spi/pxa2xx* F: drivers/usb/gadget/pxa2* F: include/sound/pxa2xx-lib.h -F: sound/arm/pxa* -F: sound/soc/pxa +F: sound/soc/pxa/pxa2xx* PXA168 SUPPORT P: Eric Miao @@ -5303,12 +5293,11 @@ P: Liam Girdwood M: lrg@slimlogic.co.uk P: Mark Brown M: broonie@opensource.wolfsonmicro.com -T: git git://git.kernel.org/pub/scm/linux/kernel/git/broonie/sound-2.6.git +T: git git://opensource.wolfsonmicro.com/linux-2.6-asoc L: alsa-devel@alsa-project.org (subscribers-only) W: http://alsa-project.org/main/index.php/ASoC S: Supported F: sound/soc/ -F: include/sound/soc* SPARC + UltraSPARC (sparc/sparc64) P: David S. Miller diff --git a/trunk/Makefile b/trunk/Makefile index 03373bb703ca..739fd34a72a2 100644 --- a/trunk/Makefile +++ b/trunk/Makefile @@ -1,7 +1,7 @@ VERSION = 2 PATCHLEVEL = 6 SUBLEVEL = 30 -EXTRAVERSION = +EXTRAVERSION = -rc7 NAME = Man-Eating Seals of Antiquity # *DOCUMENTATION* @@ -533,7 +533,7 @@ endif include $(srctree)/arch/$(SRCARCH)/Makefile -ifneq ($(CONFIG_FRAME_WARN),0) +ifneq (CONFIG_FRAME_WARN,0) KBUILD_CFLAGS += $(call cc-option,-Wframe-larger-than=${CONFIG_FRAME_WARN}) endif diff --git a/trunk/arch/arm/include/asm/assembler.h b/trunk/arch/arm/include/asm/assembler.h index 15f8a092b700..6116e4893c0a 100644 --- a/trunk/arch/arm/include/asm/assembler.h +++ b/trunk/arch/arm/include/asm/assembler.h @@ -114,16 +114,3 @@ .align 3; \ .long 9999b,9001f; \ .previous - -/* - * SMP data memory barrier - */ - .macro smp_dmb -#ifdef CONFIG_SMP -#if __LINUX_ARM_ARCH__ >= 7 - dmb -#elif __LINUX_ARM_ARCH__ == 6 - mcr p15, 0, r0, c7, c10, 5 @ dmb -#endif -#endif - .endm diff --git a/trunk/arch/arm/include/asm/atomic.h b/trunk/arch/arm/include/asm/atomic.h index 16b52f397983..ee99723b3a6c 100644 --- a/trunk/arch/arm/include/asm/atomic.h +++ b/trunk/arch/arm/include/asm/atomic.h @@ -44,29 +44,11 @@ static inline void atomic_set(atomic_t *v, int i) : "cc"); } -static inline void atomic_add(int i, atomic_t *v) -{ - unsigned long tmp; - int result; - - __asm__ __volatile__("@ atomic_add\n" -"1: ldrex %0, [%2]\n" -" add %0, %0, %3\n" -" strex %1, %0, [%2]\n" -" teq %1, #0\n" -" bne 1b" - : "=&r" (result), "=&r" (tmp) - : "r" (&v->counter), "Ir" (i) - : "cc"); -} - static inline int atomic_add_return(int i, atomic_t *v) { unsigned long tmp; int result; - smp_mb(); - __asm__ __volatile__("@ atomic_add_return\n" "1: ldrex %0, [%2]\n" " add %0, %0, %3\n" @@ -77,34 +59,14 @@ static inline int atomic_add_return(int i, atomic_t *v) : "r" (&v->counter), "Ir" (i) : "cc"); - smp_mb(); - return result; } -static inline void atomic_sub(int i, atomic_t *v) -{ - unsigned long tmp; - int result; - - __asm__ __volatile__("@ atomic_sub\n" -"1: ldrex %0, [%2]\n" -" sub %0, %0, %3\n" -" strex %1, %0, [%2]\n" -" teq %1, #0\n" -" bne 1b" - : "=&r" (result), "=&r" (tmp) - : "r" (&v->counter), "Ir" (i) - : "cc"); -} - static inline int atomic_sub_return(int i, atomic_t *v) { unsigned long tmp; int result; - smp_mb(); - __asm__ __volatile__("@ atomic_sub_return\n" "1: ldrex %0, [%2]\n" " sub %0, %0, %3\n" @@ -115,8 +77,6 @@ static inline int atomic_sub_return(int i, atomic_t *v) : "r" (&v->counter), "Ir" (i) : "cc"); - smp_mb(); - return result; } @@ -124,8 +84,6 @@ static inline int atomic_cmpxchg(atomic_t *ptr, int old, int new) { unsigned long oldval, res; - smp_mb(); - do { __asm__ __volatile__("@ atomic_cmpxchg\n" "ldrex %1, [%2]\n" @@ -137,8 +95,6 @@ static inline int atomic_cmpxchg(atomic_t *ptr, int old, int new) : "cc"); } while (res); - smp_mb(); - return oldval; } @@ -179,7 +135,6 @@ static inline int atomic_add_return(int i, atomic_t *v) return val; } -#define atomic_add(i, v) (void) atomic_add_return(i, v) static inline int atomic_sub_return(int i, atomic_t *v) { @@ -193,7 +148,6 @@ static inline int atomic_sub_return(int i, atomic_t *v) return val; } -#define atomic_sub(i, v) (void) atomic_sub_return(i, v) static inline int atomic_cmpxchg(atomic_t *v, int old, int new) { @@ -233,8 +187,10 @@ static inline int atomic_add_unless(atomic_t *v, int a, int u) } #define atomic_inc_not_zero(v) atomic_add_unless((v), 1, 0) -#define atomic_inc(v) atomic_add(1, v) -#define atomic_dec(v) atomic_sub(1, v) +#define atomic_add(i, v) (void) atomic_add_return(i, v) +#define atomic_inc(v) (void) atomic_add_return(1, v) +#define atomic_sub(i, v) (void) atomic_sub_return(i, v) +#define atomic_dec(v) (void) atomic_sub_return(1, v) #define atomic_inc_and_test(v) (atomic_add_return(1, v) == 0) #define atomic_dec_and_test(v) (atomic_sub_return(1, v) == 0) @@ -244,10 +200,11 @@ static inline int atomic_add_unless(atomic_t *v, int a, int u) #define atomic_add_negative(i,v) (atomic_add_return(i, v) < 0) -#define smp_mb__before_atomic_dec() smp_mb() -#define smp_mb__after_atomic_dec() smp_mb() -#define smp_mb__before_atomic_inc() smp_mb() -#define smp_mb__after_atomic_inc() smp_mb() +/* Atomic operations are already serializing on ARM */ +#define smp_mb__before_atomic_dec() barrier() +#define smp_mb__after_atomic_dec() barrier() +#define smp_mb__before_atomic_inc() barrier() +#define smp_mb__after_atomic_inc() barrier() #include #endif diff --git a/trunk/arch/arm/include/asm/cache.h b/trunk/arch/arm/include/asm/cache.h index feaa75f0013e..cb7a9e97fd7e 100644 --- a/trunk/arch/arm/include/asm/cache.h +++ b/trunk/arch/arm/include/asm/cache.h @@ -7,20 +7,4 @@ #define L1_CACHE_SHIFT 5 #define L1_CACHE_BYTES (1 << L1_CACHE_SHIFT) -/* - * Memory returned by kmalloc() may be used for DMA, so we must make - * sure that all such allocations are cache aligned. Otherwise, - * unrelated code may cause parts of the buffer to be read into the - * cache before the transfer is done, causing old data to be seen by - * the CPU. - */ -#define ARCH_KMALLOC_MINALIGN L1_CACHE_BYTES - -/* - * With EABI on ARMv5 and above we must have 64-bit aligned slab pointers. - */ -#if defined(CONFIG_AEABI) && (__LINUX_ARM_ARCH__ >= 5) -#define ARCH_SLAB_MINALIGN 8 -#endif - #endif diff --git a/trunk/arch/arm/include/asm/page.h b/trunk/arch/arm/include/asm/page.h index 7b522770f29d..e6eb8a67b807 100644 --- a/trunk/arch/arm/include/asm/page.h +++ b/trunk/arch/arm/include/asm/page.h @@ -202,6 +202,13 @@ typedef struct page *pgtable_t; (((current->personality & READ_IMPLIES_EXEC) ? VM_EXEC : 0) | \ VM_READ | VM_WRITE | VM_MAYREAD | VM_MAYWRITE | VM_MAYEXEC) +/* + * With EABI on ARMv5 and above we must have 64-bit aligned slab pointers. + */ +#if defined(CONFIG_AEABI) && (__LINUX_ARM_ARCH__ >= 5) +#define ARCH_SLAB_MINALIGN 8 +#endif + #include #endif diff --git a/trunk/arch/arm/include/asm/system.h b/trunk/arch/arm/include/asm/system.h index d65b2f5bf41f..bd4dc8ed53d5 100644 --- a/trunk/arch/arm/include/asm/system.h +++ b/trunk/arch/arm/include/asm/system.h @@ -248,8 +248,6 @@ static inline unsigned long __xchg(unsigned long x, volatile void *ptr, int size unsigned int tmp; #endif - smp_mb(); - switch (size) { #if __LINUX_ARM_ARCH__ >= 6 case 1: @@ -309,7 +307,6 @@ static inline unsigned long __xchg(unsigned long x, volatile void *ptr, int size __bad_xchg(ptr, size), ret = 0; break; } - smp_mb(); return ret; } @@ -319,12 +316,6 @@ extern void enable_hlt(void); #include -#if __LINUX_ARM_ARCH__ < 6 - -#ifdef CONFIG_SMP -#error "SMP is not supported on this platform" -#endif - /* * cmpxchg_local and cmpxchg64_local are atomic wrt current CPU. Always make * them available. @@ -338,173 +329,6 @@ extern void enable_hlt(void); #include #endif -#else /* __LINUX_ARM_ARCH__ >= 6 */ - -extern void __bad_cmpxchg(volatile void *ptr, int size); - -/* - * cmpxchg only support 32-bits operands on ARMv6. - */ - -static inline unsigned long __cmpxchg(volatile void *ptr, unsigned long old, - unsigned long new, int size) -{ - unsigned long oldval, res; - - switch (size) { -#ifdef CONFIG_CPU_32v6K - case 1: - do { - asm volatile("@ __cmpxchg1\n" - " ldrexb %1, [%2]\n" - " mov %0, #0\n" - " teq %1, %3\n" - " strexbeq %0, %4, [%2]\n" - : "=&r" (res), "=&r" (oldval) - : "r" (ptr), "Ir" (old), "r" (new) - : "memory", "cc"); - } while (res); - break; - case 2: - do { - asm volatile("@ __cmpxchg1\n" - " ldrexh %1, [%2]\n" - " mov %0, #0\n" - " teq %1, %3\n" - " strexheq %0, %4, [%2]\n" - : "=&r" (res), "=&r" (oldval) - : "r" (ptr), "Ir" (old), "r" (new) - : "memory", "cc"); - } while (res); - break; -#endif /* CONFIG_CPU_32v6K */ - case 4: - do { - asm volatile("@ __cmpxchg4\n" - " ldrex %1, [%2]\n" - " mov %0, #0\n" - " teq %1, %3\n" - " strexeq %0, %4, [%2]\n" - : "=&r" (res), "=&r" (oldval) - : "r" (ptr), "Ir" (old), "r" (new) - : "memory", "cc"); - } while (res); - break; - default: - __bad_cmpxchg(ptr, size); - oldval = 0; - } - - return oldval; -} - -static inline unsigned long __cmpxchg_mb(volatile void *ptr, unsigned long old, - unsigned long new, int size) -{ - unsigned long ret; - - smp_mb(); - ret = __cmpxchg(ptr, old, new, size); - smp_mb(); - - return ret; -} - -#define cmpxchg(ptr,o,n) \ - ((__typeof__(*(ptr)))__cmpxchg_mb((ptr), \ - (unsigned long)(o), \ - (unsigned long)(n), \ - sizeof(*(ptr)))) - -static inline unsigned long __cmpxchg_local(volatile void *ptr, - unsigned long old, - unsigned long new, int size) -{ - unsigned long ret; - - switch (size) { -#ifndef CONFIG_CPU_32v6K - case 1: - case 2: - ret = __cmpxchg_local_generic(ptr, old, new, size); - break; -#endif /* !CONFIG_CPU_32v6K */ - default: - ret = __cmpxchg(ptr, old, new, size); - } - - return ret; -} - -#define cmpxchg_local(ptr,o,n) \ - ((__typeof__(*(ptr)))__cmpxchg_local((ptr), \ - (unsigned long)(o), \ - (unsigned long)(n), \ - sizeof(*(ptr)))) - -#ifdef CONFIG_CPU_32v6K - -/* - * Note : ARMv7-M (currently unsupported by Linux) does not support - * ldrexd/strexd. If ARMv7-M is ever supported by the Linux kernel, it should - * not be allowed to use __cmpxchg64. - */ -static inline unsigned long long __cmpxchg64(volatile void *ptr, - unsigned long long old, - unsigned long long new) -{ - register unsigned long long oldval asm("r0"); - register unsigned long long __old asm("r2") = old; - register unsigned long long __new asm("r4") = new; - unsigned long res; - - do { - asm volatile( - " @ __cmpxchg8\n" - " ldrexd %1, %H1, [%2]\n" - " mov %0, #0\n" - " teq %1, %3\n" - " teqeq %H1, %H3\n" - " strexdeq %0, %4, %H4, [%2]\n" - : "=&r" (res), "=&r" (oldval) - : "r" (ptr), "Ir" (__old), "r" (__new) - : "memory", "cc"); - } while (res); - - return oldval; -} - -static inline unsigned long long __cmpxchg64_mb(volatile void *ptr, - unsigned long long old, - unsigned long long new) -{ - unsigned long long ret; - - smp_mb(); - ret = __cmpxchg64(ptr, old, new); - smp_mb(); - - return ret; -} - -#define cmpxchg64(ptr,o,n) \ - ((__typeof__(*(ptr)))__cmpxchg64_mb((ptr), \ - (unsigned long long)(o), \ - (unsigned long long)(n))) - -#define cmpxchg64_local(ptr,o,n) \ - ((__typeof__(*(ptr)))__cmpxchg64((ptr), \ - (unsigned long long)(o), \ - (unsigned long long)(n))) - -#else /* !CONFIG_CPU_32v6K */ - -#define cmpxchg64_local(ptr, o, n) __cmpxchg64_local_generic((ptr), (o), (n)) - -#endif /* CONFIG_CPU_32v6K */ - -#endif /* __LINUX_ARM_ARCH__ >= 6 */ - #endif /* __ASSEMBLY__ */ #define arch_align_stack(x) (x) diff --git a/trunk/arch/arm/kernel/elf.c b/trunk/arch/arm/kernel/elf.c index 950391f194c4..d4a0da1e48f4 100644 --- a/trunk/arch/arm/kernel/elf.c +++ b/trunk/arch/arm/kernel/elf.c @@ -78,15 +78,6 @@ int arm_elf_read_implies_exec(const struct elf32_hdr *x, int executable_stack) return 1; if (cpu_architecture() < CPU_ARCH_ARMv6) return 1; -#if !defined(CONFIG_AEABI) || defined(CONFIG_OABI_COMPAT) - /* - * If we have support for OABI programs, we can never allow NX - * support - our signal syscall restart mechanism relies upon - * being able to execute code placed on the user stack. - */ - return 1; -#else return 0; -#endif } EXPORT_SYMBOL(arm_elf_read_implies_exec); diff --git a/trunk/arch/arm/kernel/entry-armv.S b/trunk/arch/arm/kernel/entry-armv.S index 83b1da6b7baa..d662a2f1fd85 100644 --- a/trunk/arch/arm/kernel/entry-armv.S +++ b/trunk/arch/arm/kernel/entry-armv.S @@ -815,7 +815,10 @@ __kuser_helper_start: */ __kuser_memory_barrier: @ 0xffff0fa0 - smp_dmb + +#if __LINUX_ARM_ARCH__ >= 6 && defined(CONFIG_SMP) + mcr p15, 0, r0, c7, c10, 5 @ dmb +#endif usr_ret lr .align 5 diff --git a/trunk/arch/arm/lib/bitops.h b/trunk/arch/arm/lib/bitops.h index c7f2627385e7..2e787d40d599 100644 --- a/trunk/arch/arm/lib/bitops.h +++ b/trunk/arch/arm/lib/bitops.h @@ -18,14 +18,12 @@ mov r2, #1 add r1, r1, r0, lsr #3 @ Get byte offset mov r3, r2, lsl r3 @ create mask - smp_dmb 1: ldrexb r2, [r1] ands r0, r2, r3 @ save old value of bit \instr r2, r2, r3 @ toggle bit strexb ip, r2, [r1] cmp ip, #0 bne 1b - smp_dmb cmp r0, #0 movne r0, #1 2: mov pc, lr diff --git a/trunk/arch/arm/mach-gemini/include/mach/hardware.h b/trunk/arch/arm/mach-gemini/include/mach/hardware.h index 213a4fcfeb1c..de6752674c05 100644 --- a/trunk/arch/arm/mach-gemini/include/mach/hardware.h +++ b/trunk/arch/arm/mach-gemini/include/mach/hardware.h @@ -15,9 +15,10 @@ /* * Memory Map definitions */ +/* FIXME: Does it really swap SRAM like this? */ #ifdef CONFIG_GEMINI_MEM_SWAP # define GEMINI_DRAM_BASE 0x00000000 -# define GEMINI_SRAM_BASE 0x70000000 +# define GEMINI_SRAM_BASE 0x20000000 #else # define GEMINI_SRAM_BASE 0x00000000 # define GEMINI_DRAM_BASE 0x10000000 diff --git a/trunk/arch/arm/mach-kirkwood/common.c b/trunk/arch/arm/mach-kirkwood/common.c index be1ca28fed3f..eeb00240d784 100644 --- a/trunk/arch/arm/mach-kirkwood/common.c +++ b/trunk/arch/arm/mach-kirkwood/common.c @@ -144,9 +144,6 @@ static struct platform_device kirkwood_ge00 = { .id = 0, .num_resources = 1, .resource = kirkwood_ge00_resources, - .dev = { - .coherent_dma_mask = 0xffffffff, - }, }; void __init kirkwood_ge00_init(struct mv643xx_eth_platform_data *eth_data) @@ -205,9 +202,6 @@ static struct platform_device kirkwood_ge01 = { .id = 1, .num_resources = 1, .resource = kirkwood_ge01_resources, - .dev = { - .coherent_dma_mask = 0xffffffff, - }, }; void __init kirkwood_ge01_init(struct mv643xx_eth_platform_data *eth_data) @@ -392,10 +386,12 @@ static struct mv64xxx_i2c_pdata kirkwood_i2c_pdata = { static struct resource kirkwood_i2c_resources[] = { { + .name = "i2c", .start = I2C_PHYS_BASE, .end = I2C_PHYS_BASE + 0x1f, .flags = IORESOURCE_MEM, }, { + .name = "i2c", .start = IRQ_KIRKWOOD_TWSI, .end = IRQ_KIRKWOOD_TWSI, .flags = IORESOURCE_IRQ, diff --git a/trunk/arch/arm/mach-kirkwood/ts219-setup.c b/trunk/arch/arm/mach-kirkwood/ts219-setup.c index 01aa213c0a6f..dda5743cf3e0 100644 --- a/trunk/arch/arm/mach-kirkwood/ts219-setup.c +++ b/trunk/arch/arm/mach-kirkwood/ts219-setup.c @@ -142,8 +142,6 @@ static unsigned int qnap_ts219_mpp_config[] __initdata = { MPP1_SPI_MOSI, MPP2_SPI_SCK, MPP3_SPI_MISO, - MPP4_SATA1_ACTn, - MPP5_SATA0_ACTn, MPP8_TW_SDA, MPP9_TW_SCK, MPP10_UART0_TXD, @@ -152,6 +150,10 @@ static unsigned int qnap_ts219_mpp_config[] __initdata = { MPP14_UART1_RXD, /* PIC controller */ MPP15_GPIO, /* USB Copy button */ MPP16_GPIO, /* Reset button */ + MPP20_SATA1_ACTn, + MPP21_SATA0_ACTn, + MPP22_SATA1_PRESENTn, + MPP23_SATA0_PRESENTn, 0 }; diff --git a/trunk/arch/arm/mach-loki/common.c b/trunk/arch/arm/mach-loki/common.c index 818f19d7ab1f..c0d2d9d12e74 100644 --- a/trunk/arch/arm/mach-loki/common.c +++ b/trunk/arch/arm/mach-loki/common.c @@ -82,9 +82,6 @@ static struct platform_device loki_ge0 = { .id = 0, .num_resources = 1, .resource = loki_ge0_resources, - .dev = { - .coherent_dma_mask = 0xffffffff, - }, }; void __init loki_ge0_init(struct mv643xx_eth_platform_data *eth_data) @@ -139,9 +136,6 @@ static struct platform_device loki_ge1 = { .id = 1, .num_resources = 1, .resource = loki_ge1_resources, - .dev = { - .coherent_dma_mask = 0xffffffff, - }, }; void __init loki_ge1_init(struct mv643xx_eth_platform_data *eth_data) diff --git a/trunk/arch/arm/mach-mmp/include/mach/mfp-pxa168.h b/trunk/arch/arm/mach-mmp/include/mach/mfp-pxa168.h index 2e914649b9e4..d0bdb6e3682b 100644 --- a/trunk/arch/arm/mach-mmp/include/mach/mfp-pxa168.h +++ b/trunk/arch/arm/mach-mmp/include/mach/mfp-pxa168.h @@ -3,11 +3,6 @@ #include -#define MFP_DRIVE_VERY_SLOW (0x0 << 13) -#define MFP_DRIVE_SLOW (0x1 << 13) -#define MFP_DRIVE_MEDIUM (0x2 << 13) -#define MFP_DRIVE_FAST (0x3 << 13) - /* GPIO */ #define GPIO0_GPIO MFP_CFG(GPIO0, AF5) #define GPIO1_GPIO MFP_CFG(GPIO1, AF5) diff --git a/trunk/arch/arm/mach-mmp/include/mach/mfp-pxa910.h b/trunk/arch/arm/mach-mmp/include/mach/mfp-pxa910.h index d97de36c50ad..48a1cbc7c56b 100644 --- a/trunk/arch/arm/mach-mmp/include/mach/mfp-pxa910.h +++ b/trunk/arch/arm/mach-mmp/include/mach/mfp-pxa910.h @@ -3,11 +3,6 @@ #include -#define MFP_DRIVE_VERY_SLOW (0x0 << 13) -#define MFP_DRIVE_SLOW (0x2 << 13) -#define MFP_DRIVE_MEDIUM (0x4 << 13) -#define MFP_DRIVE_FAST (0x8 << 13) - /* UART2 */ #define GPIO47_UART2_RXD MFP_CFG(GPIO47, AF6) #define GPIO48_UART2_TXD MFP_CFG(GPIO48, AF6) diff --git a/trunk/arch/arm/mach-mmp/include/mach/mfp.h b/trunk/arch/arm/mach-mmp/include/mach/mfp.h index 62e510e80a58..277ea4cd0f9f 100644 --- a/trunk/arch/arm/mach-mmp/include/mach/mfp.h +++ b/trunk/arch/arm/mach-mmp/include/mach/mfp.h @@ -12,13 +12,16 @@ * possible, we make the following compromise: * * 1. SLEEP_OE_N will always be programmed to '1' (by MFP_LPM_FLOAT) - * 2. DRIVE strength definitions redefined to include the reserved bit - * - the reserved bit differs between pxa168 and pxa910, and the - * MFP_DRIVE_* macros are individually defined in mfp-pxa{168,910}.h + * 2. DRIVE strength definitions redefined to include the reserved bit10 * 3. Override MFP_CFG() and MFP_CFG_DRV() * 4. Drop the use of MFP_CFG_LPM() and MFP_CFG_X() */ +#define MFP_DRIVE_VERY_SLOW (0x0 << 13) +#define MFP_DRIVE_SLOW (0x2 << 13) +#define MFP_DRIVE_MEDIUM (0x4 << 13) +#define MFP_DRIVE_FAST (0x8 << 13) + #undef MFP_CFG #undef MFP_CFG_DRV #undef MFP_CFG_LPM diff --git a/trunk/arch/arm/mach-mmp/time.c b/trunk/arch/arm/mach-mmp/time.c index a8400bb891e7..b03a6eda7419 100644 --- a/trunk/arch/arm/mach-mmp/time.c +++ b/trunk/arch/arm/mach-mmp/time.c @@ -136,7 +136,7 @@ static struct clock_event_device ckevt = { .set_mode = timer_set_mode, }; -static cycle_t clksrc_read(struct clocksource *cs) +static cycle_t clksrc_read(void) { return timer_read(); } diff --git a/trunk/arch/arm/mach-mv78xx0/common.c b/trunk/arch/arm/mach-mv78xx0/common.c index 1b22e4af8791..9ba595083dab 100644 --- a/trunk/arch/arm/mach-mv78xx0/common.c +++ b/trunk/arch/arm/mach-mv78xx0/common.c @@ -321,9 +321,6 @@ static struct platform_device mv78xx0_ge00 = { .id = 0, .num_resources = 1, .resource = mv78xx0_ge00_resources, - .dev = { - .coherent_dma_mask = 0xffffffff, - }, }; void __init mv78xx0_ge00_init(struct mv643xx_eth_platform_data *eth_data) @@ -378,9 +375,6 @@ static struct platform_device mv78xx0_ge01 = { .id = 1, .num_resources = 1, .resource = mv78xx0_ge01_resources, - .dev = { - .coherent_dma_mask = 0xffffffff, - }, }; void __init mv78xx0_ge01_init(struct mv643xx_eth_platform_data *eth_data) @@ -435,9 +429,6 @@ static struct platform_device mv78xx0_ge10 = { .id = 2, .num_resources = 1, .resource = mv78xx0_ge10_resources, - .dev = { - .coherent_dma_mask = 0xffffffff, - }, }; void __init mv78xx0_ge10_init(struct mv643xx_eth_platform_data *eth_data) @@ -505,9 +496,6 @@ static struct platform_device mv78xx0_ge11 = { .id = 3, .num_resources = 1, .resource = mv78xx0_ge11_resources, - .dev = { - .coherent_dma_mask = 0xffffffff, - }, }; void __init mv78xx0_ge11_init(struct mv643xx_eth_platform_data *eth_data) @@ -544,10 +532,12 @@ static struct mv64xxx_i2c_pdata mv78xx0_i2c_0_pdata = { static struct resource mv78xx0_i2c_0_resources[] = { { + .name = "i2c 0 base", .start = I2C_0_PHYS_BASE, .end = I2C_0_PHYS_BASE + 0x1f, .flags = IORESOURCE_MEM, }, { + .name = "i2c 0 irq", .start = IRQ_MV78XX0_I2C_0, .end = IRQ_MV78XX0_I2C_0, .flags = IORESOURCE_IRQ, @@ -577,10 +567,12 @@ static struct mv64xxx_i2c_pdata mv78xx0_i2c_1_pdata = { static struct resource mv78xx0_i2c_1_resources[] = { { + .name = "i2c 1 base", .start = I2C_1_PHYS_BASE, .end = I2C_1_PHYS_BASE + 0x1f, .flags = IORESOURCE_MEM, }, { + .name = "i2c 1 irq", .start = IRQ_MV78XX0_I2C_1, .end = IRQ_MV78XX0_I2C_1, .flags = IORESOURCE_IRQ, diff --git a/trunk/arch/arm/mach-mx2/clock_imx21.c b/trunk/arch/arm/mach-mx2/clock_imx21.c index e4b08ca804ea..999d013e06e3 100644 --- a/trunk/arch/arm/mach-mx2/clock_imx21.c +++ b/trunk/arch/arm/mach-mx2/clock_imx21.c @@ -890,7 +890,7 @@ static struct clk clko_clk = { .con_id = n, \ .clk = &c, \ }, -static struct clk_lookup lookups[] = { +static struct clk_lookup lookups[] __initdata = { /* It's unlikely that any driver wants one of them directly: _REGISTER_CLOCK(NULL, "ckih", ckih_clk) _REGISTER_CLOCK(NULL, "ckil", ckil_clk) diff --git a/trunk/arch/arm/mach-mx2/clock_imx27.c b/trunk/arch/arm/mach-mx2/clock_imx27.c index 2c971442f3f2..3f7280c490f0 100644 --- a/trunk/arch/arm/mach-mx2/clock_imx27.c +++ b/trunk/arch/arm/mach-mx2/clock_imx27.c @@ -621,7 +621,7 @@ DEFINE_CLOCK1(csi_clk, 0, 0, 0, parent, &csi_clk1, &per4_clk); .clk = &c, \ }, -static struct clk_lookup lookups[] = { +static struct clk_lookup lookups[] __initdata = { _REGISTER_CLOCK("imx-uart.0", NULL, uart1_clk) _REGISTER_CLOCK("imx-uart.1", NULL, uart2_clk) _REGISTER_CLOCK("imx-uart.2", NULL, uart3_clk) diff --git a/trunk/arch/arm/mach-mx3/clock-imx35.c b/trunk/arch/arm/mach-mx3/clock-imx35.c index 3c1e06f56dd6..53a112d4e04a 100644 --- a/trunk/arch/arm/mach-mx3/clock-imx35.c +++ b/trunk/arch/arm/mach-mx3/clock-imx35.c @@ -404,7 +404,7 @@ DEFINE_CLOCK(gpu2d_clk, 0, CCM_CGR3, 4, NULL, NULL); .clk = &c, \ }, -static struct clk_lookup lookups[] = { +static struct clk_lookup lookups[] __initdata = { _REGISTER_CLOCK(NULL, "asrc", asrc_clk) _REGISTER_CLOCK(NULL, "ata", ata_clk) _REGISTER_CLOCK(NULL, "audmux", audmux_clk) diff --git a/trunk/arch/arm/mach-mx3/clock.c b/trunk/arch/arm/mach-mx3/clock.c index a68fcf981edf..9957a11533a4 100644 --- a/trunk/arch/arm/mach-mx3/clock.c +++ b/trunk/arch/arm/mach-mx3/clock.c @@ -516,7 +516,7 @@ DEFINE_CLOCK(ipg_clk, 0, NULL, 0, ipg_get_rate, NULL, &ahb_clk); .clk = &c, \ }, -static struct clk_lookup lookups[] = { +static struct clk_lookup lookups[] __initdata = { _REGISTER_CLOCK(NULL, "emi", emi_clk) _REGISTER_CLOCK(NULL, "cspi", cspi1_clk) _REGISTER_CLOCK(NULL, "cspi", cspi2_clk) diff --git a/trunk/arch/arm/mach-orion5x/common.c b/trunk/arch/arm/mach-orion5x/common.c index b1c7778d9f96..6af99ddabdfb 100644 --- a/trunk/arch/arm/mach-orion5x/common.c +++ b/trunk/arch/arm/mach-orion5x/common.c @@ -188,9 +188,6 @@ static struct platform_device orion5x_eth = { .id = 0, .num_resources = 1, .resource = orion5x_eth_resources, - .dev = { - .coherent_dma_mask = 0xffffffff, - }, }; void __init orion5x_eth_init(struct mv643xx_eth_platform_data *eth_data) @@ -251,10 +248,12 @@ static struct mv64xxx_i2c_pdata orion5x_i2c_pdata = { static struct resource orion5x_i2c_resources[] = { { + .name = "i2c base", .start = I2C_PHYS_BASE, .end = I2C_PHYS_BASE + 0x1f, .flags = IORESOURCE_MEM, }, { + .name = "i2c irq", .start = IRQ_ORION5X_I2C, .end = IRQ_ORION5X_I2C, .flags = IORESOURCE_IRQ, diff --git a/trunk/arch/arm/mach-pxa/devices.c b/trunk/arch/arm/mach-pxa/devices.c index 29970f703f3c..d245e59c51b1 100644 --- a/trunk/arch/arm/mach-pxa/devices.c +++ b/trunk/arch/arm/mach-pxa/devices.c @@ -72,10 +72,7 @@ void __init pxa_set_mci_info(struct pxamci_platform_data *info) } -static struct pxa2xx_udc_mach_info pxa_udc_info = { - .gpio_pullup = -1, - .gpio_vbus = -1, -}; +static struct pxa2xx_udc_mach_info pxa_udc_info; void __init pxa_set_udc_info(struct pxa2xx_udc_mach_info *info) { diff --git a/trunk/arch/arm/mach-pxa/ezx.c b/trunk/arch/arm/mach-pxa/ezx.c index 7db966dc29ce..92ba16e1b6fc 100644 --- a/trunk/arch/arm/mach-pxa/ezx.c +++ b/trunk/arch/arm/mach-pxa/ezx.c @@ -111,9 +111,9 @@ static unsigned long ezx_pin_config[] __initdata = { GPIO25_SSP1_TXD, GPIO26_SSP1_RXD, GPIO24_GPIO, /* pcap chip select */ - GPIO1_GPIO | WAKEUP_ON_EDGE_RISE, /* pcap interrupt */ - GPIO4_GPIO | MFP_LPM_DRIVE_HIGH, /* WDI_AP */ - GPIO55_GPIO | MFP_LPM_DRIVE_HIGH, /* SYS_RESTART */ + GPIO1_GPIO, /* pcap interrupt */ + GPIO4_GPIO, /* WDI_AP */ + GPIO55_GPIO, /* SYS_RESTART */ /* MMC */ GPIO32_MMC_CLK, @@ -144,20 +144,20 @@ static unsigned long ezx_pin_config[] __initdata = { #if defined(CONFIG_MACH_EZX_A780) || defined(CONFIG_MACH_EZX_E680) static unsigned long gen1_pin_config[] __initdata = { /* flip / lockswitch */ - GPIO12_GPIO | WAKEUP_ON_EDGE_BOTH, + GPIO12_GPIO, /* bluetooth (bcm2035) */ - GPIO14_GPIO | WAKEUP_ON_EDGE_RISE, /* HOSTWAKE */ + GPIO14_GPIO | WAKEUP_ON_LEVEL_HIGH, /* HOSTWAKE */ GPIO48_GPIO, /* RESET */ GPIO28_GPIO, /* WAKEUP */ /* Neptune handshake */ - GPIO0_GPIO | WAKEUP_ON_EDGE_FALL, /* BP_RDY */ - GPIO57_GPIO | MFP_LPM_DRIVE_HIGH, /* AP_RDY */ - GPIO13_GPIO | WAKEUP_ON_EDGE_BOTH, /* WDI */ - GPIO3_GPIO | WAKEUP_ON_EDGE_BOTH, /* WDI2 */ - GPIO82_GPIO | MFP_LPM_DRIVE_HIGH, /* RESET */ - GPIO99_GPIO | MFP_LPM_DRIVE_HIGH, /* TC_MM_EN */ + GPIO0_GPIO | WAKEUP_ON_LEVEL_HIGH, /* BP_RDY */ + GPIO57_GPIO, /* AP_RDY */ + GPIO13_GPIO | WAKEUP_ON_LEVEL_HIGH, /* WDI */ + GPIO3_GPIO | WAKEUP_ON_LEVEL_HIGH, /* WDI2 */ + GPIO82_GPIO, /* RESET */ + GPIO99_GPIO, /* TC_MM_EN */ /* sound */ GPIO52_SSP3_SCLK, @@ -199,21 +199,21 @@ static unsigned long gen1_pin_config[] __initdata = { defined(CONFIG_MACH_EZX_E2) || defined(CONFIG_MACH_EZX_E6) static unsigned long gen2_pin_config[] __initdata = { /* flip / lockswitch */ - GPIO15_GPIO | WAKEUP_ON_EDGE_BOTH, + GPIO15_GPIO, /* EOC */ - GPIO10_GPIO | WAKEUP_ON_EDGE_RISE, + GPIO10_GPIO, /* bluetooth (bcm2045) */ - GPIO13_GPIO | WAKEUP_ON_EDGE_RISE, /* HOSTWAKE */ + GPIO13_GPIO | WAKEUP_ON_LEVEL_HIGH, /* HOSTWAKE */ GPIO37_GPIO, /* RESET */ GPIO57_GPIO, /* WAKEUP */ /* Neptune handshake */ - GPIO0_GPIO | WAKEUP_ON_EDGE_FALL, /* BP_RDY */ - GPIO96_GPIO | MFP_LPM_DRIVE_HIGH, /* AP_RDY */ - GPIO3_GPIO | WAKEUP_ON_EDGE_FALL, /* WDI */ - GPIO116_GPIO | MFP_LPM_DRIVE_HIGH, /* RESET */ + GPIO0_GPIO | WAKEUP_ON_LEVEL_HIGH, /* BP_RDY */ + GPIO96_GPIO, /* AP_RDY */ + GPIO3_GPIO | WAKEUP_ON_LEVEL_HIGH, /* WDI */ + GPIO116_GPIO, /* RESET */ GPIO41_GPIO, /* BP_FLASH */ /* sound */ diff --git a/trunk/arch/arm/mach-pxa/imote2.c b/trunk/arch/arm/mach-pxa/imote2.c index 2b27336c29f1..2121309b2474 100644 --- a/trunk/arch/arm/mach-pxa/imote2.c +++ b/trunk/arch/arm/mach-pxa/imote2.c @@ -412,7 +412,7 @@ static struct platform_device imote2_flash_device = { */ static struct i2c_board_info __initdata imote2_i2c_board_info[] = { { /* UCAM sensor board */ - .type = "max1239", + .type = "max1238", .addr = 0x35, }, { /* ITS400 Sensor board only */ .type = "max1363", diff --git a/trunk/arch/arm/mach-pxa/include/mach/reset.h b/trunk/arch/arm/mach-pxa/include/mach/reset.h index b6c10556fbc7..31e6a7b6ad80 100644 --- a/trunk/arch/arm/mach-pxa/include/mach/reset.h +++ b/trunk/arch/arm/mach-pxa/include/mach/reset.h @@ -13,9 +13,8 @@ extern void clear_reset_status(unsigned int mask); /** * init_gpio_reset() - register GPIO as reset generator * @gpio: gpio nr - * @output: set gpio as output instead of input during normal work - * @level: output level + * @output: set gpio as out/low instead of input during normal work */ -extern int init_gpio_reset(int gpio, int output, int level); +extern int init_gpio_reset(int gpio, int output); #endif /* __ASM_ARCH_RESET_H */ diff --git a/trunk/arch/arm/mach-pxa/mfp-pxa2xx.c b/trunk/arch/arm/mach-pxa/mfp-pxa2xx.c index cf6b720c055f..7ffb91d64c39 100644 --- a/trunk/arch/arm/mach-pxa/mfp-pxa2xx.c +++ b/trunk/arch/arm/mach-pxa/mfp-pxa2xx.c @@ -322,7 +322,6 @@ static inline void pxa27x_mfp_init(void) {} #ifdef CONFIG_PM static unsigned long saved_gafr[2][4]; static unsigned long saved_gpdr[4]; -static unsigned long saved_pgsr[4]; static int pxa2xx_mfp_suspend(struct sys_device *d, pm_message_t state) { @@ -333,7 +332,6 @@ static int pxa2xx_mfp_suspend(struct sys_device *d, pm_message_t state) saved_gafr[0][i] = GAFR_L(i); saved_gafr[1][i] = GAFR_U(i); saved_gpdr[i] = GPDR(i * 32); - saved_pgsr[i] = PGSR(i); GPDR(i * 32) = gpdr_lpm[i]; } @@ -348,7 +346,6 @@ static int pxa2xx_mfp_resume(struct sys_device *d) GAFR_L(i) = saved_gafr[0][i]; GAFR_U(i) = saved_gafr[1][i]; GPDR(i * 32) = saved_gpdr[i]; - PGSR(i) = saved_pgsr[i]; } PSSR = PSSR_RDH | PSSR_PH; return 0; @@ -377,9 +374,6 @@ static int __init pxa2xx_mfp_init(void) if (cpu_is_pxa27x()) pxa27x_mfp_init(); - /* clear RDH bit to enable GPIO receivers after reset/sleep exit */ - PSSR = PSSR_RDH; - /* initialize gafr_run[], pgsr_lpm[] from existing values */ for (i = 0; i <= gpio_to_bank(pxa_last_gpio); i++) gpdr_lpm[i] = GPDR(i * 32); diff --git a/trunk/arch/arm/mach-pxa/palmld.c b/trunk/arch/arm/mach-pxa/palmld.c index 471a853e548b..1cec1806f002 100644 --- a/trunk/arch/arm/mach-pxa/palmld.c +++ b/trunk/arch/arm/mach-pxa/palmld.c @@ -62,8 +62,6 @@ static unsigned long palmld_pin_config[] __initdata = { GPIO29_AC97_SDATA_IN_0, GPIO30_AC97_SDATA_OUT, GPIO31_AC97_SYNC, - GPIO89_AC97_SYSCLK, - GPIO95_AC97_nRESET, /* IrDA */ GPIO108_GPIO, /* ir disable */ diff --git a/trunk/arch/arm/mach-pxa/palmt5.c b/trunk/arch/arm/mach-pxa/palmt5.c index 05bf979b78a6..30662363907b 100644 --- a/trunk/arch/arm/mach-pxa/palmt5.c +++ b/trunk/arch/arm/mach-pxa/palmt5.c @@ -64,7 +64,6 @@ static unsigned long palmt5_pin_config[] __initdata = { GPIO29_AC97_SDATA_IN_0, GPIO30_AC97_SDATA_OUT, GPIO31_AC97_SYNC, - GPIO89_AC97_SYSCLK, GPIO95_AC97_nRESET, /* IrDA */ diff --git a/trunk/arch/arm/mach-pxa/palmtx.c b/trunk/arch/arm/mach-pxa/palmtx.c index e99a893c58a7..e2d44b1a8a9b 100644 --- a/trunk/arch/arm/mach-pxa/palmtx.c +++ b/trunk/arch/arm/mach-pxa/palmtx.c @@ -65,7 +65,6 @@ static unsigned long palmtx_pin_config[] __initdata = { GPIO29_AC97_SDATA_IN_0, GPIO30_AC97_SDATA_OUT, GPIO31_AC97_SYNC, - GPIO89_AC97_SYSCLK, GPIO95_AC97_nRESET, /* IrDA */ diff --git a/trunk/arch/arm/mach-pxa/reset.c b/trunk/arch/arm/mach-pxa/reset.c index 01e9d643394a..df29d45fb4e7 100644 --- a/trunk/arch/arm/mach-pxa/reset.c +++ b/trunk/arch/arm/mach-pxa/reset.c @@ -20,7 +20,7 @@ static void do_hw_reset(void); static int reset_gpio = -1; -int init_gpio_reset(int gpio, int output, int level) +int init_gpio_reset(int gpio, int output) { int rc; @@ -31,7 +31,7 @@ int init_gpio_reset(int gpio, int output, int level) } if (output) - rc = gpio_direction_output(gpio, level); + rc = gpio_direction_output(gpio, 0); else rc = gpio_direction_input(gpio); if (rc) { diff --git a/trunk/arch/arm/mach-pxa/spitz.c b/trunk/arch/arm/mach-pxa/spitz.c index 5a45fe340a10..c18e34acafcb 100644 --- a/trunk/arch/arm/mach-pxa/spitz.c +++ b/trunk/arch/arm/mach-pxa/spitz.c @@ -531,15 +531,9 @@ static int spitz_ohci_init(struct device *dev) return gpio_direction_output(SPITZ_GPIO_USB_HOST, 1); } -static void spitz_ohci_exit(struct device *dev) -{ - gpio_free(SPITZ_GPIO_USB_HOST); -} - static struct pxaohci_platform_data spitz_ohci_platform_data = { .port_mode = PMM_NPS_MODE, .init = spitz_ohci_init, - .exit = spitz_ohci_exit, .flags = ENABLE_PORT_ALL | NO_OC_PROTECTION, .power_budget = 150, }; @@ -737,7 +731,7 @@ static void spitz_restart(char mode, const char *cmd) static void __init common_init(void) { - init_gpio_reset(SPITZ_GPIO_ON_RESET, 1, 0); + init_gpio_reset(SPITZ_GPIO_ON_RESET, 1); pm_power_off = spitz_poweroff; arm_pm_restart = spitz_restart; diff --git a/trunk/arch/arm/mach-pxa/tosa.c b/trunk/arch/arm/mach-pxa/tosa.c index a0bd46ef5d30..afac5b6d3d78 100644 --- a/trunk/arch/arm/mach-pxa/tosa.c +++ b/trunk/arch/arm/mach-pxa/tosa.c @@ -897,7 +897,7 @@ static void __init tosa_init(void) gpio_set_wake(MFP_PIN_GPIO1, 1); /* We can't pass to gpio-keys since it will drop the Reset altfunc */ - init_gpio_reset(TOSA_GPIO_ON_RESET, 0, 0); + init_gpio_reset(TOSA_GPIO_ON_RESET, 0); pm_power_off = tosa_poweroff; arm_pm_restart = tosa_restart; diff --git a/trunk/arch/arm/mm/proc-v7.S b/trunk/arch/arm/mm/proc-v7.S index a08d9d2380d3..3397f1e64d76 100644 --- a/trunk/arch/arm/mm/proc-v7.S +++ b/trunk/arch/arm/mm/proc-v7.S @@ -184,37 +184,23 @@ __v7_setup: stmia r12, {r0-r5, r7, r9, r11, lr} bl v7_flush_dcache_all ldmia r12, {r0-r5, r7, r9, r11, lr} - - mrc p15, 0, r0, c0, c0, 0 @ read main ID register - and r10, r0, #0xff000000 @ ARM? - teq r10, #0x41000000 - bne 2f - and r5, r0, #0x00f00000 @ variant - and r6, r0, #0x0000000f @ revision - orr r0, r6, r5, lsr #20-4 @ combine variant and revision - #ifdef CONFIG_ARM_ERRATA_430973 - teq r5, #0x00100000 @ only present in r1p* - mrceq p15, 0, r10, c1, c0, 1 @ read aux control register - orreq r10, r10, #(1 << 6) @ set IBE to 1 - mcreq p15, 0, r10, c1, c0, 1 @ write aux control register + mrc p15, 0, r10, c1, c0, 1 @ read aux control register + orr r10, r10, #(1 << 6) @ set IBE to 1 + mcr p15, 0, r10, c1, c0, 1 @ write aux control register #endif #ifdef CONFIG_ARM_ERRATA_458693 - teq r0, #0x20 @ only present in r2p0 - mrceq p15, 0, r10, c1, c0, 1 @ read aux control register - orreq r10, r10, #(1 << 5) @ set L1NEON to 1 - orreq r10, r10, #(1 << 9) @ set PLDNOP to 1 - mcreq p15, 0, r10, c1, c0, 1 @ write aux control register + mrc p15, 0, r10, c1, c0, 1 @ read aux control register + orr r10, r10, #(1 << 5) @ set L1NEON to 1 + orr r10, r10, #(1 << 9) @ set PLDNOP to 1 + mcr p15, 0, r10, c1, c0, 1 @ write aux control register #endif #ifdef CONFIG_ARM_ERRATA_460075 - teq r0, #0x20 @ only present in r2p0 - mrceq p15, 1, r10, c9, c0, 2 @ read L2 cache aux ctrl register - tsteq r10, #1 << 22 - orreq r10, r10, #(1 << 22) @ set the Write Allocate disable bit - mcreq p15, 1, r10, c9, c0, 2 @ write the L2 cache aux ctrl register + mrc p15, 1, r10, c9, c0, 2 @ read L2 cache aux ctrl register + orr r10, r10, #(1 << 22) @ set the Write Allocate disable bit + mcr p15, 1, r10, c9, c0, 2 @ write the L2 cache aux ctrl register #endif - -2: mov r10, #0 + mov r10, #0 #ifdef HARVARD_CACHE mcr p15, 0, r10, c7, c5, 0 @ I+BTB cache invalidate #endif diff --git a/trunk/arch/arm/tools/mach-types b/trunk/arch/arm/tools/mach-types index fec64678a63a..945e0d237a1d 100644 --- a/trunk/arch/arm/tools/mach-types +++ b/trunk/arch/arm/tools/mach-types @@ -12,7 +12,7 @@ # # http://www.arm.linux.org.uk/developer/machines/?action=new # -# Last update: Fri May 29 10:14:20 2009 +# Last update: Mon Mar 23 20:09:01 2009 # # machine_is_xxx CONFIG_xxxx MACH_TYPE_xxx number # @@ -916,7 +916,7 @@ nxdb500 MACH_NXDB500 NXDB500 905 apf9328 MACH_APF9328 APF9328 906 omap_wipoq MACH_OMAP_WIPOQ OMAP_WIPOQ 907 omap_twip MACH_OMAP_TWIP OMAP_TWIP 908 -treo650 MACH_TREO650 TREO650 909 +palmt650 MACH_PALMT650 PALMT650 909 acumen MACH_ACUMEN ACUMEN 910 xp100 MACH_XP100 XP100 911 fs2410 MACH_FS2410 FS2410 912 @@ -1232,7 +1232,7 @@ ql202b MACH_QL202B QL202B 1226 vpac270 MACH_VPAC270 VPAC270 1227 rd129 MACH_RD129 RD129 1228 htcwizard MACH_HTCWIZARD HTCWIZARD 1229 -treo680 MACH_TREO680 TREO680 1230 +xscale_treo680 MACH_XSCALE_TREO680 XSCALE_TREO680 1230 tecon_tmezon MACH_TECON_TMEZON TECON_TMEZON 1231 zylonite MACH_ZYLONITE ZYLONITE 1233 gene1270 MACH_GENE1270 GENE1270 1234 @@ -1418,10 +1418,10 @@ looxc550 MACH_LOOXC550 LOOXC550 1417 cnty_titan MACH_CNTY_TITAN CNTY_TITAN 1418 app3xx MACH_APP3XX APP3XX 1419 sideoatsgrama MACH_SIDEOATSGRAMA SIDEOATSGRAMA 1420 -treo700p MACH_TREO700P TREO700P 1421 -treo700w MACH_TREO700W TREO700W 1422 -treo750 MACH_TREO750 TREO750 1423 -treo755p MACH_TREO755P TREO755P 1424 +palmtreo700p MACH_PALMTREO700P PALMTREO700P 1421 +palmtreo700w MACH_PALMTREO700W PALMTREO700W 1422 +palmtreo750 MACH_PALMTREO750 PALMTREO750 1423 +palmtreo755p MACH_PALMTREO755P PALMTREO755P 1424 ezreganut9200 MACH_EZREGANUT9200 EZREGANUT9200 1425 sarge MACH_SARGE SARGE 1426 a696 MACH_A696 A696 1427 @@ -1721,7 +1721,7 @@ sapphire MACH_SAPPHIRE SAPPHIRE 1729 csb637xo MACH_CSB637XO CSB637XO 1730 evisiong MACH_EVISIONG EVISIONG 1731 stmp37xx MACH_STMP37XX STMP37XX 1732 -stmp378x MACH_STMP378X STMP378X 1733 +stmp378x MACH_STMP38XX STMP38XX 1733 tnt MACH_TNT TNT 1734 tbxt MACH_TBXT TBXT 1735 playmate MACH_PLAYMATE PLAYMATE 1736 @@ -1817,7 +1817,7 @@ smdkc100 MACH_SMDKC100 SMDKC100 1826 tavorevb MACH_TAVOREVB TAVOREVB 1827 saar MACH_SAAR SAAR 1828 deister_eyecam MACH_DEISTER_EYECAM DEISTER_EYECAM 1829 -at91sam9m10g45ek MACH_AT91SAM9M10G45EK AT91SAM9M10G45EK 1830 +at91sam9m10ek MACH_AT91SAM9M10EK AT91SAM9M10EK 1830 linkstation_produo MACH_LINKSTATION_PRODUO LINKSTATION_PRODUO 1831 hit_b0 MACH_HIT_B0 HIT_B0 1832 adx_rmu MACH_ADX_RMU ADX_RMU 1833 @@ -2132,116 +2132,3 @@ apollo MACH_APOLLO APOLLO 2141 at91cap9stk MACH_AT91CAP9STK AT91CAP9STK 2142 spc300 MACH_SPC300 SPC300 2143 eko MACH_EKO EKO 2144 -ccw9m2443 MACH_CCW9M2443 CCW9M2443 2145 -ccw9m2443js MACH_CCW9M2443JS CCW9M2443JS 2146 -m2m_router_device MACH_M2M_ROUTER_DEVICE M2M_ROUTER_DEVICE 2147 -str9104nas MACH_STAR9104NAS STAR9104NAS 2148 -pca100 MACH_PCA100 PCA100 2149 -z3_dm365_mod_01 MACH_Z3_DM365_MOD_01 Z3_DM365_MOD_01 2150 -hipox MACH_HIPOX HIPOX 2151 -omap3_piteds MACH_OMAP3_PITEDS OMAP3_PITEDS 2152 -bm150r MACH_BM150R BM150R 2153 -tbone MACH_TBONE TBONE 2154 -merlin MACH_MERLIN MERLIN 2155 -falcon MACH_FALCON FALCON 2156 -davinci_da850_evm MACH_DAVINCI_DA850_EVM DAVINCI_DA850_EVM 2157 -s5p6440 MACH_S5P6440 S5P6440 2158 -at91sam9g10ek MACH_AT91SAM9G10EK AT91SAM9G10EK 2159 -omap_4430sdp MACH_OMAP_4430SDP OMAP_4430SDP 2160 -lpc313x MACH_LPC313X LPC313X 2161 -magx_zn5 MACH_MAGX_ZN5 MAGX_ZN5 2162 -magx_em30 MACH_MAGX_EM30 MAGX_EM30 2163 -magx_ve66 MACH_MAGX_VE66 MAGX_VE66 2164 -meesc MACH_MEESC MEESC 2165 -otc570 MACH_OTC570 OTC570 2166 -bcu2412 MACH_BCU2412 BCU2412 2167 -beacon MACH_BEACON BEACON 2168 -actia_tgw MACH_ACTIA_TGW ACTIA_TGW 2169 -e4430 MACH_E4430 E4430 2170 -ql300 MACH_QL300 QL300 2171 -btmavb101 MACH_BTMAVB101 BTMAVB101 2172 -btmawb101 MACH_BTMAWB101 BTMAWB101 2173 -sq201 MACH_SQ201 SQ201 2174 -quatro45xx MACH_QUATRO45XX QUATRO45XX 2175 -openpad MACH_OPENPAD OPENPAD 2176 -tx25 MACH_TX25 TX25 2177 -omap3_torpedo MACH_OMAP3_TORPEDO OMAP3_TORPEDO 2178 -htcraphael_k MACH_HTCRAPHAEL_K HTCRAPHAEL_K 2179 -lal43 MACH_LAL43 LAL43 2181 -htcraphael_cdma500 MACH_HTCRAPHAEL_CDMA500 HTCRAPHAEL_CDMA500 2182 -anw6410 MACH_ANW6410 ANW6410 2183 -htcprophet MACH_HTCPROPHET HTCPROPHET 2185 -cfa_10022 MACH_CFA_10022 CFA_10022 2186 -imx27_visstrim_m10 MACH_IMX27_VISSTRIM_M10 IMX27_VISSTRIM_M10 2187 -px2imx27 MACH_PX2IMX27 PX2IMX27 2188 -stm3210e_eval MACH_STM3210E_EVAL STM3210E_EVAL 2189 -dvs10 MACH_DVS10 DVS10 2190 -portuxg20 MACH_PORTUXG20 PORTUXG20 2191 -arm_spv MACH_ARM_SPV ARM_SPV 2192 -smdkc110 MACH_SMDKC110 SMDKC110 2193 -cabespresso MACH_CABESPRESSO CABESPRESSO 2194 -hmc800 MACH_HMC800 HMC800 2195 -sholes MACH_SHOLES SHOLES 2196 -btmxc31 MACH_BTMXC31 BTMXC31 2197 -dt501 MACH_DT501 DT501 2198 -ktx MACH_KTX KTX 2199 -omap3517evm MACH_OMAP3517EVM OMAP3517EVM 2200 -netspace_v2 MACH_NETSPACE_V2 NETSPACE_V2 2201 -netspace_max_v2 MACH_NETSPACE_MAX_V2 NETSPACE_MAX_V2 2202 -d2net_v2 MACH_D2NET_V2 D2NET_V2 2203 -net2big_v2 MACH_NET2BIG_V2 NET2BIG_V2 2204 -net4big_v2 MACH_NET4BIG_V2 NET4BIG_V2 2205 -net5big_v2 MACH_NET5BIG_V2 NET5BIG_V2 2206 -endb2443 MACH_ENDB2443 ENDB2443 2207 -inetspace_v2 MACH_INETSPACE_V2 INETSPACE_V2 2208 -tros MACH_TROS TROS 2209 -pelco_homer MACH_PELCO_HOMER PELCO_HOMER 2210 -ofsp8 MACH_OFSP8 OFSP8 2211 -at91sam9g45ekes MACH_AT91SAM9G45EKES AT91SAM9G45EKES 2212 -guf_cupid MACH_GUF_CUPID GUF_CUPID 2213 -eab1r MACH_EAB1R EAB1R 2214 -desirec MACH_DESIREC DESIREC 2215 -cordoba MACH_CORDOBA CORDOBA 2216 -irvine MACH_IRVINE IRVINE 2217 -sff772 MACH_SFF772 SFF772 2218 -pelco_milano MACH_PELCO_MILANO PELCO_MILANO 2219 -pc7302 MACH_PC7302 PC7302 2220 -bip6000 MACH_BIP6000 BIP6000 2221 -silvermoon MACH_SILVERMOON SILVERMOON 2222 -vc0830 MACH_VC0830 VC0830 2223 -dt430 MACH_DT430 DT430 2224 -ji42pf MACH_JI42PF JI42PF 2225 -gnet_ksm MACH_GNET_KSM GNET_KSM 2226 -gnet_sgm MACH_GNET_SGM GNET_SGM 2227 -gnet_sgr MACH_GNET_SGR GNET_SGR 2228 -omap3_icetekevm MACH_OMAP3_ICETEKEVM OMAP3_ICETEKEVM 2229 -pnp MACH_PNP PNP 2230 -ctera_2bay_k MACH_CTERA_2BAY_K CTERA_2BAY_K 2231 -ctera_2bay_u MACH_CTERA_2BAY_U CTERA_2BAY_U 2232 -sas_c MACH_SAS_C SAS_C 2233 -vma2315 MACH_VMA2315 VMA2315 2234 -vcs MACH_VCS VCS 2235 -spear600 MACH_SPEAR600 SPEAR600 2236 -spear300 MACH_SPEAR300 SPEAR300 2237 -spear1300 MACH_SPEAR1300 SPEAR1300 2238 -lilly1131 MACH_LILLY1131 LILLY1131 2239 -arvoo_ax301 MACH_ARVOO_AX301 ARVOO_AX301 2240 -mapphone MACH_MAPPHONE MAPPHONE 2241 -legend MACH_LEGEND LEGEND 2242 -salsa MACH_SALSA SALSA 2243 -lounge MACH_LOUNGE LOUNGE 2244 -vision MACH_VISION VISION 2245 -vmb20 MACH_VMB20 VMB20 2246 -hy2410 MACH_HY2410 HY2410 2247 -hy9315 MACH_HY9315 HY9315 2248 -bullwinkle MACH_BULLWINKLE BULLWINKLE 2249 -arm_ultimator2 MACH_ARM_ULTIMATOR2 ARM_ULTIMATOR2 2250 -vs_v210 MACH_VS_V210 VS_V210 2252 -vs_v212 MACH_VS_V212 VS_V212 2253 -hmt MACH_HMT HMT 2254 -suen3 MACH_SUEN3 SUEN3 2255 -vesper MACH_VESPER VESPER 2256 -str9 MACH_STR9 STR9 2257 -omap3_wl_ff MACH_OMAP3_WL_FF OMAP3_WL_FF 2258 -simcom MACH_SIMCOM SIMCOM 2259 -mcwebio MACH_MCWEBIO MCWEBIO 2260 diff --git a/trunk/arch/mips/Kconfig b/trunk/arch/mips/Kconfig index 25f3b0a11ca8..09b1287a92ce 100644 --- a/trunk/arch/mips/Kconfig +++ b/trunk/arch/mips/Kconfig @@ -72,7 +72,6 @@ config MIPS_COBALT select IRQ_CPU select IRQ_GT641XX select PCI_GT64XXX_PCI0 - select PCI select SYS_HAS_CPU_NEVADA select SYS_HAS_EARLY_PRINTK select SYS_SUPPORTS_32BIT_KERNEL @@ -594,7 +593,7 @@ config WR_PPMC board, which is based on GT64120 bridge chip. config CAVIUM_OCTEON_SIMULATOR - bool "Cavium Networks Octeon Simulator" + bool "Support for the Cavium Networks Octeon Simulator" select CEVT_R4K select 64BIT_PHYS_ADDR select DMA_COHERENT @@ -608,7 +607,7 @@ config CAVIUM_OCTEON_SIMULATOR hardware. config CAVIUM_OCTEON_REFERENCE_BOARD - bool "Cavium Networks Octeon reference board" + bool "Support for the Cavium Networks Octeon reference board" select CEVT_R4K select 64BIT_PHYS_ADDR select DMA_COHERENT diff --git a/trunk/arch/mips/include/asm/cpu-info.h b/trunk/arch/mips/include/asm/cpu-info.h index 126044308dec..744cd8fb107f 100644 --- a/trunk/arch/mips/include/asm/cpu-info.h +++ b/trunk/arch/mips/include/asm/cpu-info.h @@ -39,8 +39,8 @@ struct cache_desc { #define MIPS_CACHE_PINDEX 0x00000020 /* Physically indexed cache */ struct cpuinfo_mips { - unsigned int udelay_val; - unsigned int asid_cache; + unsigned long udelay_val; + unsigned long asid_cache; /* * Capability and feature descriptor structure for MIPS CPU diff --git a/trunk/arch/mips/include/asm/delay.h b/trunk/arch/mips/include/asm/delay.h index a07e51b2be13..b0bccd2c4ed5 100644 --- a/trunk/arch/mips/include/asm/delay.h +++ b/trunk/arch/mips/include/asm/delay.h @@ -11,12 +11,94 @@ #ifndef _ASM_DELAY_H #define _ASM_DELAY_H -extern void __delay(unsigned int loops); -extern void __ndelay(unsigned int ns); -extern void __udelay(unsigned int us); +#include +#include -#define ndelay(ns) __udelay(ns) -#define udelay(us) __udelay(us) +#include +#include + +static inline void __delay(unsigned long loops) +{ + if (sizeof(long) == 4) + __asm__ __volatile__ ( + " .set noreorder \n" + " .align 3 \n" + "1: bnez %0, 1b \n" + " subu %0, 1 \n" + " .set reorder \n" + : "=r" (loops) + : "0" (loops)); + else if (sizeof(long) == 8 && !DADDI_WAR) + __asm__ __volatile__ ( + " .set noreorder \n" + " .align 3 \n" + "1: bnez %0, 1b \n" + " dsubu %0, 1 \n" + " .set reorder \n" + : "=r" (loops) + : "0" (loops)); + else if (sizeof(long) == 8 && DADDI_WAR) + __asm__ __volatile__ ( + " .set noreorder \n" + " .align 3 \n" + "1: bnez %0, 1b \n" + " dsubu %0, %2 \n" + " .set reorder \n" + : "=r" (loops) + : "0" (loops), "r" (1)); +} + + +/* + * Division by multiplication: you don't have to worry about + * loss of precision. + * + * Use only for very small delays ( < 1 msec). Should probably use a + * lookup table, really, as the multiplications take much too long with + * short delays. This is a "reasonable" implementation, though (and the + * first constant multiplications gets optimized away if the delay is + * a constant) + */ + +static inline void __udelay(unsigned long usecs, unsigned long lpj) +{ + unsigned long hi, lo; + + /* + * The rates of 128 is rounded wrongly by the catchall case + * for 64-bit. Excessive precission? Probably ... + */ +#if defined(CONFIG_64BIT) && (HZ == 128) + usecs *= 0x0008637bd05af6c7UL; /* 2**64 / (1000000 / HZ) */ +#elif defined(CONFIG_64BIT) + usecs *= (0x8000000000000000UL / (500000 / HZ)); +#else /* 32-bit junk follows here */ + usecs *= (unsigned long) (((0x8000000000000000ULL / (500000 / HZ)) + + 0x80000000ULL) >> 32); +#endif + + if (sizeof(long) == 4) + __asm__("multu\t%2, %3" + : "=h" (usecs), "=l" (lo) + : "r" (usecs), "r" (lpj) + : GCC_REG_ACCUM); + else if (sizeof(long) == 8 && !R4000_WAR) + __asm__("dmultu\t%2, %3" + : "=h" (usecs), "=l" (lo) + : "r" (usecs), "r" (lpj) + : GCC_REG_ACCUM); + else if (sizeof(long) == 8 && R4000_WAR) + __asm__("dmultu\t%3, %4\n\tmfhi\t%0" + : "=r" (usecs), "=h" (hi), "=l" (lo) + : "r" (usecs), "r" (lpj) + : GCC_REG_ACCUM); + + __delay(usecs); +} + +#define __udelay_val cpu_data[raw_smp_processor_id()].udelay_val + +#define udelay(usecs) __udelay((usecs), __udelay_val) /* make sure "usecs *= ..." in udelay do not overflow. */ #if HZ >= 1000 diff --git a/trunk/arch/mips/include/asm/ioctl.h b/trunk/arch/mips/include/asm/ioctl.h index 916163401b2c..85067e248a83 100644 --- a/trunk/arch/mips/include/asm/ioctl.h +++ b/trunk/arch/mips/include/asm/ioctl.h @@ -60,16 +60,12 @@ ((nr) << _IOC_NRSHIFT) | \ ((size) << _IOC_SIZESHIFT)) -#ifdef __KERNEL__ /* provoke compile error for invalid uses of size argument */ extern unsigned int __invalid_size_argument_for_IOC; #define _IOC_TYPECHECK(t) \ ((sizeof(t) == sizeof(t[1]) && \ sizeof(t) < (1 << _IOC_SIZEBITS)) ? \ sizeof(t) : __invalid_size_argument_for_IOC) -#else -#define _IOC_TYPECHECK(t) (sizeof(t)) -#endif /* used to create numbers */ #define _IO(type, nr) _IOC(_IOC_NONE, (type), (nr), 0) diff --git a/trunk/arch/mips/kernel/proc.c b/trunk/arch/mips/kernel/proc.c index e0a4ac18fa07..26760cad8b69 100644 --- a/trunk/arch/mips/kernel/proc.c +++ b/trunk/arch/mips/kernel/proc.c @@ -42,7 +42,7 @@ static int show_cpuinfo(struct seq_file *m, void *v) seq_printf(m, fmt, __cpu_name[n], (version >> 4) & 0x0f, version & 0x0f, (fp_vers >> 4) & 0x0f, fp_vers & 0x0f); - seq_printf(m, "BogoMIPS\t\t: %u.%02u\n", + seq_printf(m, "BogoMIPS\t\t: %lu.%02lu\n", cpu_data[n].udelay_val / (500000/HZ), (cpu_data[n].udelay_val / (5000/HZ)) % 100); seq_printf(m, "wait instruction\t: %s\n", cpu_wait ? "yes" : "no"); diff --git a/trunk/arch/mips/lib/Makefile b/trunk/arch/mips/lib/Makefile index 2adead5a8a37..c13c7ad2cdae 100644 --- a/trunk/arch/mips/lib/Makefile +++ b/trunk/arch/mips/lib/Makefile @@ -2,8 +2,8 @@ # Makefile for MIPS-specific library files.. # -lib-y += csum_partial.o delay.o memcpy.o memcpy-inatomic.o memset.o \ - strlen_user.o strncpy_user.o strnlen_user.o uncached.o +lib-y += csum_partial.o memcpy.o memcpy-inatomic.o memset.o strlen_user.o \ + strncpy_user.o strnlen_user.o uncached.o obj-y += iomap.o obj-$(CONFIG_PCI) += iomap-pci.o diff --git a/trunk/arch/mips/lib/delay.c b/trunk/arch/mips/lib/delay.c deleted file mode 100644 index f69c6b569eb3..000000000000 --- a/trunk/arch/mips/lib/delay.c +++ /dev/null @@ -1,56 +0,0 @@ -/* - * This file is subject to the terms and conditions of the GNU General Public - * License. See the file "COPYING" in the main directory of this archive - * for more details. - * - * Copyright (C) 1994 by Waldorf Electronics - * Copyright (C) 1995 - 2000, 01, 03 by Ralf Baechle - * Copyright (C) 1999, 2000 Silicon Graphics, Inc. - * Copyright (C) 2007 Maciej W. Rozycki - */ -#include -#include -#include - -#include -#include - -inline void __delay(unsigned int loops) -{ - __asm__ __volatile__ ( - " .set noreorder \n" - " .align 3 \n" - "1: bnez %0, 1b \n" - " subu %0, 1 \n" - " .set reorder \n" - : "=r" (loops) - : "0" (loops)); -} -EXPORT_SYMBOL(__delay); - -/* - * Division by multiplication: you don't have to worry about - * loss of precision. - * - * Use only for very small delays ( < 1 msec). Should probably use a - * lookup table, really, as the multiplications take much too long with - * short delays. This is a "reasonable" implementation, though (and the - * first constant multiplications gets optimized away if the delay is - * a constant) - */ - -void __udelay(unsigned long us) -{ - unsigned int lpj = current_cpu_data.udelay_val; - - __delay((us * 0x000010c7 * HZ * lpj) >> 32); -} -EXPORT_SYMBOL(__udelay); - -void __ndelay(unsigned long ns) -{ - unsigned int lpj = current_cpu_data.udelay_val; - - __delay((us * 0x00000005 * HZ * lpj) >> 32); -} -EXPORT_SYMBOL(__ndelay); diff --git a/trunk/arch/mips/sibyte/cfe/setup.c b/trunk/arch/mips/sibyte/cfe/setup.c index eb5396cf81bb..3de30f79db3f 100644 --- a/trunk/arch/mips/sibyte/cfe/setup.c +++ b/trunk/arch/mips/sibyte/cfe/setup.c @@ -288,7 +288,13 @@ void __init prom_init(void) */ cfe_cons_handle = cfe_getstdhandle(CFE_STDHANDLE_CONSOLE); if (cfe_getenv("LINUX_CMDLINE", arcs_cmdline, CL_SIZE) < 0) { - if (argc >= 0) { + if (argc < 0) { + /* + * It's OK for direct boot to not provide a + * command line + */ + strcpy(arcs_cmdline, "root=/dev/ram0 "); + } else { /* The loader should have set the command line */ /* too early for panic to do any good */ printk("LINUX_CMDLINE not defined in cfe."); diff --git a/trunk/arch/powerpc/configs/pmac32_defconfig b/trunk/arch/powerpc/configs/pmac32_defconfig index ea8870a34482..5339bb44cce9 100644 --- a/trunk/arch/powerpc/configs/pmac32_defconfig +++ b/trunk/arch/powerpc/configs/pmac32_defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.30-rc7 -# Mon May 25 14:53:25 2009 +# Linux kernel version: 2.6.28-rc3 +# Tue Nov 11 19:36:51 2008 # # CONFIG_PPC64 is not set @@ -14,7 +14,6 @@ CONFIG_6xx=y # CONFIG_40x is not set # CONFIG_44x is not set # CONFIG_E200 is not set -CONFIG_PPC_BOOK3S=y CONFIG_PPC_FPU=y CONFIG_ALTIVEC=y CONFIG_PPC_STD_MMU=y @@ -44,7 +43,7 @@ CONFIG_GENERIC_FIND_NEXT_BIT=y CONFIG_PPC=y CONFIG_EARLY_PRINTK=y CONFIG_GENERIC_NVRAM=y -CONFIG_SCHED_OMIT_FRAME_POINTER=y +CONFIG_SCHED_NO_NO_OMIT_FRAME_POINTER=y CONFIG_ARCH_MAY_HAVE_PC_FDC=y CONFIG_PPC_OF=y CONFIG_OF=y @@ -53,14 +52,12 @@ CONFIG_OF=y CONFIG_AUDIT_ARCH=y CONFIG_GENERIC_BUG=y CONFIG_SYS_SUPPORTS_APM_EMULATION=y -CONFIG_DTC=y # CONFIG_DEFAULT_UIMAGE is not set CONFIG_HIBERNATE_32=y CONFIG_ARCH_HIBERNATION_POSSIBLE=y CONFIG_ARCH_SUSPEND_POSSIBLE=y # CONFIG_PPC_DCR_NATIVE is not set # CONFIG_PPC_DCR_MMIO is not set -CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" # @@ -75,24 +72,14 @@ CONFIG_SWAP=y CONFIG_SYSVIPC=y CONFIG_SYSVIPC_SYSCTL=y CONFIG_POSIX_MQUEUE=y -CONFIG_POSIX_MQUEUE_SYSCTL=y # CONFIG_BSD_PROCESS_ACCT is not set # CONFIG_TASKSTATS is not set # CONFIG_AUDIT is not set - -# -# RCU Subsystem -# -CONFIG_CLASSIC_RCU=y -# CONFIG_TREE_RCU is not set -# CONFIG_PREEMPT_RCU is not set -# CONFIG_TREE_RCU_TRACE is not set -# CONFIG_PREEMPT_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=14 -# CONFIG_GROUP_SCHED is not set # CONFIG_CGROUPS is not set +# CONFIG_GROUP_SCHED is not set CONFIG_SYSFS_DEPRECATED=y CONFIG_SYSFS_DEPRECATED_V2=y # CONFIG_RELAY is not set @@ -101,27 +88,23 @@ CONFIG_NAMESPACES=y # CONFIG_IPC_NS is not set # CONFIG_USER_NS is not set # CONFIG_PID_NS is not set -# CONFIG_NET_NS is not set CONFIG_BLK_DEV_INITRD=y CONFIG_INITRAMFS_SOURCE="" -CONFIG_RD_GZIP=y -CONFIG_RD_BZIP2=y -CONFIG_RD_LZMA=y # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set CONFIG_SYSCTL=y -CONFIG_ANON_INODES=y # CONFIG_EMBEDDED is not set CONFIG_SYSCTL_SYSCALL=y CONFIG_KALLSYMS=y CONFIG_KALLSYMS_ALL=y # CONFIG_KALLSYMS_EXTRA_PASS is not set -# CONFIG_STRIP_ASM_SYMS is not set CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y CONFIG_ELF_CORE=y +# CONFIG_COMPAT_BRK is not set CONFIG_BASE_FULL=y CONFIG_FUTEX=y +CONFIG_ANON_INODES=y CONFIG_EPOLL=y CONFIG_SIGNALFD=y CONFIG_TIMERFD=y @@ -131,12 +114,10 @@ CONFIG_AIO=y CONFIG_VM_EVENT_COUNTERS=y CONFIG_PCI_QUIRKS=y CONFIG_SLUB_DEBUG=y -# CONFIG_COMPAT_BRK is not set # CONFIG_SLAB is not set CONFIG_SLUB=y # CONFIG_SLOB is not set CONFIG_PROFILING=y -CONFIG_TRACEPOINTS=y # CONFIG_MARKERS is not set CONFIG_OPROFILE=y CONFIG_HAVE_OPROFILE=y @@ -146,10 +127,10 @@ CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y -# CONFIG_SLOW_WORK is not set # CONFIG_HAVE_GENERIC_DMA_COHERENT is not set CONFIG_SLABINFO=y CONFIG_RT_MUTEXES=y +# CONFIG_TINY_SHMEM is not set CONFIG_BASE_SMALL=0 CONFIG_MODULES=y # CONFIG_MODULE_FORCE_LOAD is not set @@ -157,8 +138,11 @@ CONFIG_MODULE_UNLOAD=y CONFIG_MODULE_FORCE_UNLOAD=y # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set +CONFIG_KMOD=y CONFIG_BLOCK=y CONFIG_LBD=y +# CONFIG_BLK_DEV_IO_TRACE is not set +CONFIG_LSF=y CONFIG_BLK_DEV_BSG=y # CONFIG_BLK_DEV_INTEGRITY is not set @@ -174,11 +158,14 @@ CONFIG_DEFAULT_AS=y # CONFIG_DEFAULT_CFQ is not set # CONFIG_DEFAULT_NOOP is not set CONFIG_DEFAULT_IOSCHED="anticipatory" +CONFIG_CLASSIC_RCU=y CONFIG_FREEZER=y # # Platform support # +CONFIG_PPC_MULTIPLATFORM=y +CONFIG_CLASSIC32=y # CONFIG_PPC_CHRP is not set # CONFIG_MPC5121_ADS is not set # CONFIG_MPC5121_GENERIC is not set @@ -191,9 +178,7 @@ CONFIG_PPC_PMAC=y # CONFIG_PPC_83xx is not set # CONFIG_PPC_86xx is not set # CONFIG_EMBEDDED6xx is not set -# CONFIG_AMIGAONE is not set CONFIG_PPC_NATIVE=y -CONFIG_PPC_OF_BOOT_TRAMPOLINE=y # CONFIG_IPIC is not set CONFIG_MPIC=y # CONFIG_MPIC_WEIRD is not set @@ -227,12 +212,11 @@ CONFIG_CPU_FREQ_PMAC=y CONFIG_PPC601_SYNC_FIX=y # CONFIG_TAU is not set # CONFIG_FSL_ULI1575 is not set -# CONFIG_SIMPLE_GPIO is not set # # Kernel options # -CONFIG_HIGHMEM=y +# CONFIG_HIGHMEM is not set CONFIG_TICK_ONESHOT=y CONFIG_NO_HZ=y CONFIG_HIGH_RES_TIMERS=y @@ -255,7 +239,6 @@ CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set -# CONFIG_CRASH_DUMP is not set CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y CONFIG_SELECT_MEMORY_MODEL=y @@ -267,17 +250,12 @@ CONFIG_FLAT_NODE_MEM_MAP=y CONFIG_PAGEFLAGS_EXTENDED=y CONFIG_SPLIT_PTLOCK_CPUS=4 # CONFIG_MIGRATION is not set +# CONFIG_RESOURCES_64BIT is not set # CONFIG_PHYS_ADDR_T_64BIT is not set CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y CONFIG_UNEVICTABLE_LRU=y -CONFIG_HAVE_MLOCK=y -CONFIG_HAVE_MLOCKED_PAGE_BIT=y -CONFIG_PPC_4K_PAGES=y -# CONFIG_PPC_16K_PAGES is not set -# CONFIG_PPC_64K_PAGES is not set -# CONFIG_PPC_256K_PAGES is not set CONFIG_FORCE_MAX_ZONEORDER=11 CONFIG_PROC_DEVICETREE=y # CONFIG_CMDLINE_BOOL is not set @@ -310,8 +288,6 @@ CONFIG_ARCH_SUPPORTS_MSI=y # CONFIG_PCI_MSI is not set # CONFIG_PCI_LEGACY is not set # CONFIG_PCI_DEBUG is not set -# CONFIG_PCI_STUB is not set -# CONFIG_PCI_IOV is not set CONFIG_PCCARD=m # CONFIG_PCMCIA_DEBUG is not set CONFIG_PCMCIA=m @@ -421,8 +397,6 @@ CONFIG_NETFILTER_XTABLES=m CONFIG_NETFILTER_XT_TARGET_CLASSIFY=m # CONFIG_NETFILTER_XT_TARGET_CONNMARK is not set # CONFIG_NETFILTER_XT_TARGET_DSCP is not set -CONFIG_NETFILTER_XT_TARGET_HL=m -# CONFIG_NETFILTER_XT_TARGET_LED is not set CONFIG_NETFILTER_XT_TARGET_MARK=m CONFIG_NETFILTER_XT_TARGET_NFLOG=m CONFIG_NETFILTER_XT_TARGET_NFQUEUE=m @@ -431,7 +405,6 @@ CONFIG_NETFILTER_XT_TARGET_RATEEST=m CONFIG_NETFILTER_XT_TARGET_TRACE=m CONFIG_NETFILTER_XT_TARGET_TCPMSS=m CONFIG_NETFILTER_XT_TARGET_TCPOPTSTRIP=m -# CONFIG_NETFILTER_XT_MATCH_CLUSTER is not set CONFIG_NETFILTER_XT_MATCH_COMMENT=m # CONFIG_NETFILTER_XT_MATCH_CONNBYTES is not set CONFIG_NETFILTER_XT_MATCH_CONNLIMIT=m @@ -442,7 +415,6 @@ CONFIG_NETFILTER_XT_MATCH_DSCP=m CONFIG_NETFILTER_XT_MATCH_ESP=m # CONFIG_NETFILTER_XT_MATCH_HASHLIMIT is not set CONFIG_NETFILTER_XT_MATCH_HELPER=m -CONFIG_NETFILTER_XT_MATCH_HL=m CONFIG_NETFILTER_XT_MATCH_IPRANGE=m CONFIG_NETFILTER_XT_MATCH_LENGTH=m CONFIG_NETFILTER_XT_MATCH_LIMIT=m @@ -506,15 +478,17 @@ CONFIG_IP_NF_ARPFILTER=m CONFIG_IP_NF_ARP_MANGLE=m CONFIG_IP_DCCP=m CONFIG_INET_DCCP_DIAG=m +CONFIG_IP_DCCP_ACKVEC=y # # DCCP CCIDs Configuration (EXPERIMENTAL) # +CONFIG_IP_DCCP_CCID2=m # CONFIG_IP_DCCP_CCID2_DEBUG is not set -CONFIG_IP_DCCP_CCID3=y +CONFIG_IP_DCCP_CCID3=m # CONFIG_IP_DCCP_CCID3_DEBUG is not set CONFIG_IP_DCCP_CCID3_RTO=100 -CONFIG_IP_DCCP_TFRC_LIB=y +CONFIG_IP_DCCP_TFRC_LIB=m # # DCCP Kernel Hacking @@ -534,16 +508,13 @@ CONFIG_IP_DCCP_TFRC_LIB=y # CONFIG_LAPB is not set # CONFIG_ECONET is not set # CONFIG_WAN_ROUTER is not set -# CONFIG_PHONET is not set # CONFIG_NET_SCHED is not set CONFIG_NET_CLS_ROUTE=y -# CONFIG_DCB is not set # # Network testing # # CONFIG_NET_PKTGEN is not set -# CONFIG_NET_DROP_MONITOR is not set # CONFIG_HAMRADIO is not set # CONFIG_CAN is not set CONFIG_IRDA=m @@ -606,6 +577,8 @@ CONFIG_BT_HIDP=m # # Bluetooth device drivers # +CONFIG_BT_HCIUSB=m +# CONFIG_BT_HCIUSB_SCO is not set # CONFIG_BT_HCIBTUSB is not set # CONFIG_BT_HCIUART is not set CONFIG_BT_HCIBCM203X=m @@ -617,27 +590,31 @@ CONFIG_BT_HCIBFUSB=m # CONFIG_BT_HCIBTUART is not set # CONFIG_BT_HCIVHCI is not set # CONFIG_AF_RXRPC is not set +# CONFIG_PHONET is not set CONFIG_WIRELESS=y CONFIG_CFG80211=m -# CONFIG_CFG80211_REG_DEBUG is not set +CONFIG_NL80211=y CONFIG_WIRELESS_OLD_REGULATORY=y CONFIG_WIRELESS_EXT=y CONFIG_WIRELESS_EXT_SYSFS=y -# CONFIG_LIB80211 is not set CONFIG_MAC80211=m # # Rate control algorithm selection # -CONFIG_MAC80211_RC_MINSTREL=y -# CONFIG_MAC80211_RC_DEFAULT_PID is not set -CONFIG_MAC80211_RC_DEFAULT_MINSTREL=y -CONFIG_MAC80211_RC_DEFAULT="minstrel" +CONFIG_MAC80211_RC_PID=y +# CONFIG_MAC80211_RC_MINSTREL is not set +CONFIG_MAC80211_RC_DEFAULT_PID=y +# CONFIG_MAC80211_RC_DEFAULT_MINSTREL is not set +CONFIG_MAC80211_RC_DEFAULT="pid" # CONFIG_MAC80211_MESH is not set CONFIG_MAC80211_LEDS=y -# CONFIG_MAC80211_DEBUGFS is not set # CONFIG_MAC80211_DEBUG_MENU is not set -# CONFIG_WIMAX is not set +CONFIG_IEEE80211=m +# CONFIG_IEEE80211_DEBUG is not set +CONFIG_IEEE80211_CRYPT_WEP=m +CONFIG_IEEE80211_CRYPT_CCMP=m +CONFIG_IEEE80211_CRYPT_TKIP=m # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -685,27 +662,17 @@ CONFIG_BLK_DEV_RAM_SIZE=4096 # CONFIG_BLK_DEV_HD is not set CONFIG_MISC_DEVICES=y # CONFIG_PHANTOM is not set +# CONFIG_EEPROM_93CX6 is not set # CONFIG_SGI_IOC4 is not set # CONFIG_TIFM_CORE is not set -# CONFIG_ICS932S401 is not set # CONFIG_ENCLOSURE_SERVICES is not set # CONFIG_HP_ILO is not set -# CONFIG_ISL29003 is not set -# CONFIG_C2PORT is not set - -# -# EEPROM support -# -# CONFIG_EEPROM_AT24 is not set -# CONFIG_EEPROM_LEGACY is not set -# CONFIG_EEPROM_93CX6 is not set CONFIG_HAVE_IDE=y CONFIG_IDE=y # # Please see Documentation/ide/ide.txt for help/info on IDE drives # -CONFIG_IDE_XFER_MODE=y CONFIG_IDE_TIMINGS=y CONFIG_IDE_ATAPI=y # CONFIG_BLK_DEV_IDE_SATA is not set @@ -717,6 +684,7 @@ CONFIG_BLK_DEV_IDECS=m CONFIG_BLK_DEV_IDECD=y CONFIG_BLK_DEV_IDECD_VERBOSE_ERRORS=y # CONFIG_BLK_DEV_IDETAPE is not set +CONFIG_BLK_DEV_IDESCSI=y # CONFIG_IDE_TASK_IOCTL is not set CONFIG_IDE_PROC_FS=y @@ -746,7 +714,6 @@ CONFIG_BLK_DEV_IDEDMA_PCI=y # CONFIG_BLK_DEV_JMICRON is not set # CONFIG_BLK_DEV_SC1200 is not set # CONFIG_BLK_DEV_PIIX is not set -# CONFIG_BLK_DEV_IT8172 is not set # CONFIG_BLK_DEV_IT8213 is not set # CONFIG_BLK_DEV_IT821X is not set # CONFIG_BLK_DEV_NS87415 is not set @@ -761,6 +728,7 @@ CONFIG_BLK_DEV_SL82C105=y # CONFIG_BLK_DEV_TC86C001 is not set CONFIG_BLK_DEV_IDE_PMAC=y CONFIG_BLK_DEV_IDE_PMAC_ATA100FIRST=y +CONFIG_BLK_DEV_IDEDMA_PMAC=y CONFIG_BLK_DEV_IDEDMA=y # @@ -804,7 +772,6 @@ CONFIG_SCSI_FC_ATTRS=y # CONFIG_SCSI_SRP_ATTRS is not set CONFIG_SCSI_LOWLEVEL=y # CONFIG_ISCSI_TCP is not set -# CONFIG_SCSI_CXGB3_ISCSI is not set # CONFIG_BLK_DEV_3W_XXXX_RAID is not set # CONFIG_SCSI_3W_9XXX is not set # CONFIG_SCSI_ACARD is not set @@ -824,12 +791,8 @@ CONFIG_SCSI_AIC7XXX_OLD=m # CONFIG_MEGARAID_NEWGEN is not set # CONFIG_MEGARAID_LEGACY is not set # CONFIG_MEGARAID_SAS is not set -# CONFIG_SCSI_MPT2SAS is not set # CONFIG_SCSI_HPTIOP is not set # CONFIG_SCSI_BUSLOGIC is not set -# CONFIG_LIBFC is not set -# CONFIG_LIBFCOE is not set -# CONFIG_FCOE is not set # CONFIG_SCSI_DMX3191D is not set # CONFIG_SCSI_EATA is not set # CONFIG_SCSI_FUTURE_DOMAIN is not set @@ -859,7 +822,6 @@ CONFIG_SCSI_MAC53C94=y # CONFIG_SCSI_SRP is not set # CONFIG_SCSI_LOWLEVEL_PCMCIA is not set # CONFIG_SCSI_DH is not set -# CONFIG_SCSI_OSD_INITIATOR is not set # CONFIG_ATA is not set CONFIG_MD=y CONFIG_BLK_DEV_MD=m @@ -919,7 +881,6 @@ CONFIG_THERM_ADT746X=m # CONFIG_ANSLCD is not set CONFIG_PMAC_RACKMETER=m CONFIG_NETDEVICES=y -CONFIG_COMPAT_NET_DEV_OPS=y CONFIG_DUMMY=m # CONFIG_BONDING is not set # CONFIG_MACVLAN is not set @@ -937,8 +898,6 @@ CONFIG_BMAC=y CONFIG_SUNGEM=y # CONFIG_CASSINI is not set # CONFIG_NET_VENDOR_3COM is not set -# CONFIG_ETHOC is not set -# CONFIG_DNET is not set # CONFIG_NET_TULIP is not set # CONFIG_HP100 is not set # CONFIG_IBM_NEW_EMAC_ZMII is not set @@ -954,6 +913,7 @@ CONFIG_PCNET32=y # CONFIG_ADAPTEC_STARFIRE is not set # CONFIG_B44 is not set # CONFIG_FORCEDETH is not set +# CONFIG_EEPRO100 is not set # CONFIG_E100 is not set # CONFIG_FEALNX is not set # CONFIG_NATSEMI is not set @@ -963,7 +923,6 @@ CONFIG_PCNET32=y # CONFIG_R6040 is not set # CONFIG_SIS900 is not set # CONFIG_EPIC100 is not set -# CONFIG_SMSC9420 is not set # CONFIG_SUNDANCE is not set # CONFIG_TLAN is not set # CONFIG_VIA_RHINE is not set @@ -976,7 +935,6 @@ CONFIG_NETDEV_1000=y # CONFIG_E1000E is not set # CONFIG_IP1000 is not set # CONFIG_IGB is not set -# CONFIG_IGBVF is not set # CONFIG_NS83820 is not set # CONFIG_HAMACHI is not set # CONFIG_YELLOWFIN is not set @@ -987,20 +945,18 @@ CONFIG_NETDEV_1000=y # CONFIG_VIA_VELOCITY is not set # CONFIG_TIGON3 is not set # CONFIG_BNX2 is not set +# CONFIG_MV643XX_ETH is not set # CONFIG_QLA3XXX is not set # CONFIG_ATL1 is not set # CONFIG_ATL1E is not set -# CONFIG_ATL1C is not set # CONFIG_JME is not set CONFIG_NETDEV_10000=y # CONFIG_CHELSIO_T1 is not set -CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_CHELSIO_T3 is not set # CONFIG_ENIC is not set # CONFIG_IXGBE is not set # CONFIG_IXGB is not set # CONFIG_S2IO is not set -# CONFIG_VXGE is not set # CONFIG_MYRI10GE is not set # CONFIG_NETXEN_NIC is not set # CONFIG_NIU is not set @@ -1010,7 +966,6 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_BNX2X is not set # CONFIG_QLGE is not set # CONFIG_SFC is not set -# CONFIG_BE2NET is not set # CONFIG_TR is not set # @@ -1019,11 +974,20 @@ CONFIG_CHELSIO_T3_DEPENDS=y # CONFIG_WLAN_PRE80211 is not set CONFIG_WLAN_80211=y # CONFIG_PCMCIA_RAYCS is not set +# CONFIG_IPW2100 is not set +# CONFIG_IPW2200 is not set # CONFIG_LIBERTAS is not set # CONFIG_LIBERTAS_THINFIRM is not set # CONFIG_AIRO is not set +CONFIG_HERMES=m +CONFIG_APPLE_AIRPORT=m +# CONFIG_PLX_HERMES is not set +# CONFIG_TMD_HERMES is not set +# CONFIG_NORTEL_HERMES is not set +CONFIG_PCI_HERMES=m +CONFIG_PCMCIA_HERMES=m +# CONFIG_PCMCIA_SPECTRUM is not set # CONFIG_ATMEL is not set -# CONFIG_AT76C50X_USB is not set # CONFIG_AIRO_CS is not set # CONFIG_PCMCIA_WL3501 is not set CONFIG_PRISM54=m @@ -1033,17 +997,15 @@ CONFIG_PRISM54=m # CONFIG_RTL8187 is not set # CONFIG_ADM8211 is not set # CONFIG_MAC80211_HWSIM is not set -# CONFIG_MWL8K is not set CONFIG_P54_COMMON=m # CONFIG_P54_USB is not set # CONFIG_P54_PCI is not set -CONFIG_P54_LEDS=y # CONFIG_ATH5K is not set # CONFIG_ATH9K is not set -# CONFIG_AR9170_USB is not set -# CONFIG_IPW2100 is not set -# CONFIG_IPW2200 is not set -# CONFIG_IWLWIFI is not set +# CONFIG_IWLCORE is not set +# CONFIG_IWLWIFI_LEDS is not set +# CONFIG_IWLAGN is not set +# CONFIG_IWL3945 is not set # CONFIG_HOSTAP is not set CONFIG_B43=m CONFIG_B43_PCI_AUTOSELECT=y @@ -1063,19 +1025,6 @@ CONFIG_B43LEGACY_DMA_AND_PIO_MODE=y # CONFIG_B43LEGACY_PIO_MODE is not set # CONFIG_ZD1211RW is not set # CONFIG_RT2X00 is not set -CONFIG_HERMES=m -CONFIG_HERMES_CACHE_FW_ON_INIT=y -CONFIG_APPLE_AIRPORT=m -# CONFIG_PLX_HERMES is not set -# CONFIG_TMD_HERMES is not set -# CONFIG_NORTEL_HERMES is not set -CONFIG_PCI_HERMES=m -CONFIG_PCMCIA_HERMES=m -# CONFIG_PCMCIA_SPECTRUM is not set - -# -# Enable WiMAX (Networking options) to see the WiMAX drivers -# # # USB Network Adapters @@ -1087,7 +1036,6 @@ CONFIG_PCMCIA_HERMES=m CONFIG_USB_USBNET=m CONFIG_USB_NET_AX8817X=m CONFIG_USB_NET_CDCETHER=m -# CONFIG_USB_NET_CDC_EEM is not set # CONFIG_USB_NET_DM9601 is not set # CONFIG_USB_NET_SMSC95XX is not set # CONFIG_USB_NET_GL620A is not set @@ -1151,7 +1099,7 @@ CONFIG_INPUT_KEYBOARD=y CONFIG_INPUT_MOUSE=y # CONFIG_MOUSE_PS2 is not set # CONFIG_MOUSE_SERIAL is not set -CONFIG_MOUSE_APPLETOUCH=y +# CONFIG_MOUSE_APPLETOUCH is not set # CONFIG_MOUSE_BCM5974 is not set # CONFIG_MOUSE_VSXXXAA is not set # CONFIG_INPUT_JOYSTICK is not set @@ -1202,13 +1150,10 @@ CONFIG_SERIAL_PMACZILOG_TTYS=y # CONFIG_SERIAL_JSM is not set # CONFIG_SERIAL_OF_PLATFORM is not set CONFIG_UNIX98_PTYS=y -# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set CONFIG_LEGACY_PTYS=y CONFIG_LEGACY_PTY_COUNT=256 -# CONFIG_HVC_UDBG is not set # CONFIG_IPMI_HANDLER is not set CONFIG_HW_RANDOM=m -# CONFIG_HW_RANDOM_TIMERIOMEM is not set CONFIG_NVRAM=y CONFIG_GEN_RTC=y # CONFIG_GEN_RTC_X is not set @@ -1287,9 +1232,12 @@ CONFIG_I2C_POWERMAC=y # Miscellaneous I2C Chip support # # CONFIG_DS1682 is not set +# CONFIG_EEPROM_AT24 is not set +# CONFIG_EEPROM_LEGACY is not set # CONFIG_SENSORS_PCF8574 is not set # CONFIG_PCF8575 is not set # CONFIG_SENSORS_PCA9539 is not set +# CONFIG_SENSORS_PCF8591 is not set # CONFIG_SENSORS_MAX6875 is not set # CONFIG_SENSORS_TSL2550 is not set # CONFIG_I2C_DEBUG_CORE is not set @@ -1311,11 +1259,11 @@ CONFIG_BATTERY_PMU=y # CONFIG_THERMAL is not set # CONFIG_THERMAL_HWMON is not set # CONFIG_WATCHDOG is not set -CONFIG_SSB_POSSIBLE=y # # Sonics Silicon Backplane # +CONFIG_SSB_POSSIBLE=y CONFIG_SSB=m CONFIG_SSB_SPROM=y CONFIG_SSB_PCIHOST_POSSIBLE=y @@ -1333,13 +1281,18 @@ CONFIG_SSB_DRIVER_PCICORE=y # CONFIG_MFD_CORE is not set # CONFIG_MFD_SM501 is not set # CONFIG_HTC_PASIC3 is not set -# CONFIG_TWL4030_CORE is not set # CONFIG_MFD_TMIO is not set # CONFIG_PMIC_DA903X is not set # CONFIG_MFD_WM8400 is not set # CONFIG_MFD_WM8350_I2C is not set -# CONFIG_MFD_PCF50633 is not set + +# +# Voltage and Current regulators +# # CONFIG_REGULATOR is not set +# CONFIG_REGULATOR_FIXED_VOLTAGE is not set +# CONFIG_REGULATOR_VIRTUAL_CONSUMER is not set +# CONFIG_REGULATOR_BQ24022 is not set # # Multimedia devices @@ -1437,7 +1390,6 @@ CONFIG_FB_ATY_BACKLIGHT=y # CONFIG_FB_KYRO is not set CONFIG_FB_3DFX=y # CONFIG_FB_3DFX_ACCEL is not set -CONFIG_FB_3DFX_I2C=y # CONFIG_FB_VOODOO1 is not set # CONFIG_FB_VT8623 is not set # CONFIG_FB_TRIDENT is not set @@ -1447,14 +1399,12 @@ CONFIG_FB_3DFX_I2C=y # CONFIG_FB_IBM_GXT4500 is not set # CONFIG_FB_VIRTUAL is not set # CONFIG_FB_METRONOME is not set -# CONFIG_FB_MB862XX is not set -# CONFIG_FB_BROADSHEET is not set CONFIG_BACKLIGHT_LCD_SUPPORT=y CONFIG_LCD_CLASS_DEVICE=m # CONFIG_LCD_ILI9320 is not set # CONFIG_LCD_PLATFORM is not set CONFIG_BACKLIGHT_CLASS_DEVICE=y -CONFIG_BACKLIGHT_GENERIC=y +# CONFIG_BACKLIGHT_CORGI is not set # # Display device support @@ -1494,13 +1444,11 @@ CONFIG_SND_MIXER_OSS=m CONFIG_SND_PCM_OSS=m CONFIG_SND_PCM_OSS_PLUGINS=y CONFIG_SND_SEQUENCER_OSS=y -# CONFIG_SND_HRTIMER is not set # CONFIG_SND_DYNAMIC_MINORS is not set CONFIG_SND_SUPPORT_OLD_API=y CONFIG_SND_VERBOSE_PROCFS=y # CONFIG_SND_VERBOSE_PRINTK is not set # CONFIG_SND_DEBUG is not set -CONFIG_SND_VMASTER=y CONFIG_SND_DRIVERS=y CONFIG_SND_DUMMY=m # CONFIG_SND_VIRMIDI is not set @@ -1538,8 +1486,6 @@ CONFIG_SND_PCI=y # CONFIG_SND_INDIGO is not set # CONFIG_SND_INDIGOIO is not set # CONFIG_SND_INDIGODJ is not set -# CONFIG_SND_INDIGOIOX is not set -# CONFIG_SND_INDIGODJX is not set # CONFIG_SND_EMU10K1 is not set # CONFIG_SND_EMU10K1X is not set # CONFIG_SND_ENS1370 is not set @@ -1605,31 +1551,28 @@ CONFIG_USB_HID=y # # Special HID drivers # +CONFIG_HID_COMPAT=y CONFIG_HID_A4TECH=y CONFIG_HID_APPLE=y CONFIG_HID_BELKIN=y +CONFIG_HID_BRIGHT=y CONFIG_HID_CHERRY=y CONFIG_HID_CHICONY=y CONFIG_HID_CYPRESS=y -# CONFIG_DRAGONRISE_FF is not set +CONFIG_HID_DELL=y CONFIG_HID_EZKEY=y -CONFIG_HID_KYE=y CONFIG_HID_GYRATION=y -CONFIG_HID_KENSINGTON=y CONFIG_HID_LOGITECH=y # CONFIG_LOGITECH_FF is not set # CONFIG_LOGIRUMBLEPAD2_FF is not set CONFIG_HID_MICROSOFT=y CONFIG_HID_MONTEREY=y -CONFIG_HID_NTRIG=y CONFIG_HID_PANTHERLORD=y # CONFIG_PANTHERLORD_FF is not set CONFIG_HID_PETALYNX=y CONFIG_HID_SAMSUNG=y CONFIG_HID_SONY=y CONFIG_HID_SUNPLUS=y -# CONFIG_GREENASIA_FF is not set -CONFIG_HID_TOPSEED=y # CONFIG_THRUSTMASTER_FF is not set # CONFIG_ZEROPLUS_FF is not set CONFIG_USB_SUPPORT=y @@ -1660,7 +1603,6 @@ CONFIG_USB_EHCI_HCD=m CONFIG_USB_EHCI_ROOT_HUB_TT=y # CONFIG_USB_EHCI_TT_NEWSCHED is not set # CONFIG_USB_EHCI_HCD_PPC_OF is not set -# CONFIG_USB_OXU210HP_HCD is not set # CONFIG_USB_ISP116X_HCD is not set # CONFIG_USB_ISP1760_HCD is not set CONFIG_USB_OHCI_HCD=y @@ -1683,23 +1625,24 @@ CONFIG_USB_PRINTER=m # CONFIG_USB_TMC is not set # -# NOTE: USB_STORAGE depends on SCSI but BLK_DEV_SD may +# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' # # -# also be needed; see USB_STORAGE Help for more info +# may also be needed; see USB_STORAGE Help for more information # CONFIG_USB_STORAGE=m # CONFIG_USB_STORAGE_DEBUG is not set # CONFIG_USB_STORAGE_DATAFAB is not set # CONFIG_USB_STORAGE_FREECOM is not set # CONFIG_USB_STORAGE_ISD200 is not set +# CONFIG_USB_STORAGE_DPCM is not set # CONFIG_USB_STORAGE_USBAT is not set # CONFIG_USB_STORAGE_SDDR09 is not set # CONFIG_USB_STORAGE_SDDR55 is not set # CONFIG_USB_STORAGE_JUMPSHOT is not set # CONFIG_USB_STORAGE_ALAUDA is not set -CONFIG_USB_STORAGE_ONETOUCH=m +CONFIG_USB_STORAGE_ONETOUCH=y # CONFIG_USB_STORAGE_KARMA is not set # CONFIG_USB_STORAGE_CYPRESS_ATACB is not set # CONFIG_USB_LIBUSUAL is not set @@ -1722,7 +1665,7 @@ CONFIG_USB_EZUSB=y # CONFIG_USB_SERIAL_CH341 is not set # CONFIG_USB_SERIAL_WHITEHEAT is not set # CONFIG_USB_SERIAL_DIGI_ACCELEPORT is not set -# CONFIG_USB_SERIAL_CP210X is not set +# CONFIG_USB_SERIAL_CP2101 is not set # CONFIG_USB_SERIAL_CYPRESS_M8 is not set # CONFIG_USB_SERIAL_EMPEG is not set # CONFIG_USB_SERIAL_FTDI_SIO is not set @@ -1758,19 +1701,15 @@ CONFIG_USB_SERIAL_KEYSPAN_USA49WLC=y # CONFIG_USB_SERIAL_NAVMAN is not set # CONFIG_USB_SERIAL_PL2303 is not set # CONFIG_USB_SERIAL_OTI6858 is not set -# CONFIG_USB_SERIAL_QUALCOMM is not set # CONFIG_USB_SERIAL_SPCP8X5 is not set # CONFIG_USB_SERIAL_HP4X is not set # CONFIG_USB_SERIAL_SAFE is not set -# CONFIG_USB_SERIAL_SIEMENS_MPI is not set # CONFIG_USB_SERIAL_SIERRAWIRELESS is not set -# CONFIG_USB_SERIAL_SYMBOL is not set # CONFIG_USB_SERIAL_TI is not set # CONFIG_USB_SERIAL_CYBERJACK is not set # CONFIG_USB_SERIAL_XIRCOM is not set # CONFIG_USB_SERIAL_OPTION is not set # CONFIG_USB_SERIAL_OMNINET is not set -# CONFIG_USB_SERIAL_OPTICON is not set # CONFIG_USB_SERIAL_DEBUG is not set # @@ -1787,6 +1726,7 @@ CONFIG_USB_SERIAL_KEYSPAN_USA49WLC=y # CONFIG_USB_LED is not set # CONFIG_USB_CYPRESS_CY7C63 is not set # CONFIG_USB_CYTHERM is not set +# CONFIG_USB_PHIDGET is not set # CONFIG_USB_IDMOUSE is not set # CONFIG_USB_FTDI_ELAN is not set CONFIG_USB_APPLEDISPLAY=m @@ -1798,11 +1738,6 @@ CONFIG_USB_APPLEDISPLAY=m # CONFIG_USB_ISIGHTFW is not set # CONFIG_USB_VST is not set # CONFIG_USB_GADGET is not set - -# -# OTG and related infrastructure -# -# CONFIG_NOP_USB_XCEIV is not set # CONFIG_UWB is not set # CONFIG_MMC is not set # CONFIG_MEMSTICK is not set @@ -1813,9 +1748,7 @@ CONFIG_LEDS_CLASS=y # LED drivers # # CONFIG_LEDS_PCA9532 is not set -# CONFIG_LEDS_LP5521 is not set # CONFIG_LEDS_PCA955X is not set -# CONFIG_LEDS_BD2802 is not set # # LED Triggers @@ -1826,16 +1759,11 @@ CONFIG_LEDS_TRIGGER_IDE_DISK=y # CONFIG_LEDS_TRIGGER_HEARTBEAT is not set # CONFIG_LEDS_TRIGGER_BACKLIGHT is not set CONFIG_LEDS_TRIGGER_DEFAULT_ON=y - -# -# iptables trigger is under Netfilter config (LED target) -# # CONFIG_ACCESSIBILITY is not set # CONFIG_INFINIBAND is not set # CONFIG_EDAC is not set # CONFIG_RTC_CLASS is not set # CONFIG_DMADEVICES is not set -# CONFIG_AUXDISPLAY is not set # CONFIG_UIO is not set # CONFIG_STAGING is not set @@ -1846,7 +1774,6 @@ CONFIG_EXT2_FS=y # CONFIG_EXT2_FS_XATTR is not set # CONFIG_EXT2_FS_XIP is not set CONFIG_EXT3_FS=y -# CONFIG_EXT3_DEFAULTS_TO_ORDERED is not set CONFIG_EXT3_FS_XATTR=y CONFIG_EXT3_FS_POSIX_ACL=y # CONFIG_EXT3_FS_SECURITY is not set @@ -1856,9 +1783,7 @@ CONFIG_EXT4_FS_XATTR=y # CONFIG_EXT4_FS_POSIX_ACL is not set # CONFIG_EXT4_FS_SECURITY is not set CONFIG_JBD=y -# CONFIG_JBD_DEBUG is not set CONFIG_JBD2=y -# CONFIG_JBD2_DEBUG is not set CONFIG_FS_MBCACHE=y # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set @@ -1867,7 +1792,6 @@ CONFIG_FILE_LOCKING=y # CONFIG_XFS_FS is not set # CONFIG_GFS2_FS is not set # CONFIG_OCFS2_FS is not set -# CONFIG_BTRFS_FS is not set CONFIG_DNOTIFY=y CONFIG_INOTIFY=y CONFIG_INOTIFY_USER=y @@ -1876,11 +1800,6 @@ CONFIG_INOTIFY_USER=y CONFIG_AUTOFS4_FS=m CONFIG_FUSE_FS=m -# -# Caches -# -# CONFIG_FSCACHE is not set - # # CD-ROM/DVD Filesystems # @@ -1912,7 +1831,10 @@ CONFIG_TMPFS=y # CONFIG_TMPFS_POSIX_ACL is not set # CONFIG_HUGETLB_PAGE is not set # CONFIG_CONFIGFS_FS is not set -CONFIG_MISC_FILESYSTEMS=y + +# +# Miscellaneous filesystems +# # CONFIG_ADFS_FS is not set # CONFIG_AFFS_FS is not set CONFIG_HFS_FS=m @@ -1921,7 +1843,6 @@ CONFIG_HFSPLUS_FS=m # CONFIG_BFS_FS is not set # CONFIG_EFS_FS is not set # CONFIG_CRAMFS is not set -# CONFIG_SQUASHFS is not set # CONFIG_VXFS_FS is not set # CONFIG_MINIX_FS is not set # CONFIG_OMFS_FS is not set @@ -1930,7 +1851,6 @@ CONFIG_HFSPLUS_FS=m # CONFIG_ROMFS_FS is not set # CONFIG_SYSV_FS is not set # CONFIG_UFS_FS is not set -# CONFIG_NILFS2_FS is not set CONFIG_NETWORK_FILESYSTEMS=y CONFIG_NFS_FS=y CONFIG_NFS_V3=y @@ -1948,6 +1868,7 @@ CONFIG_NFS_ACL_SUPPORT=y CONFIG_NFS_COMMON=y CONFIG_SUNRPC=y CONFIG_SUNRPC_GSS=y +# CONFIG_SUNRPC_REGISTER_V4 is not set CONFIG_RPCSEC_GSS_KRB5=y # CONFIG_RPCSEC_GSS_SPKM3 is not set CONFIG_SMB_FS=m @@ -2019,13 +1940,11 @@ CONFIG_NLS_ISO8859_1=m # CONFIG_NLS_KOI8_U is not set CONFIG_NLS_UTF8=m # CONFIG_DLM is not set -CONFIG_BINARY_PRINTF=y # # Library routines # CONFIG_BITREVERSE=y -CONFIG_GENERIC_FIND_LAST_BIT=y CONFIG_CRC_CCITT=y CONFIG_CRC16=y CONFIG_CRC_T10DIF=y @@ -2035,18 +1954,15 @@ CONFIG_CRC32=y CONFIG_LIBCRC32C=m CONFIG_ZLIB_INFLATE=y CONFIG_ZLIB_DEFLATE=y -CONFIG_DECOMPRESS_GZIP=y -CONFIG_DECOMPRESS_BZIP2=y -CONFIG_DECOMPRESS_LZMA=y CONFIG_TEXTSEARCH=y CONFIG_TEXTSEARCH_KMP=m CONFIG_TEXTSEARCH_BM=m CONFIG_TEXTSEARCH_FSM=m +CONFIG_PLIST=y CONFIG_HAS_IOMEM=y CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_HAVE_LMB=y -CONFIG_NLATTR=y # # Kernel hacking @@ -2057,16 +1973,13 @@ CONFIG_ENABLE_MUST_CHECK=y CONFIG_FRAME_WARN=1024 CONFIG_MAGIC_SYSRQ=y # CONFIG_UNUSED_SYMBOLS is not set -CONFIG_DEBUG_FS=y +# CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set CONFIG_DEBUG_KERNEL=y # CONFIG_DEBUG_SHIRQ is not set CONFIG_DETECT_SOFTLOCKUP=y # CONFIG_BOOTPARAM_SOFTLOCKUP_PANIC is not set CONFIG_BOOTPARAM_SOFTLOCKUP_PANIC_VALUE=0 -CONFIG_DETECT_HUNG_TASK=y -# CONFIG_BOOTPARAM_HUNG_TASK_PANIC is not set -CONFIG_BOOTPARAM_HUNG_TASK_PANIC_VALUE=0 CONFIG_SCHED_DEBUG=y CONFIG_SCHEDSTATS=y # CONFIG_TIMER_STATS is not set @@ -2081,7 +1994,6 @@ CONFIG_SCHEDSTATS=y # CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set CONFIG_STACKTRACE=y # CONFIG_DEBUG_KOBJECT is not set -# CONFIG_DEBUG_HIGHMEM is not set CONFIG_DEBUG_BUGVERBOSE=y # CONFIG_DEBUG_INFO is not set # CONFIG_DEBUG_VM is not set @@ -2089,7 +2001,6 @@ CONFIG_DEBUG_BUGVERBOSE=y CONFIG_DEBUG_MEMORY_INIT=y # CONFIG_DEBUG_LIST is not set # CONFIG_DEBUG_SG is not set -# CONFIG_DEBUG_NOTIFIERS is not set # CONFIG_BOOT_PRINTK_DELAY is not set # CONFIG_RCU_TORTURE_TEST is not set # CONFIG_RCU_CPU_STALL_DETECTOR is not set @@ -2098,14 +2009,7 @@ CONFIG_DEBUG_MEMORY_INIT=y # CONFIG_FAULT_INJECTION is not set CONFIG_LATENCYTOP=y CONFIG_SYSCTL_SYSCALL_CHECK=y -CONFIG_NOP_TRACER=y CONFIG_HAVE_FUNCTION_TRACER=y -CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y -CONFIG_HAVE_DYNAMIC_FTRACE=y -CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y -CONFIG_RING_BUFFER=y -CONFIG_TRACING=y -CONFIG_TRACING_SUPPORT=y # # Tracers @@ -2113,19 +2017,12 @@ CONFIG_TRACING_SUPPORT=y # CONFIG_FUNCTION_TRACER is not set # CONFIG_SCHED_TRACER is not set # CONFIG_CONTEXT_SWITCH_TRACER is not set -# CONFIG_EVENT_TRACER is not set # CONFIG_BOOT_TRACER is not set -# CONFIG_TRACE_BRANCH_PROFILING is not set # CONFIG_STACK_TRACER is not set -# CONFIG_KMEMTRACE is not set -# CONFIG_WORKQUEUE_TRACER is not set -# CONFIG_BLK_DEV_IO_TRACE is not set -# CONFIG_FTRACE_STARTUP_TEST is not set -# CONFIG_DYNAMIC_DEBUG is not set +# CONFIG_DYNAMIC_PRINTK_DEBUG is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y # CONFIG_KGDB is not set -CONFIG_PRINT_STACK_DEPTH=64 # CONFIG_DEBUG_STACKOVERFLOW is not set # CONFIG_DEBUG_STACK_USAGE is not set # CONFIG_CODE_PATCHING_SELFTEST is not set @@ -2136,7 +2033,6 @@ CONFIG_XMON_DEFAULT=y CONFIG_XMON_DISASSEMBLY=y CONFIG_DEBUGGER=y CONFIG_IRQSTACKS=y -# CONFIG_VIRQ_DEBUG is not set # CONFIG_BDI_SWITCH is not set CONFIG_BOOTX_TEXT=y # CONFIG_PPC_EARLY_DEBUG is not set @@ -2155,20 +2051,13 @@ CONFIG_CRYPTO=y # # CONFIG_CRYPTO_FIPS is not set CONFIG_CRYPTO_ALGAPI=y -CONFIG_CRYPTO_ALGAPI2=y CONFIG_CRYPTO_AEAD=y -CONFIG_CRYPTO_AEAD2=y CONFIG_CRYPTO_BLKCIPHER=y -CONFIG_CRYPTO_BLKCIPHER2=y CONFIG_CRYPTO_HASH=y -CONFIG_CRYPTO_HASH2=y -CONFIG_CRYPTO_RNG2=y -CONFIG_CRYPTO_PCOMP=y +CONFIG_CRYPTO_RNG=y CONFIG_CRYPTO_MANAGER=y -CONFIG_CRYPTO_MANAGER2=y # CONFIG_CRYPTO_GF128MUL is not set CONFIG_CRYPTO_NULL=m -CONFIG_CRYPTO_WORKQUEUE=y # CONFIG_CRYPTO_CRYPTD is not set CONFIG_CRYPTO_AUTHENC=y # CONFIG_CRYPTO_TEST is not set @@ -2238,7 +2127,6 @@ CONFIG_CRYPTO_TWOFISH_COMMON=m # Compression # CONFIG_CRYPTO_DEFLATE=m -# CONFIG_CRYPTO_ZLIB is not set # CONFIG_CRYPTO_LZO is not set # diff --git a/trunk/arch/powerpc/include/asm/mpc52xx_psc.h b/trunk/arch/powerpc/include/asm/mpc52xx_psc.h index fb8412057450..a218da6bec7c 100644 --- a/trunk/arch/powerpc/include/asm/mpc52xx_psc.h +++ b/trunk/arch/powerpc/include/asm/mpc52xx_psc.h @@ -28,10 +28,6 @@ #define MPC52xx_PSC_MAXNUM 6 /* Programmable Serial Controller (PSC) status register bits */ -#define MPC52xx_PSC_SR_UNEX_RX 0x0001 -#define MPC52xx_PSC_SR_DATA_VAL 0x0002 -#define MPC52xx_PSC_SR_DATA_OVR 0x0004 -#define MPC52xx_PSC_SR_CMDSEND 0x0008 #define MPC52xx_PSC_SR_CDE 0x0080 #define MPC52xx_PSC_SR_RXRDY 0x0100 #define MPC52xx_PSC_SR_RXFULL 0x0200 @@ -65,12 +61,6 @@ #define MPC52xx_PSC_RXTX_FIFO_EMPTY 0x0001 /* PSC interrupt status/mask bits */ -#define MPC52xx_PSC_IMR_UNEX_RX_SLOT 0x0001 -#define MPC52xx_PSC_IMR_DATA_VALID 0x0002 -#define MPC52xx_PSC_IMR_DATA_OVR 0x0004 -#define MPC52xx_PSC_IMR_CMD_SEND 0x0008 -#define MPC52xx_PSC_IMR_ERROR 0x0040 -#define MPC52xx_PSC_IMR_DEOF 0x0080 #define MPC52xx_PSC_IMR_TXRDY 0x0100 #define MPC52xx_PSC_IMR_RXRDY 0x0200 #define MPC52xx_PSC_IMR_DB 0x0400 @@ -127,7 +117,6 @@ #define MPC52xx_PSC_SICR_SIM_FIR (0x6 << 24) #define MPC52xx_PSC_SICR_SIM_CODEC_24 (0x7 << 24) #define MPC52xx_PSC_SICR_SIM_CODEC_32 (0xf << 24) -#define MPC52xx_PSC_SICR_AWR (1 << 30) #define MPC52xx_PSC_SICR_GENCLK (1 << 23) #define MPC52xx_PSC_SICR_I2S (1 << 22) #define MPC52xx_PSC_SICR_CLKPOL (1 << 21) diff --git a/trunk/arch/sparc/include/asm/elf_64.h b/trunk/arch/sparc/include/asm/elf_64.h index d42e393078c4..425c2f9be6d5 100644 --- a/trunk/arch/sparc/include/asm/elf_64.h +++ b/trunk/arch/sparc/include/asm/elf_64.h @@ -208,9 +208,8 @@ do { unsigned long new_flags = current_thread_info()->flags; \ else \ clear_thread_flag(TIF_ABI_PENDING); \ /* flush_thread will update pgd cache */ \ - if (personality(current->personality) != PER_LINUX32) \ - set_personality(PER_LINUX | \ - (current->personality & (~PER_MASK))); \ + if (current->personality != PER_LINUX32) \ + set_personality(PER_LINUX); \ } while (0) #endif /* !(__ASM_SPARC64_ELF_H) */ diff --git a/trunk/arch/sparc/lib/csum_copy_from_user.S b/trunk/arch/sparc/lib/csum_copy_from_user.S index e0304e6a2242..a22eddbe5dba 100644 --- a/trunk/arch/sparc/lib/csum_copy_from_user.S +++ b/trunk/arch/sparc/lib/csum_copy_from_user.S @@ -5,7 +5,7 @@ #define EX_LD(x) \ 98: x; \ - .section .fixup, "ax"; \ + .section .fixup; \ .align 4; \ 99: retl; \ mov -1, %o0; \ diff --git a/trunk/arch/sparc/lib/csum_copy_to_user.S b/trunk/arch/sparc/lib/csum_copy_to_user.S index afd01acc587c..d5b12f441f02 100644 --- a/trunk/arch/sparc/lib/csum_copy_to_user.S +++ b/trunk/arch/sparc/lib/csum_copy_to_user.S @@ -5,7 +5,7 @@ #define EX_ST(x) \ 98: x; \ - .section .fixup,"ax"; \ + .section .fixup; \ .align 4; \ 99: retl; \ mov -1, %o0; \ diff --git a/trunk/arch/x86/kernel/cpu/cpufreq/acpi-cpufreq.c b/trunk/arch/x86/kernel/cpu/cpufreq/acpi-cpufreq.c index 752e8c6b2c7e..208ecf6643df 100644 --- a/trunk/arch/x86/kernel/cpu/cpufreq/acpi-cpufreq.c +++ b/trunk/arch/x86/kernel/cpu/cpufreq/acpi-cpufreq.c @@ -550,7 +550,7 @@ static int __init acpi_cpufreq_early_init(void) return -ENOMEM; } for_each_possible_cpu(i) { - if (!zalloc_cpumask_var_node( + if (!alloc_cpumask_var_node( &per_cpu_ptr(acpi_perf_data, i)->shared_cpu_map, GFP_KERNEL, cpu_to_node(i))) { @@ -693,8 +693,8 @@ static int acpi_cpufreq_cpu_init(struct cpufreq_policy *policy) if (perf->control_register.space_id == ACPI_ADR_SPACE_FIXED_HARDWARE && policy->cpuinfo.transition_latency > 20 * 1000) { policy->cpuinfo.transition_latency = 20 * 1000; - printk_once(KERN_INFO - "P-state transition latency capped at 20 uS\n"); + printk_once(KERN_INFO "Capping off P-state tranision" + " latency at 20 uS\n"); } /* table init */ diff --git a/trunk/arch/x86/kernel/cpu/cpufreq/powernow-k7.c b/trunk/arch/x86/kernel/cpu/cpufreq/powernow-k7.c index d47c775eb0ab..a8363e5be4ef 100644 --- a/trunk/arch/x86/kernel/cpu/cpufreq/powernow-k7.c +++ b/trunk/arch/x86/kernel/cpu/cpufreq/powernow-k7.c @@ -322,7 +322,7 @@ static int powernow_acpi_init(void) goto err0; } - if (!zalloc_cpumask_var(&acpi_processor_perf->shared_cpu_map, + if (!alloc_cpumask_var(&acpi_processor_perf->shared_cpu_map, GFP_KERNEL)) { retval = -ENOMEM; goto err05; diff --git a/trunk/arch/x86/kernel/cpu/cpufreq/powernow-k8.c b/trunk/arch/x86/kernel/cpu/cpufreq/powernow-k8.c index cf52215d9eb1..f6b32d112357 100644 --- a/trunk/arch/x86/kernel/cpu/cpufreq/powernow-k8.c +++ b/trunk/arch/x86/kernel/cpu/cpufreq/powernow-k8.c @@ -835,7 +835,7 @@ static int powernow_k8_cpu_init_acpi(struct powernow_k8_data *data) { struct cpufreq_frequency_table *powernow_table; int ret_val = -ENODEV; - acpi_integer control, status; + acpi_integer space_id; if (acpi_processor_register_performance(&data->acpi_data, data->cpu)) { dprintk("register performance failed: bad ACPI data\n"); @@ -848,13 +848,12 @@ static int powernow_k8_cpu_init_acpi(struct powernow_k8_data *data) goto err_out; } - control = data->acpi_data.control_register.space_id; - status = data->acpi_data.status_register.space_id; - - if ((control != ACPI_ADR_SPACE_FIXED_HARDWARE) || - (status != ACPI_ADR_SPACE_FIXED_HARDWARE)) { + space_id = data->acpi_data.control_register.space_id; + if ((space_id != ACPI_ADR_SPACE_FIXED_HARDWARE) || + (space_id != ACPI_ADR_SPACE_FIXED_HARDWARE)) { dprintk("Invalid control/status registers (%x - %x)\n", - control, status); + data->acpi_data.control_register.space_id, + space_id); goto err_out; } @@ -887,7 +886,7 @@ static int powernow_k8_cpu_init_acpi(struct powernow_k8_data *data) /* notify BIOS that we exist */ acpi_processor_notify_smm(THIS_MODULE); - if (!zalloc_cpumask_var(&data->acpi_data.shared_cpu_map, GFP_KERNEL)) { + if (!alloc_cpumask_var(&data->acpi_data.shared_cpu_map, GFP_KERNEL)) { printk(KERN_ERR PFX "unable to alloc powernow_k8_data cpumask\n"); ret_val = -ENOMEM; diff --git a/trunk/arch/x86/kernel/cpu/cpufreq/speedstep-centrino.c b/trunk/arch/x86/kernel/cpu/cpufreq/speedstep-centrino.c index 55c831ed71ce..c9f1fdc02830 100644 --- a/trunk/arch/x86/kernel/cpu/cpufreq/speedstep-centrino.c +++ b/trunk/arch/x86/kernel/cpu/cpufreq/speedstep-centrino.c @@ -471,7 +471,7 @@ static int centrino_target (struct cpufreq_policy *policy, if (unlikely(!alloc_cpumask_var(&saved_mask, GFP_KERNEL))) return -ENOMEM; - if (unlikely(!zalloc_cpumask_var(&covered_cpus, GFP_KERNEL))) { + if (unlikely(!alloc_cpumask_var(&covered_cpus, GFP_KERNEL))) { free_cpumask_var(saved_mask); return -ENOMEM; } diff --git a/trunk/arch/x86/kernel/cpu/mcheck/mce_64.c b/trunk/arch/x86/kernel/cpu/mcheck/mce_64.c index 09dd1d414fc3..6fb0b359d2a5 100644 --- a/trunk/arch/x86/kernel/cpu/mcheck/mce_64.c +++ b/trunk/arch/x86/kernel/cpu/mcheck/mce_64.c @@ -1163,7 +1163,7 @@ static __init int mce_init_device(void) if (!mce_available(&boot_cpu_data)) return -EIO; - zalloc_cpumask_var(&mce_device_initialized, GFP_KERNEL); + alloc_cpumask_var(&mce_device_initialized, GFP_KERNEL); err = mce_init_banks(); if (err) diff --git a/trunk/arch/x86/kernel/tlb_uv.c b/trunk/arch/x86/kernel/tlb_uv.c index 8c7b03b0cfcb..ed0c33761e6d 100644 --- a/trunk/arch/x86/kernel/tlb_uv.c +++ b/trunk/arch/x86/kernel/tlb_uv.c @@ -832,7 +832,7 @@ static int __init uv_bau_init(void) return 0; for_each_possible_cpu(cur_cpu) - zalloc_cpumask_var_node(&per_cpu(uv_flush_tlb_mask, cur_cpu), + alloc_cpumask_var_node(&per_cpu(uv_flush_tlb_mask, cur_cpu), GFP_KERNEL, cpu_to_node(cur_cpu)); uv_bau_retry_limit = 1; diff --git a/trunk/arch/x86/lguest/Makefile b/trunk/arch/x86/lguest/Makefile index 94e0e54056a9..27f0c9ed7f60 100644 --- a/trunk/arch/x86/lguest/Makefile +++ b/trunk/arch/x86/lguest/Makefile @@ -1,2 +1 @@ obj-y := i386_head.o boot.o -CFLAGS_boot.o := $(call cc-option, -fno-stack-protector) diff --git a/trunk/arch/x86/lguest/boot.c b/trunk/arch/x86/lguest/boot.c index 33a93b417396..ca7ec44bafc3 100644 --- a/trunk/arch/x86/lguest/boot.c +++ b/trunk/arch/x86/lguest/boot.c @@ -67,7 +67,6 @@ #include #include #include -#include #include /* for struct machine_ops */ /*G:010 Welcome to the Guest! @@ -1089,21 +1088,13 @@ __init void lguest_init(void) * lguest_init() where the rest of the fairly chaotic boot setup * occurs. */ - /* The stack protector is a weird thing where gcc places a canary - * value on the stack and then checks it on return. This file is - * compiled with -fno-stack-protector it, so we got this far without - * problems. The value of the canary is kept at offset 20 from the - * %gs register, so we need to set that up before calling C functions - * in other files. */ - setup_stack_canary_segment(0); - /* We could just call load_stack_canary_segment(), but we might as - * call switch_to_new_gdt() which loads the whole table and sets up - * the per-cpu segment descriptor register %fs as well. */ - switch_to_new_gdt(0); - /* As described in head_32.S, we map the first 128M of memory. */ max_pfn_mapped = (128*1024*1024) >> PAGE_SHIFT; + /* Load the %fs segment register (the per-cpu segment register) with + * the normal data segment to get through booting. */ + asm volatile ("mov %0, %%fs" : : "r" (__KERNEL_DS) : "memory"); + /* The Host<->Guest Switcher lives at the top of our address space, and * the Host told us how big it is when we made LGUEST_INIT hypercall: * it put the answer in lguest_data.reserve_mem */ diff --git a/trunk/arch/x86/pci/mmconfig-shared.c b/trunk/arch/x86/pci/mmconfig-shared.c index 8766b0e216c5..5fa10bb9604f 100644 --- a/trunk/arch/x86/pci/mmconfig-shared.c +++ b/trunk/arch/x86/pci/mmconfig-shared.c @@ -375,7 +375,7 @@ static acpi_status __init check_mcfg_resource(struct acpi_resource *res, if (!fixmem32) return AE_OK; if ((mcfg_res->start >= fixmem32->address) && - (mcfg_res->end < (fixmem32->address + + (mcfg_res->end <= (fixmem32->address + fixmem32->address_length))) { mcfg_res->flags = 1; return AE_CTRL_TERMINATE; @@ -392,7 +392,7 @@ static acpi_status __init check_mcfg_resource(struct acpi_resource *res, return AE_OK; if ((mcfg_res->start >= address.minimum) && - (mcfg_res->end < (address.minimum + address.address_length))) { + (mcfg_res->end <= (address.minimum + address.address_length))) { mcfg_res->flags = 1; return AE_CTRL_TERMINATE; } @@ -418,7 +418,7 @@ static int __init is_acpi_reserved(u64 start, u64 end, unsigned not_used) struct resource mcfg_res; mcfg_res.start = start; - mcfg_res.end = end - 1; + mcfg_res.end = end; mcfg_res.flags = 0; acpi_get_devices("PNP0C01", find_mboard_resource, &mcfg_res, NULL); diff --git a/trunk/block/bsg.c b/trunk/block/bsg.c index dd81be455e00..206060e795da 100644 --- a/trunk/block/bsg.c +++ b/trunk/block/bsg.c @@ -315,7 +315,6 @@ bsg_map_hdr(struct bsg_device *bd, struct sg_io_v4 *hdr, fmode_t has_write_perm, blk_put_request(rq); if (next_rq) { blk_rq_unmap_user(next_rq->bio); - next_rq->bio = NULL; blk_put_request(next_rq); } return ERR_PTR(ret); @@ -449,7 +448,6 @@ static int blk_complete_sgv4_hdr_rq(struct request *rq, struct sg_io_v4 *hdr, hdr->dout_resid = rq->data_len; hdr->din_resid = rq->next_rq->data_len; blk_rq_unmap_user(bidi_bio); - rq->next_rq->bio = NULL; blk_put_request(rq->next_rq); } else if (rq_data_dir(rq) == READ) hdr->din_resid = rq->data_len; @@ -468,7 +466,6 @@ static int blk_complete_sgv4_hdr_rq(struct request *rq, struct sg_io_v4 *hdr, blk_rq_unmap_user(bio); if (rq->cmd != rq->__cmd) kfree(rq->cmd); - rq->bio = NULL; blk_put_request(rq); return ret; diff --git a/trunk/crypto/ahash.c b/trunk/crypto/ahash.c index f3476374f764..b2d1ee32cfe8 100644 --- a/trunk/crypto/ahash.c +++ b/trunk/crypto/ahash.c @@ -82,11 +82,10 @@ int crypto_hash_walk_done(struct crypto_hash_walk *walk, int err) if (err) return err; - if (nbytes) { - walk->offset = 0; - walk->pg++; + walk->offset = 0; + + if (nbytes) return hash_walk_next(walk); - } if (!walk->total) return 0; diff --git a/trunk/drivers/acpi/pci_bind.c b/trunk/drivers/acpi/pci_bind.c index bc46de3d967f..95650f83ce2e 100644 --- a/trunk/drivers/acpi/pci_bind.c +++ b/trunk/drivers/acpi/pci_bind.c @@ -116,6 +116,9 @@ int acpi_pci_bind(struct acpi_device *device) struct acpi_pci_data *pdata; struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; acpi_handle handle; + struct pci_dev *dev; + struct pci_bus *bus; + if (!device || !device->parent) return -EINVAL; @@ -173,9 +176,20 @@ int acpi_pci_bind(struct acpi_device *device) * Locate matching device in PCI namespace. If it doesn't exist * this typically means that the device isn't currently inserted * (e.g. docking station, port replicator, etc.). + * We cannot simply search the global pci device list, since + * PCI devices are added to the global pci list when the root + * bridge start ops are run, which may not have happened yet. */ - data->dev = pci_get_slot(pdata->bus, - PCI_DEVFN(data->id.device, data->id.function)); + bus = pci_find_bus(data->id.segment, data->id.bus); + if (bus) { + list_for_each_entry(dev, &bus->devices, bus_list) { + if (dev->devfn == PCI_DEVFN(data->id.device, + data->id.function)) { + data->dev = dev; + break; + } + } + } if (!data->dev) { ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Device %04x:%02x:%02x.%d not present in PCI namespace\n", @@ -245,10 +259,9 @@ int acpi_pci_bind(struct acpi_device *device) end: kfree(buffer.pointer); - if (result) { - pci_dev_put(data->dev); + if (result) kfree(data); - } + return result; } @@ -290,7 +303,6 @@ static int acpi_pci_unbind(struct acpi_device *device) if (data->dev->subordinate) { acpi_pci_irq_del_prt(data->id.segment, data->bus->number); } - pci_dev_put(data->dev); kfree(data); end: diff --git a/trunk/drivers/acpi/processor_core.c b/trunk/drivers/acpi/processor_core.c index 23f0fb84f1c1..45ad3288c5ff 100644 --- a/trunk/drivers/acpi/processor_core.c +++ b/trunk/drivers/acpi/processor_core.c @@ -844,7 +844,7 @@ static int acpi_processor_add(struct acpi_device *device) if (!pr) return -ENOMEM; - if (!zalloc_cpumask_var(&pr->throttling.shared_cpu_map, GFP_KERNEL)) { + if (!alloc_cpumask_var(&pr->throttling.shared_cpu_map, GFP_KERNEL)) { kfree(pr); return -ENOMEM; } diff --git a/trunk/drivers/acpi/processor_idle.c b/trunk/drivers/acpi/processor_idle.c index 10a2d913635a..72069ba5f1ed 100644 --- a/trunk/drivers/acpi/processor_idle.c +++ b/trunk/drivers/acpi/processor_idle.c @@ -148,9 +148,6 @@ static void acpi_timer_check_state(int state, struct acpi_processor *pr, if (cpu_has(&cpu_data(pr->id), X86_FEATURE_ARAT)) return; - if (boot_cpu_has(X86_FEATURE_AMDC1E)) - type = ACPI_STATE_C1; - /* * Check, if one of the previous states already marked the lapic * unstable @@ -614,7 +611,6 @@ static int acpi_processor_power_verify(struct acpi_processor *pr) switch (cx->type) { case ACPI_STATE_C1: cx->valid = 1; - acpi_timer_check_state(i, pr, cx); break; case ACPI_STATE_C2: @@ -834,12 +830,11 @@ static int acpi_idle_enter_c1(struct cpuidle_device *dev, /* Do not access any ACPI IO ports in suspend path */ if (acpi_idle_suspend) { + acpi_safe_halt(); local_irq_enable(); - cpu_relax(); return 0; } - acpi_state_timer_broadcast(pr, cx, 1); kt1 = ktime_get_real(); acpi_idle_do_entry(cx); kt2 = ktime_get_real(); @@ -847,7 +842,6 @@ static int acpi_idle_enter_c1(struct cpuidle_device *dev, local_irq_enable(); cx->usage++; - acpi_state_timer_broadcast(pr, cx, 0); return idle_time; } diff --git a/trunk/drivers/acpi/processor_perflib.c b/trunk/drivers/acpi/processor_perflib.c index 60e543d3234e..cafb41000f6b 100644 --- a/trunk/drivers/acpi/processor_perflib.c +++ b/trunk/drivers/acpi/processor_perflib.c @@ -309,15 +309,9 @@ static int acpi_processor_get_performance_states(struct acpi_processor *pr) (u32) px->bus_master_latency, (u32) px->control, (u32) px->status)); - /* - * Check that ACPI's u64 MHz will be valid as u32 KHz in cpufreq - */ - if (!px->core_frequency || - ((u32)(px->core_frequency * 1000) != - (px->core_frequency * 1000))) { - printk(KERN_ERR FW_BUG PREFIX - "Invalid BIOS _PSS frequency: 0x%llx MHz\n", - px->core_frequency); + if (!px->core_frequency) { + printk(KERN_ERR PREFIX + "Invalid _PSS data: freq is zero\n"); result = -EFAULT; kfree(pr->performance->states); goto end; diff --git a/trunk/drivers/acpi/processor_throttling.c b/trunk/drivers/acpi/processor_throttling.c index 227543789ba9..7f16f5f8e7d3 100644 --- a/trunk/drivers/acpi/processor_throttling.c +++ b/trunk/drivers/acpi/processor_throttling.c @@ -840,7 +840,7 @@ static int acpi_processor_get_throttling_ptc(struct acpi_processor *pr) state = acpi_get_throttling_state(pr, value); if (state == -1) { ACPI_WARNING((AE_INFO, - "Invalid throttling state, reset")); + "Invalid throttling state, reset\n")); state = 0; ret = acpi_processor_set_throttling(pr, state); if (ret) diff --git a/trunk/drivers/acpi/video.c b/trunk/drivers/acpi/video.c index 1bdfb37377e3..810cca90ca7f 100644 --- a/trunk/drivers/acpi/video.c +++ b/trunk/drivers/acpi/video.c @@ -570,22 +570,6 @@ static struct dmi_system_id video_dmi_table[] __initdata = { DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 5710Z"), }, }, - { - .callback = video_set_bqc_offset, - .ident = "eMachines E510", - .matches = { - DMI_MATCH(DMI_BOARD_VENDOR, "EMACHINES"), - DMI_MATCH(DMI_PRODUCT_NAME, "eMachines E510"), - }, - }, - { - .callback = video_set_bqc_offset, - .ident = "Acer Aspire 5315", - .matches = { - DMI_MATCH(DMI_BOARD_VENDOR, "Acer"), - DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 5315"), - }, - }, {} }; @@ -2350,7 +2334,7 @@ static int __init acpi_video_init(void) return acpi_video_register(); } -void acpi_video_exit(void) +void __exit acpi_video_exit(void) { acpi_bus_unregister_driver(&acpi_video_bus); diff --git a/trunk/drivers/ata/ahci.c b/trunk/drivers/ata/ahci.c index 6b91c26a4635..08186ecbaf8d 100644 --- a/trunk/drivers/ata/ahci.c +++ b/trunk/drivers/ata/ahci.c @@ -220,7 +220,6 @@ enum { AHCI_HFLAG_NO_HOTPLUG = (1 << 7), /* ignore PxSERR.DIAG.N */ AHCI_HFLAG_SECT255 = (1 << 8), /* max 255 sectors */ AHCI_HFLAG_YES_NCQ = (1 << 9), /* force NCQ cap on */ - AHCI_HFLAG_NO_SUSPEND = (1 << 10), /* don't suspend */ /* ap->flags bits */ @@ -2317,17 +2316,9 @@ static int ahci_port_suspend(struct ata_port *ap, pm_message_t mesg) static int ahci_pci_device_suspend(struct pci_dev *pdev, pm_message_t mesg) { struct ata_host *host = dev_get_drvdata(&pdev->dev); - struct ahci_host_priv *hpriv = host->private_data; void __iomem *mmio = host->iomap[AHCI_PCI_BAR]; u32 ctl; - if (mesg.event & PM_EVENT_SUSPEND && - hpriv->flags & AHCI_HFLAG_NO_SUSPEND) { - dev_printk(KERN_ERR, &pdev->dev, - "BIOS update required for suspend/resume\n"); - return -EIO; - } - if (mesg.event & PM_EVENT_SLEEP) { /* AHCI spec rev1.1 section 8.3.3: * Software must disable interrupts prior to requesting a @@ -2619,63 +2610,6 @@ static bool ahci_broken_system_poweroff(struct pci_dev *pdev) return false; } -static bool ahci_broken_suspend(struct pci_dev *pdev) -{ - static const struct dmi_system_id sysids[] = { - /* - * On HP dv[4-6] and HDX18 with earlier BIOSen, link - * to the harddisk doesn't become online after - * resuming from STR. Warn and fail suspend. - */ - { - .ident = "dv4", - .matches = { - DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), - DMI_MATCH(DMI_PRODUCT_NAME, - "HP Pavilion dv4 Notebook PC"), - }, - .driver_data = "F.30", /* cutoff BIOS version */ - }, - { - .ident = "dv5", - .matches = { - DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), - DMI_MATCH(DMI_PRODUCT_NAME, - "HP Pavilion dv5 Notebook PC"), - }, - .driver_data = "F.16", /* cutoff BIOS version */ - }, - { - .ident = "dv6", - .matches = { - DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), - DMI_MATCH(DMI_PRODUCT_NAME, - "HP Pavilion dv6 Notebook PC"), - }, - .driver_data = "F.21", /* cutoff BIOS version */ - }, - { - .ident = "HDX18", - .matches = { - DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), - DMI_MATCH(DMI_PRODUCT_NAME, - "HP HDX18 Notebook PC"), - }, - .driver_data = "F.23", /* cutoff BIOS version */ - }, - { } /* terminate list */ - }; - const struct dmi_system_id *dmi = dmi_first_match(sysids); - const char *ver; - - if (!dmi || pdev->bus->number || pdev->devfn != PCI_DEVFN(0x1f, 2)) - return false; - - ver = dmi_get_system_info(DMI_BIOS_VERSION); - - return !ver || strcmp(ver, dmi->driver_data) < 0; -} - static int ahci_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) { static int printed_version; @@ -2781,12 +2715,6 @@ static int ahci_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) "quirky BIOS, skipping spindown on poweroff\n"); } - if (ahci_broken_suspend(pdev)) { - hpriv->flags |= AHCI_HFLAG_NO_SUSPEND; - dev_printk(KERN_WARNING, &pdev->dev, - "BIOS update required for suspend/resume\n"); - } - /* CAP.NP sometimes indicate the index of the last enabled * port, at other times, that of the last possible port, so * determining the maximum port number requires looking at diff --git a/trunk/drivers/ata/ata_piix.c b/trunk/drivers/ata/ata_piix.c index 1aeb7082b0c4..d51a17c0f59b 100644 --- a/trunk/drivers/ata/ata_piix.c +++ b/trunk/drivers/ata/ata_piix.c @@ -1455,15 +1455,6 @@ static bool piix_broken_system_poweroff(struct pci_dev *pdev) /* PCI slot number of the controller */ .driver_data = (void *)0x1FUL, }, - { - .ident = "HP Compaq nc6000", - .matches = { - DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), - DMI_MATCH(DMI_PRODUCT_NAME, "HP Compaq nc6000"), - }, - /* PCI slot number of the controller */ - .driver_data = (void *)0x1FUL, - }, { } /* terminate list */ }; diff --git a/trunk/drivers/ata/pata_ali.c b/trunk/drivers/ata/pata_ali.c index fc9c5d6d7d80..751b7ea4816c 100644 --- a/trunk/drivers/ata/pata_ali.c +++ b/trunk/drivers/ata/pata_ali.c @@ -497,16 +497,14 @@ static int ali_init_one(struct pci_dev *pdev, const struct pci_device_id *id) }; /* Revision 0x20 added DMA */ static const struct ata_port_info info_20 = { - .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_PIO_LBA48 | - ATA_FLAG_IGN_SIMPLEX, + .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_PIO_LBA48, .pio_mask = ATA_PIO4, .mwdma_mask = ATA_MWDMA2, .port_ops = &ali_20_port_ops }; /* Revision 0x20 with support logic added UDMA */ static const struct ata_port_info info_20_udma = { - .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_PIO_LBA48 | - ATA_FLAG_IGN_SIMPLEX, + .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_PIO_LBA48, .pio_mask = ATA_PIO4, .mwdma_mask = ATA_MWDMA2, .udma_mask = ATA_UDMA2, @@ -514,8 +512,7 @@ static int ali_init_one(struct pci_dev *pdev, const struct pci_device_id *id) }; /* Revision 0xC2 adds UDMA66 */ static const struct ata_port_info info_c2 = { - .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_PIO_LBA48 | - ATA_FLAG_IGN_SIMPLEX, + .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_PIO_LBA48, .pio_mask = ATA_PIO4, .mwdma_mask = ATA_MWDMA2, .udma_mask = ATA_UDMA4, @@ -523,8 +520,7 @@ static int ali_init_one(struct pci_dev *pdev, const struct pci_device_id *id) }; /* Revision 0xC3 is UDMA66 for now */ static const struct ata_port_info info_c3 = { - .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_PIO_LBA48 | - ATA_FLAG_IGN_SIMPLEX, + .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_PIO_LBA48, .pio_mask = ATA_PIO4, .mwdma_mask = ATA_MWDMA2, .udma_mask = ATA_UDMA4, @@ -532,8 +528,7 @@ static int ali_init_one(struct pci_dev *pdev, const struct pci_device_id *id) }; /* Revision 0xC4 is UDMA100 */ static const struct ata_port_info info_c4 = { - .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_PIO_LBA48 | - ATA_FLAG_IGN_SIMPLEX, + .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_PIO_LBA48, .pio_mask = ATA_PIO4, .mwdma_mask = ATA_MWDMA2, .udma_mask = ATA_UDMA5, @@ -541,7 +536,7 @@ static int ali_init_one(struct pci_dev *pdev, const struct pci_device_id *id) }; /* Revision 0xC5 is UDMA133 with LBA48 DMA */ static const struct ata_port_info info_c5 = { - .flags = ATA_FLAG_SLAVE_POSS | ATA_FLAG_IGN_SIMPLEX, + .flags = ATA_FLAG_SLAVE_POSS, .pio_mask = ATA_PIO4, .mwdma_mask = ATA_MWDMA2, .udma_mask = ATA_UDMA6, diff --git a/trunk/drivers/ata/pata_efar.c b/trunk/drivers/ata/pata_efar.c index 2a6412f5d117..2085e0a3a05a 100644 --- a/trunk/drivers/ata/pata_efar.c +++ b/trunk/drivers/ata/pata_efar.c @@ -22,7 +22,7 @@ #include #define DRV_NAME "pata_efar" -#define DRV_VERSION "0.4.5" +#define DRV_VERSION "0.4.4" /** * efar_pre_reset - Enable bits @@ -98,17 +98,18 @@ static void efar_set_piomode (struct ata_port *ap, struct ata_device *adev) { 2, 1 }, { 2, 3 }, }; - if (pio > 1) - control |= 1; /* TIME */ + if (pio > 2) + control |= 1; /* TIME1 enable */ if (ata_pio_need_iordy(adev)) /* PIO 3/4 require IORDY */ - control |= 2; /* IE */ - /* Intel specifies that the prefetch/posting is for disk only */ + control |= 2; /* IE enable */ + /* Intel specifies that the PPE functionality is for disk only */ if (adev->class == ATA_DEV_ATA) - control |= 4; /* PPE */ + control |= 4; /* PPE enable */ pci_read_config_word(dev, idetm_port, &idetm_data); - /* Set PPE, IE, and TIME as appropriate */ + /* Enable PPE, IE and TIME as appropriate */ + if (adev->devno == 0) { idetm_data &= 0xCCF0; idetm_data |= control; @@ -128,7 +129,7 @@ static void efar_set_piomode (struct ata_port *ap, struct ata_device *adev) pci_write_config_byte(dev, 0x44, slave_data); } - idetm_data |= 0x4000; /* Ensure SITRE is set */ + idetm_data |= 0x4000; /* Ensure SITRE is enabled */ pci_write_config_word(dev, idetm_port, idetm_data); } diff --git a/trunk/drivers/ata/pata_legacy.c b/trunk/drivers/ata/pata_legacy.c index 6932e56d179c..f72c6c5b820f 100644 --- a/trunk/drivers/ata/pata_legacy.c +++ b/trunk/drivers/ata/pata_legacy.c @@ -48,7 +48,6 @@ * */ -#include #include #include #include @@ -1029,7 +1028,6 @@ static __init int legacy_init_one(struct legacy_probe *probe) &legacy_sht); if (ret) goto fail; - async_synchronize_full(); ld->platform_dev = pdev; /* Nothing found means we drop the port as its probably not there */ diff --git a/trunk/drivers/ata/pata_netcell.c b/trunk/drivers/ata/pata_netcell.c index f0d52f72f5bb..bdb236957cb9 100644 --- a/trunk/drivers/ata/pata_netcell.c +++ b/trunk/drivers/ata/pata_netcell.c @@ -20,24 +20,13 @@ /* No PIO or DMA methods needed for this device */ -static unsigned int netcell_read_id(struct ata_device *adev, - struct ata_taskfile *tf, u16 *id) -{ - unsigned int err_mask = ata_do_dev_read_id(adev, tf, id); - /* Firmware forgets to mark words 85-87 valid */ - if (err_mask == 0) - id[ATA_ID_CSF_DEFAULT] |= 0x4000; - return err_mask; -} - static struct scsi_host_template netcell_sht = { ATA_BMDMA_SHT(DRV_NAME), }; static struct ata_port_operations netcell_ops = { .inherits = &ata_bmdma_port_ops, - .cable_detect = ata_cable_80wire, - .read_id = netcell_read_id, + .cable_detect = ata_cable_80wire, }; diff --git a/trunk/drivers/char/mem.c b/trunk/drivers/char/mem.c index 65e12bca657c..8f05c38c2f06 100644 --- a/trunk/drivers/char/mem.c +++ b/trunk/drivers/char/mem.c @@ -694,9 +694,6 @@ static ssize_t read_zero(struct file * file, char __user * buf, written += chunk - unwritten; if (unwritten) break; - /* Consider changing this to just 'signal_pending()' with lots of testing */ - if (fatal_signal_pending(current)) - return written ? written : -EINTR; buf += chunk; count -= chunk; cond_resched(); diff --git a/trunk/drivers/char/mxser.c b/trunk/drivers/char/mxser.c index 13f8871e5b21..a420e8d437dd 100644 --- a/trunk/drivers/char/mxser.c +++ b/trunk/drivers/char/mxser.c @@ -2711,7 +2711,7 @@ static int __init mxser_module_init(void) continue; brd = &mxser_boards[m]; - retval = mxser_get_ISA_conf(ioaddr[b], brd); + retval = mxser_get_ISA_conf(!ioaddr[b], brd); if (retval <= 0) { brd->info = NULL; continue; diff --git a/trunk/drivers/cpufreq/cpufreq.c b/trunk/drivers/cpufreq/cpufreq.c index 6e2ec0b18948..47d2ad0ae079 100644 --- a/trunk/drivers/cpufreq/cpufreq.c +++ b/trunk/drivers/cpufreq/cpufreq.c @@ -808,7 +808,7 @@ static int cpufreq_add_dev(struct sys_device *sys_dev) ret = -ENOMEM; goto nomem_out; } - if (!zalloc_cpumask_var(&policy->related_cpus, GFP_KERNEL)) { + if (!alloc_cpumask_var(&policy->related_cpus, GFP_KERNEL)) { free_cpumask_var(policy->cpus); kfree(policy); ret = -ENOMEM; diff --git a/trunk/drivers/dma/fsldma.c b/trunk/drivers/dma/fsldma.c index f18d1bde0439..da8a8ed9e411 100644 --- a/trunk/drivers/dma/fsldma.c +++ b/trunk/drivers/dma/fsldma.c @@ -179,14 +179,9 @@ static void dma_halt(struct fsl_dma_chan *fsl_chan) static void set_ld_eol(struct fsl_dma_chan *fsl_chan, struct fsl_desc_sw *desc) { - u64 snoop_bits; - - snoop_bits = ((fsl_chan->feature & FSL_DMA_IP_MASK) == FSL_DMA_IP_83XX) - ? FSL_DMA_SNEN : 0; - desc->hw.next_ln_addr = CPU_TO_DMA(fsl_chan, - DMA_TO_CPU(fsl_chan, desc->hw.next_ln_addr, 64) | FSL_DMA_EOL - | snoop_bits, 64); + DMA_TO_CPU(fsl_chan, desc->hw.next_ln_addr, 64) | FSL_DMA_EOL, + 64); } static void append_ld_queue(struct fsl_dma_chan *fsl_chan, @@ -318,8 +313,8 @@ static void fsl_chan_toggle_ext_start(struct fsl_dma_chan *fsl_chan, int enable) static dma_cookie_t fsl_dma_tx_submit(struct dma_async_tx_descriptor *tx) { + struct fsl_desc_sw *desc = tx_to_fsl_desc(tx); struct fsl_dma_chan *fsl_chan = to_fsl_chan(tx->chan); - struct fsl_desc_sw *desc; unsigned long flags; dma_cookie_t cookie; @@ -327,17 +322,14 @@ static dma_cookie_t fsl_dma_tx_submit(struct dma_async_tx_descriptor *tx) spin_lock_irqsave(&fsl_chan->desc_lock, flags); cookie = fsl_chan->common.cookie; - list_for_each_entry(desc, &tx->tx_list, node) { - cookie++; - if (cookie < 0) - cookie = 1; + cookie++; + if (cookie < 0) + cookie = 1; + desc->async_tx.cookie = cookie; + fsl_chan->common.cookie = desc->async_tx.cookie; - desc->async_tx.cookie = cookie; - } - - fsl_chan->common.cookie = cookie; - append_ld_queue(fsl_chan, tx_to_fsl_desc(tx)); - list_splice_init(&tx->tx_list, fsl_chan->ld_queue.prev); + append_ld_queue(fsl_chan, desc); + list_splice_init(&desc->async_tx.tx_list, fsl_chan->ld_queue.prev); spin_unlock_irqrestore(&fsl_chan->desc_lock, flags); @@ -462,8 +454,8 @@ static struct dma_async_tx_descriptor *fsl_dma_prep_memcpy( { struct fsl_dma_chan *fsl_chan; struct fsl_desc_sw *first = NULL, *prev = NULL, *new; - struct list_head *list; size_t copy; + LIST_HEAD(link_chain); if (!chan) return NULL; @@ -480,7 +472,7 @@ static struct dma_async_tx_descriptor *fsl_dma_prep_memcpy( if (!new) { dev_err(fsl_chan->dev, "No free memory for link descriptor\n"); - goto fail; + return NULL; } #ifdef FSL_DMA_LD_DEBUG dev_dbg(fsl_chan->dev, "new link desc alloc %p\n", new); @@ -515,19 +507,7 @@ static struct dma_async_tx_descriptor *fsl_dma_prep_memcpy( /* Set End-of-link to the last link descriptor of new list*/ set_ld_eol(fsl_chan, new); - return &first->async_tx; - -fail: - if (!first) - return NULL; - - list = &first->async_tx.tx_list; - list_for_each_entry_safe_reverse(new, prev, list, node) { - list_del(&new->node); - dma_pool_free(fsl_chan->desc_pool, new, new->async_tx.phys); - } - - return NULL; + return first ? &first->async_tx : NULL; } /** @@ -618,16 +598,15 @@ static void fsl_chan_xfer_ld_queue(struct fsl_dma_chan *fsl_chan) dma_addr_t next_dest_addr; unsigned long flags; - spin_lock_irqsave(&fsl_chan->desc_lock, flags); - if (!dma_is_idle(fsl_chan)) - goto out_unlock; + return; dma_halt(fsl_chan); /* If there are some link descriptors * not transfered in queue. We need to start it. */ + spin_lock_irqsave(&fsl_chan->desc_lock, flags); /* Find the first un-transfer desciptor */ for (ld_node = fsl_chan->ld_queue.next; @@ -638,20 +617,19 @@ static void fsl_chan_xfer_ld_queue(struct fsl_dma_chan *fsl_chan) fsl_chan->common.cookie) == DMA_SUCCESS); ld_node = ld_node->next); + spin_unlock_irqrestore(&fsl_chan->desc_lock, flags); + if (ld_node != &fsl_chan->ld_queue) { /* Get the ld start address from ld_queue */ next_dest_addr = to_fsl_desc(ld_node)->async_tx.phys; - dev_dbg(fsl_chan->dev, "xfer LDs staring from 0x%llx\n", - (unsigned long long)next_dest_addr); + dev_dbg(fsl_chan->dev, "xfer LDs staring from %p\n", + (void *)next_dest_addr); set_cdar(fsl_chan, next_dest_addr); dma_start(fsl_chan); } else { set_cdar(fsl_chan, 0); set_ndar(fsl_chan, 0); } - -out_unlock: - spin_unlock_irqrestore(&fsl_chan->desc_lock, flags); } /** @@ -756,9 +734,8 @@ static irqreturn_t fsl_dma_chan_do_interrupt(int irq, void *data) */ if (stat & FSL_DMA_SR_EOSI) { dev_dbg(fsl_chan->dev, "event: End-of-segments INT\n"); - dev_dbg(fsl_chan->dev, "event: clndar 0x%llx, nlndar 0x%llx\n", - (unsigned long long)get_cdar(fsl_chan), - (unsigned long long)get_ndar(fsl_chan)); + dev_dbg(fsl_chan->dev, "event: clndar %p, nlndar %p\n", + (void *)get_cdar(fsl_chan), (void *)get_ndar(fsl_chan)); stat &= ~FSL_DMA_SR_EOSI; update_cookie = 1; } @@ -853,7 +830,7 @@ static int __devinit fsl_dma_chan_probe(struct fsl_dma_device *fdev, new_fsl_chan->reg.end - new_fsl_chan->reg.start + 1); new_fsl_chan->id = ((new_fsl_chan->reg.start - 0x100) & 0xfff) >> 7; - if (new_fsl_chan->id >= FSL_DMA_MAX_CHANS_PER_DEVICE) { + if (new_fsl_chan->id > FSL_DMA_MAX_CHANS_PER_DEVICE) { dev_err(fdev->dev, "There is no %d channel!\n", new_fsl_chan->id); err = -EINVAL; @@ -948,8 +925,8 @@ static int __devinit of_fsl_dma_probe(struct of_device *dev, } dev_info(&dev->dev, "Probe the Freescale DMA driver for %s " - "controller at 0x%llx...\n", - match->compatible, (unsigned long long)fdev->reg.start); + "controller at %p...\n", + match->compatible, (void *)fdev->reg.start); fdev->reg_base = ioremap(fdev->reg.start, fdev->reg.end - fdev->reg.start + 1); diff --git a/trunk/drivers/dma/ioat_dma.c b/trunk/drivers/dma/ioat_dma.c index a600fc0f7962..1955ee8d6d20 100644 --- a/trunk/drivers/dma/ioat_dma.c +++ b/trunk/drivers/dma/ioat_dma.c @@ -173,7 +173,7 @@ static int ioat_dma_enumerate_channels(struct ioatdma_device *device) xfercap = (xfercap_scale == 0 ? -1 : (1UL << xfercap_scale)); #ifdef CONFIG_I7300_IDLE_IOAT_CHANNEL - if (i7300_idle_platform_probe(NULL, NULL, 1) == 0) { + if (i7300_idle_platform_probe(NULL, NULL) == 0) { device->common.chancnt--; } #endif diff --git a/trunk/drivers/gpu/drm/Kconfig b/trunk/drivers/gpu/drm/Kconfig index f5d46e7199d4..4cd35d8fd799 100644 --- a/trunk/drivers/gpu/drm/Kconfig +++ b/trunk/drivers/gpu/drm/Kconfig @@ -67,18 +67,12 @@ config DRM_I830 will load the correct one. config DRM_I915 - tristate "i915 driver" select FB_CFB_FILLRECT select FB_CFB_COPYAREA select FB_CFB_IMAGEBLIT select FB select FRAMEBUFFER_CONSOLE if !EMBEDDED - # i915 depends on ACPI_VIDEO when ACPI is enabled - # but for select to work, need to select ACPI_VIDEO's dependencies, ick - select VIDEO_OUTPUT_CONTROL if ACPI - select BACKLIGHT_CLASS_DEVICE if ACPI - select INPUT if ACPI - select ACPI_VIDEO if ACPI + tristate "i915 driver" help Choose this option if you have a system that has Intel 830M, 845G, 852GM, 855GM 865G or 915G integrated graphics. If M is selected, the @@ -90,6 +84,12 @@ config DRM_I915 config DRM_I915_KMS bool "Enable modesetting on intel by default" depends on DRM_I915 + # i915 KMS depends on ACPI_VIDEO when ACPI is enabled + # but for select to work, need to select ACPI_VIDEO's dependencies, ick + select VIDEO_OUTPUT_CONTROL if ACPI + select BACKLIGHT_CLASS_DEVICE if ACPI + select INPUT if ACPI + select ACPI_VIDEO if ACPI help Choose this option if you want kernel modesetting enabled by default, and you have a new enough userspace to support this. Running old diff --git a/trunk/drivers/gpu/drm/drm_crtc.c b/trunk/drivers/gpu/drm/drm_crtc.c index 8fab7890a363..94a768871734 100644 --- a/trunk/drivers/gpu/drm/drm_crtc.c +++ b/trunk/drivers/gpu/drm/drm_crtc.c @@ -2294,12 +2294,7 @@ int drm_mode_connector_property_set_ioctl(struct drm_device *dev, } } - /* Do DPMS ourselves */ - if (property == connector->dev->mode_config.dpms_property) { - if (connector->funcs->dpms) - (*connector->funcs->dpms)(connector, (int) out_resp->value); - ret = 0; - } else if (connector->funcs->set_property) + if (connector->funcs->set_property) ret = connector->funcs->set_property(connector, property, out_resp->value); /* store the property value if succesful */ diff --git a/trunk/drivers/gpu/drm/drm_crtc_helper.c b/trunk/drivers/gpu/drm/drm_crtc_helper.c index a6f73f1e99d9..45890447feec 100644 --- a/trunk/drivers/gpu/drm/drm_crtc_helper.c +++ b/trunk/drivers/gpu/drm/drm_crtc_helper.c @@ -198,29 +198,6 @@ static void drm_helper_add_std_modes(struct drm_device *dev, } } -/** - * drm_helper_encoder_in_use - check if a given encoder is in use - * @encoder: encoder to check - * - * LOCKING: - * Caller must hold mode config lock. - * - * Walk @encoders's DRM device's mode_config and see if it's in use. - * - * RETURNS: - * True if @encoder is part of the mode_config, false otherwise. - */ -bool drm_helper_encoder_in_use(struct drm_encoder *encoder) -{ - struct drm_connector *connector; - struct drm_device *dev = encoder->dev; - list_for_each_entry(connector, &dev->mode_config.connector_list, head) - if (connector->encoder == encoder) - return true; - return false; -} -EXPORT_SYMBOL(drm_helper_encoder_in_use); - /** * drm_helper_crtc_in_use - check if a given CRTC is in a mode_config * @crtc: CRTC to check @@ -239,7 +216,7 @@ bool drm_helper_crtc_in_use(struct drm_crtc *crtc) struct drm_device *dev = crtc->dev; /* FIXME: Locking around list access? */ list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) - if (encoder->crtc == crtc && drm_helper_encoder_in_use(encoder)) + if (encoder->crtc == crtc) return true; return false; } @@ -263,7 +240,7 @@ void drm_helper_disable_unused_functions(struct drm_device *dev) list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { encoder_funcs = encoder->helper_private; - if (!drm_helper_encoder_in_use(encoder)) + if (!encoder->crtc) (*encoder_funcs->dpms)(encoder, DRM_MODE_DPMS_OFF); } @@ -958,88 +935,6 @@ bool drm_helper_initial_config(struct drm_device *dev) } EXPORT_SYMBOL(drm_helper_initial_config); -static int drm_helper_choose_encoder_dpms(struct drm_encoder *encoder) -{ - int dpms = DRM_MODE_DPMS_OFF; - struct drm_connector *connector; - struct drm_device *dev = encoder->dev; - - list_for_each_entry(connector, &dev->mode_config.connector_list, head) - if (connector->encoder == encoder) - if (connector->dpms < dpms) - dpms = connector->dpms; - return dpms; -} - -static int drm_helper_choose_crtc_dpms(struct drm_crtc *crtc) -{ - int dpms = DRM_MODE_DPMS_OFF; - struct drm_connector *connector; - struct drm_device *dev = crtc->dev; - - list_for_each_entry(connector, &dev->mode_config.connector_list, head) - if (connector->encoder && connector->encoder->crtc == crtc) - if (connector->dpms < dpms) - dpms = connector->dpms; - return dpms; -} - -/** - * drm_helper_connector_dpms - * @connector affected connector - * @mode DPMS mode - * - * Calls the low-level connector DPMS function, then - * calls appropriate encoder and crtc DPMS functions as well - */ -void drm_helper_connector_dpms(struct drm_connector *connector, int mode) -{ - struct drm_encoder *encoder = connector->encoder; - struct drm_crtc *crtc = encoder ? encoder->crtc : NULL; - int old_dpms; - - if (mode == connector->dpms) - return; - - old_dpms = connector->dpms; - connector->dpms = mode; - - /* from off to on, do crtc then encoder */ - if (mode < old_dpms) { - if (crtc) { - struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private; - if (crtc_funcs->dpms) - (*crtc_funcs->dpms) (crtc, - drm_helper_choose_crtc_dpms(crtc)); - } - if (encoder) { - struct drm_encoder_helper_funcs *encoder_funcs = encoder->helper_private; - if (encoder_funcs->dpms) - (*encoder_funcs->dpms) (encoder, - drm_helper_choose_encoder_dpms(encoder)); - } - } - - /* from on to off, do encoder then crtc */ - if (mode > old_dpms) { - if (encoder) { - struct drm_encoder_helper_funcs *encoder_funcs = encoder->helper_private; - if (encoder_funcs->dpms) - (*encoder_funcs->dpms) (encoder, - drm_helper_choose_encoder_dpms(encoder)); - } - if (crtc) { - struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private; - if (crtc_funcs->dpms) - (*crtc_funcs->dpms) (crtc, - drm_helper_choose_crtc_dpms(crtc)); - } - } - - return; -} -EXPORT_SYMBOL(drm_helper_connector_dpms); - /** * drm_hotplug_stage_two * @dev DRM device diff --git a/trunk/drivers/gpu/drm/drm_edid.c b/trunk/drivers/gpu/drm/drm_edid.c index 6f6b26479d82..ca9c61656714 100644 --- a/trunk/drivers/gpu/drm/drm_edid.c +++ b/trunk/drivers/gpu/drm/drm_edid.c @@ -289,11 +289,6 @@ static struct drm_display_mode *drm_mode_detailed(struct drm_device *dev, struct drm_display_mode *mode; struct detailed_pixel_timing *pt = &timing->data.pixel_data; - /* ignore tiny modes */ - if (((pt->hactive_hi << 8) | pt->hactive_lo) < 64 || - ((pt->vactive_hi << 8) | pt->hactive_lo) < 64) - return NULL; - if (pt->stereo) { printk(KERN_WARNING "stereo mode not supported\n"); return NULL; diff --git a/trunk/drivers/gpu/drm/drm_irq.c b/trunk/drivers/gpu/drm/drm_irq.c index fc8e5acd9d9a..93e677a481f5 100644 --- a/trunk/drivers/gpu/drm/drm_irq.c +++ b/trunk/drivers/gpu/drm/drm_irq.c @@ -196,7 +196,6 @@ int drm_irq_install(struct drm_device *dev) { int ret = 0; unsigned long sh_flags = 0; - char *irqname; if (!drm_core_check_feature(dev, DRIVER_HAVE_IRQ)) return -EINVAL; @@ -228,13 +227,8 @@ int drm_irq_install(struct drm_device *dev) if (drm_core_check_feature(dev, DRIVER_IRQ_SHARED)) sh_flags = IRQF_SHARED; - if (dev->devname) - irqname = dev->devname; - else - irqname = dev->driver->name; - ret = request_irq(drm_dev_to_irq(dev), dev->driver->irq_handler, - sh_flags, irqname, dev); + sh_flags, dev->devname, dev); if (ret < 0) { mutex_lock(&dev->struct_mutex); diff --git a/trunk/drivers/gpu/drm/drm_sysfs.c b/trunk/drivers/gpu/drm/drm_sysfs.c index 9987ab880835..8f9372921f82 100644 --- a/trunk/drivers/gpu/drm/drm_sysfs.c +++ b/trunk/drivers/gpu/drm/drm_sysfs.c @@ -147,7 +147,7 @@ static ssize_t status_show(struct device *device, enum drm_connector_status status; status = connector->funcs->detect(connector); - return snprintf(buf, PAGE_SIZE, "%s\n", + return snprintf(buf, PAGE_SIZE, "%s", drm_get_connector_status_name(status)); } @@ -166,7 +166,7 @@ static ssize_t dpms_show(struct device *device, if (ret) return 0; - return snprintf(buf, PAGE_SIZE, "%s\n", + return snprintf(buf, PAGE_SIZE, "%s", drm_get_dpms_name((int)dpms_status)); } @@ -176,7 +176,7 @@ static ssize_t enabled_show(struct device *device, { struct drm_connector *connector = to_drm_connector(device); - return snprintf(buf, PAGE_SIZE, "%s\n", connector->encoder ? "enabled" : + return snprintf(buf, PAGE_SIZE, connector->encoder ? "enabled" : "disabled"); } @@ -317,7 +317,6 @@ static struct device_attribute connector_attrs_opt1[] = { static struct bin_attribute edid_attr = { .attr.name = "edid", - .attr.mode = 0444, .size = 128, .read = edid_show, }; diff --git a/trunk/drivers/gpu/drm/i915/i915_dma.c b/trunk/drivers/gpu/drm/i915/i915_dma.c index 0ccb63ee50ee..53d544552625 100644 --- a/trunk/drivers/gpu/drm/i915/i915_dma.c +++ b/trunk/drivers/gpu/drm/i915/i915_dma.c @@ -987,6 +987,12 @@ static int i915_load_modeset_init(struct drm_device *dev) int fb_bar = IS_I9XX(dev) ? 2 : 0; int ret = 0; + dev->devname = kstrdup(DRIVER_NAME, GFP_KERNEL); + if (!dev->devname) { + ret = -ENOMEM; + goto out; + } + dev->mode_config.fb_base = drm_get_resource_start(dev, fb_bar) & 0xff000000; @@ -1000,7 +1006,7 @@ static int i915_load_modeset_init(struct drm_device *dev) ret = i915_probe_agp(dev, &agp_size, &prealloc_size); if (ret) - goto out; + goto kfree_devname; /* Basic memrange allocator for stolen space (aka vram) */ drm_mm_init(&dev_priv->vram, 0, prealloc_size); @@ -1018,7 +1024,7 @@ static int i915_load_modeset_init(struct drm_device *dev) ret = i915_gem_init_ringbuffer(dev); if (ret) - goto out; + goto kfree_devname; /* Allow hardware batchbuffers unless told otherwise. */ @@ -1050,6 +1056,8 @@ static int i915_load_modeset_init(struct drm_device *dev) destroy_ringbuffer: i915_gem_cleanup_ringbuffer(dev); +kfree_devname: + kfree(dev->devname); out: return ret; } diff --git a/trunk/drivers/gpu/drm/i915/i915_gem.c b/trunk/drivers/gpu/drm/i915/i915_gem.c index 39f5c658ef5e..670d12881468 100644 --- a/trunk/drivers/gpu/drm/i915/i915_gem.c +++ b/trunk/drivers/gpu/drm/i915/i915_gem.c @@ -2260,6 +2260,9 @@ i915_gem_object_get_fence_reg(struct drm_gem_object *obj, bool write) goto try_again; } + BUG_ON(old_obj_priv->active || + (reg->obj->write_domain & I915_GEM_GPU_DOMAINS)); + /* * Zap this virtual mapping so we can set up a fence again * for this object next time we need it. diff --git a/trunk/drivers/gpu/drm/i915/intel_crt.c b/trunk/drivers/gpu/drm/i915/intel_crt.c index 79acc4f4c1f8..640f5158effc 100644 --- a/trunk/drivers/gpu/drm/i915/intel_crt.c +++ b/trunk/drivers/gpu/drm/i915/intel_crt.c @@ -381,6 +381,11 @@ static int intel_crt_set_property(struct drm_connector *connector, struct drm_property *property, uint64_t value) { + struct drm_device *dev = connector->dev; + + if (property == dev->mode_config.dpms_property && connector->encoder) + intel_crt_dpms(connector->encoder, (uint32_t)(value & 0xf)); + return 0; } @@ -397,7 +402,6 @@ static const struct drm_encoder_helper_funcs intel_crt_helper_funcs = { }; static const struct drm_connector_funcs intel_crt_connector_funcs = { - .dpms = drm_helper_connector_dpms, .detect = intel_crt_detect, .fill_modes = drm_helper_probe_single_connector_modes, .destroy = intel_crt_destroy, diff --git a/trunk/drivers/gpu/drm/i915/intel_dvo.c b/trunk/drivers/gpu/drm/i915/intel_dvo.c index 1ee3007d6ec0..8b8d6e65cd3f 100644 --- a/trunk/drivers/gpu/drm/i915/intel_dvo.c +++ b/trunk/drivers/gpu/drm/i915/intel_dvo.c @@ -316,7 +316,6 @@ static const struct drm_encoder_helper_funcs intel_dvo_helper_funcs = { }; static const struct drm_connector_funcs intel_dvo_connector_funcs = { - .dpms = drm_helper_connector_dpms, .save = intel_dvo_save, .restore = intel_dvo_restore, .detect = intel_dvo_detect, diff --git a/trunk/drivers/gpu/drm/i915/intel_hdmi.c b/trunk/drivers/gpu/drm/i915/intel_hdmi.c index 7d6bdd705326..d0983bb93a18 100644 --- a/trunk/drivers/gpu/drm/i915/intel_hdmi.c +++ b/trunk/drivers/gpu/drm/i915/intel_hdmi.c @@ -219,7 +219,6 @@ static const struct drm_encoder_helper_funcs intel_hdmi_helper_funcs = { }; static const struct drm_connector_funcs intel_hdmi_connector_funcs = { - .dpms = drm_helper_connector_dpms, .save = intel_hdmi_save, .restore = intel_hdmi_restore, .detect = intel_hdmi_detect, diff --git a/trunk/drivers/gpu/drm/i915/intel_lvds.c b/trunk/drivers/gpu/drm/i915/intel_lvds.c index 53cccfa58b95..53731f0ffcb5 100644 --- a/trunk/drivers/gpu/drm/i915/intel_lvds.c +++ b/trunk/drivers/gpu/drm/i915/intel_lvds.c @@ -343,6 +343,11 @@ static int intel_lvds_set_property(struct drm_connector *connector, struct drm_property *property, uint64_t value) { + struct drm_device *dev = connector->dev; + + if (property == dev->mode_config.dpms_property && connector->encoder) + intel_lvds_dpms(connector->encoder, (uint32_t)(value & 0xf)); + return 0; } @@ -361,7 +366,6 @@ static const struct drm_connector_helper_funcs intel_lvds_connector_helper_funcs }; static const struct drm_connector_funcs intel_lvds_connector_funcs = { - .dpms = drm_helper_connector_dpms, .save = intel_lvds_save, .restore = intel_lvds_restore, .detect = intel_lvds_detect, @@ -387,7 +391,7 @@ static int __init intel_no_lvds_dmi_callback(const struct dmi_system_id *id) } /* These systems claim to have LVDS, but really don't */ -static const struct dmi_system_id intel_no_lvds[] = { +static const struct dmi_system_id __initdata intel_no_lvds[] = { { .callback = intel_no_lvds_dmi_callback, .ident = "Apple Mac Mini (Core series)", diff --git a/trunk/drivers/gpu/drm/i915/intel_sdvo.c b/trunk/drivers/gpu/drm/i915/intel_sdvo.c index 3093b4d4a4dd..f3ef6bfd8ffc 100644 --- a/trunk/drivers/gpu/drm/i915/intel_sdvo.c +++ b/trunk/drivers/gpu/drm/i915/intel_sdvo.c @@ -1616,7 +1616,6 @@ static const struct drm_encoder_helper_funcs intel_sdvo_helper_funcs = { }; static const struct drm_connector_funcs intel_sdvo_connector_funcs = { - .dpms = drm_helper_connector_dpms, .save = intel_sdvo_save, .restore = intel_sdvo_restore, .detect = intel_sdvo_detect, diff --git a/trunk/drivers/gpu/drm/i915/intel_tv.c b/trunk/drivers/gpu/drm/i915/intel_tv.c index 98ac0546b7bd..d2c32983242d 100644 --- a/trunk/drivers/gpu/drm/i915/intel_tv.c +++ b/trunk/drivers/gpu/drm/i915/intel_tv.c @@ -1626,7 +1626,6 @@ static const struct drm_encoder_helper_funcs intel_tv_helper_funcs = { }; static const struct drm_connector_funcs intel_tv_connector_funcs = { - .dpms = drm_helper_connector_dpms, .save = intel_tv_save, .restore = intel_tv_restore, .detect = intel_tv_detect, diff --git a/trunk/drivers/gpu/drm/radeon/radeon_cp.c b/trunk/drivers/gpu/drm/radeon/radeon_cp.c index aff90bb96488..77a7a4d84650 100644 --- a/trunk/drivers/gpu/drm/radeon/radeon_cp.c +++ b/trunk/drivers/gpu/drm/radeon/radeon_cp.c @@ -2185,9 +2185,9 @@ void radeon_commit_ring(drm_radeon_private_t *dev_priv) /* check if the ring is padded out to 16-dword alignment */ - tail_aligned = dev_priv->ring.tail & (RADEON_RING_ALIGN-1); + tail_aligned = dev_priv->ring.tail & 0xf; if (tail_aligned) { - int num_p2 = RADEON_RING_ALIGN - tail_aligned; + int num_p2 = 16 - tail_aligned; ring = dev_priv->ring.start; /* pad with some CP_PACKET2 */ diff --git a/trunk/drivers/gpu/drm/radeon/radeon_drv.h b/trunk/drivers/gpu/drm/radeon/radeon_drv.h index 0c6bfc1de153..8071d965f142 100644 --- a/trunk/drivers/gpu/drm/radeon/radeon_drv.h +++ b/trunk/drivers/gpu/drm/radeon/radeon_drv.h @@ -1964,14 +1964,11 @@ do { \ #define RING_LOCALS int write, _nr, _align_nr; unsigned int mask; u32 *ring; -#define RADEON_RING_ALIGN 16 - #define BEGIN_RING( n ) do { \ if ( RADEON_VERBOSE ) { \ DRM_INFO( "BEGIN_RING( %d )\n", (n)); \ } \ - _align_nr = RADEON_RING_ALIGN - ((dev_priv->ring.tail + n) & (RADEON_RING_ALIGN-1)); \ - _align_nr += n; \ + _align_nr = (n + 0xf) & ~0xf; \ if (dev_priv->ring.space <= (_align_nr * sizeof(u32))) { \ COMMIT_RING(); \ radeon_wait_ring( dev_priv, _align_nr * sizeof(u32)); \ diff --git a/trunk/drivers/hwmon/lm78.c b/trunk/drivers/hwmon/lm78.c index a1787fdf5b9f..b5e3b2851698 100644 --- a/trunk/drivers/hwmon/lm78.c +++ b/trunk/drivers/hwmon/lm78.c @@ -182,7 +182,7 @@ static struct platform_driver lm78_isa_driver = { .name = "lm78", }, .probe = lm78_isa_probe, - .remove = __devexit_p(lm78_isa_remove), + .remove = lm78_isa_remove, }; diff --git a/trunk/drivers/ide/ide-pci-generic.c b/trunk/drivers/ide/ide-pci-generic.c index 39d4e01f5c9c..61111fd27130 100644 --- a/trunk/drivers/ide/ide-pci-generic.c +++ b/trunk/drivers/ide/ide-pci-generic.c @@ -33,16 +33,6 @@ static int ide_generic_all; /* Set to claim all devices */ module_param_named(all_generic_ide, ide_generic_all, bool, 0444); MODULE_PARM_DESC(all_generic_ide, "IDE generic will claim all unknown PCI IDE storage controllers."); -static void netcell_quirkproc(ide_drive_t *drive) -{ - /* mark words 85-87 as valid */ - drive->id[ATA_ID_CSF_DEFAULT] |= 0x4000; -} - -static const struct ide_port_ops netcell_port_ops = { - .quirkproc = netcell_quirkproc, -}; - #define DECLARE_GENERIC_PCI_DEV(extra_flags) \ { \ .name = DRV_NAME, \ @@ -84,7 +74,6 @@ static const struct ide_port_info generic_chipsets[] __devinitdata = { { /* 6: Revolution */ .name = DRV_NAME, - .port_ops = &netcell_port_ops, .host_flags = IDE_HFLAG_CLEAR_SIMPLEX | IDE_HFLAG_TRUST_BIOS_FOR_DMA | IDE_HFLAG_OFF_BOARD, diff --git a/trunk/drivers/ide/pdc202xx_old.c b/trunk/drivers/ide/pdc202xx_old.c index b3bc96f930a6..248a54bd2386 100644 --- a/trunk/drivers/ide/pdc202xx_old.c +++ b/trunk/drivers/ide/pdc202xx_old.c @@ -1,6 +1,6 @@ /* * Copyright (C) 1998-2002 Andre Hedrick - * Copyright (C) 2006-2007, 2009 MontaVista Software, Inc. + * Copyright (C) 2006-2007 MontaVista Software, Inc. * Copyright (C) 2007 Bartlomiej Zolnierkiewicz * * Portions Copyright (C) 1999 Promise Technology, Inc. @@ -227,19 +227,28 @@ static int pdc202xx_dma_test_irq(ide_drive_t *drive) return (dma_stat & 4) == 4; /* return 1 if INTR asserted */ } -static void pdc202xx_reset(ide_drive_t *drive) +static void pdc202xx_reset_host (ide_hwif_t *hwif) { - ide_hwif_t *hwif = drive->hwif; unsigned long high_16 = hwif->extra_base - 16; u8 udma_speed_flag = inb(high_16 | 0x001f); - printk(KERN_WARNING "PDC202xx: software reset...\n"); - outb(udma_speed_flag | 0x10, high_16 | 0x001f); mdelay(100); outb(udma_speed_flag & ~0x10, high_16 | 0x001f); mdelay(2000); /* 2 seconds ?! */ + printk(KERN_WARNING "PDC202XX: %s channel reset.\n", + hwif->channel ? "Secondary" : "Primary"); +} + +static void pdc202xx_reset (ide_drive_t *drive) +{ + ide_hwif_t *hwif = drive->hwif; + ide_hwif_t *mate = hwif->mate; + + pdc202xx_reset_host(hwif); + pdc202xx_reset_host(mate); + ide_set_max_pio(drive); } @@ -319,8 +328,9 @@ static const struct ide_dma_ops pdc20246_dma_ops = { .dma_start = ide_dma_start, .dma_end = ide_dma_end, .dma_test_irq = pdc202xx_dma_test_irq, - .dma_lost_irq = ide_dma_lost_irq, + .dma_lost_irq = pdc202xx_dma_lost_irq, .dma_timer_expiry = ide_dma_sff_timer_expiry, + .dma_clear = pdc202xx_reset, .dma_sff_read_status = ide_dma_sff_read_status, }; diff --git a/trunk/drivers/idle/i7300_idle.c b/trunk/drivers/idle/i7300_idle.c index 949c97ff57e3..bf740394d704 100644 --- a/trunk/drivers/idle/i7300_idle.c +++ b/trunk/drivers/idle/i7300_idle.c @@ -41,10 +41,6 @@ static int debug; module_param_named(debug, debug, uint, 0644); MODULE_PARM_DESC(debug, "Enable debug printks in this driver"); -static int forceload; -module_param_named(forceload, forceload, uint, 0644); -MODULE_PARM_DESC(debug, "Enable driver testing on unvalidated i5000"); - #define dprintk(fmt, arg...) \ do { if (debug) printk(KERN_INFO I7300_PRINT fmt, ##arg); } while (0) @@ -556,7 +552,7 @@ static int __init i7300_idle_init(void) cpus_clear(idle_cpumask); total_us = 0; - if (i7300_idle_platform_probe(&fbd_dev, &ioat_dev, forceload)) + if (i7300_idle_platform_probe(&fbd_dev, &ioat_dev)) return -ENODEV; if (i7300_idle_thrt_save()) diff --git a/trunk/drivers/md/raid5.c b/trunk/drivers/md/raid5.c index bb37fb1b2d82..5d400aef8d9b 100644 --- a/trunk/drivers/md/raid5.c +++ b/trunk/drivers/md/raid5.c @@ -362,7 +362,7 @@ static void raid5_unplug_device(struct request_queue *q); static struct stripe_head * get_active_stripe(raid5_conf_t *conf, sector_t sector, - int previous, int noblock, int noquiesce) + int previous, int noblock) { struct stripe_head *sh; @@ -372,7 +372,7 @@ get_active_stripe(raid5_conf_t *conf, sector_t sector, do { wait_event_lock_irq(conf->wait_for_stripe, - conf->quiesce == 0 || noquiesce, + conf->quiesce == 0, conf->device_lock, /* nothing */); sh = __find_stripe(conf, sector, conf->generation - previous); if (!sh) { @@ -2671,7 +2671,7 @@ static void handle_stripe_expansion(raid5_conf_t *conf, struct stripe_head *sh, sector_t bn = compute_blocknr(sh, i, 1); sector_t s = raid5_compute_sector(conf, bn, 0, &dd_idx, NULL); - sh2 = get_active_stripe(conf, s, 0, 1, 1); + sh2 = get_active_stripe(conf, s, 0, 1); if (sh2 == NULL) /* so far only the early blocks of this stripe * have been requested. When later blocks @@ -2944,7 +2944,7 @@ static bool handle_stripe5(struct stripe_head *sh) /* Finish reconstruct operations initiated by the expansion process */ if (sh->reconstruct_state == reconstruct_state_result) { struct stripe_head *sh2 - = get_active_stripe(conf, sh->sector, 1, 1, 1); + = get_active_stripe(conf, sh->sector, 1, 1); if (sh2 && test_bit(STRIPE_EXPAND_SOURCE, &sh2->state)) { /* sh cannot be written until sh2 has been read. * so arrange for sh to be delayed a little @@ -3189,7 +3189,7 @@ static bool handle_stripe6(struct stripe_head *sh, struct page *tmp_page) if (s.expanded && test_bit(STRIPE_EXPANDING, &sh->state)) { struct stripe_head *sh2 - = get_active_stripe(conf, sh->sector, 1, 1, 1); + = get_active_stripe(conf, sh->sector, 1, 1); if (sh2 && test_bit(STRIPE_EXPAND_SOURCE, &sh2->state)) { /* sh cannot be written until sh2 has been read. * so arrange for sh to be delayed a little @@ -3288,7 +3288,7 @@ static void unplug_slaves(mddev_t *mddev) int i; rcu_read_lock(); - for (i = 0; i < conf->raid_disks; i++) { + for (i=0; iraid_disks; i++) { mdk_rdev_t *rdev = rcu_dereference(conf->disks[i].rdev); if (rdev && !test_bit(Faulty, &rdev->flags) && atomic_read(&rdev->nr_pending)) { struct request_queue *r_queue = bdev_get_queue(rdev->bdev); @@ -3675,7 +3675,7 @@ static int make_request(struct request_queue *q, struct bio * bi) (unsigned long long)logical_sector); sh = get_active_stripe(conf, new_sector, previous, - (bi->bi_rw&RWA_MASK), 0); + (bi->bi_rw&RWA_MASK)); if (sh) { if (unlikely(previous)) { /* expansion might have moved on while waiting for a @@ -3873,7 +3873,7 @@ static sector_t reshape_request(mddev_t *mddev, sector_t sector_nr, int *skipped for (i = 0; i < reshape_sectors; i += STRIPE_SECTORS) { int j; int skipped = 0; - sh = get_active_stripe(conf, stripe_addr+i, 0, 0, 1); + sh = get_active_stripe(conf, stripe_addr+i, 0, 0); set_bit(STRIPE_EXPANDING, &sh->state); atomic_inc(&conf->reshape_stripes); /* If any of this stripe is beyond the end of the old @@ -3916,13 +3916,13 @@ static sector_t reshape_request(mddev_t *mddev, sector_t sector_nr, int *skipped raid5_compute_sector(conf, stripe_addr*(new_data_disks), 1, &dd_idx, NULL); last_sector = - raid5_compute_sector(conf, ((stripe_addr+reshape_sectors) + raid5_compute_sector(conf, ((stripe_addr+conf->chunk_size/512) *(new_data_disks) - 1), 1, &dd_idx, NULL); if (last_sector >= mddev->dev_sectors) last_sector = mddev->dev_sectors - 1; while (first_sector <= last_sector) { - sh = get_active_stripe(conf, first_sector, 1, 0, 1); + sh = get_active_stripe(conf, first_sector, 1, 0); set_bit(STRIPE_EXPAND_SOURCE, &sh->state); set_bit(STRIPE_HANDLE, &sh->state); release_stripe(sh); @@ -4022,9 +4022,9 @@ static inline sector_t sync_request(mddev_t *mddev, sector_t sector_nr, int *ski bitmap_cond_end_sync(mddev->bitmap, sector_nr); - sh = get_active_stripe(conf, sector_nr, 0, 1, 0); + sh = get_active_stripe(conf, sector_nr, 0, 1); if (sh == NULL) { - sh = get_active_stripe(conf, sector_nr, 0, 0, 0); + sh = get_active_stripe(conf, sector_nr, 0, 0); /* make sure we don't swamp the stripe cache if someone else * is trying to get access */ @@ -4034,7 +4034,7 @@ static inline sector_t sync_request(mddev_t *mddev, sector_t sector_nr, int *ski * We don't need to check the 'failed' flag as when that gets set, * recovery aborts. */ - for (i = 0; i < conf->raid_disks; i++) + for (i=0; iraid_disks; i++) if (conf->disks[i].rdev == NULL) still_degraded = 1; @@ -4086,7 +4086,7 @@ static int retry_aligned_read(raid5_conf_t *conf, struct bio *raid_bio) /* already done this stripe */ continue; - sh = get_active_stripe(conf, sector, 0, 1, 0); + sh = get_active_stripe(conf, sector, 0, 1); if (!sh) { /* failed to get a stripe - must wait */ diff --git a/trunk/drivers/media/video/ivtv/ivtv-queue.c b/trunk/drivers/media/video/ivtv/ivtv-queue.c index 7fde36e6d227..ff7b7deded4f 100644 --- a/trunk/drivers/media/video/ivtv/ivtv-queue.c +++ b/trunk/drivers/media/video/ivtv/ivtv-queue.c @@ -230,8 +230,7 @@ int ivtv_stream_alloc(struct ivtv_stream *s) return -ENOMEM; } if (ivtv_might_use_dma(s)) { - s->sg_handle = pci_map_single(itv->pdev, s->sg_dma, - sizeof(struct ivtv_sg_element), PCI_DMA_TODEVICE); + s->sg_handle = pci_map_single(itv->pdev, s->sg_dma, sizeof(struct ivtv_sg_element), s->dma); ivtv_stream_sync_for_cpu(s); } diff --git a/trunk/drivers/mmc/host/mvsdio.c b/trunk/drivers/mmc/host/mvsdio.c index b56d72ff06e9..c643d0fe118f 100644 --- a/trunk/drivers/mmc/host/mvsdio.c +++ b/trunk/drivers/mmc/host/mvsdio.c @@ -64,31 +64,6 @@ static int mvsd_setup_data(struct mvsd_host *host, struct mmc_data *data) unsigned int tmout; int tmout_index; - /* - * Hardware weirdness. The FIFO_EMPTY bit of the HW_STATE - * register is sometimes not set before a while when some - * "unusual" data block sizes are used (such as with the SWITCH - * command), even despite the fact that the XFER_DONE interrupt - * was raised. And if another data transfer starts before - * this bit comes to good sense (which eventually happens by - * itself) then the new transfer simply fails with a timeout. - */ - if (!(mvsd_read(MVSD_HW_STATE) & (1 << 13))) { - unsigned long t = jiffies + HZ; - unsigned int hw_state, count = 0; - do { - if (time_after(jiffies, t)) { - dev_warn(host->dev, "FIFO_EMPTY bit missing\n"); - break; - } - hw_state = mvsd_read(MVSD_HW_STATE); - count++; - } while (!(hw_state & (1 << 13))); - dev_dbg(host->dev, "*** wait for FIFO_EMPTY bit " - "(hw=0x%04x, count=%d, jiffies=%ld)\n", - hw_state, count, jiffies - (t - HZ)); - } - /* If timeout=0 then maximum timeout index is used. */ tmout = DIV_ROUND_UP(data->timeout_ns, host->ns_per_clk); tmout += data->timeout_clks; @@ -645,18 +620,9 @@ static void mvsd_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) if (ios->bus_width == MMC_BUS_WIDTH_4) ctrl_reg |= MVSD_HOST_CTRL_DATA_WIDTH_4_BITS; - /* - * The HI_SPEED_EN bit is causing trouble with many (but not all) - * high speed SD, SDHC and SDIO cards. Not enabling that bit - * makes all cards work. So let's just ignore that bit for now - * and revisit this issue if problems for not enabling this bit - * are ever reported. - */ -#if 0 if (ios->timing == MMC_TIMING_MMC_HS || ios->timing == MMC_TIMING_SD_HS) ctrl_reg |= MVSD_HOST_CTRL_HI_SPEED_EN; -#endif host->ctrl = ctrl_reg; mvsd_write(MVSD_HOST_CTRL, ctrl_reg); @@ -916,4 +882,3 @@ module_param(nodma, int, 0); MODULE_AUTHOR("Maen Suleiman, Nicolas Pitre"); MODULE_DESCRIPTION("Marvell MMC,SD,SDIO Host Controller driver"); MODULE_LICENSE("GPL"); -MODULE_ALIAS("platform:mvsdio"); diff --git a/trunk/drivers/mmc/host/mxcmmc.c b/trunk/drivers/mmc/host/mxcmmc.c index f4cbe473670e..b4a615c55f28 100644 --- a/trunk/drivers/mmc/host/mxcmmc.c +++ b/trunk/drivers/mmc/host/mxcmmc.c @@ -140,8 +140,6 @@ struct mxcmci_host { struct work_struct datawork; }; -static void mxcmci_set_clk_rate(struct mxcmci_host *host, unsigned int clk_ios); - static inline int mxcmci_use_dma(struct mxcmci_host *host) { return host->do_dma; @@ -162,7 +160,7 @@ static void mxcmci_softreset(struct mxcmci_host *host) writew(0xff, host->base + MMC_REG_RES_TO); } -static int mxcmci_setup_data(struct mxcmci_host *host, struct mmc_data *data) +static void mxcmci_setup_data(struct mxcmci_host *host, struct mmc_data *data) { unsigned int nob = data->blocks; unsigned int blksz = data->blksz; @@ -170,7 +168,6 @@ static int mxcmci_setup_data(struct mxcmci_host *host, struct mmc_data *data) #ifdef HAS_DMA struct scatterlist *sg; int i; - int ret; #endif if (data->flags & MMC_DATA_STREAM) nob = 0xffff; @@ -186,7 +183,7 @@ static int mxcmci_setup_data(struct mxcmci_host *host, struct mmc_data *data) for_each_sg(data->sg, sg, data->sg_len, i) { if (sg->offset & 3 || sg->length & 3) { host->do_dma = 0; - return 0; + return; } } @@ -195,30 +192,23 @@ static int mxcmci_setup_data(struct mxcmci_host *host, struct mmc_data *data) host->dma_nents = dma_map_sg(mmc_dev(host->mmc), data->sg, data->sg_len, host->dma_dir); - ret = imx_dma_setup_sg(host->dma, data->sg, host->dma_nents, - datasize, - host->res->start + MMC_REG_BUFFER_ACCESS, - DMA_MODE_READ); + imx_dma_setup_sg(host->dma, data->sg, host->dma_nents, datasize, + host->res->start + MMC_REG_BUFFER_ACCESS, + DMA_MODE_READ); } else { host->dma_dir = DMA_TO_DEVICE; host->dma_nents = dma_map_sg(mmc_dev(host->mmc), data->sg, data->sg_len, host->dma_dir); - ret = imx_dma_setup_sg(host->dma, data->sg, host->dma_nents, - datasize, - host->res->start + MMC_REG_BUFFER_ACCESS, - DMA_MODE_WRITE); + imx_dma_setup_sg(host->dma, data->sg, host->dma_nents, datasize, + host->res->start + MMC_REG_BUFFER_ACCESS, + DMA_MODE_WRITE); } - if (ret) { - dev_err(mmc_dev(host->mmc), "failed to setup DMA : %d\n", ret); - return ret; - } wmb(); imx_dma_enable(host->dma); #endif /* HAS_DMA */ - return 0; } static int mxcmci_start_cmd(struct mxcmci_host *host, struct mmc_command *cmd, @@ -355,11 +345,8 @@ static int mxcmci_poll_status(struct mxcmci_host *host, u32 mask) stat = readl(host->base + MMC_REG_STATUS); if (stat & STATUS_ERR_MASK) return stat; - if (time_after(jiffies, timeout)) { - mxcmci_softreset(host); - mxcmci_set_clk_rate(host, host->clock); + if (time_after(jiffies, timeout)) return STATUS_TIME_OUT_READ; - } if (stat & mask) return 0; cpu_relax(); @@ -544,7 +531,6 @@ static void mxcmci_request(struct mmc_host *mmc, struct mmc_request *req) { struct mxcmci_host *host = mmc_priv(mmc); unsigned int cmdat = host->cmdat; - int error; WARN_ON(host->req != NULL); @@ -554,12 +540,7 @@ static void mxcmci_request(struct mmc_host *mmc, struct mmc_request *req) host->do_dma = 1; #endif if (req->data) { - error = mxcmci_setup_data(host, req->data); - if (error) { - req->cmd->error = error; - goto out; - } - + mxcmci_setup_data(host, req->data); cmdat |= CMD_DAT_CONT_DATA_ENABLE; @@ -567,9 +548,7 @@ static void mxcmci_request(struct mmc_host *mmc, struct mmc_request *req) cmdat |= CMD_DAT_CONT_WRITE; } - error = mxcmci_start_cmd(host, req->cmd, cmdat); -out: - if (error) + if (mxcmci_start_cmd(host, req->cmd, cmdat)) mxcmci_finish_request(host, req); } @@ -745,9 +724,7 @@ static int mxcmci_probe(struct platform_device *pdev) goto out_clk_put; } - mmc->f_min = clk_get_rate(host->clk) >> 16; - if (mmc->f_min < 400000) - mmc->f_min = 400000; + mmc->f_min = clk_get_rate(host->clk) >> 7; mmc->f_max = clk_get_rate(host->clk) >> 1; /* recommended in data sheet */ diff --git a/trunk/drivers/mmc/host/omap.c b/trunk/drivers/mmc/host/omap.c index dceb5ee3bda0..bfa25c01c872 100644 --- a/trunk/drivers/mmc/host/omap.c +++ b/trunk/drivers/mmc/host/omap.c @@ -822,7 +822,7 @@ static irqreturn_t mmc_omap_irq(int irq, void *dev_id) del_timer(&host->cmd_abort_timer); host->abort = 1; OMAP_MMC_WRITE(host, IE, 0); - disable_irq_nosync(host->irq); + disable_irq(host->irq); schedule_work(&host->cmd_abort_work); return IRQ_HANDLED; } diff --git a/trunk/drivers/mmc/host/omap_hsmmc.c b/trunk/drivers/mmc/host/omap_hsmmc.c index c40cb96255a2..e62a22a7f00c 100644 --- a/trunk/drivers/mmc/host/omap_hsmmc.c +++ b/trunk/drivers/mmc/host/omap_hsmmc.c @@ -680,7 +680,7 @@ static void mmc_omap_dma_cb(int lch, u16 ch_status, void *data) host->dma_ch = -1; /* * DMA Callback: run in interrupt context. - * mutex_unlock will throw a kernel warning if used. + * mutex_unlock will through a kernel warning if used. */ up(&host->sem); } diff --git a/trunk/drivers/mmc/host/sdhci-of.c b/trunk/drivers/mmc/host/sdhci-of.c index 128c614d11aa..3ff4ac3abe8b 100644 --- a/trunk/drivers/mmc/host/sdhci-of.c +++ b/trunk/drivers/mmc/host/sdhci-of.c @@ -55,13 +55,7 @@ static u32 esdhc_readl(struct sdhci_host *host, int reg) static u16 esdhc_readw(struct sdhci_host *host, int reg) { - u16 ret; - - if (unlikely(reg == SDHCI_HOST_VERSION)) - ret = in_be16(host->ioaddr + reg); - else - ret = in_be16(host->ioaddr + (reg ^ 0x2)); - return ret; + return in_be16(host->ioaddr + (reg ^ 0x2)); } static u8 esdhc_readb(struct sdhci_host *host, int reg) @@ -283,7 +277,6 @@ static int __devexit sdhci_of_remove(struct of_device *ofdev) static const struct of_device_id sdhci_of_match[] = { { .compatible = "fsl,mpc8379-esdhc", .data = &sdhci_esdhc, }, { .compatible = "fsl,mpc8536-esdhc", .data = &sdhci_esdhc, }, - { .compatible = "fsl,esdhc", .data = &sdhci_esdhc, }, { .compatible = "generic-sdhci", }, {}, }; diff --git a/trunk/drivers/mtd/nand/davinci_nand.c b/trunk/drivers/mtd/nand/davinci_nand.c index 02700f769b8a..0119220de7d0 100644 --- a/trunk/drivers/mtd/nand/davinci_nand.c +++ b/trunk/drivers/mtd/nand/davinci_nand.c @@ -407,17 +407,16 @@ static int __init nand_davinci_probe(struct platform_device *pdev) } info->chip.ecc.mode = ecc_mode; - info->clk = clk_get(&pdev->dev, "aemif"); + info->clk = clk_get(&pdev->dev, "AEMIFCLK"); if (IS_ERR(info->clk)) { ret = PTR_ERR(info->clk); - dev_dbg(&pdev->dev, "unable to get AEMIF clock, err %d\n", ret); + dev_dbg(&pdev->dev, "unable to get AEMIFCLK, err %d\n", ret); goto err_clk; } ret = clk_enable(info->clk); if (ret < 0) { - dev_dbg(&pdev->dev, "unable to enable AEMIF clock, err %d\n", - ret); + dev_dbg(&pdev->dev, "unable to enable AEMIFCLK, err %d\n", ret); goto err_clk_enable; } diff --git a/trunk/drivers/net/3c509.c b/trunk/drivers/net/3c509.c index 682aad897081..fbb371921991 100644 --- a/trunk/drivers/net/3c509.c +++ b/trunk/drivers/net/3c509.c @@ -480,13 +480,9 @@ static int pnp_registered; #ifdef CONFIG_EISA static struct eisa_device_id el3_eisa_ids[] = { - { "TCM5090" }, - { "TCM5091" }, { "TCM5092" }, { "TCM5093" }, - { "TCM5094" }, { "TCM5095" }, - { "TCM5098" }, { "" } }; MODULE_DEVICE_TABLE(eisa, el3_eisa_ids); diff --git a/trunk/drivers/net/atl1e/atl1e_main.c b/trunk/drivers/net/atl1e/atl1e_main.c index 1342418fb209..fb57b750866b 100644 --- a/trunk/drivers/net/atl1e/atl1e_main.c +++ b/trunk/drivers/net/atl1e/atl1e_main.c @@ -37,7 +37,6 @@ char atl1e_driver_version[] = DRV_VERSION; */ static struct pci_device_id atl1e_pci_tbl[] = { {PCI_DEVICE(PCI_VENDOR_ID_ATTANSIC, PCI_DEVICE_ID_ATTANSIC_L1E)}, - {PCI_DEVICE(PCI_VENDOR_ID_ATTANSIC, 0x1066)}, /* required last entry */ { 0 } }; diff --git a/trunk/drivers/net/atlx/atl1.c b/trunk/drivers/net/atlx/atl1.c index 4e817126e280..0ab22540bf59 100644 --- a/trunk/drivers/net/atlx/atl1.c +++ b/trunk/drivers/net/atlx/atl1.c @@ -82,12 +82,6 @@ #include "atl1.h" -#define ATLX_DRIVER_VERSION "2.1.3" -MODULE_AUTHOR("Xiong Huang , \ - Chris Snook , Jay Cliburn "); -MODULE_LICENSE("GPL"); -MODULE_VERSION(ATLX_DRIVER_VERSION); - /* Temporary hack for merging atl1 and atl2 */ #include "atlx.c" diff --git a/trunk/drivers/net/atlx/atlx.h b/trunk/drivers/net/atlx/atlx.h index 14054b75aa62..297a03da6b7f 100644 --- a/trunk/drivers/net/atlx/atlx.h +++ b/trunk/drivers/net/atlx/atlx.h @@ -29,6 +29,12 @@ #include #include +#define ATLX_DRIVER_VERSION "2.1.3" +MODULE_AUTHOR("Xiong Huang , \ + Chris Snook , Jay Cliburn "); +MODULE_LICENSE("GPL"); +MODULE_VERSION(ATLX_DRIVER_VERSION); + #define ATLX_ERR_PHY 2 #define ATLX_ERR_PHY_SPEED 7 #define ATLX_ERR_PHY_RES 8 diff --git a/trunk/drivers/net/bfin_mac.c b/trunk/drivers/net/bfin_mac.c index b4da18213324..9f971ed6b58d 100644 --- a/trunk/drivers/net/bfin_mac.c +++ b/trunk/drivers/net/bfin_mac.c @@ -979,7 +979,22 @@ static int bfin_mac_open(struct net_device *dev) return 0; } +static const struct net_device_ops bfin_mac_netdev_ops = { + .ndo_open = bfin_mac_open, + .ndo_stop = bfin_mac_close, + .ndo_start_xmit = bfin_mac_hard_start_xmit, + .ndo_set_mac_address = bfin_mac_set_mac_address, + .ndo_tx_timeout = bfin_mac_timeout, + .ndo_set_multicast_list = bfin_mac_set_multicast_list, + .ndo_validate_addr = eth_validate_addr, + .ndo_change_mtu = eth_change_mtu, +#ifdef CONFIG_NET_POLL_CONTROLLER + .ndo_poll_controller = bfin_mac_poll, +#endif +}; + /* + * * this makes the board clean up everything that it can * and not talk to the outside world. Caused by * an 'ifconfig ethX down' @@ -1004,20 +1019,6 @@ static int bfin_mac_close(struct net_device *dev) return 0; } -static const struct net_device_ops bfin_mac_netdev_ops = { - .ndo_open = bfin_mac_open, - .ndo_stop = bfin_mac_close, - .ndo_start_xmit = bfin_mac_hard_start_xmit, - .ndo_set_mac_address = bfin_mac_set_mac_address, - .ndo_tx_timeout = bfin_mac_timeout, - .ndo_set_multicast_list = bfin_mac_set_multicast_list, - .ndo_validate_addr = eth_validate_addr, - .ndo_change_mtu = eth_change_mtu, -#ifdef CONFIG_NET_POLL_CONTROLLER - .ndo_poll_controller = bfin_mac_poll, -#endif -}; - static int __devinit bfin_mac_probe(struct platform_device *pdev) { struct net_device *ndev; diff --git a/trunk/drivers/net/cxgb3/adapter.h b/trunk/drivers/net/cxgb3/adapter.h index c888e97c9671..714df2b675e6 100644 --- a/trunk/drivers/net/cxgb3/adapter.h +++ b/trunk/drivers/net/cxgb3/adapter.h @@ -85,8 +85,8 @@ struct fl_pg_chunk { struct page *page; void *va; unsigned int offset; - unsigned long *p_cnt; - dma_addr_t mapping; + u64 *p_cnt; + DECLARE_PCI_UNMAP_ADDR(mapping); }; struct rx_desc; diff --git a/trunk/drivers/net/cxgb3/cxgb3_main.c b/trunk/drivers/net/cxgb3/cxgb3_main.c index 17858b9a5830..7ea48414c6cb 100644 --- a/trunk/drivers/net/cxgb3/cxgb3_main.c +++ b/trunk/drivers/net/cxgb3/cxgb3_main.c @@ -2496,16 +2496,14 @@ static void check_link_status(struct adapter *adapter) for_each_port(adapter, i) { struct net_device *dev = adapter->port[i]; struct port_info *p = netdev_priv(dev); - int link_fault; spin_lock_irq(&adapter->work_lock); - link_fault = p->link_fault; - spin_unlock_irq(&adapter->work_lock); - - if (link_fault) { + if (p->link_fault) { t3_link_fault(adapter, i); + spin_unlock_irq(&adapter->work_lock); continue; } + spin_unlock_irq(&adapter->work_lock); if (!(p->phy.caps & SUPPORTED_IRQ) && netif_running(dev)) { t3_xgm_intr_disable(adapter, i); diff --git a/trunk/drivers/net/cxgb3/sge.c b/trunk/drivers/net/cxgb3/sge.c index b3ee2bc1a005..26d3587f3399 100644 --- a/trunk/drivers/net/cxgb3/sge.c +++ b/trunk/drivers/net/cxgb3/sge.c @@ -355,7 +355,7 @@ static void clear_rx_desc(struct pci_dev *pdev, const struct sge_fl *q, (*d->pg_chunk.p_cnt)--; if (!*d->pg_chunk.p_cnt) pci_unmap_page(pdev, - d->pg_chunk.mapping, + pci_unmap_addr(&d->pg_chunk, mapping), q->alloc_size, PCI_DMA_FROMDEVICE); put_page(d->pg_chunk.page); @@ -454,7 +454,7 @@ static int alloc_pg_chunk(struct adapter *adapter, struct sge_fl *q, q->pg_chunk.offset = 0; mapping = pci_map_page(adapter->pdev, q->pg_chunk.page, 0, q->alloc_size, PCI_DMA_FROMDEVICE); - q->pg_chunk.mapping = mapping; + pci_unmap_addr_set(&q->pg_chunk, mapping, mapping); } sd->pg_chunk = q->pg_chunk; @@ -511,7 +511,8 @@ static int refill_fl(struct adapter *adap, struct sge_fl *q, int n, gfp_t gfp) nomem: q->alloc_failed++; break; } - mapping = sd->pg_chunk.mapping + sd->pg_chunk.offset; + mapping = pci_unmap_addr(&sd->pg_chunk, mapping) + + sd->pg_chunk.offset; pci_unmap_addr_set(sd, dma_addr, mapping); add_one_rx_chunk(mapping, d, q->gen); @@ -880,7 +881,7 @@ static struct sk_buff *get_packet_pg(struct adapter *adap, struct sge_fl *fl, (*sd->pg_chunk.p_cnt)--; if (!*sd->pg_chunk.p_cnt) pci_unmap_page(adap->pdev, - sd->pg_chunk.mapping, + pci_unmap_addr(&sd->pg_chunk, mapping), fl->alloc_size, PCI_DMA_FROMDEVICE); if (!skb) { @@ -2095,7 +2096,7 @@ static void lro_add_page(struct adapter *adap, struct sge_qset *qs, (*sd->pg_chunk.p_cnt)--; if (!*sd->pg_chunk.p_cnt) pci_unmap_page(adap->pdev, - sd->pg_chunk.mapping, + pci_unmap_addr(&sd->pg_chunk, mapping), fl->alloc_size, PCI_DMA_FROMDEVICE); diff --git a/trunk/drivers/net/cxgb3/t3_hw.c b/trunk/drivers/net/cxgb3/t3_hw.c index 4950d5d789ae..4f68aeb2679a 100644 --- a/trunk/drivers/net/cxgb3/t3_hw.c +++ b/trunk/drivers/net/cxgb3/t3_hw.c @@ -1274,11 +1274,6 @@ void t3_link_fault(struct adapter *adapter, int port_id) A_XGM_INT_STATUS + mac->offset); link_fault &= F_LINKFAULTCHANGE; - link_ok = lc->link_ok; - speed = lc->speed; - duplex = lc->duplex; - fc = lc->fc; - phy->ops->get_link_status(phy, &link_ok, &speed, &duplex, &fc); if (link_fault) { diff --git a/trunk/drivers/net/e1000/e1000_main.c b/trunk/drivers/net/e1000/e1000_main.c index fffb006b7d95..b1419e21b46b 100644 --- a/trunk/drivers/net/e1000/e1000_main.c +++ b/trunk/drivers/net/e1000/e1000_main.c @@ -4027,9 +4027,8 @@ static bool e1000_clean_rx_irq(struct e1000_adapter *adapter, PCI_DMA_FROMDEVICE); length = le16_to_cpu(rx_desc->length); - /* !EOP means multiple descriptors were used to store a single - * packet, also make sure the frame isn't just CRC only */ - if (unlikely(!(status & E1000_RXD_STAT_EOP) || (length <= 4))) { + + if (unlikely(!(status & E1000_RXD_STAT_EOP))) { /* All receives must fit into a single buffer */ E1000_DBG("%s: Receive packet consumed multiple" " buffers\n", netdev->name); diff --git a/trunk/drivers/net/forcedeth.c b/trunk/drivers/net/forcedeth.c index 9f6a68fb7b45..f9a846b1b92f 100644 --- a/trunk/drivers/net/forcedeth.c +++ b/trunk/drivers/net/forcedeth.c @@ -897,12 +897,6 @@ enum { }; static int phy_cross = NV_CROSSOVER_DETECTION_DISABLED; -/* - * Power down phy when interface is down (persists through reboot; - * older Linux and other OSes may not power it up again) - */ -static int phy_power_down = 0; - static inline struct fe_priv *get_nvpriv(struct net_device *dev) { return netdev_priv(dev); @@ -1491,10 +1485,7 @@ static int phy_init(struct net_device *dev) /* restart auto negotiation, power down phy */ mii_control = mii_rw(dev, np->phyaddr, MII_BMCR, MII_READ); - mii_control |= (BMCR_ANRESTART | BMCR_ANENABLE); - if (phy_power_down) { - mii_control |= BMCR_PDOWN; - } + mii_control |= (BMCR_ANRESTART | BMCR_ANENABLE | BMCR_PDOWN); if (mii_rw(dev, np->phyaddr, MII_BMCR, mii_control)) { return PHY_ERROR; } @@ -5522,7 +5513,7 @@ static int nv_close(struct net_device *dev) nv_drain_rxtx(dev); - if (np->wolenabled || !phy_power_down) { + if (np->wolenabled) { writel(NVREG_PFF_ALWAYS|NVREG_PFF_MYADDR, base + NvRegPacketFilterFlags); nv_start_rx(dev); } else { @@ -6376,8 +6367,6 @@ module_param(dma_64bit, int, 0); MODULE_PARM_DESC(dma_64bit, "High DMA is enabled by setting to 1 and disabled by setting to 0."); module_param(phy_cross, int, 0); MODULE_PARM_DESC(phy_cross, "Phy crossover detection for Realtek 8201 phy is enabled by setting to 1 and disabled by setting to 0."); -module_param(phy_power_down, int, 0); -MODULE_PARM_DESC(phy_power_down, "Power down phy and disable link when interface is down (1), or leave phy powered up (0)."); MODULE_AUTHOR("Manfred Spraul "); MODULE_DESCRIPTION("Reverse Engineered nForce ethernet driver"); diff --git a/trunk/drivers/net/gianfar.h b/trunk/drivers/net/gianfar.h index cf352961ae9b..0642d52aef5c 100644 --- a/trunk/drivers/net/gianfar.h +++ b/trunk/drivers/net/gianfar.h @@ -259,7 +259,7 @@ extern const char gfar_driver_version[]; (IEVENT_RXC | IEVENT_BSY | IEVENT_EBERR | IEVENT_MSRO | \ IEVENT_BABT | IEVENT_TXC | IEVENT_TXE | IEVENT_LC \ | IEVENT_CRL | IEVENT_XFUN | IEVENT_DPE | IEVENT_PERR \ - | IEVENT_MAG | IEVENT_BABR) + | IEVENT_MAG) #define IMASK_INIT_CLEAR 0x00000000 #define IMASK_BABR 0x80000000 diff --git a/trunk/drivers/net/mac8390.c b/trunk/drivers/net/mac8390.c index 22e74a0e0361..f26667d5eaae 100644 --- a/trunk/drivers/net/mac8390.c +++ b/trunk/drivers/net/mac8390.c @@ -489,7 +489,7 @@ static const struct net_device_ops mac8390_netdev_ops = { .ndo_set_mac_address = eth_mac_addr, .ndo_change_mtu = eth_change_mtu, #ifdef CONFIG_NET_POLL_CONTROLLER - .ndo_poll_controller = __ei_poll, + .ndo_poll_controller = ei_poll, #endif }; diff --git a/trunk/drivers/net/mlx4/en_tx.c b/trunk/drivers/net/mlx4/en_tx.c index e5c98a98ad37..ac6fc499b280 100644 --- a/trunk/drivers/net/mlx4/en_tx.c +++ b/trunk/drivers/net/mlx4/en_tx.c @@ -426,7 +426,7 @@ void mlx4_en_poll_tx_cq(unsigned long data) INC_PERF_COUNTER(priv->pstats.tx_poll); - if (!spin_trylock_irq(&ring->comp_lock)) { + if (!spin_trylock(&ring->comp_lock)) { mod_timer(&cq->timer, jiffies + MLX4_EN_TX_POLL_TIMEOUT); return; } @@ -439,7 +439,7 @@ void mlx4_en_poll_tx_cq(unsigned long data) if (inflight && priv->port_up) mod_timer(&cq->timer, jiffies + MLX4_EN_TX_POLL_TIMEOUT); - spin_unlock_irq(&ring->comp_lock); + spin_unlock(&ring->comp_lock); } static struct mlx4_en_tx_desc *mlx4_en_bounce_to_desc(struct mlx4_en_priv *priv, @@ -482,9 +482,9 @@ static inline void mlx4_en_xmit_poll(struct mlx4_en_priv *priv, int tx_ind) /* Poll the CQ every mlx4_en_TX_MODER_POLL packets */ if ((++ring->poll_cnt & (MLX4_EN_TX_POLL_MODER - 1)) == 0) - if (spin_trylock_irq(&ring->comp_lock)) { + if (spin_trylock(&ring->comp_lock)) { mlx4_en_process_tx_cq(priv->dev, cq); - spin_unlock_irq(&ring->comp_lock); + spin_unlock(&ring->comp_lock); } } diff --git a/trunk/drivers/net/r8169.c b/trunk/drivers/net/r8169.c index 3b19e0ce290f..8247a945a1d9 100644 --- a/trunk/drivers/net/r8169.c +++ b/trunk/drivers/net/r8169.c @@ -66,6 +66,7 @@ static const int multicast_filter_limit = 32; #define RX_DMA_BURST 6 /* Maximum PCI burst, '6' is 1024 */ #define TX_DMA_BURST 6 /* Maximum PCI burst, '6' is 1024 */ #define EarlyTxThld 0x3F /* 0x3F means NO early transmit */ +#define RxPacketMaxSize 0x3FE8 /* 16K - 1 - ETH_HLEN - VLAN - CRC... */ #define SafeMtu 0x1c20 /* ... actually life sucks beyond ~7k */ #define InterFrameGap 0x03 /* 3 means InterFrameGap = the shortest one */ @@ -2356,10 +2357,10 @@ static u16 rtl_rw_cpluscmd(void __iomem *ioaddr) return cmd; } -static void rtl_set_rx_max_size(void __iomem *ioaddr, unsigned int rx_buf_sz) +static void rtl_set_rx_max_size(void __iomem *ioaddr) { /* Low hurts. Let's disable the filtering. */ - RTL_W16(RxMaxSize, rx_buf_sz); + RTL_W16(RxMaxSize, 16383); } static void rtl8169_set_magic_reg(void __iomem *ioaddr, unsigned mac_version) @@ -2406,7 +2407,7 @@ static void rtl_hw_start_8169(struct net_device *dev) RTL_W8(EarlyTxThres, EarlyTxThld); - rtl_set_rx_max_size(ioaddr, tp->rx_buf_sz); + rtl_set_rx_max_size(ioaddr); if ((tp->mac_version == RTL_GIGA_MAC_VER_01) || (tp->mac_version == RTL_GIGA_MAC_VER_02) || @@ -2667,7 +2668,7 @@ static void rtl_hw_start_8168(struct net_device *dev) RTL_W8(EarlyTxThres, EarlyTxThld); - rtl_set_rx_max_size(ioaddr, tp->rx_buf_sz); + rtl_set_rx_max_size(ioaddr); tp->cp_cmd |= RTL_R16(CPlusCmd) | PktCntrDisable | INTT_1; @@ -2845,7 +2846,7 @@ static void rtl_hw_start_8101(struct net_device *dev) RTL_W8(EarlyTxThres, EarlyTxThld); - rtl_set_rx_max_size(ioaddr, tp->rx_buf_sz); + rtl_set_rx_max_size(ioaddr); tp->cp_cmd |= rtl_rw_cpluscmd(ioaddr) | PCIMulRW; diff --git a/trunk/drivers/net/wireless/Kconfig b/trunk/drivers/net/wireless/Kconfig index 3d94e7dfea69..8a0823588c51 100644 --- a/trunk/drivers/net/wireless/Kconfig +++ b/trunk/drivers/net/wireless/Kconfig @@ -430,7 +430,6 @@ config RTL8187 ASUS P5B Deluxe Toshiba Satellite Pro series of laptops Asus Wireless Link - Linksys WUSB54GC-EU Thanks to Realtek for their support! diff --git a/trunk/drivers/net/wireless/at76c50x-usb.c b/trunk/drivers/net/wireless/at76c50x-usb.c index 8d93ca4651b9..744f4f4dd3d1 100644 --- a/trunk/drivers/net/wireless/at76c50x-usb.c +++ b/trunk/drivers/net/wireless/at76c50x-usb.c @@ -1873,18 +1873,18 @@ static void at76_dwork_hw_scan(struct work_struct *work) if (ret != CMD_STATUS_COMPLETE) { queue_delayed_work(priv->hw->workqueue, &priv->dwork_hw_scan, SCAN_POLL_INTERVAL); - mutex_unlock(&priv->mtx); - return; + goto exit; } + ieee80211_scan_completed(priv->hw, false); + if (is_valid_ether_addr(priv->bssid)) at76_join(priv); - mutex_unlock(&priv->mtx); - - ieee80211_scan_completed(priv->hw, false); - ieee80211_wake_queues(priv->hw); + +exit: + mutex_unlock(&priv->mtx); } static int at76_hw_scan(struct ieee80211_hw *hw, diff --git a/trunk/drivers/net/wireless/rtl818x/rtl8187_dev.c b/trunk/drivers/net/wireless/rtl818x/rtl8187_dev.c index d51ba0a88c23..bac6cfba6abd 100644 --- a/trunk/drivers/net/wireless/rtl818x/rtl8187_dev.c +++ b/trunk/drivers/net/wireless/rtl818x/rtl8187_dev.c @@ -71,8 +71,6 @@ static struct usb_device_id rtl8187_table[] __devinitdata = { {USB_DEVICE(0x18E8, 0x6232), .driver_info = DEVICE_RTL8187}, /* AirLive */ {USB_DEVICE(0x1b75, 0x8187), .driver_info = DEVICE_RTL8187}, - /* Linksys */ - {USB_DEVICE(0x1737, 0x0073), .driver_info = DEVICE_RTL8187B}, {} }; diff --git a/trunk/drivers/parport/share.c b/trunk/drivers/parport/share.c index dffa5d4fb298..0ebca450ed29 100644 --- a/trunk/drivers/parport/share.c +++ b/trunk/drivers/parport/share.c @@ -614,10 +614,7 @@ parport_register_device(struct parport *port, const char *name, * pardevice fields. -arca */ port->ops->init_state(tmp, tmp->state); - if (!test_and_set_bit(PARPORT_DEVPROC_REGISTERED, &port->devflags)) { - port->proc_device = tmp; - parport_device_proc_register(tmp); - } + parport_device_proc_register(tmp); return tmp; out_free_all: @@ -649,13 +646,9 @@ void parport_unregister_device(struct pardevice *dev) } #endif - port = dev->port->physport; + parport_device_proc_unregister(dev); - if (port->proc_device == dev) { - port->proc_device = NULL; - clear_bit(PARPORT_DEVPROC_REGISTERED, &port->devflags); - parport_device_proc_unregister(dev); - } + port = dev->port->physport; if (port->cad == dev) { printk(KERN_DEBUG "%s: %s forgot to release port\n", diff --git a/trunk/drivers/pci/hotplug/acpiphp.h b/trunk/drivers/pci/hotplug/acpiphp.h index e68d5f20ffb3..4fc168b70095 100644 --- a/trunk/drivers/pci/hotplug/acpiphp.h +++ b/trunk/drivers/pci/hotplug/acpiphp.h @@ -129,6 +129,7 @@ struct acpiphp_func { struct acpiphp_bridge *bridge; /* Ejectable PCI-to-PCI bridge */ struct list_head sibling; + struct pci_dev *pci_dev; struct notifier_block nb; acpi_handle handle; diff --git a/trunk/drivers/pci/hotplug/acpiphp_glue.c b/trunk/drivers/pci/hotplug/acpiphp_glue.c index 3a6064bce561..a33794d9e0dc 100644 --- a/trunk/drivers/pci/hotplug/acpiphp_glue.c +++ b/trunk/drivers/pci/hotplug/acpiphp_glue.c @@ -32,6 +32,9 @@ /* * Lifetime rules for pci_dev: + * - The one in acpiphp_func has its refcount elevated by pci_get_slot() + * when the driver is loaded or when an insertion event occurs. It loses + * a refcount when its ejected or the driver unloads. * - The one in acpiphp_bridge has its refcount elevated by pci_get_slot() * when the bridge is scanned and it loses a refcount when the bridge * is removed. @@ -127,7 +130,6 @@ register_slot(acpi_handle handle, u32 lvl, void *context, void **rv) unsigned long long adr, sun; int device, function, retval; struct pci_bus *pbus = bridge->pci_bus; - struct pci_dev *pdev; if (!acpi_pci_check_ejectable(pbus, handle) && !is_dock_device(handle)) return AE_OK; @@ -211,10 +213,10 @@ register_slot(acpi_handle handle, u32 lvl, void *context, void **rv) newfunc->slot = slot; list_add_tail(&newfunc->sibling, &slot->funcs); - pdev = pci_get_slot(pbus, PCI_DEVFN(device, function)); - if (pdev) { + /* associate corresponding pci_dev */ + newfunc->pci_dev = pci_get_slot(pbus, PCI_DEVFN(device, function)); + if (newfunc->pci_dev) { slot->flags |= (SLOT_ENABLED | SLOT_POWEREDON); - pci_dev_put(pdev); } if (is_dock_device(handle)) { @@ -615,6 +617,7 @@ static void cleanup_bridge(struct acpiphp_bridge *bridge) if (ACPI_FAILURE(status)) err("failed to remove notify handler\n"); } + pci_dev_put(func->pci_dev); list_del(list); kfree(func); } @@ -1098,24 +1101,22 @@ static int __ref enable_device(struct acpiphp_slot *slot) pci_enable_bridges(bus); pci_bus_add_devices(bus); + /* associate pci_dev to our representation */ list_for_each (l, &slot->funcs) { func = list_entry(l, struct acpiphp_func, sibling); - dev = pci_get_slot(bus, PCI_DEVFN(slot->device, - func->function)); - if (!dev) + func->pci_dev = pci_get_slot(bus, PCI_DEVFN(slot->device, + func->function)); + if (!func->pci_dev) continue; - if (dev->hdr_type != PCI_HEADER_TYPE_BRIDGE && - dev->hdr_type != PCI_HEADER_TYPE_CARDBUS) { - pci_dev_put(dev); + if (func->pci_dev->hdr_type != PCI_HEADER_TYPE_BRIDGE && + func->pci_dev->hdr_type != PCI_HEADER_TYPE_CARDBUS) continue; - } status = find_p2p_bridge(func->handle, (u32)1, bus, NULL); if (ACPI_FAILURE(status)) warn("find_p2p_bridge failed (error code = 0x%x)\n", status); - pci_dev_put(dev); } slot->flags |= SLOT_ENABLED; @@ -1141,14 +1142,17 @@ static void disable_bridges(struct pci_bus *bus) */ static int disable_device(struct acpiphp_slot *slot) { + int retval = 0; struct acpiphp_func *func; - struct pci_dev *pdev; + struct list_head *l; /* is this slot already disabled? */ if (!(slot->flags & SLOT_ENABLED)) goto err_exit; - list_for_each_entry(func, &slot->funcs, sibling) { + list_for_each (l, &slot->funcs) { + func = list_entry(l, struct acpiphp_func, sibling); + if (func->bridge) { /* cleanup p2p bridges under this P2P bridge */ cleanup_p2p_bridge(func->bridge->handle, @@ -1156,28 +1160,35 @@ static int disable_device(struct acpiphp_slot *slot) func->bridge = NULL; } - pdev = pci_get_slot(slot->bridge->pci_bus, - PCI_DEVFN(slot->device, func->function)); - if (pdev) { - pci_stop_bus_device(pdev); - if (pdev->subordinate) { - disable_bridges(pdev->subordinate); - pci_disable_device(pdev); + if (func->pci_dev) { + pci_stop_bus_device(func->pci_dev); + if (func->pci_dev->subordinate) { + disable_bridges(func->pci_dev->subordinate); + pci_disable_device(func->pci_dev); } - pci_remove_bus_device(pdev); - pci_dev_put(pdev); } } - list_for_each_entry(func, &slot->funcs, sibling) { + list_for_each (l, &slot->funcs) { + func = list_entry(l, struct acpiphp_func, sibling); + acpiphp_unconfigure_ioapics(func->handle); acpiphp_bus_trim(func->handle); + /* try to remove anyway. + * acpiphp_bus_add might have been failed */ + + if (!func->pci_dev) + continue; + + pci_remove_bus_device(func->pci_dev); + pci_dev_put(func->pci_dev); + func->pci_dev = NULL; } slot->flags &= (~SLOT_ENABLED); -err_exit: - return 0; + err_exit: + return retval; } diff --git a/trunk/drivers/pci/probe.c b/trunk/drivers/pci/probe.c index f1ae2475ffff..e3c3e081b834 100644 --- a/trunk/drivers/pci/probe.c +++ b/trunk/drivers/pci/probe.c @@ -745,8 +745,6 @@ int pci_setup_device(struct pci_dev *dev) /* Early fixups, before probing the BARs */ pci_fixup_device(pci_fixup_early, dev); - /* device class may be changed after fixup */ - class = dev->class >> 8; switch (dev->hdr_type) { /* header type */ case PCI_HEADER_TYPE_NORMAL: /* standard header */ diff --git a/trunk/drivers/serial/imx.c b/trunk/drivers/serial/imx.c index 5f0be40dfdab..9f460b175c50 100644 --- a/trunk/drivers/serial/imx.c +++ b/trunk/drivers/serial/imx.c @@ -1031,8 +1031,6 @@ imx_console_setup(struct console *co, char *options) if (co->index == -1 || co->index >= ARRAY_SIZE(imx_ports)) co->index = 0; sport = imx_ports[co->index]; - if(sport == NULL) - return -ENODEV; if (options) uart_parse_options(options, &baud, &parity, &bits, &flow); diff --git a/trunk/drivers/ssb/embedded.c b/trunk/drivers/ssb/embedded.c index a0e0d246b592..7dc3a6b41397 100644 --- a/trunk/drivers/ssb/embedded.c +++ b/trunk/drivers/ssb/embedded.c @@ -29,7 +29,6 @@ int ssb_watchdog_timer_set(struct ssb_bus *bus, u32 ticks) } return -ENODEV; } -EXPORT_SYMBOL(ssb_watchdog_timer_set); u32 ssb_gpio_in(struct ssb_bus *bus, u32 mask) { diff --git a/trunk/firmware/cis/.gitignore b/trunk/firmware/cis/.gitignore deleted file mode 100644 index 1de39847f261..000000000000 --- a/trunk/firmware/cis/.gitignore +++ /dev/null @@ -1 +0,0 @@ -*.cis diff --git a/trunk/fs/autofs4/waitq.c b/trunk/fs/autofs4/waitq.c index 2341375386f8..eeb246845909 100644 --- a/trunk/fs/autofs4/waitq.c +++ b/trunk/fs/autofs4/waitq.c @@ -297,14 +297,20 @@ static int validate_request(struct autofs_wait_queue **wait, */ if (notify == NFY_MOUNT) { /* - * If the dentry was successfully mounted while we slept - * on the wait queue mutex we can return success. If it - * isn't mounted (doesn't have submounts for the case of - * a multi-mount with no mount at it's base) we can - * continue on and create a new request. - */ - if (have_submounts(dentry)) - return 0; + * If the dentry isn't hashed just go ahead and try the + * mount again with a new wait (not much else we can do). + */ + if (!d_unhashed(dentry)) { + /* + * But if the dentry is hashed, that means that we + * got here through the revalidate path. Thus, we + * need to check if the dentry has been mounted + * while we waited on the wq_mutex. If it has, + * simply return success. + */ + if (d_mountpoint(dentry)) + return 0; + } } return 1; diff --git a/trunk/fs/btrfs/extent-tree.c b/trunk/fs/btrfs/extent-tree.c index 35af93355063..3e2c7c738f23 100644 --- a/trunk/fs/btrfs/extent-tree.c +++ b/trunk/fs/btrfs/extent-tree.c @@ -2622,18 +2622,7 @@ static noinline int find_free_extent(struct btrfs_trans_handle *trans, search_start); if (block_group && block_group_bits(block_group, data)) { down_read(&space_info->groups_sem); - if (list_empty(&block_group->list) || - block_group->ro) { - /* - * someone is removing this block group, - * we can't jump into the have_block_group - * target because our list pointers are not - * valid - */ - btrfs_put_block_group(block_group); - up_read(&space_info->groups_sem); - } else - goto have_block_group; + goto have_block_group; } else if (block_group) { btrfs_put_block_group(block_group); } @@ -2667,13 +2656,6 @@ static noinline int find_free_extent(struct btrfs_trans_handle *trans, * people trying to start a new cluster */ spin_lock(&last_ptr->refill_lock); - if (last_ptr->block_group && - (last_ptr->block_group->ro || - !block_group_bits(last_ptr->block_group, data))) { - offset = 0; - goto refill_cluster; - } - offset = btrfs_alloc_from_cluster(block_group, last_ptr, num_bytes, search_start); if (offset) { @@ -2699,17 +2681,10 @@ static noinline int find_free_extent(struct btrfs_trans_handle *trans, last_ptr_loop = 1; search_start = block_group->key.objectid; - /* - * we know this block group is properly - * in the list because - * btrfs_remove_block_group, drops the - * cluster before it removes the block - * group from the list - */ goto have_block_group; } spin_unlock(&last_ptr->lock); -refill_cluster: + /* * this cluster didn't work out, free it and * start over @@ -5993,7 +5968,6 @@ int btrfs_remove_block_group(struct btrfs_trans_handle *trans, { struct btrfs_path *path; struct btrfs_block_group_cache *block_group; - struct btrfs_free_cluster *cluster; struct btrfs_key key; int ret; @@ -6005,21 +5979,6 @@ int btrfs_remove_block_group(struct btrfs_trans_handle *trans, memcpy(&key, &block_group->key, sizeof(key)); - /* make sure this block group isn't part of an allocation cluster */ - cluster = &root->fs_info->data_alloc_cluster; - spin_lock(&cluster->refill_lock); - btrfs_return_cluster_to_free_space(block_group, cluster); - spin_unlock(&cluster->refill_lock); - - /* - * make sure this block group isn't part of a metadata - * allocation cluster - */ - cluster = &root->fs_info->meta_alloc_cluster; - spin_lock(&cluster->refill_lock); - btrfs_return_cluster_to_free_space(block_group, cluster); - spin_unlock(&cluster->refill_lock); - path = btrfs_alloc_path(); BUG_ON(!path); @@ -6029,11 +5988,7 @@ int btrfs_remove_block_group(struct btrfs_trans_handle *trans, spin_unlock(&root->fs_info->block_group_cache_lock); btrfs_remove_free_space_cache(block_group); down_write(&block_group->space_info->groups_sem); - /* - * we must use list_del_init so people can check to see if they - * are still on the list after taking the semaphore - */ - list_del_init(&block_group->list); + list_del(&block_group->list); up_write(&block_group->space_info->groups_sem); spin_lock(&block_group->space_info->lock); diff --git a/trunk/fs/btrfs/volumes.c b/trunk/fs/btrfs/volumes.c index a6d35b0054ca..5f01dad4b696 100644 --- a/trunk/fs/btrfs/volumes.c +++ b/trunk/fs/btrfs/volumes.c @@ -1440,7 +1440,6 @@ int btrfs_init_new_device(struct btrfs_root *root, char *device_path) device->io_align = root->sectorsize; device->sector_size = root->sectorsize; device->total_bytes = i_size_read(bdev->bd_inode); - device->disk_total_bytes = device->total_bytes; device->dev_root = root->fs_info->dev_root; device->bdev = bdev; device->in_fs_metadata = 1; diff --git a/trunk/fs/buffer.c b/trunk/fs/buffer.c index 49106127a4aa..aed297739eb0 100644 --- a/trunk/fs/buffer.c +++ b/trunk/fs/buffer.c @@ -2736,8 +2736,6 @@ int nobh_truncate_page(struct address_space *mapping, pos += blocksize; } - map_bh.b_size = blocksize; - map_bh.b_state = 0; err = get_block(inode, iblock, &map_bh, 0); if (err) goto unlock; diff --git a/trunk/fs/inode.c b/trunk/fs/inode.c index bca0c618fdb3..0571983755dc 100644 --- a/trunk/fs/inode.c +++ b/trunk/fs/inode.c @@ -219,7 +219,6 @@ static struct inode *alloc_inode(struct super_block *sb) void destroy_inode(struct inode *inode) { BUG_ON(inode_has_buffers(inode)); - ima_inode_free(inode); security_inode_free(inode); if (inode->i_sb->s_op->destroy_inode) inode->i_sb->s_op->destroy_inode(inode); @@ -1054,22 +1053,13 @@ int insert_inode_locked(struct inode *inode) struct super_block *sb = inode->i_sb; ino_t ino = inode->i_ino; struct hlist_head *head = inode_hashtable + hash(sb, ino); + struct inode *old; inode->i_state |= I_LOCK|I_NEW; while (1) { - struct hlist_node *node; - struct inode *old = NULL; spin_lock(&inode_lock); - hlist_for_each_entry(old, node, head, i_hash) { - if (old->i_ino != ino) - continue; - if (old->i_sb != sb) - continue; - if (old->i_state & (I_FREEING|I_CLEAR|I_WILL_FREE)) - continue; - break; - } - if (likely(!node)) { + old = find_inode_fast(sb, head, ino); + if (likely(!old)) { hlist_add_head(&inode->i_hash, head); spin_unlock(&inode_lock); return 0; @@ -1091,24 +1081,14 @@ int insert_inode_locked4(struct inode *inode, unsigned long hashval, { struct super_block *sb = inode->i_sb; struct hlist_head *head = inode_hashtable + hash(sb, hashval); + struct inode *old; inode->i_state |= I_LOCK|I_NEW; while (1) { - struct hlist_node *node; - struct inode *old = NULL; - spin_lock(&inode_lock); - hlist_for_each_entry(old, node, head, i_hash) { - if (old->i_sb != sb) - continue; - if (!test(old, data)) - continue; - if (old->i_state & (I_FREEING|I_CLEAR|I_WILL_FREE)) - continue; - break; - } - if (likely(!node)) { + old = find_inode(sb, head, test, data); + if (likely(!old)) { hlist_add_head(&inode->i_hash, head); spin_unlock(&inode_lock); return 0; diff --git a/trunk/fs/jbd/commit.c b/trunk/fs/jbd/commit.c index 618e21c0b7a3..06560c520f49 100644 --- a/trunk/fs/jbd/commit.c +++ b/trunk/fs/jbd/commit.c @@ -241,7 +241,7 @@ static int journal_submit_data_buffers(journal_t *journal, spin_lock(&journal->j_list_lock); } /* Someone already cleaned up the buffer? */ - if (!buffer_jbd(bh) || bh2jh(bh) != jh + if (!buffer_jbd(bh) || jh->b_transaction != commit_transaction || jh->b_jlist != BJ_SyncData) { jbd_unlock_bh_state(bh); @@ -478,9 +478,7 @@ void journal_commit_transaction(journal_t *journal) spin_lock(&journal->j_list_lock); continue; } - if (buffer_jbd(bh) && bh2jh(bh) == jh && - jh->b_transaction == commit_transaction && - jh->b_jlist == BJ_Locked) { + if (buffer_jbd(bh) && jh->b_jlist == BJ_Locked) { __journal_unfile_buffer(jh); jbd_unlock_bh_state(bh); journal_remove_journal_head(bh); diff --git a/trunk/fs/nilfs2/cpfile.c b/trunk/fs/nilfs2/cpfile.c index 300f1cdfa862..e90b60dfced9 100644 --- a/trunk/fs/nilfs2/cpfile.c +++ b/trunk/fs/nilfs2/cpfile.c @@ -311,7 +311,7 @@ int nilfs_cpfile_delete_checkpoints(struct inode *cpfile, ret = nilfs_cpfile_get_checkpoint_block(cpfile, cno, 0, &cp_bh); if (ret < 0) { if (ret != -ENOENT) - goto out_header; + goto out_sem; /* skip hole */ ret = 0; continue; @@ -344,7 +344,7 @@ int nilfs_cpfile_delete_checkpoints(struct inode *cpfile, continue; printk(KERN_ERR "%s: cannot delete block\n", __func__); - goto out_header; + goto out_sem; } } @@ -361,8 +361,6 @@ int nilfs_cpfile_delete_checkpoints(struct inode *cpfile, nilfs_mdt_mark_dirty(cpfile); kunmap_atomic(kaddr, KM_USER0); } - - out_header: brelse(header_bh); out_sem: diff --git a/trunk/fs/xfs/linux-2.6/kmem.h b/trunk/fs/xfs/linux-2.6/kmem.h index 179cbd630f69..af6843c7ee4b 100644 --- a/trunk/fs/xfs/linux-2.6/kmem.h +++ b/trunk/fs/xfs/linux-2.6/kmem.h @@ -103,7 +103,7 @@ extern void *kmem_zone_zalloc(kmem_zone_t *, unsigned int __nocast); static inline int kmem_shake_allow(gfp_t gfp_mask) { - return ((gfp_mask & __GFP_WAIT) && (gfp_mask & __GFP_FS)); + return (gfp_mask & __GFP_WAIT) != 0; } #endif /* __XFS_SUPPORT_KMEM_H__ */ diff --git a/trunk/fs/xfs/xfs_dfrag.c b/trunk/fs/xfs/xfs_dfrag.c index 7465f9ee125f..e6d839bddbf0 100644 --- a/trunk/fs/xfs/xfs_dfrag.c +++ b/trunk/fs/xfs/xfs_dfrag.c @@ -347,14 +347,12 @@ xfs_swap_extents( error = xfs_trans_commit(tp, XFS_TRANS_SWAPEXT); -out: - kmem_free(tempifp); - return error; - out_unlock: xfs_iunlock(ip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL); xfs_iunlock(tip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL); - goto out; +out: + kmem_free(tempifp); + return error; out_trans_cancel: xfs_trans_cancel(tp, 0); diff --git a/trunk/fs/xfs/xfs_fsops.c b/trunk/fs/xfs/xfs_fsops.c index cbd451bb4848..8379e3bca26c 100644 --- a/trunk/fs/xfs/xfs_fsops.c +++ b/trunk/fs/xfs/xfs_fsops.c @@ -160,7 +160,7 @@ xfs_growfs_data_private( nagcount = new + (nb_mod != 0); if (nb_mod && nb_mod < XFS_MIN_AG_BLOCKS) { nagcount--; - nb = (xfs_rfsblock_t)nagcount * mp->m_sb.sb_agblocks; + nb = nagcount * mp->m_sb.sb_agblocks; if (nb < mp->m_sb.sb_dblocks) return XFS_ERROR(EINVAL); } diff --git a/trunk/include/drm/drm_crtc.h b/trunk/include/drm/drm_crtc.h index 7300fb866767..3c1924c010e8 100644 --- a/trunk/include/drm/drm_crtc.h +++ b/trunk/include/drm/drm_crtc.h @@ -471,9 +471,6 @@ struct drm_connector { u32 property_ids[DRM_CONNECTOR_MAX_PROPERTY]; uint64_t property_values[DRM_CONNECTOR_MAX_PROPERTY]; - /* requested DPMS state */ - int dpms; - void *helper_private; uint32_t encoder_ids[DRM_CONNECTOR_MAX_ENCODER]; diff --git a/trunk/include/drm/drm_crtc_helper.h b/trunk/include/drm/drm_crtc_helper.h index 6769ff6c1bc0..ec073d8288d9 100644 --- a/trunk/include/drm/drm_crtc_helper.h +++ b/trunk/include/drm/drm_crtc_helper.h @@ -99,8 +99,6 @@ extern bool drm_crtc_helper_set_mode(struct drm_crtc *crtc, struct drm_framebuffer *old_fb); extern bool drm_helper_crtc_in_use(struct drm_crtc *crtc); -extern void drm_helper_connector_dpms(struct drm_connector *connector, int mode); - extern int drm_helper_mode_fill_fb_struct(struct drm_framebuffer *fb, struct drm_mode_fb_cmd *mode_cmd); diff --git a/trunk/include/linux/amba/serial.h b/trunk/include/linux/amba/serial.h index 64a982ea5d5f..48ee32a18ac5 100644 --- a/trunk/include/linux/amba/serial.h +++ b/trunk/include/linux/amba/serial.h @@ -159,7 +159,6 @@ #define UART01x_FR_MODEM_ANY (UART01x_FR_DCD|UART01x_FR_DSR|UART01x_FR_CTS) #ifndef __ASSEMBLY__ -struct amba_device; /* in uncompress this is included but amba/bus.h is not */ struct amba_pl010_data { void (*set_mctrl)(struct amba_device *dev, void __iomem *base, unsigned int mctrl); }; diff --git a/trunk/include/linux/auto_fs.h b/trunk/include/linux/auto_fs.h index 7b09c8348fd3..63265852b7d1 100644 --- a/trunk/include/linux/auto_fs.h +++ b/trunk/include/linux/auto_fs.h @@ -14,12 +14,13 @@ #ifndef _LINUX_AUTO_FS_H #define _LINUX_AUTO_FS_H -#include #ifdef __KERNEL__ #include #include +#include #include #else +#include #include #endif /* __KERNEL__ */ diff --git a/trunk/include/linux/cpumask.h b/trunk/include/linux/cpumask.h index c5ac87ca7bc6..9f315382610b 100644 --- a/trunk/include/linux/cpumask.h +++ b/trunk/include/linux/cpumask.h @@ -1022,8 +1022,6 @@ typedef struct cpumask *cpumask_var_t; bool alloc_cpumask_var_node(cpumask_var_t *mask, gfp_t flags, int node); bool alloc_cpumask_var(cpumask_var_t *mask, gfp_t flags); -bool zalloc_cpumask_var_node(cpumask_var_t *mask, gfp_t flags, int node); -bool zalloc_cpumask_var(cpumask_var_t *mask, gfp_t flags); void alloc_bootmem_cpumask_var(cpumask_var_t *mask); void free_cpumask_var(cpumask_var_t mask); void free_bootmem_cpumask_var(cpumask_var_t mask); @@ -1042,19 +1040,6 @@ static inline bool alloc_cpumask_var_node(cpumask_var_t *mask, gfp_t flags, return true; } -static inline bool zalloc_cpumask_var(cpumask_var_t *mask, gfp_t flags) -{ - cpumask_clear(*mask); - return true; -} - -static inline bool zalloc_cpumask_var_node(cpumask_var_t *mask, gfp_t flags, - int node) -{ - cpumask_clear(*mask); - return true; -} - static inline void alloc_bootmem_cpumask_var(cpumask_var_t *mask) { } diff --git a/trunk/include/linux/i7300_idle.h b/trunk/include/linux/i7300_idle.h index 1587b7dec505..05a80c44513c 100644 --- a/trunk/include/linux/i7300_idle.h +++ b/trunk/include/linux/i7300_idle.h @@ -16,33 +16,35 @@ struct fbd_ioat { unsigned int vendor; unsigned int ioat_dev; - unsigned int enabled; }; /* * The i5000 chip-set has the same hooks as the i7300 - * but it is not enabled by default and must be manually - * manually enabled with "forceload=1" because it is - * only lightly validated. + * but support is disabled by default because this driver + * has not been validated on that platform. */ +#define SUPPORT_I5000 0 static const struct fbd_ioat fbd_ioat_list[] = { - {PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_IOAT_CNB, 1}, - {PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_IOAT, 0}, + {PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_IOAT_CNB}, +#if SUPPORT_I5000 + {PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_IOAT}, +#endif {0, 0} }; /* table of devices that work with this driver */ static const struct pci_device_id pci_tbl[] = { { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_FBD_CNB) }, +#if SUPPORT_I5000 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_5000_ERR) }, +#endif { } /* Terminating entry */ }; /* Check for known platforms with I/O-AT */ static inline int i7300_idle_platform_probe(struct pci_dev **fbd_dev, - struct pci_dev **ioat_dev, - int enable_all) + struct pci_dev **ioat_dev) { int i; struct pci_dev *memdev, *dmadev; @@ -67,8 +69,6 @@ static inline int i7300_idle_platform_probe(struct pci_dev **fbd_dev, for (i = 0; fbd_ioat_list[i].vendor != 0; i++) { if (dmadev->vendor == fbd_ioat_list[i].vendor && dmadev->device == fbd_ioat_list[i].ioat_dev) { - if (!(fbd_ioat_list[i].enabled || enable_all)) - continue; if (fbd_dev) *fbd_dev = memdev; if (ioat_dev) diff --git a/trunk/include/linux/net_dropmon.h b/trunk/include/linux/net_dropmon.h index 0e2e100c44a2..0217fb81a630 100644 --- a/trunk/include/linux/net_dropmon.h +++ b/trunk/include/linux/net_dropmon.h @@ -1,7 +1,6 @@ #ifndef __NET_DROPMON_H #define __NET_DROPMON_H -#include #include struct net_dm_drop_point { diff --git a/trunk/include/linux/netfilter/nf_conntrack_tcp.h b/trunk/include/linux/netfilter/nf_conntrack_tcp.h index b2f384d42611..3066789b972a 100644 --- a/trunk/include/linux/netfilter/nf_conntrack_tcp.h +++ b/trunk/include/linux/netfilter/nf_conntrack_tcp.h @@ -35,9 +35,6 @@ enum tcp_conntrack { /* Has unacknowledged data */ #define IP_CT_TCP_FLAG_DATA_UNACKNOWLEDGED 0x10 -/* The field td_maxack has been set */ -#define IP_CT_TCP_FLAG_MAXACK_SET 0x20 - struct nf_ct_tcp_flags { __u8 flags; __u8 mask; @@ -49,7 +46,6 @@ struct ip_ct_tcp_state { u_int32_t td_end; /* max of seq + len */ u_int32_t td_maxend; /* max of ack + max(win, 1) */ u_int32_t td_maxwin; /* max(win) */ - u_int32_t td_maxack; /* max of ack */ u_int8_t td_scale; /* window scale factor */ u_int8_t flags; /* per direction options */ }; diff --git a/trunk/include/linux/parport.h b/trunk/include/linux/parport.h index 38a423ed3c01..e1f83c5065c5 100644 --- a/trunk/include/linux/parport.h +++ b/trunk/include/linux/parport.h @@ -324,10 +324,6 @@ struct parport { int spintime; atomic_t ref_count; - unsigned long devflags; -#define PARPORT_DEVPROC_REGISTERED 0 - struct pardevice *proc_device; /* Currently register proc device */ - struct list_head full_list; struct parport *slaves[3]; }; diff --git a/trunk/include/linux/tracehook.h b/trunk/include/linux/tracehook.h index eb96603d92db..c7aa154f4bfc 100644 --- a/trunk/include/linux/tracehook.h +++ b/trunk/include/linux/tracehook.h @@ -259,12 +259,14 @@ static inline void tracehook_finish_clone(struct task_struct *child, /** * tracehook_report_clone - in parent, new child is about to start running + * @trace: return value from tracehook_prepare_clone() * @regs: parent's user register state * @clone_flags: flags from parent's system call * @pid: new child's PID in the parent's namespace * @child: new child task * - * Called after a child is set up, but before it has been started running. + * Called after a child is set up, but before it has been started + * running. @trace is the value returned by tracehook_prepare_clone(). * This is not a good place to block, because the child has not started * yet. Suspend the child here if desired, and then block in * tracehook_report_clone_complete(). This must prevent the child from @@ -274,14 +276,13 @@ static inline void tracehook_finish_clone(struct task_struct *child, * * Called with no locks held, but the child cannot run until this returns. */ -static inline void tracehook_report_clone(struct pt_regs *regs, +static inline void tracehook_report_clone(int trace, struct pt_regs *regs, unsigned long clone_flags, pid_t pid, struct task_struct *child) { - if (unlikely(task_ptrace(child))) { + if (unlikely(trace) || unlikely(clone_flags & CLONE_PTRACE)) { /* - * It doesn't matter who attached/attaching to this - * task, the pending SIGSTOP is right in any case. + * The child starts up with an immediate SIGSTOP. */ sigaddset(&child->pending.signal, SIGSTOP); set_tsk_thread_flag(child, TIF_SIGPENDING); diff --git a/trunk/include/sound/core.h b/trunk/include/sound/core.h index 309cb9659a05..0e8ae10155ab 100644 --- a/trunk/include/sound/core.h +++ b/trunk/include/sound/core.h @@ -300,6 +300,16 @@ int snd_card_create(int idx, const char *id, struct module *module, int extra_size, struct snd_card **card_ret); +static inline __deprecated +struct snd_card *snd_card_new(int idx, const char *id, + struct module *module, int extra_size) +{ + struct snd_card *card; + if (snd_card_create(idx, id, module, extra_size, &card) < 0) + return NULL; + return card; +} + int snd_card_disconnect(struct snd_card *card); int snd_card_free(struct snd_card *card); int snd_card_free_when_closed(struct snd_card *card); diff --git a/trunk/include/sound/driver.h b/trunk/include/sound/driver.h new file mode 100644 index 000000000000..f0359437d01a --- /dev/null +++ b/trunk/include/sound/driver.h @@ -0,0 +1 @@ +#warning "This file is deprecated" diff --git a/trunk/include/sound/soc-dai.h b/trunk/include/sound/soc-dai.h index 352d7eee9b6d..13676472ddfc 100644 --- a/trunk/include/sound/soc-dai.h +++ b/trunk/include/sound/soc-dai.h @@ -44,6 +44,24 @@ struct snd_pcm_substream; #define SND_SOC_DAIFMT_CONT (0 << 4) /* continuous clock */ #define SND_SOC_DAIFMT_GATED (1 << 4) /* clock is gated */ +/* + * DAI Left/Right Clocks. + * + * Specifies whether the DAI can support different samples for similtanious + * playback and capture. This usually requires a seperate physical frame + * clock for playback and capture. + */ +#define SND_SOC_DAIFMT_SYNC (0 << 5) /* Tx FRM = Rx FRM */ +#define SND_SOC_DAIFMT_ASYNC (1 << 5) /* Tx FRM ~ Rx FRM */ + +/* + * TDM + * + * Time Division Multiplexing. Allows PCM data to be multplexed with other + * data on the DAI. + */ +#define SND_SOC_DAIFMT_TDM (1 << 6) + /* * DAI hardware signal inversions. * @@ -78,10 +96,6 @@ struct snd_pcm_substream; #define SND_SOC_CLOCK_IN 0 #define SND_SOC_CLOCK_OUT 1 -#define SND_SOC_STD_AC97_FMTS (SNDRV_PCM_FMTBIT_S16_LE |\ - SNDRV_PCM_FMTBIT_S32_LE |\ - SNDRV_PCM_FMTBIT_S32_BE) - struct snd_soc_dai_ops; struct snd_soc_dai; struct snd_ac97_bus_ops; @@ -194,7 +208,6 @@ struct snd_soc_dai { /* DAI capabilities */ struct snd_soc_pcm_stream capture; struct snd_soc_pcm_stream playback; - unsigned int symmetric_rates:1; /* DAI runtime info */ struct snd_pcm_runtime *runtime; @@ -206,8 +219,11 @@ struct snd_soc_dai { /* DAI private data */ void *private_data; - /* parent platform */ - struct snd_soc_platform *platform; + /* parent codec/platform */ + union { + struct snd_soc_codec *codec; + struct snd_soc_platform *platform; + }; struct list_head list; }; diff --git a/trunk/include/sound/soc-dapm.h b/trunk/include/sound/soc-dapm.h index ec8a45f9a069..a7def6a9a030 100644 --- a/trunk/include/sound/soc-dapm.h +++ b/trunk/include/sound/soc-dapm.h @@ -140,30 +140,16 @@ #define SND_SOC_DAPM_DAC(wname, stname, wreg, wshift, winvert) \ { .id = snd_soc_dapm_dac, .name = wname, .sname = stname, .reg = wreg, \ .shift = wshift, .invert = winvert} -#define SND_SOC_DAPM_DAC_E(wname, stname, wreg, wshift, winvert, \ - wevent, wflags) \ -{ .id = snd_soc_dapm_dac, .name = wname, .sname = stname, .reg = wreg, \ - .shift = wshift, .invert = winvert, \ - .event = wevent, .event_flags = wflags} #define SND_SOC_DAPM_ADC(wname, stname, wreg, wshift, winvert) \ { .id = snd_soc_dapm_adc, .name = wname, .sname = stname, .reg = wreg, \ .shift = wshift, .invert = winvert} -#define SND_SOC_DAPM_ADC_E(wname, stname, wreg, wshift, winvert, \ - wevent, wflags) \ -{ .id = snd_soc_dapm_adc, .name = wname, .sname = stname, .reg = wreg, \ - .shift = wshift, .invert = winvert, \ - .event = wevent, .event_flags = wflags} -/* generic widgets */ +/* generic register modifier widget */ #define SND_SOC_DAPM_REG(wid, wname, wreg, wshift, wmask, won_val, woff_val) \ { .id = wid, .name = wname, .kcontrols = NULL, .num_kcontrols = 0, \ .reg = -((wreg) + 1), .shift = wshift, .mask = wmask, \ .on_val = won_val, .off_val = woff_val, .event = dapm_reg_event, \ .event_flags = SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD} -#define SND_SOC_DAPM_SUPPLY(wname, wreg, wshift, winvert, wevent, wflags) \ -{ .id = snd_soc_dapm_supply, .name = wname, .reg = wreg, \ - .shift = wshift, .invert = winvert, .event = wevent, \ - .event_flags = wflags} /* dapm kcontrol types */ #define SOC_DAPM_SINGLE(xname, reg, shift, max, invert) \ @@ -279,6 +265,8 @@ int snd_soc_dapm_add_routes(struct snd_soc_codec *codec, /* dapm events */ int snd_soc_dapm_stream_event(struct snd_soc_codec *codec, char *stream, int event); +int snd_soc_dapm_set_bias_level(struct snd_soc_device *socdev, + enum snd_soc_bias_level level); /* dapm sys fs - used by the core */ int snd_soc_dapm_sys_add(struct device *dev); @@ -310,7 +298,6 @@ enum snd_soc_dapm_type { snd_soc_dapm_vmid, /* codec bias/vmid - to minimise pops */ snd_soc_dapm_pre, /* machine specific pre widget - exec first */ snd_soc_dapm_post, /* machine specific post widget - exec last */ - snd_soc_dapm_supply, /* power/clock supply */ }; /* @@ -370,8 +357,6 @@ struct snd_soc_dapm_widget { unsigned char suspend:1; /* was active before suspend */ unsigned char pmdown:1; /* waiting for timeout */ - int (*power_check)(struct snd_soc_dapm_widget *w); - /* external events */ unsigned short event_flags; /* flags to specify event types */ int (*event)(struct snd_soc_dapm_widget*, struct snd_kcontrol *, int); @@ -383,9 +368,6 @@ struct snd_soc_dapm_widget { /* widget input and outputs */ struct list_head sources; struct list_head sinks; - - /* used during DAPM updates */ - struct list_head power_list; }; #endif diff --git a/trunk/include/sound/soc.h b/trunk/include/sound/soc.h index cf6111d72b17..a40bc6f316fc 100644 --- a/trunk/include/sound/soc.h +++ b/trunk/include/sound/soc.h @@ -118,14 +118,6 @@ .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,\ - 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, .invert = xinvert} } #define SOC_SINGLE_EXT_TLV(xname, xreg, xshift, xmax, xinvert,\ xhandler_get, xhandler_put, tlv_array) \ { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \ @@ -214,6 +206,10 @@ void snd_soc_jack_free_gpios(struct snd_soc_jack *jack, int count, struct snd_soc_jack_gpio *gpios); #endif +/* codec IO */ +#define snd_soc_read(codec, reg) codec->read(codec, reg) +#define snd_soc_write(codec, reg, value) codec->write(codec, reg, value) + /* codec register bit access */ int snd_soc_update_bits(struct snd_soc_codec *codec, unsigned short reg, unsigned short mask, unsigned short value); @@ -335,7 +331,6 @@ struct snd_soc_codec { struct module *owner; struct mutex mutex; struct device *dev; - struct snd_soc_device *socdev; struct list_head list; @@ -369,8 +364,6 @@ struct snd_soc_codec { enum snd_soc_bias_level bias_level; enum snd_soc_bias_level suspend_bias_level; struct delayed_work delayed_work; - struct list_head up_list; - struct list_head down_list; /* codec DAI's */ struct snd_soc_dai *dai; @@ -424,12 +417,6 @@ struct snd_soc_dai_link { /* codec/machine specific init - e.g. add machine controls */ int (*init)(struct snd_soc_codec *codec); - /* Symmetry requirements */ - unsigned int symmetric_rates:1; - - /* Symmetry data - only valid if symmetry is being enforced */ - unsigned int rate; - /* DAI pcm */ struct snd_pcm *pcm; }; @@ -503,19 +490,6 @@ struct soc_enum { void *dapm; }; -/* codec IO */ -static inline unsigned int snd_soc_read(struct snd_soc_codec *codec, - unsigned int reg) -{ - return codec->read(codec, reg); -} - -static inline unsigned int snd_soc_write(struct snd_soc_codec *codec, - unsigned int reg, unsigned int val) -{ - return codec->write(codec, reg, val); -} - #include #endif diff --git a/trunk/include/sound/wm9081.h b/trunk/include/sound/wm9081.h deleted file mode 100644 index e173ddbf6bd4..000000000000 --- a/trunk/include/sound/wm9081.h +++ /dev/null @@ -1,25 +0,0 @@ -/* - * linux/sound/wm9081.h -- Platform data for WM9081 - * - * Copyright 2009 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_WM_9081_H -#define __LINUX_SND_WM_9081_H - -struct wm9081_retune_mobile_setting { - const char *name; - unsigned int rate; - u16 config[20]; -}; - -struct wm9081_retune_mobile_config { - struct wm9081_retune_mobile_setting *configs; - int num_configs; -}; - -#endif diff --git a/trunk/ipc/shm.c b/trunk/ipc/shm.c index 425971600485..faa46da99ebe 100644 --- a/trunk/ipc/shm.c +++ b/trunk/ipc/shm.c @@ -969,13 +969,10 @@ SYSCALL_DEFINE3(shmat, int, shmid, char __user *, shmaddr, int, shmflg) SYSCALL_DEFINE1(shmdt, char __user *, shmaddr) { struct mm_struct *mm = current->mm; - struct vm_area_struct *vma; + struct vm_area_struct *vma, *next; unsigned long addr = (unsigned long)shmaddr; - int retval = -EINVAL; -#ifdef CONFIG_MMU loff_t size = 0; - struct vm_area_struct *next; -#endif + int retval = -EINVAL; if (addr & ~PAGE_MASK) return retval; diff --git a/trunk/kernel/async.c b/trunk/kernel/async.c index 27235f5de198..50540301ed0f 100644 --- a/trunk/kernel/async.c +++ b/trunk/kernel/async.c @@ -92,18 +92,23 @@ extern int initcall_debug; static async_cookie_t __lowest_in_progress(struct list_head *running) { struct async_entry *entry; + async_cookie_t ret = next_cookie; /* begin with "infinity" value */ if (!list_empty(running)) { entry = list_first_entry(running, struct async_entry, list); - return entry->cookie; + ret = entry->cookie; } - list_for_each_entry(entry, &async_pending, list) - if (entry->running == running) - return entry->cookie; + if (!list_empty(&async_pending)) { + list_for_each_entry(entry, &async_pending, list) + if (entry->running == running) { + ret = entry->cookie; + break; + } + } - return next_cookie; /* "infinity" value */ + return ret; } static async_cookie_t lowest_in_progress(struct list_head *running) diff --git a/trunk/kernel/fork.c b/trunk/kernel/fork.c index 875ffbdd96d0..b9e2edd00726 100644 --- a/trunk/kernel/fork.c +++ b/trunk/kernel/fork.c @@ -1409,7 +1409,7 @@ long do_fork(unsigned long clone_flags, } audit_finish_fork(p); - tracehook_report_clone(regs, clone_flags, nr, p); + tracehook_report_clone(trace, regs, clone_flags, nr, p); /* * We set PF_STARTING at creation in case tracing wants to diff --git a/trunk/kernel/ptrace.c b/trunk/kernel/ptrace.c index 42c317874cfa..0692ab5a0d67 100644 --- a/trunk/kernel/ptrace.c +++ b/trunk/kernel/ptrace.c @@ -304,8 +304,6 @@ int ptrace_detach(struct task_struct *child, unsigned int data) if (child->ptrace) { child->exit_code = data; dead = __ptrace_detach(current, child); - if (!child->exit_state) - wake_up_process(child); } write_unlock_irq(&tasklist_lock); diff --git a/trunk/kernel/sched_cpupri.c b/trunk/kernel/sched_cpupri.c index 344712a5e3ed..cdd3c89574cd 100644 --- a/trunk/kernel/sched_cpupri.c +++ b/trunk/kernel/sched_cpupri.c @@ -165,7 +165,7 @@ int __init_refok cpupri_init(struct cpupri *cp, bool bootmem) vec->count = 0; if (bootmem) alloc_bootmem_cpumask_var(&vec->mask); - else if (!zalloc_cpumask_var(&vec->mask, GFP_KERNEL)) + else if (!alloc_cpumask_var(&vec->mask, GFP_KERNEL)) goto cleanup; } diff --git a/trunk/kernel/sched_rt.c b/trunk/kernel/sched_rt.c index 9bf0d2a73045..f2c66f8f9712 100644 --- a/trunk/kernel/sched_rt.c +++ b/trunk/kernel/sched_rt.c @@ -1591,7 +1591,7 @@ static inline void init_sched_rt_class(void) unsigned int i; for_each_possible_cpu(i) - zalloc_cpumask_var_node(&per_cpu(local_cpu_mask, i), + alloc_cpumask_var_node(&per_cpu(local_cpu_mask, i), GFP_KERNEL, cpu_to_node(i)); } #endif /* CONFIG_SMP */ diff --git a/trunk/kernel/smp.c b/trunk/kernel/smp.c index ad63d8501207..858baac568ee 100644 --- a/trunk/kernel/smp.c +++ b/trunk/kernel/smp.c @@ -52,7 +52,7 @@ hotplug_cfd(struct notifier_block *nfb, unsigned long action, void *hcpu) switch (action) { case CPU_UP_PREPARE: case CPU_UP_PREPARE_FROZEN: - if (!zalloc_cpumask_var_node(&cfd->cpumask, GFP_KERNEL, + if (!alloc_cpumask_var_node(&cfd->cpumask, GFP_KERNEL, cpu_to_node(cpu))) return NOTIFY_BAD; break; diff --git a/trunk/lib/cpumask.c b/trunk/lib/cpumask.c index eb23aaa0c7b8..1f71b97de0f9 100644 --- a/trunk/lib/cpumask.c +++ b/trunk/lib/cpumask.c @@ -119,12 +119,6 @@ bool alloc_cpumask_var_node(cpumask_var_t *mask, gfp_t flags, int node) } EXPORT_SYMBOL(alloc_cpumask_var_node); -bool zalloc_cpumask_var_node(cpumask_var_t *mask, gfp_t flags, int node) -{ - return alloc_cpumask_var_node(mask, flags | __GFP_ZERO, node); -} -EXPORT_SYMBOL(zalloc_cpumask_var_node); - /** * alloc_cpumask_var - allocate a struct cpumask * @mask: pointer to cpumask_var_t where the cpumask is returned @@ -141,12 +135,6 @@ bool alloc_cpumask_var(cpumask_var_t *mask, gfp_t flags) } EXPORT_SYMBOL(alloc_cpumask_var); -bool zalloc_cpumask_var(cpumask_var_t *mask, gfp_t flags) -{ - return alloc_cpumask_var(mask, flags | __GFP_ZERO); -} -EXPORT_SYMBOL(zalloc_cpumask_var); - /** * alloc_bootmem_cpumask_var - allocate a struct cpumask from the bootmem arena. * @mask: pointer to cpumask_var_t where the cpumask is returned diff --git a/trunk/net/bluetooth/hci_sysfs.c b/trunk/net/bluetooth/hci_sysfs.c index 95f7a7a544b4..4cc3624bd22d 100644 --- a/trunk/net/bluetooth/hci_sysfs.c +++ b/trunk/net/bluetooth/hci_sysfs.c @@ -90,6 +90,9 @@ static void add_conn(struct work_struct *work) struct hci_conn *conn = container_of(work, struct hci_conn, work_add); struct hci_dev *hdev = conn->hdev; + /* ensure previous del is complete */ + flush_work(&conn->work_del); + dev_set_name(&conn->dev, "%s:%d", hdev->name, conn->handle); if (device_add(&conn->dev) < 0) { @@ -115,6 +118,9 @@ static void del_conn(struct work_struct *work) struct hci_conn *conn = container_of(work, struct hci_conn, work_del); struct hci_dev *hdev = conn->hdev; + /* ensure previous add is complete */ + flush_work(&conn->work_add); + if (!device_is_registered(&conn->dev)) return; diff --git a/trunk/net/netfilter/nf_conntrack_proto_dccp.c b/trunk/net/netfilter/nf_conntrack_proto_dccp.c index aee0d6bea309..8e757dd53396 100644 --- a/trunk/net/netfilter/nf_conntrack_proto_dccp.c +++ b/trunk/net/netfilter/nf_conntrack_proto_dccp.c @@ -22,7 +22,6 @@ #include #include #include -#include #include static DEFINE_RWLOCK(dccp_lock); @@ -554,9 +553,6 @@ static int dccp_packet(struct nf_conn *ct, const struct sk_buff *skb, ct->proto.dccp.state = new_state; write_unlock_bh(&dccp_lock); - if (new_state != old_state) - nf_conntrack_event_cache(IPCT_PROTOINFO, ct); - dn = dccp_pernet(net); nf_ct_refresh_acct(ct, ctinfo, skb, dn->dccp_timeout[new_state]); diff --git a/trunk/net/netfilter/nf_conntrack_proto_tcp.c b/trunk/net/netfilter/nf_conntrack_proto_tcp.c index 97a6e93d742e..b5ccf2b4b2e7 100644 --- a/trunk/net/netfilter/nf_conntrack_proto_tcp.c +++ b/trunk/net/netfilter/nf_conntrack_proto_tcp.c @@ -634,14 +634,6 @@ static bool tcp_in_window(const struct nf_conn *ct, sender->td_end = end; sender->flags |= IP_CT_TCP_FLAG_DATA_UNACKNOWLEDGED; } - if (tcph->ack) { - if (!(sender->flags & IP_CT_TCP_FLAG_MAXACK_SET)) { - sender->td_maxack = ack; - sender->flags |= IP_CT_TCP_FLAG_MAXACK_SET; - } else if (after(ack, sender->td_maxack)) - sender->td_maxack = ack; - } - /* * Update receiver data. */ @@ -926,16 +918,6 @@ static int tcp_packet(struct nf_conn *ct, "nf_ct_tcp: invalid state "); return -NF_ACCEPT; case TCP_CONNTRACK_CLOSE: - if (index == TCP_RST_SET - && (ct->proto.tcp.seen[!dir].flags & IP_CT_TCP_FLAG_MAXACK_SET) - && before(ntohl(th->seq), ct->proto.tcp.seen[!dir].td_maxack)) { - /* Invalid RST */ - write_unlock_bh(&tcp_lock); - if (LOG_INVALID(net, IPPROTO_TCP)) - nf_log_packet(pf, 0, skb, NULL, NULL, NULL, - "nf_ct_tcp: invalid RST "); - return -NF_ACCEPT; - } if (index == TCP_RST_SET && ((test_bit(IPS_SEEN_REPLY_BIT, &ct->status) && ct->proto.tcp.last_index == TCP_SYN_SET) diff --git a/trunk/net/netfilter/nfnetlink_log.c b/trunk/net/netfilter/nfnetlink_log.c index 66a6dd5c519a..fd326ac27ec8 100644 --- a/trunk/net/netfilter/nfnetlink_log.c +++ b/trunk/net/netfilter/nfnetlink_log.c @@ -581,12 +581,6 @@ nfulnl_log_packet(u_int8_t pf, + nla_total_size(sizeof(struct nfulnl_msg_packet_hw)) + nla_total_size(sizeof(struct nfulnl_msg_packet_timestamp)); - if (in && skb_mac_header_was_set(skb)) { - size += nla_total_size(skb->dev->hard_header_len) - + nla_total_size(sizeof(u_int16_t)) /* hwtype */ - + nla_total_size(sizeof(u_int16_t)); /* hwlen */ - } - spin_lock_bh(&inst->lock); if (inst->flags & NFULNL_CFG_F_SEQ) diff --git a/trunk/net/netfilter/xt_hashlimit.c b/trunk/net/netfilter/xt_hashlimit.c index 219dcdbe388c..a5b5369c30f9 100644 --- a/trunk/net/netfilter/xt_hashlimit.c +++ b/trunk/net/netfilter/xt_hashlimit.c @@ -926,7 +926,7 @@ static int dl_seq_show(struct seq_file *s, void *v) if (!hlist_empty(&htable->hash[*bucket])) { hlist_for_each_entry(ent, pos, &htable->hash[*bucket], node) if (dl_seq_real_show(ent, htable->family, s)) - return -1; + return 1; } return 0; } diff --git a/trunk/net/sched/cls_api.c b/trunk/net/sched/cls_api.c index 09cdcdfe7e91..0759f32e9dca 100644 --- a/trunk/net/sched/cls_api.c +++ b/trunk/net/sched/cls_api.c @@ -135,7 +135,6 @@ static int tc_ctl_tfilter(struct sk_buff *skb, struct nlmsghdr *n, void *arg) unsigned long cl; unsigned long fh; int err; - int tp_created = 0; if (net != &init_net) return -EINVAL; @@ -267,7 +266,10 @@ static int tc_ctl_tfilter(struct sk_buff *skb, struct nlmsghdr *n, void *arg) goto errout; } - tp_created = 1; + spin_lock_bh(root_lock); + tp->next = *back; + *back = tp; + spin_unlock_bh(root_lock); } else if (tca[TCA_KIND] && nla_strcmp(tca[TCA_KIND], tp->ops->kind)) goto errout; @@ -294,11 +296,8 @@ static int tc_ctl_tfilter(struct sk_buff *skb, struct nlmsghdr *n, void *arg) switch (n->nlmsg_type) { case RTM_NEWTFILTER: err = -EEXIST; - if (n->nlmsg_flags & NLM_F_EXCL) { - if (tp_created) - tcf_destroy(tp); + if (n->nlmsg_flags & NLM_F_EXCL) goto errout; - } break; case RTM_DELTFILTER: err = tp->ops->delete(tp, fh); @@ -315,18 +314,8 @@ static int tc_ctl_tfilter(struct sk_buff *skb, struct nlmsghdr *n, void *arg) } err = tp->ops->change(tp, cl, t->tcm_handle, tca, &fh); - if (err == 0) { - if (tp_created) { - spin_lock_bh(root_lock); - tp->next = *back; - *back = tp; - spin_unlock_bh(root_lock); - } + if (err == 0) tfilter_notify(skb, n, tp, fh, RTM_NEWTFILTER); - } else { - if (tp_created) - tcf_destroy(tp); - } errout: if (cl) diff --git a/trunk/net/sched/cls_cgroup.c b/trunk/net/sched/cls_cgroup.c index e5becb92b3e7..91a3db4a76f8 100644 --- a/trunk/net/sched/cls_cgroup.c +++ b/trunk/net/sched/cls_cgroup.c @@ -104,7 +104,8 @@ static int cls_cgroup_classify(struct sk_buff *skb, struct tcf_proto *tp, struct tcf_result *res) { struct cls_cgroup_head *head = tp->root; - u32 classid; + struct cgroup_cls_state *cs; + int ret = 0; /* * Due to the nature of the classifier it is required to ignore all @@ -120,18 +121,17 @@ static int cls_cgroup_classify(struct sk_buff *skb, struct tcf_proto *tp, return -1; rcu_read_lock(); - classid = task_cls_state(current)->classid; - rcu_read_unlock(); - - if (!classid) - return -1; + cs = task_cls_state(current); + if (cs->classid && tcf_em_tree_match(skb, &head->ematches, NULL)) { + res->classid = cs->classid; + res->class = 0; + ret = tcf_exts_exec(skb, &head->exts, res); + } else + ret = -1; - if (!tcf_em_tree_match(skb, &head->ematches, NULL)) - return -1; + rcu_read_unlock(); - res->classid = classid; - res->class = 0; - return tcf_exts_exec(skb, &head->exts, res); + return ret; } static unsigned long cls_cgroup_get(struct tcf_proto *tp, u32 handle) @@ -167,9 +167,6 @@ static int cls_cgroup_change(struct tcf_proto *tp, unsigned long base, struct tcf_exts e; int err; - if (!tca[TCA_OPTIONS]) - return -EINVAL; - if (head == NULL) { if (!handle) return -EINVAL; diff --git a/trunk/sound/aoa/fabrics/layout.c b/trunk/sound/aoa/fabrics/layout.c index 586965f9605f..fbf5c933baa4 100644 --- a/trunk/sound/aoa/fabrics/layout.c +++ b/trunk/sound/aoa/fabrics/layout.c @@ -1037,7 +1037,7 @@ static int aoa_fabric_layout_probe(struct soundbus_dev *sdev) } ldev->selfptr_headphone.ptr = ldev; ldev->selfptr_lineout.ptr = ldev; - dev_set_drvdata(&sdev->ofdev.dev, ldev); + sdev->ofdev.dev.driver_data = ldev; list_add(&ldev->list, &layouts_list); layouts_list_items++; @@ -1081,7 +1081,7 @@ static int aoa_fabric_layout_probe(struct soundbus_dev *sdev) static int aoa_fabric_layout_remove(struct soundbus_dev *sdev) { - struct layout_dev *ldev = dev_get_drvdata(&sdev->ofdev.dev); + struct layout_dev *ldev = sdev->ofdev.dev.driver_data; int i; for (i=0; iofdev.dev); + struct layout_dev *ldev = sdev->ofdev.dev.driver_data; if (ldev->gpio.methods && ldev->gpio.methods->all_amps_off) ldev->gpio.methods->all_amps_off(&ldev->gpio); @@ -1124,7 +1124,7 @@ static int aoa_fabric_layout_suspend(struct soundbus_dev *sdev, pm_message_t sta static int aoa_fabric_layout_resume(struct soundbus_dev *sdev) { - struct layout_dev *ldev = dev_get_drvdata(&sdev->ofdev.dev); + struct layout_dev *ldev = sdev->ofdev.dev.driver_data; if (ldev->gpio.methods && ldev->gpio.methods->all_amps_off) ldev->gpio.methods->all_amps_restore(&ldev->gpio); diff --git a/trunk/sound/aoa/soundbus/i2sbus/core.c b/trunk/sound/aoa/soundbus/i2sbus/core.c index 4e3b819d4993..418c84c99d69 100644 --- a/trunk/sound/aoa/soundbus/i2sbus/core.c +++ b/trunk/sound/aoa/soundbus/i2sbus/core.c @@ -358,14 +358,14 @@ static int i2sbus_probe(struct macio_dev* dev, const struct of_device_id *match) return -ENODEV; } - dev_set_drvdata(&dev->ofdev.dev, control); + dev->ofdev.dev.driver_data = control; return 0; } static int i2sbus_remove(struct macio_dev* dev) { - struct i2sbus_control *control = dev_get_drvdata(&dev->ofdev.dev); + struct i2sbus_control *control = dev->ofdev.dev.driver_data; struct i2sbus_dev *i2sdev, *tmp; list_for_each_entry_safe(i2sdev, tmp, &control->list, item) @@ -377,7 +377,7 @@ static int i2sbus_remove(struct macio_dev* dev) #ifdef CONFIG_PM static int i2sbus_suspend(struct macio_dev* dev, pm_message_t state) { - struct i2sbus_control *control = dev_get_drvdata(&dev->ofdev.dev); + struct i2sbus_control *control = dev->ofdev.dev.driver_data; struct codec_info_item *cii; struct i2sbus_dev* i2sdev; int err, ret = 0; @@ -407,7 +407,7 @@ static int i2sbus_suspend(struct macio_dev* dev, pm_message_t state) static int i2sbus_resume(struct macio_dev* dev) { - struct i2sbus_control *control = dev_get_drvdata(&dev->ofdev.dev); + struct i2sbus_control *control = dev->ofdev.dev.driver_data; struct codec_info_item *cii; struct i2sbus_dev* i2sdev; int err, ret = 0; diff --git a/trunk/sound/core/init.c b/trunk/sound/core/init.c index 6557dd85e191..a578d05f9e13 100644 --- a/trunk/sound/core/init.c +++ b/trunk/sound/core/init.c @@ -476,15 +476,8 @@ int snd_card_free(struct snd_card *card) EXPORT_SYMBOL(snd_card_free); -/** - * snd_card_set_id - set card identification name - * @card: soundcard structure - * @nid: new identification string - * - * This function sets the card identification and checks for name - * collisions. - */ -void snd_card_set_id(struct snd_card *card, const char *nid) +static void snd_card_set_id_internal(struct snd_card *card, const char *nid, + int do_locking) { int i, len, idx_flag = 0, loops = SNDRV_CARDS; const char *spos, *src; @@ -529,14 +522,16 @@ void snd_card_set_id(struct snd_card *card, const char *nid) } if (!snd_info_check_reserved_words(id)) goto __change; - mutex_lock(&snd_card_mutex); + if (do_locking) + mutex_lock(&snd_card_mutex); for (i = 0; i < snd_ecards_limit; i++) { if (snd_cards[i] && !strcmp(snd_cards[i]->id, id)) { mutex_unlock(&snd_card_mutex); goto __change; } } - mutex_unlock(&snd_card_mutex); + if (do_locking) + mutex_unlock(&snd_card_mutex); break; __change: @@ -561,6 +556,18 @@ void snd_card_set_id(struct snd_card *card, const char *nid) } } +/** + * snd_card_set_id - set card identification name + * @card: soundcard structure + * @nid: new identification string + * + * This function sets the card identification and checks for name + * collisions. + */ +void snd_card_set_id(struct snd_card *card, const char *nid) +{ + snd_card_set_id_internal(card, nid, 1); +} EXPORT_SYMBOL(snd_card_set_id); #ifndef CONFIG_SYSFS_DEPRECATED @@ -657,7 +664,7 @@ int snd_card_register(struct snd_card *card) return 0; } if (card->id[0] == '\0') - snd_card_set_id(card, NULL); + snd_card_set_id_internal(card, NULL, 0); snd_cards[card->number] = card; mutex_unlock(&snd_card_mutex); init_info_for_card(card); diff --git a/trunk/sound/pci/au88x0/au88x0_core.c b/trunk/sound/pci/au88x0/au88x0_core.c index 23f49f356e0f..3906f5afe27a 100644 --- a/trunk/sound/pci/au88x0/au88x0_core.c +++ b/trunk/sound/pci/au88x0/au88x0_core.c @@ -1255,8 +1255,8 @@ static int inline vortex_adbdma_getlinearpos(vortex_t * vortex, int adbdma) int temp; temp = hwread(vortex->mmio, VORTEX_ADBDMA_STAT + (adbdma << 2)); - temp = (dma->period_virt * dma->period_bytes) + (temp & (dma->period_bytes - 1)); - return temp; + temp = (dma->period_virt * dma->period_bytes) + (temp & POS_MASK); + return (temp); } static void vortex_adbdma_startfifo(vortex_t * vortex, int adbdma) @@ -1504,7 +1504,8 @@ static int inline vortex_wtdma_getlinearpos(vortex_t * vortex, int wtdma) int temp; temp = hwread(vortex->mmio, VORTEX_WTDMA_STAT + (wtdma << 2)); - temp = (dma->period_virt * dma->period_bytes) + (temp & (dma->period_bytes - 1)); + //temp = (temp & POS_MASK) + (((temp>>WT_SUBBUF_SHIFT) & WT_SUBBUF_MASK)*(dma->cfg0&POS_MASK)); + temp = (temp & POS_MASK) + ((dma->period_virt) * (dma->period_bytes)); return temp; } @@ -2440,8 +2441,7 @@ static irqreturn_t vortex_interrupt(int irq, void *dev_id) spin_lock(&vortex->lock); for (i = 0; i < NR_ADB; i++) { if (vortex->dma_adb[i].fifo_status == FIFO_START) { - if (!vortex_adbdma_bufshift(vortex, i)) - continue; + if (vortex_adbdma_bufshift(vortex, i)) ; spin_unlock(&vortex->lock); snd_pcm_period_elapsed(vortex->dma_adb[i]. substream); diff --git a/trunk/sound/pci/ca0106/ca0106_mixer.c b/trunk/sound/pci/ca0106/ca0106_mixer.c index c8c6f437f5b3..c111efe61c3c 100644 --- a/trunk/sound/pci/ca0106/ca0106_mixer.c +++ b/trunk/sound/pci/ca0106/ca0106_mixer.c @@ -739,7 +739,7 @@ static int __devinit rename_ctl(struct snd_card *card, const char *src, const ch } while (0) static __devinitdata -DECLARE_TLV_DB_SCALE(snd_ca0106_master_db_scale, -6375, 25, 1); +DECLARE_TLV_DB_SCALE(snd_ca0106_master_db_scale, -6375, 50, 1); static char *slave_vols[] __devinitdata = { "Analog Front Playback Volume", @@ -841,9 +841,6 @@ int __devinit snd_ca0106_mixer(struct snd_ca0106 *emu) snd_ca0106_master_db_scale); if (!vmaster) return -ENOMEM; - err = snd_ctl_add(card, vmaster); - if (err < 0) - return err; add_slaves(card, vmaster, slave_vols); if (emu->details->spi_dac == 1) { @@ -851,13 +848,8 @@ int __devinit snd_ca0106_mixer(struct snd_ca0106 *emu) NULL); if (!vmaster) return -ENOMEM; - err = snd_ctl_add(card, vmaster); - if (err < 0) - return err; add_slaves(card, vmaster, slave_sws); } - - strcpy(card->mixername, "CA0106"); return 0; } diff --git a/trunk/sound/soc/Kconfig b/trunk/sound/soc/Kconfig index d3e786a9a0a7..3d2bb6fc6dcc 100644 --- a/trunk/sound/soc/Kconfig +++ b/trunk/sound/soc/Kconfig @@ -32,9 +32,7 @@ source "sound/soc/fsl/Kconfig" source "sound/soc/omap/Kconfig" source "sound/soc/pxa/Kconfig" source "sound/soc/s3c24xx/Kconfig" -source "sound/soc/s6000/Kconfig" source "sound/soc/sh/Kconfig" -source "sound/soc/txx9/Kconfig" # Supported codecs source "sound/soc/codecs/Kconfig" diff --git a/trunk/sound/soc/Makefile b/trunk/sound/soc/Makefile index 6f1e28de23cf..0237879fd412 100644 --- a/trunk/sound/soc/Makefile +++ b/trunk/sound/soc/Makefile @@ -10,6 +10,4 @@ obj-$(CONFIG_SND_SOC) += fsl/ obj-$(CONFIG_SND_SOC) += omap/ obj-$(CONFIG_SND_SOC) += pxa/ obj-$(CONFIG_SND_SOC) += s3c24xx/ -obj-$(CONFIG_SND_SOC) += s6000/ obj-$(CONFIG_SND_SOC) += sh/ -obj-$(CONFIG_SND_SOC) += txx9/ diff --git a/trunk/sound/soc/atmel/Kconfig b/trunk/sound/soc/atmel/Kconfig index e720d5e6f04c..a608d7009dbd 100644 --- a/trunk/sound/soc/atmel/Kconfig +++ b/trunk/sound/soc/atmel/Kconfig @@ -41,11 +41,3 @@ config SND_AT32_SOC_PLAYPAQ_SLAVE and FRAME signals on the PlayPaq. Unless you want to play with the AT32 as the SSC master, you probably want to say N here, as this will give you better sound quality. - -config SND_AT91_SOC_AFEB9260 - tristate "SoC Audio support for AFEB9260 board" - depends on ARCH_AT91 && MACH_AFEB9260 && SND_ATMEL_SOC - select SND_ATMEL_SOC_SSC - select SND_SOC_TLV320AIC23 - help - Say Y here to support sound on AFEB9260 board. diff --git a/trunk/sound/soc/atmel/Makefile b/trunk/sound/soc/atmel/Makefile index e7ea56bd5f82..f54a7cc68e66 100644 --- a/trunk/sound/soc/atmel/Makefile +++ b/trunk/sound/soc/atmel/Makefile @@ -13,4 +13,3 @@ snd-soc-playpaq-objs := playpaq_wm8510.o obj-$(CONFIG_SND_AT91_SOC_SAM9G20_WM8731) += snd-soc-sam9g20-wm8731.o obj-$(CONFIG_SND_AT32_SOC_PLAYPAQ) += snd-soc-playpaq.o -obj-$(CONFIG_SND_AT91_SOC_AFEB9260) += snd-soc-afeb9260.o diff --git a/trunk/sound/soc/atmel/playpaq_wm8510.c b/trunk/sound/soc/atmel/playpaq_wm8510.c index 9eb610c2ba91..70657534e6b1 100644 --- a/trunk/sound/soc/atmel/playpaq_wm8510.c +++ b/trunk/sound/soc/atmel/playpaq_wm8510.c @@ -117,7 +117,7 @@ static struct ssc_clock_data playpaq_wm8510_calc_ssc_clock( * Find actual rate, compare to requested rate */ actual_rate = (cd.ssc_rate / (cd.cmr_div * 2)) / (2 * (cd.period + 1)); - pr_debug("playpaq_wm8510: Request rate = %u, actual rate = %u\n", + pr_debug("playpaq_wm8510: Request rate = %d, actual rate = %d\n", rate, actual_rate); diff --git a/trunk/sound/soc/atmel/snd-soc-afeb9260.c b/trunk/sound/soc/atmel/snd-soc-afeb9260.c deleted file mode 100644 index 23349de27313..000000000000 --- a/trunk/sound/soc/atmel/snd-soc-afeb9260.c +++ /dev/null @@ -1,203 +0,0 @@ -/* - * afeb9260.c -- SoC audio for AFEB9260 - * - * Copyright (C) 2009 Sergey Lapin - * - * 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. - * - * This program is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA - * 02110-1301 USA - * - */ - -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include - -#include -#include -#include - -#include "../codecs/tlv320aic23.h" -#include "atmel-pcm.h" -#include "atmel_ssc_dai.h" - -#define CODEC_CLOCK 12000000 - -static int afeb9260_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_dai *codec_dai = rtd->dai->codec_dai; - struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai; - int err; - - /* Set codec DAI configuration */ - err = snd_soc_dai_set_fmt(codec_dai, - SND_SOC_DAIFMT_I2S| - SND_SOC_DAIFMT_NB_IF | - SND_SOC_DAIFMT_CBM_CFM); - if (err < 0) { - printk(KERN_ERR "can't set codec DAI configuration\n"); - return err; - } - - /* Set cpu DAI configuration */ - err = snd_soc_dai_set_fmt(cpu_dai, - SND_SOC_DAIFMT_I2S | - SND_SOC_DAIFMT_NB_IF | - SND_SOC_DAIFMT_CBM_CFM); - if (err < 0) { - printk(KERN_ERR "can't set cpu DAI configuration\n"); - return err; - } - - /* Set the codec system clock for DAC and ADC */ - err = - snd_soc_dai_set_sysclk(codec_dai, 0, CODEC_CLOCK, SND_SOC_CLOCK_IN); - - if (err < 0) { - printk(KERN_ERR "can't set codec system clock\n"); - return err; - } - - return err; -} - -static struct snd_soc_ops afeb9260_ops = { - .hw_params = afeb9260_hw_params, -}; - -static const struct snd_soc_dapm_widget tlv320aic23_dapm_widgets[] = { - SND_SOC_DAPM_HP("Headphone Jack", NULL), - SND_SOC_DAPM_LINE("Line In", NULL), - SND_SOC_DAPM_MIC("Mic Jack", NULL), -}; - -static const struct snd_soc_dapm_route audio_map[] = { - {"Headphone Jack", NULL, "LHPOUT"}, - {"Headphone Jack", NULL, "RHPOUT"}, - - {"LLINEIN", NULL, "Line In"}, - {"RLINEIN", NULL, "Line In"}, - - {"MICIN", NULL, "Mic Jack"}, -}; - -static int afeb9260_tlv320aic23_init(struct snd_soc_codec *codec) -{ - - /* Add afeb9260 specific widgets */ - snd_soc_dapm_new_controls(codec, tlv320aic23_dapm_widgets, - ARRAY_SIZE(tlv320aic23_dapm_widgets)); - - /* Set up afeb9260 specific audio path audio_map */ - snd_soc_dapm_add_routes(codec, audio_map, ARRAY_SIZE(audio_map)); - - snd_soc_dapm_enable_pin(codec, "Headphone Jack"); - snd_soc_dapm_enable_pin(codec, "Line In"); - snd_soc_dapm_enable_pin(codec, "Mic Jack"); - - snd_soc_dapm_sync(codec); - - return 0; -} - -/* Digital audio interface glue - connects codec <--> CPU */ -static struct snd_soc_dai_link afeb9260_dai = { - .name = "TLV320AIC23", - .stream_name = "AIC23", - .cpu_dai = &atmel_ssc_dai[0], - .codec_dai = &tlv320aic23_dai, - .init = afeb9260_tlv320aic23_init, - .ops = &afeb9260_ops, -}; - -/* Audio machine driver */ -static struct snd_soc_card snd_soc_machine_afeb9260 = { - .name = "AFEB9260", - .platform = &atmel_soc_platform, - .dai_link = &afeb9260_dai, - .num_links = 1, -}; - -/* Audio subsystem */ -static struct snd_soc_device afeb9260_snd_devdata = { - .card = &snd_soc_machine_afeb9260, - .codec_dev = &soc_codec_dev_tlv320aic23, -}; - -static struct platform_device *afeb9260_snd_device; - -static int __init afeb9260_soc_init(void) -{ - int err; - struct device *dev; - struct atmel_ssc_info *ssc_p = afeb9260_dai.cpu_dai->private_data; - struct ssc_device *ssc = NULL; - - if (!(machine_is_afeb9260())) - return -ENODEV; - - ssc = ssc_request(0); - if (IS_ERR(ssc)) { - printk(KERN_ERR "ASoC: Failed to request SSC 0\n"); - err = PTR_ERR(ssc); - ssc = NULL; - goto err_ssc; - } - ssc_p->ssc = ssc; - - afeb9260_snd_device = platform_device_alloc("soc-audio", -1); - if (!afeb9260_snd_device) { - printk(KERN_ERR "ASoC: Platform device allocation failed\n"); - return -ENOMEM; - } - - platform_set_drvdata(afeb9260_snd_device, &afeb9260_snd_devdata); - afeb9260_snd_devdata.dev = &afeb9260_snd_device->dev; - err = platform_device_add(afeb9260_snd_device); - if (err) - goto err1; - - dev = &afeb9260_snd_device->dev; - - return 0; -err1: - platform_device_del(afeb9260_snd_device); - platform_device_put(afeb9260_snd_device); -err_ssc: - return err; - -} - -static void __exit afeb9260_soc_exit(void) -{ - platform_device_unregister(afeb9260_snd_device); -} - -module_init(afeb9260_soc_init); -module_exit(afeb9260_soc_exit); - -MODULE_AUTHOR("Sergey Lapin "); -MODULE_DESCRIPTION("ALSA SoC for AFEB9260"); -MODULE_LICENSE("GPL"); - diff --git a/trunk/sound/soc/blackfin/bf5xx-ac97.c b/trunk/sound/soc/blackfin/bf5xx-ac97.c index b1ed423fabd5..8a935f2d1767 100644 --- a/trunk/sound/soc/blackfin/bf5xx-ac97.c +++ b/trunk/sound/soc/blackfin/bf5xx-ac97.c @@ -31,15 +31,6 @@ #include "bf5xx-sport.h" #include "bf5xx-ac97.h" -/* Anomaly notes: - * 05000250 - AD1980 is running in TDM mode and RFS/TFS are generated by SPORT - * contrtoller. But, RFSDIV and TFSDIV are always set to 16*16-1, - * while the max AC97 data size is 13*16. The DIV is always larger - * than data size. AD73311 and ad2602 are not running in TDM mode. - * AD1836 and AD73322 depend on external RFS/TFS only. So, this - * anomaly does not affect blackfin sound drivers. -*/ - static int *cmd_count; static int sport_num = CONFIG_SND_BF5XX_SPORT_NUM; diff --git a/trunk/sound/soc/blackfin/bf5xx-sport.c b/trunk/sound/soc/blackfin/bf5xx-sport.c index 469ce7fab20c..b7953c8cf838 100644 --- a/trunk/sound/soc/blackfin/bf5xx-sport.c +++ b/trunk/sound/soc/blackfin/bf5xx-sport.c @@ -190,7 +190,7 @@ static inline int sport_hook_rx_dummy(struct sport_device *sport) desc = get_dma_next_desc_ptr(sport->dma_rx_chan); /* Copy the descriptor which will be damaged to backup */ temp_desc = *desc; - desc->x_count = sport->dummy_count / 2; + desc->x_count = 0xa; desc->y_count = 0; desc->next_desc_addr = sport->dummy_rx_desc; local_irq_restore(flags); @@ -309,7 +309,7 @@ static inline int sport_hook_tx_dummy(struct sport_device *sport) desc = get_dma_next_desc_ptr(sport->dma_tx_chan); /* Store the descriptor which will be damaged */ temp_desc = *desc; - desc->x_count = sport->dummy_count / 2; + desc->x_count = 0xa; desc->y_count = 0; desc->next_desc_addr = sport->dummy_tx_desc; local_irq_restore(flags); diff --git a/trunk/sound/soc/codecs/Kconfig b/trunk/sound/soc/codecs/Kconfig index bbc97fd76648..b6c7f7a01cb0 100644 --- a/trunk/sound/soc/codecs/Kconfig +++ b/trunk/sound/soc/codecs/Kconfig @@ -18,9 +18,7 @@ config SND_SOC_ALL_CODECS select SND_SOC_AK4535 if I2C select SND_SOC_CS4270 if I2C select SND_SOC_PCM3008 - select SND_SOC_SPDIF select SND_SOC_SSM2602 if I2C - select SND_SOC_STAC9766 if SND_SOC_AC97_BUS select SND_SOC_TLV320AIC23 if I2C select SND_SOC_TLV320AIC26 if SPI_MASTER select SND_SOC_TLV320AIC3X if I2C @@ -37,12 +35,8 @@ config SND_SOC_ALL_CODECS select SND_SOC_WM8753 if SND_SOC_I2C_AND_SPI select SND_SOC_WM8900 if I2C select SND_SOC_WM8903 if I2C - select SND_SOC_WM8940 if I2C - select SND_SOC_WM8960 if I2C select SND_SOC_WM8971 if I2C - select SND_SOC_WM8988 if SND_SOC_I2C_AND_SPI select SND_SOC_WM8990 if I2C - select SND_SOC_WM9081 if I2C select SND_SOC_WM9705 if SND_SOC_AC97_BUS select SND_SOC_WM9712 if SND_SOC_AC97_BUS select SND_SOC_WM9713 if SND_SOC_AC97_BUS @@ -92,15 +86,9 @@ config SND_SOC_L3 config SND_SOC_PCM3008 tristate -config SND_SOC_SPDIF - tristate - config SND_SOC_SSM2602 tristate -config SND_SOC_STAC9766 - tristate - config SND_SOC_TLV320AIC23 tristate @@ -150,24 +138,12 @@ config SND_SOC_WM8900 config SND_SOC_WM8903 tristate -config SND_SOC_WM8940 - tristate - -config SND_SOC_WM8960 - tristate - config SND_SOC_WM8971 tristate -config SND_SOC_WM8988 - tristate - config SND_SOC_WM8990 tristate -config SND_SOC_WM9081 - tristate - config SND_SOC_WM9705 tristate diff --git a/trunk/sound/soc/codecs/Makefile b/trunk/sound/soc/codecs/Makefile index 8b7530546f4d..f2653803ede8 100644 --- a/trunk/sound/soc/codecs/Makefile +++ b/trunk/sound/soc/codecs/Makefile @@ -6,9 +6,7 @@ snd-soc-ak4535-objs := ak4535.o snd-soc-cs4270-objs := cs4270.o snd-soc-l3-objs := l3.o snd-soc-pcm3008-objs := pcm3008.o -snd-soc-spdif-objs := spdif_transciever.o snd-soc-ssm2602-objs := ssm2602.o -snd-soc-stac9766-objs := stac9766.o snd-soc-tlv320aic23-objs := tlv320aic23.o snd-soc-tlv320aic26-objs := tlv320aic26.o snd-soc-tlv320aic3x-objs := tlv320aic3x.o @@ -25,12 +23,8 @@ snd-soc-wm8750-objs := wm8750.o snd-soc-wm8753-objs := wm8753.o snd-soc-wm8900-objs := wm8900.o snd-soc-wm8903-objs := wm8903.o -snd-soc-wm8940-objs := wm8940.o -snd-soc-wm8960-objs := wm8960.o snd-soc-wm8971-objs := wm8971.o -snd-soc-wm8988-objs := wm8988.o snd-soc-wm8990-objs := wm8990.o -snd-soc-wm9081-objs := wm9081.o snd-soc-wm9705-objs := wm9705.o snd-soc-wm9712-objs := wm9712.o snd-soc-wm9713-objs := wm9713.o @@ -43,9 +37,7 @@ obj-$(CONFIG_SND_SOC_AK4535) += snd-soc-ak4535.o obj-$(CONFIG_SND_SOC_CS4270) += snd-soc-cs4270.o obj-$(CONFIG_SND_SOC_L3) += snd-soc-l3.o obj-$(CONFIG_SND_SOC_PCM3008) += snd-soc-pcm3008.o -obj-$(CONFIG_SND_SOC_SPDIF) += snd-soc-spdif.o obj-$(CONFIG_SND_SOC_SSM2602) += snd-soc-ssm2602.o -obj-$(CONFIG_SND_SOC_STAC9766) += snd-soc-stac9766.o obj-$(CONFIG_SND_SOC_TLV320AIC23) += snd-soc-tlv320aic23.o obj-$(CONFIG_SND_SOC_TLV320AIC26) += snd-soc-tlv320aic26.o obj-$(CONFIG_SND_SOC_TLV320AIC3X) += snd-soc-tlv320aic3x.o @@ -63,11 +55,7 @@ obj-$(CONFIG_SND_SOC_WM8753) += snd-soc-wm8753.o obj-$(CONFIG_SND_SOC_WM8900) += snd-soc-wm8900.o obj-$(CONFIG_SND_SOC_WM8903) += snd-soc-wm8903.o obj-$(CONFIG_SND_SOC_WM8971) += snd-soc-wm8971.o -obj-$(CONFIG_SND_SOC_WM8940) += snd-soc-wm8940.o -obj-$(CONFIG_SND_SOC_WM8960) += snd-soc-wm8960.o -obj-$(CONFIG_SND_SOC_WM8988) += snd-soc-wm8988.o obj-$(CONFIG_SND_SOC_WM8990) += snd-soc-wm8990.o -obj-$(CONFIG_SND_SOC_WM9081) += snd-soc-wm9081.o obj-$(CONFIG_SND_SOC_WM9705) += snd-soc-wm9705.o obj-$(CONFIG_SND_SOC_WM9712) += snd-soc-wm9712.o obj-$(CONFIG_SND_SOC_WM9713) += snd-soc-wm9713.o diff --git a/trunk/sound/soc/codecs/ac97.c b/trunk/sound/soc/codecs/ac97.c index 932299bb5d1e..b0d4af145b87 100644 --- a/trunk/sound/soc/codecs/ac97.c +++ b/trunk/sound/soc/codecs/ac97.c @@ -53,13 +53,13 @@ struct snd_soc_dai ac97_dai = { .channels_min = 1, .channels_max = 2, .rates = STD_AC97_RATES, - .formats = SND_SOC_STD_AC97_FMTS,}, + .formats = SNDRV_PCM_FMTBIT_S16_LE,}, .capture = { .stream_name = "AC97 Capture", .channels_min = 1, .channels_max = 2, .rates = STD_AC97_RATES, - .formats = SND_SOC_STD_AC97_FMTS,}, + .formats = SNDRV_PCM_FMTBIT_S16_LE,}, .ops = &ac97_dai_ops, }; EXPORT_SYMBOL_GPL(ac97_dai); diff --git a/trunk/sound/soc/codecs/ad1980.c b/trunk/sound/soc/codecs/ad1980.c index d7440a982d22..ddb3b08ac23c 100644 --- a/trunk/sound/soc/codecs/ad1980.c +++ b/trunk/sound/soc/codecs/ad1980.c @@ -137,13 +137,13 @@ struct snd_soc_dai ad1980_dai = { .channels_min = 2, .channels_max = 6, .rates = SNDRV_PCM_RATE_48000, - .formats = SND_SOC_STD_AC97_FMTS, }, + .formats = SNDRV_PCM_FMTBIT_S16_LE, }, .capture = { .stream_name = "Capture", .channels_min = 2, .channels_max = 2, .rates = SNDRV_PCM_RATE_48000, - .formats = SND_SOC_STD_AC97_FMTS, }, + .formats = SNDRV_PCM_FMTBIT_S16_LE, }, }; EXPORT_SYMBOL_GPL(ad1980_dai); diff --git a/trunk/sound/soc/codecs/cs4270.c b/trunk/sound/soc/codecs/cs4270.c index a32b8226c8a4..7fa09a387622 100644 --- a/trunk/sound/soc/codecs/cs4270.c +++ b/trunk/sound/soc/codecs/cs4270.c @@ -18,7 +18,7 @@ * - The machine driver's 'startup' function must call * cs4270_set_dai_sysclk() with the value of MCLK. * - Only I2S and left-justified modes are supported - * - Power management is supported + * - Power management is not supported */ #include @@ -27,7 +27,6 @@ #include #include #include -#include #include "cs4270.h" @@ -57,7 +56,6 @@ #define CS4270_FIRSTREG 0x01 #define CS4270_LASTREG 0x08 #define CS4270_NUMREGS (CS4270_LASTREG - CS4270_FIRSTREG + 1) -#define CS4270_I2C_INCR 0x80 /* Bit masks for the CS4270 registers */ #define CS4270_CHIPID_ID 0xF0 @@ -66,8 +64,6 @@ #define CS4270_PWRCTL_PDN_ADC 0x20 #define CS4270_PWRCTL_PDN_DAC 0x02 #define CS4270_PWRCTL_PDN 0x01 -#define CS4270_PWRCTL_PDN_ALL \ - (CS4270_PWRCTL_PDN_ADC | CS4270_PWRCTL_PDN_DAC | CS4270_PWRCTL_PDN) #define CS4270_MODE_SPEED_MASK 0x30 #define CS4270_MODE_1X 0x00 #define CS4270_MODE_2X 0x10 @@ -113,7 +109,6 @@ struct cs4270_private { unsigned int mclk; /* Input frequency of the MCLK pin */ unsigned int mode; /* The mode (I2S or left-justified) */ unsigned int slave_mode; - unsigned int manual_mute; }; /** @@ -300,7 +295,7 @@ static int cs4270_fill_cache(struct snd_soc_codec *codec) s32 length; length = i2c_smbus_read_i2c_block_data(i2c_client, - CS4270_FIRSTREG | CS4270_I2C_INCR, CS4270_NUMREGS, cache); + CS4270_FIRSTREG | 0x80, CS4270_NUMREGS, cache); if (length != CS4270_NUMREGS) { dev_err(codec->dev, "i2c read failure, addr=0x%x\n", @@ -458,7 +453,7 @@ static int cs4270_hw_params(struct snd_pcm_substream *substream, } /** - * cs4270_dai_mute - enable/disable the CS4270 external mute + * cs4270_mute - enable/disable the CS4270 external mute * @dai: the SOC DAI * @mute: 0 = disable mute, 1 = enable mute * @@ -467,52 +462,21 @@ static int cs4270_hw_params(struct snd_pcm_substream *substream, * board does not have the MUTEA or MUTEB pins connected to such circuitry, * then this function will do nothing. */ -static int cs4270_dai_mute(struct snd_soc_dai *dai, int mute) +static int cs4270_mute(struct snd_soc_dai *dai, int mute) { struct snd_soc_codec *codec = dai->codec; - struct cs4270_private *cs4270 = codec->private_data; int reg6; reg6 = snd_soc_read(codec, CS4270_MUTE); if (mute) reg6 |= CS4270_MUTE_DAC_A | CS4270_MUTE_DAC_B; - else { + else reg6 &= ~(CS4270_MUTE_DAC_A | CS4270_MUTE_DAC_B); - reg6 |= cs4270->manual_mute; - } return snd_soc_write(codec, CS4270_MUTE, reg6); } -/** - * cs4270_soc_put_mute - put callback for the 'Master Playback switch' - * alsa control. - * @kcontrol: mixer control - * @ucontrol: control element information - * - * This function basically passes the arguments on to the generic - * snd_soc_put_volsw() function and saves the mute information in - * our private data structure. This is because we want to prevent - * cs4270_dai_mute() neglecting the user's decision to manually - * mute the codec's output. - * - * Returns 0 for success. - */ -static int cs4270_soc_put_mute(struct snd_kcontrol *kcontrol, - struct snd_ctl_elem_value *ucontrol) -{ - struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol); - struct cs4270_private *cs4270 = codec->private_data; - int left = !ucontrol->value.integer.value[0]; - int right = !ucontrol->value.integer.value[1]; - - cs4270->manual_mute = (left ? CS4270_MUTE_DAC_A : 0) | - (right ? CS4270_MUTE_DAC_B : 0); - - return snd_soc_put_volsw(kcontrol, ucontrol); -} - /* A list of non-DAPM controls that the CS4270 supports */ static const struct snd_kcontrol_new cs4270_snd_controls[] = { SOC_DOUBLE_R("Master Playback Volume", @@ -522,9 +486,7 @@ static const struct snd_kcontrol_new cs4270_snd_controls[] = { SOC_SINGLE("Zero Cross Switch", CS4270_TRANS, 5, 1, 0), SOC_SINGLE("Popguard Switch", CS4270_MODE, 0, 1, 1), SOC_SINGLE("Auto-Mute Switch", CS4270_MUTE, 5, 1, 0), - SOC_DOUBLE("Master Capture Switch", CS4270_MUTE, 3, 4, 1, 1), - SOC_DOUBLE_EXT("Master Playback Switch", CS4270_MUTE, 0, 1, 1, 1, - snd_soc_get_volsw, cs4270_soc_put_mute), + SOC_DOUBLE("Master Capture Switch", CS4270_MUTE, 3, 4, 1, 0) }; /* @@ -544,7 +506,7 @@ static struct snd_soc_dai_ops cs4270_dai_ops = { .hw_params = cs4270_hw_params, .set_sysclk = cs4270_set_dai_sysclk, .set_fmt = cs4270_set_dai_fmt, - .digital_mute = cs4270_dai_mute, + .digital_mute = cs4270_mute, }; struct snd_soc_dai cs4270_dai = { @@ -791,57 +753,6 @@ static struct i2c_device_id cs4270_id[] = { }; MODULE_DEVICE_TABLE(i2c, cs4270_id); -#ifdef CONFIG_PM - -/* This suspend/resume implementation can handle both - a simple standby - * where the codec remains powered, and a full suspend, where the voltage - * domain the codec is connected to is teared down and/or any other hardware - * reset condition is asserted. - * - * The codec's own power saving features are enabled in the suspend callback, - * and all registers are written back to the hardware when resuming. - */ - -static int cs4270_i2c_suspend(struct i2c_client *client, pm_message_t mesg) -{ - struct cs4270_private *cs4270 = i2c_get_clientdata(client); - struct snd_soc_codec *codec = &cs4270->codec; - int reg = snd_soc_read(codec, CS4270_PWRCTL) | CS4270_PWRCTL_PDN_ALL; - - return snd_soc_write(codec, CS4270_PWRCTL, reg); -} - -static int cs4270_i2c_resume(struct i2c_client *client) -{ - struct cs4270_private *cs4270 = i2c_get_clientdata(client); - struct snd_soc_codec *codec = &cs4270->codec; - int reg; - - /* In case the device was put to hard reset during sleep, we need to - * wait 500ns here before any I2C communication. */ - ndelay(500); - - /* first restore the entire register cache ... */ - for (reg = CS4270_FIRSTREG; reg <= CS4270_LASTREG; reg++) { - u8 val = snd_soc_read(codec, reg); - - if (i2c_smbus_write_byte_data(client, reg, val)) { - dev_err(codec->dev, "i2c write failed\n"); - return -EIO; - } - } - - /* ... then disable the power-down bits */ - reg = snd_soc_read(codec, CS4270_PWRCTL); - reg &= ~CS4270_PWRCTL_PDN_ALL; - - return snd_soc_write(codec, CS4270_PWRCTL, reg); -} -#else -#define cs4270_i2c_suspend NULL -#define cs4270_i2c_resume NULL -#endif /* CONFIG_PM */ - /* * cs4270_i2c_driver - I2C device identification * @@ -856,8 +767,6 @@ static struct i2c_driver cs4270_i2c_driver = { .id_table = cs4270_id, .probe = cs4270_i2c_probe, .remove = cs4270_i2c_remove, - .suspend = cs4270_i2c_suspend, - .resume = cs4270_i2c_resume, }; /* diff --git a/trunk/sound/soc/codecs/spdif_transciever.c b/trunk/sound/soc/codecs/spdif_transciever.c deleted file mode 100644 index 218b33adad90..000000000000 --- a/trunk/sound/soc/codecs/spdif_transciever.c +++ /dev/null @@ -1,71 +0,0 @@ -/* - * ALSA SoC SPDIF DIT driver - * - * This driver is used by controllers which can operate in DIT (SPDI/F) where - * no codec is needed. This file provides stub codec that can be used - * in these configurations. TI DaVinci Audio controller uses this driver. - * - * Author: Steve Chen, - * Copyright: (C) 2009 MontaVista Software, Inc., - * Copyright: (C) 2009 Texas Instruments, India - * - * 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. - */ - -#include -#include -#include -#include - -#include "spdif_transciever.h" - -#define STUB_RATES SNDRV_PCM_RATE_8000_96000 -#define STUB_FORMATS SNDRV_PCM_FMTBIT_S16_LE - -struct snd_soc_dai dit_stub_dai = { - .name = "DIT", - .playback = { - .stream_name = "Playback", - .channels_min = 1, - .channels_max = 384, - .rates = STUB_RATES, - .formats = STUB_FORMATS, - }, -}; - -static int spdif_dit_probe(struct platform_device *pdev) -{ - dit_stub_dai.dev = &pdev->dev; - return snd_soc_register_dai(&dit_stub_dai); -} - -static int spdif_dit_remove(struct platform_device *pdev) -{ - snd_soc_unregister_dai(&dit_stub_dai); - return 0; -} - -static struct platform_driver spdif_dit_driver = { - .probe = spdif_dit_probe, - .remove = spdif_dit_remove, - .driver = { - .name = "spdif-dit", - .owner = THIS_MODULE, - }, -}; - -static int __init dit_modinit(void) -{ - return platform_driver_register(&spdif_dit_driver); -} - -static void __exit dit_exit(void) -{ - platform_driver_unregister(&spdif_dit_driver); -} - -module_init(dit_modinit); -module_exit(dit_exit); - diff --git a/trunk/sound/soc/codecs/spdif_transciever.h b/trunk/sound/soc/codecs/spdif_transciever.h deleted file mode 100644 index 296f2eb6c4ef..000000000000 --- a/trunk/sound/soc/codecs/spdif_transciever.h +++ /dev/null @@ -1,17 +0,0 @@ -/* - * ALSA SoC DIT/DIR driver header - * - * Author: Steve Chen, - * Copyright: (C) 2008 MontaVista Software, Inc., - * - * 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 CODEC_STUBS_H -#define CODEC_STUBS_H - -extern struct snd_soc_dai dit_stub_dai; - -#endif /* CODEC_STUBS_H */ diff --git a/trunk/sound/soc/codecs/ssm2602.c b/trunk/sound/soc/codecs/ssm2602.c index 1fc4c8e0899c..87f606c76822 100644 --- a/trunk/sound/soc/codecs/ssm2602.c +++ b/trunk/sound/soc/codecs/ssm2602.c @@ -336,17 +336,15 @@ static int ssm2602_startup(struct snd_pcm_substream *substream, master_runtime->sample_bits, master_runtime->rate); - if (master_runtime->rate != 0) - snd_pcm_hw_constraint_minmax(substream->runtime, - SNDRV_PCM_HW_PARAM_RATE, - master_runtime->rate, - master_runtime->rate); - - if (master_runtime->sample_bits != 0) - snd_pcm_hw_constraint_minmax(substream->runtime, - SNDRV_PCM_HW_PARAM_SAMPLE_BITS, - master_runtime->sample_bits, - master_runtime->sample_bits); + snd_pcm_hw_constraint_minmax(substream->runtime, + SNDRV_PCM_HW_PARAM_RATE, + master_runtime->rate, + master_runtime->rate); + + snd_pcm_hw_constraint_minmax(substream->runtime, + SNDRV_PCM_HW_PARAM_SAMPLE_BITS, + master_runtime->sample_bits, + master_runtime->sample_bits); ssm2602->slave_substream = substream; } else @@ -374,11 +372,6 @@ static void ssm2602_shutdown(struct snd_pcm_substream *substream, struct snd_soc_device *socdev = rtd->socdev; struct snd_soc_codec *codec = socdev->card->codec; struct ssm2602_priv *ssm2602 = codec->private_data; - - if (ssm2602->master_substream == substream) - ssm2602->master_substream = ssm2602->slave_substream; - - ssm2602->slave_substream = NULL; /* deactivate */ if (!codec->active) ssm2602_write(codec, SSM2602_ACTIVE, 0); @@ -504,9 +497,11 @@ static int ssm2602_set_bias_level(struct snd_soc_codec *codec, return 0; } -#define SSM2602_RATES (SNDRV_PCM_RATE_8000 | SNDRV_PCM_RATE_32000 |\ - SNDRV_PCM_RATE_44100 | SNDRV_PCM_RATE_48000 |\ - SNDRV_PCM_RATE_88200 | SNDRV_PCM_RATE_96000) +#define SSM2602_RATES (SNDRV_PCM_RATE_8000 | SNDRV_PCM_RATE_11025 |\ + SNDRV_PCM_RATE_16000 | SNDRV_PCM_RATE_22050 |\ + SNDRV_PCM_RATE_32000 | SNDRV_PCM_RATE_44100 |\ + SNDRV_PCM_RATE_48000 | SNDRV_PCM_RATE_88200 |\ + SNDRV_PCM_RATE_96000) #define SSM2602_FORMATS (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S20_3LE |\ SNDRV_PCM_FMTBIT_S24_LE | SNDRV_PCM_FMTBIT_S32_LE) diff --git a/trunk/sound/soc/codecs/stac9766.c b/trunk/sound/soc/codecs/stac9766.c deleted file mode 100644 index 8ad4b7b3e3ba..000000000000 --- a/trunk/sound/soc/codecs/stac9766.c +++ /dev/null @@ -1,463 +0,0 @@ -/* - * stac9766.c -- ALSA SoC STAC9766 codec support - * - * Copyright 2009 Jon Smirl, Digispeaker - * Author: Jon Smirl - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. - * - * Features:- - * - * o Support for AC97 Codec, S/PDIF - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "stac9766.h" - -#define STAC9766_VERSION "0.10" - -/* - * STAC9766 register cache - */ -static const u16 stac9766_reg[] = { - 0x6A90, 0x8000, 0x8000, 0x8000, /* 6 */ - 0x0000, 0x0000, 0x8008, 0x8008, /* e */ - 0x8808, 0x8808, 0x8808, 0x8808, /* 16 */ - 0x8808, 0x0000, 0x8000, 0x0000, /* 1e */ - 0x0000, 0x0000, 0x0000, 0x000f, /* 26 */ - 0x0a05, 0x0400, 0xbb80, 0x0000, /* 2e */ - 0x0000, 0xbb80, 0x0000, 0x0000, /* 36 */ - 0x0000, 0x2000, 0x0000, 0x0100, /* 3e */ - 0x0000, 0x0000, 0x0080, 0x0000, /* 46 */ - 0x0000, 0x0000, 0x0003, 0xffff, /* 4e */ - 0x0000, 0x0000, 0x0000, 0x0000, /* 56 */ - 0x4000, 0x0000, 0x0000, 0x0000, /* 5e */ - 0x1201, 0xFFFF, 0xFFFF, 0x0000, /* 66 */ - 0x0000, 0x0000, 0x0000, 0x0000, /* 6e */ - 0x0000, 0x0000, 0x0000, 0x0006, /* 76 */ - 0x0000, 0x0000, 0x0000, 0x0000, /* 7e */ -}; - -static const char *stac9766_record_mux[] = {"Mic", "CD", "Video", "AUX", - "Line", "Stereo Mix", "Mono Mix", "Phone"}; -static const char *stac9766_mono_mux[] = {"Mix", "Mic"}; -static const char *stac9766_mic_mux[] = {"Mic1", "Mic2"}; -static const char *stac9766_SPDIF_mux[] = {"PCM", "ADC Record"}; -static const char *stac9766_popbypass_mux[] = {"Normal", "Bypass Mixer"}; -static const char *stac9766_record_all_mux[] = {"All analog", - "Analog plus DAC"}; -static const char *stac9766_boost1[] = {"0dB", "10dB"}; -static const char *stac9766_boost2[] = {"0dB", "20dB"}; -static const char *stac9766_stereo_mic[] = {"Off", "On"}; - -static const struct soc_enum stac9766_record_enum = - SOC_ENUM_DOUBLE(AC97_REC_SEL, 8, 0, 8, stac9766_record_mux); -static const struct soc_enum stac9766_mono_enum = - SOC_ENUM_SINGLE(AC97_GENERAL_PURPOSE, 9, 2, stac9766_mono_mux); -static const struct soc_enum stac9766_mic_enum = - SOC_ENUM_SINGLE(AC97_GENERAL_PURPOSE, 8, 2, stac9766_mic_mux); -static const struct soc_enum stac9766_SPDIF_enum = - SOC_ENUM_SINGLE(AC97_STAC_DA_CONTROL, 1, 2, stac9766_SPDIF_mux); -static const struct soc_enum stac9766_popbypass_enum = - SOC_ENUM_SINGLE(AC97_GENERAL_PURPOSE, 15, 2, stac9766_popbypass_mux); -static const struct soc_enum stac9766_record_all_enum = - SOC_ENUM_SINGLE(AC97_STAC_ANALOG_SPECIAL, 12, 2, - stac9766_record_all_mux); -static const struct soc_enum stac9766_boost1_enum = - SOC_ENUM_SINGLE(AC97_MIC, 6, 2, stac9766_boost1); /* 0/10dB */ -static const struct soc_enum stac9766_boost2_enum = - SOC_ENUM_SINGLE(AC97_STAC_ANALOG_SPECIAL, 2, 2, stac9766_boost2); /* 0/20dB */ -static const struct soc_enum stac9766_stereo_mic_enum = - SOC_ENUM_SINGLE(AC97_STAC_STEREO_MIC, 2, 1, stac9766_stereo_mic); - -static const DECLARE_TLV_DB_LINEAR(master_tlv, -4600, 0); -static const DECLARE_TLV_DB_LINEAR(record_tlv, 0, 2250); -static const DECLARE_TLV_DB_LINEAR(beep_tlv, -4500, 0); -static const DECLARE_TLV_DB_LINEAR(mix_tlv, -3450, 1200); - -static const struct snd_kcontrol_new stac9766_snd_ac97_controls[] = { - SOC_DOUBLE_TLV("Speaker Volume", AC97_MASTER, 8, 0, 31, 1, master_tlv), - SOC_SINGLE("Speaker Switch", AC97_MASTER, 15, 1, 1), - SOC_DOUBLE_TLV("Headphone Volume", AC97_HEADPHONE, 8, 0, 31, 1, - master_tlv), - SOC_SINGLE("Headphone Switch", AC97_HEADPHONE, 15, 1, 1), - SOC_SINGLE_TLV("Mono Out Volume", AC97_MASTER_MONO, 0, 31, 1, - master_tlv), - SOC_SINGLE("Mono Out Switch", AC97_MASTER_MONO, 15, 1, 1), - - SOC_DOUBLE_TLV("Record Volume", AC97_REC_GAIN, 8, 0, 15, 0, record_tlv), - SOC_SINGLE("Record Switch", AC97_REC_GAIN, 15, 1, 1), - - - SOC_SINGLE_TLV("Beep Volume", AC97_PC_BEEP, 1, 15, 1, beep_tlv), - SOC_SINGLE("Beep Switch", AC97_PC_BEEP, 15, 1, 1), - SOC_SINGLE("Beep Frequency", AC97_PC_BEEP, 5, 127, 1), - SOC_SINGLE_TLV("Phone Volume", AC97_PHONE, 0, 31, 1, mix_tlv), - SOC_SINGLE("Phone Switch", AC97_PHONE, 15, 1, 1), - - SOC_ENUM("Mic Boost1", stac9766_boost1_enum), - SOC_ENUM("Mic Boost2", stac9766_boost2_enum), - SOC_SINGLE_TLV("Mic Volume", AC97_MIC, 0, 31, 1, mix_tlv), - SOC_SINGLE("Mic Switch", AC97_MIC, 15, 1, 1), - SOC_ENUM("Stereo Mic", stac9766_stereo_mic_enum), - - SOC_DOUBLE_TLV("Line Volume", AC97_LINE, 8, 0, 31, 1, mix_tlv), - SOC_SINGLE("Line Switch", AC97_LINE, 15, 1, 1), - SOC_DOUBLE_TLV("CD Volume", AC97_CD, 8, 0, 31, 1, mix_tlv), - SOC_SINGLE("CD Switch", AC97_CD, 15, 1, 1), - SOC_DOUBLE_TLV("AUX Volume", AC97_AUX, 8, 0, 31, 1, mix_tlv), - SOC_SINGLE("AUX Switch", AC97_AUX, 15, 1, 1), - SOC_DOUBLE_TLV("Video Volume", AC97_VIDEO, 8, 0, 31, 1, mix_tlv), - SOC_SINGLE("Video Switch", AC97_VIDEO, 15, 1, 1), - - SOC_DOUBLE_TLV("DAC Volume", AC97_PCM, 8, 0, 31, 1, mix_tlv), - SOC_SINGLE("DAC Switch", AC97_PCM, 15, 1, 1), - SOC_SINGLE("Loopback Test Switch", AC97_GENERAL_PURPOSE, 7, 1, 0), - SOC_SINGLE("3D Volume", AC97_3D_CONTROL, 3, 2, 1), - SOC_SINGLE("3D Switch", AC97_GENERAL_PURPOSE, 13, 1, 0), - - SOC_ENUM("SPDIF Mux", stac9766_SPDIF_enum), - SOC_ENUM("Mic1/2 Mux", stac9766_mic_enum), - SOC_ENUM("Record All Mux", stac9766_record_all_enum), - SOC_ENUM("Record Mux", stac9766_record_enum), - SOC_ENUM("Mono Mux", stac9766_mono_enum), - SOC_ENUM("Pop Bypass Mux", stac9766_popbypass_enum), -}; - -static int stac9766_ac97_write(struct snd_soc_codec *codec, unsigned int reg, - unsigned int val) -{ - u16 *cache = codec->reg_cache; - - if (reg > AC97_STAC_PAGE0) { - stac9766_ac97_write(codec, AC97_INT_PAGING, 0); - soc_ac97_ops.write(codec->ac97, reg, val); - stac9766_ac97_write(codec, AC97_INT_PAGING, 1); - return 0; - } - if (reg / 2 > ARRAY_SIZE(stac9766_reg)) - return -EIO; - - soc_ac97_ops.write(codec->ac97, reg, val); - cache[reg / 2] = val; - return 0; -} - -static unsigned int stac9766_ac97_read(struct snd_soc_codec *codec, - unsigned int reg) -{ - u16 val = 0, *cache = codec->reg_cache; - - if (reg > AC97_STAC_PAGE0) { - stac9766_ac97_write(codec, AC97_INT_PAGING, 0); - val = soc_ac97_ops.read(codec->ac97, reg - AC97_STAC_PAGE0); - stac9766_ac97_write(codec, AC97_INT_PAGING, 1); - return val; - } - if (reg / 2 > ARRAY_SIZE(stac9766_reg)) - return -EIO; - - if (reg == AC97_RESET || reg == AC97_GPIO_STATUS || - reg == AC97_INT_PAGING || reg == AC97_VENDOR_ID1 || - reg == AC97_VENDOR_ID2) { - - val = soc_ac97_ops.read(codec->ac97, reg); - return val; - } - return cache[reg / 2]; -} - -static int ac97_analog_prepare(struct snd_pcm_substream *substream, - struct snd_soc_dai *dai) -{ - struct snd_soc_codec *codec = dai->codec; - struct snd_pcm_runtime *runtime = substream->runtime; - unsigned short reg, vra; - - vra = stac9766_ac97_read(codec, AC97_EXTENDED_STATUS); - - vra |= 0x1; /* enable variable rate audio */ - - stac9766_ac97_write(codec, AC97_EXTENDED_STATUS, vra); - - if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) - reg = AC97_PCM_FRONT_DAC_RATE; - else - reg = AC97_PCM_LR_ADC_RATE; - - return stac9766_ac97_write(codec, reg, runtime->rate); -} - -static int ac97_digital_prepare(struct snd_pcm_substream *substream, - struct snd_soc_dai *dai) -{ - struct snd_soc_codec *codec = dai->codec; - struct snd_pcm_runtime *runtime = substream->runtime; - unsigned short reg, vra; - - stac9766_ac97_write(codec, AC97_SPDIF, 0x2002); - - vra = stac9766_ac97_read(codec, AC97_EXTENDED_STATUS); - vra |= 0x5; /* Enable VRA and SPDIF out */ - - stac9766_ac97_write(codec, AC97_EXTENDED_STATUS, vra); - - reg = AC97_PCM_FRONT_DAC_RATE; - - return stac9766_ac97_write(codec, reg, runtime->rate); -} - -static int ac97_digital_trigger(struct snd_pcm_substream *substream, - int cmd, struct snd_soc_dai *dai) -{ - struct snd_soc_codec *codec = dai->codec; - unsigned short vra; - - switch (cmd) { - case SNDRV_PCM_TRIGGER_STOP: - vra = stac9766_ac97_read(codec, AC97_EXTENDED_STATUS); - vra &= !0x04; - stac9766_ac97_write(codec, AC97_EXTENDED_STATUS, vra); - break; - } - return 0; -} - -static int stac9766_set_bias_level(struct snd_soc_codec *codec, - enum snd_soc_bias_level level) -{ - switch (level) { - case SND_SOC_BIAS_ON: /* full On */ - case SND_SOC_BIAS_PREPARE: /* partial On */ - case SND_SOC_BIAS_STANDBY: /* Off, with power */ - stac9766_ac97_write(codec, AC97_POWERDOWN, 0x0000); - break; - case SND_SOC_BIAS_OFF: /* Off, without power */ - /* disable everything including AC link */ - stac9766_ac97_write(codec, AC97_POWERDOWN, 0xffff); - break; - } - codec->bias_level = level; - return 0; -} - -static int stac9766_reset(struct snd_soc_codec *codec, int try_warm) -{ - if (try_warm && soc_ac97_ops.warm_reset) { - soc_ac97_ops.warm_reset(codec->ac97); - if (stac9766_ac97_read(codec, 0) == stac9766_reg[0]) - return 1; - } - - soc_ac97_ops.reset(codec->ac97); - if (soc_ac97_ops.warm_reset) - soc_ac97_ops.warm_reset(codec->ac97); - if (stac9766_ac97_read(codec, 0) != stac9766_reg[0]) - return -EIO; - return 0; -} - -static int stac9766_codec_suspend(struct platform_device *pdev, - pm_message_t state) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - - stac9766_set_bias_level(codec, SND_SOC_BIAS_OFF); - return 0; -} - -static int stac9766_codec_resume(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - u16 id, reset; - - reset = 0; - /* give the codec an AC97 warm reset to start the link */ -reset: - if (reset > 5) { - printk(KERN_ERR "stac9766 failed to resume"); - return -EIO; - } - codec->ac97->bus->ops->warm_reset(codec->ac97); - id = soc_ac97_ops.read(codec->ac97, AC97_VENDOR_ID2); - if (id != 0x4c13) { - stac9766_reset(codec, 0); - reset++; - goto reset; - } - stac9766_set_bias_level(codec, SND_SOC_BIAS_STANDBY); - - if (codec->suspend_bias_level == SND_SOC_BIAS_ON) - stac9766_set_bias_level(codec, SND_SOC_BIAS_ON); - - return 0; -} - -static struct snd_soc_dai_ops stac9766_dai_ops_analog = { - .prepare = ac97_analog_prepare, -}; - -static struct snd_soc_dai_ops stac9766_dai_ops_digital = { - .prepare = ac97_digital_prepare, - .trigger = ac97_digital_trigger, -}; - -struct snd_soc_dai stac9766_dai[] = { -{ - .name = "stac9766 analog", - .id = 0, - .ac97_control = 1, - - /* stream cababilities */ - .playback = { - .stream_name = "stac9766 analog", - .channels_min = 1, - .channels_max = 2, - .rates = SNDRV_PCM_RATE_8000_48000, - .formats = SND_SOC_STD_AC97_FMTS, - }, - .capture = { - .stream_name = "stac9766 analog", - .channels_min = 1, - .channels_max = 2, - .rates = SNDRV_PCM_RATE_8000_48000, - .formats = SND_SOC_STD_AC97_FMTS, - }, - /* alsa ops */ - .ops = &stac9766_dai_ops_analog, -}, -{ - .name = "stac9766 IEC958", - .id = 1, - .ac97_control = 1, - - /* stream cababilities */ - .playback = { - .stream_name = "stac9766 IEC958", - .channels_min = 1, - .channels_max = 2, - .rates = SNDRV_PCM_RATE_32000 | \ - SNDRV_PCM_RATE_44100 | SNDRV_PCM_RATE_48000, - .formats = SNDRV_PCM_FORMAT_IEC958_SUBFRAME_BE, - }, - /* alsa ops */ - .ops = &stac9766_dai_ops_digital, -} -}; -EXPORT_SYMBOL_GPL(stac9766_dai); - -static int stac9766_codec_probe(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec; - int ret = 0; - - printk(KERN_INFO "STAC9766 SoC Audio Codec %s\n", STAC9766_VERSION); - - socdev->card->codec = kzalloc(sizeof(struct snd_soc_codec), GFP_KERNEL); - if (socdev->card->codec == NULL) - return -ENOMEM; - codec = socdev->card->codec; - mutex_init(&codec->mutex); - - codec->reg_cache = kmemdup(stac9766_reg, sizeof(stac9766_reg), - GFP_KERNEL); - if (codec->reg_cache == NULL) { - ret = -ENOMEM; - goto cache_err; - } - codec->reg_cache_size = sizeof(stac9766_reg); - codec->reg_cache_step = 2; - - codec->name = "STAC9766"; - codec->owner = THIS_MODULE; - codec->dai = stac9766_dai; - codec->num_dai = ARRAY_SIZE(stac9766_dai); - codec->write = stac9766_ac97_write; - codec->read = stac9766_ac97_read; - codec->set_bias_level = stac9766_set_bias_level; - INIT_LIST_HEAD(&codec->dapm_widgets); - INIT_LIST_HEAD(&codec->dapm_paths); - - ret = snd_soc_new_ac97_codec(codec, &soc_ac97_ops, 0); - if (ret < 0) - goto codec_err; - - /* register pcms */ - ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1); - if (ret < 0) - goto pcm_err; - - /* do a cold reset for the controller and then try - * a warm reset followed by an optional cold reset for codec */ - stac9766_reset(codec, 0); - ret = stac9766_reset(codec, 1); - if (ret < 0) { - printk(KERN_ERR "Failed to reset STAC9766: AC97 link error\n"); - goto reset_err; - } - - stac9766_set_bias_level(codec, SND_SOC_BIAS_STANDBY); - - snd_soc_add_controls(codec, stac9766_snd_ac97_controls, - ARRAY_SIZE(stac9766_snd_ac97_controls)); - - ret = snd_soc_init_card(socdev); - if (ret < 0) - goto reset_err; - return 0; - -reset_err: - snd_soc_free_pcms(socdev); -pcm_err: - snd_soc_free_ac97_codec(codec); -codec_err: - kfree(codec->private_data); -cache_err: - kfree(socdev->card->codec); - socdev->card->codec = NULL; - return ret; -} - -static int stac9766_codec_remove(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - - if (codec == NULL) - return 0; - - snd_soc_free_pcms(socdev); - snd_soc_free_ac97_codec(codec); - kfree(codec->reg_cache); - kfree(codec); - return 0; -} - -struct snd_soc_codec_device soc_codec_dev_stac9766 = { - .probe = stac9766_codec_probe, - .remove = stac9766_codec_remove, - .suspend = stac9766_codec_suspend, - .resume = stac9766_codec_resume, -}; -EXPORT_SYMBOL_GPL(soc_codec_dev_stac9766); - -MODULE_DESCRIPTION("ASoC stac9766 driver"); -MODULE_AUTHOR("Jon Smirl "); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/codecs/stac9766.h b/trunk/sound/soc/codecs/stac9766.h deleted file mode 100644 index 65642eb8393e..000000000000 --- a/trunk/sound/soc/codecs/stac9766.h +++ /dev/null @@ -1,21 +0,0 @@ -/* - * stac9766.h -- STAC9766 Soc Audio driver - */ - -#ifndef _STAC9766_H -#define _STAC9766_H - -#define AC97_STAC_PAGE0 0x1000 -#define AC97_STAC_DA_CONTROL (AC97_STAC_PAGE0 | 0x6A) -#define AC97_STAC_ANALOG_SPECIAL (AC97_STAC_PAGE0 | 0x6E) -#define AC97_STAC_STEREO_MIC 0x78 - -/* STAC9766 DAI ID's */ -#define STAC9766_DAI_AC97_ANALOG 0 -#define STAC9766_DAI_AC97_DIGITAL 1 - -extern struct snd_soc_dai stac9766_dai[]; -extern struct snd_soc_codec_device soc_codec_dev_stac9766; - - -#endif diff --git a/trunk/sound/soc/codecs/tlv320aic23.c b/trunk/sound/soc/codecs/tlv320aic23.c index 0b8dcb5cd729..c3f4afb5d017 100644 --- a/trunk/sound/soc/codecs/tlv320aic23.c +++ b/trunk/sound/soc/codecs/tlv320aic23.c @@ -86,7 +86,7 @@ static int tlv320aic23_write(struct snd_soc_codec *codec, unsigned int reg, */ if ((reg < 0 || reg > 9) && (reg != 15)) { - printk(KERN_WARNING "%s Invalid register R%u\n", __func__, reg); + printk(KERN_WARNING "%s Invalid register R%d\n", __func__, reg); return -1; } @@ -98,7 +98,7 @@ static int tlv320aic23_write(struct snd_soc_codec *codec, unsigned int reg, if (codec->hw_write(codec->control_data, data, 2) == 2) return 0; - printk(KERN_ERR "%s cannot write %03x to register R%u\n", __func__, + printk(KERN_ERR "%s cannot write %03x to register R%d\n", __func__, value, reg); return -EIO; @@ -273,14 +273,14 @@ static const unsigned short sr_valid_mask[] = { * Every divisor is a factor of 11*12 */ #define SR_MULT (11*12) -#define A(x) (SR_MULT/x) +#define A(x) (x) ? (SR_MULT/x) : 0 static const unsigned char sr_adc_mult_table[] = { - A(2), A(2), A(12), A(12), 0, 0, A(3), A(1), - A(2), A(2), A(11), A(11), 0, 0, 0, A(1) + A(2), A(2), A(12), A(12), A(0), A(0), A(3), A(1), + A(2), A(2), A(11), A(11), A(0), A(0), A(0), A(1) }; static const unsigned char sr_dac_mult_table[] = { - A(2), A(12), A(2), A(12), 0, 0, A(3), A(1), - A(2), A(11), A(2), A(11), 0, 0, 0, A(1) + A(2), A(12), A(2), A(12), A(0), A(0), A(3), A(1), + A(2), A(11), A(2), A(11), A(0), A(0), A(0), A(1) }; static unsigned get_score(int adc, int adc_l, int adc_h, int need_adc, @@ -523,8 +523,6 @@ static int tlv320aic23_set_dai_fmt(struct snd_soc_dai *codec_dai, case SND_SOC_DAIFMT_I2S: iface_reg |= TLV320AIC23_FOR_I2S; break; - case SND_SOC_DAIFMT_DSP_A: - iface_reg |= TLV320AIC23_LRP_ON; case SND_SOC_DAIFMT_DSP_B: iface_reg |= TLV320AIC23_FOR_DSP; break; diff --git a/trunk/sound/soc/codecs/twl4030.c b/trunk/sound/soc/codecs/twl4030.c index 4dbb853eef5a..df7c8c281d2f 100644 --- a/trunk/sound/soc/codecs/twl4030.c +++ b/trunk/sound/soc/codecs/twl4030.c @@ -115,7 +115,6 @@ static const u8 twl4030_reg[TWL4030_CACHEREGNUM] = { 0x00, /* REG_VIBRA_PWM_SET (0x47) */ 0x00, /* REG_ANAMIC_GAIN (0x48) */ 0x00, /* REG_MISC_SET_2 (0x49) */ - 0x00, /* REG_SW_SHADOW (0x4A) - Shadow, non HW register */ }; /* codec private data */ @@ -126,17 +125,6 @@ struct twl4030_priv { struct snd_pcm_substream *master_substream; struct snd_pcm_substream *slave_substream; - - unsigned int configured; - unsigned int rate; - unsigned int sample_bits; - unsigned int channels; - - unsigned int sysclk; - - /* Headset output state handling */ - unsigned int hsl_enabled; - unsigned int hsr_enabled; }; /* @@ -173,11 +161,7 @@ static int twl4030_write(struct snd_soc_codec *codec, unsigned int reg, unsigned int value) { twl4030_write_reg_cache(codec, reg, value); - if (likely(reg < TWL4030_REG_SW_SHADOW)) - return twl4030_i2c_write_u8(TWL4030_MODULE_AUDIO_VOICE, value, - reg); - else - return 0; + return twl4030_i2c_write_u8(TWL4030_MODULE_AUDIO_VOICE, value, reg); } static void twl4030_codec_enable(struct snd_soc_codec *codec, int enable) @@ -204,7 +188,6 @@ static void twl4030_codec_enable(struct snd_soc_codec *codec, int enable) static void twl4030_init_chip(struct snd_soc_codec *codec) { - u8 *cache = codec->reg_cache; int i; /* clear CODECPDZ prior to setting register defaults */ @@ -212,7 +195,7 @@ static void twl4030_init_chip(struct snd_soc_codec *codec) /* set all audio section registers to reasonable defaults */ for (i = TWL4030_REG_OPTION; i <= TWL4030_REG_MISC_SET_2; i++) - twl4030_write(codec, i, cache[i]); + twl4030_write(codec, i, twl4030_reg[i]); } @@ -249,7 +232,7 @@ static void twl4030_codec_mute(struct snd_soc_codec *codec, int mute) TWL4030_REG_PRECKL_CTL); reg_val = twl4030_read_reg_cache(codec, TWL4030_REG_PRECKR_CTL); twl4030_i2c_write_u8(TWL4030_MODULE_AUDIO_VOICE, - reg_val & (~TWL4030_PRECKR_GAIN), + reg_val & (~TWL4030_PRECKL_GAIN), TWL4030_REG_PRECKR_CTL); /* Disable PLL */ @@ -333,60 +316,104 @@ static void twl4030_power_down(struct snd_soc_codec *codec) } /* Earpiece */ -static const struct snd_kcontrol_new twl4030_dapm_earpiece_controls[] = { - SOC_DAPM_SINGLE("Voice", TWL4030_REG_EAR_CTL, 0, 1, 0), - SOC_DAPM_SINGLE("AudioL1", TWL4030_REG_EAR_CTL, 1, 1, 0), - SOC_DAPM_SINGLE("AudioL2", TWL4030_REG_EAR_CTL, 2, 1, 0), - SOC_DAPM_SINGLE("AudioR1", TWL4030_REG_EAR_CTL, 3, 1, 0), -}; +static const char *twl4030_earpiece_texts[] = + {"Off", "DACL1", "DACL2", "DACR1"}; + +static const unsigned int twl4030_earpiece_values[] = + {0x0, 0x1, 0x2, 0x4}; + +static const struct soc_enum twl4030_earpiece_enum = + SOC_VALUE_ENUM_SINGLE(TWL4030_REG_EAR_CTL, 1, 0x7, + ARRAY_SIZE(twl4030_earpiece_texts), + twl4030_earpiece_texts, + twl4030_earpiece_values); + +static const struct snd_kcontrol_new twl4030_dapm_earpiece_control = +SOC_DAPM_VALUE_ENUM("Route", twl4030_earpiece_enum); /* PreDrive Left */ -static const struct snd_kcontrol_new twl4030_dapm_predrivel_controls[] = { - SOC_DAPM_SINGLE("Voice", TWL4030_REG_PREDL_CTL, 0, 1, 0), - SOC_DAPM_SINGLE("AudioL1", TWL4030_REG_PREDL_CTL, 1, 1, 0), - SOC_DAPM_SINGLE("AudioL2", TWL4030_REG_PREDL_CTL, 2, 1, 0), - SOC_DAPM_SINGLE("AudioR2", TWL4030_REG_PREDL_CTL, 3, 1, 0), -}; +static const char *twl4030_predrivel_texts[] = + {"Off", "DACL1", "DACL2", "DACR2"}; + +static const unsigned int twl4030_predrivel_values[] = + {0x0, 0x1, 0x2, 0x4}; + +static const struct soc_enum twl4030_predrivel_enum = + SOC_VALUE_ENUM_SINGLE(TWL4030_REG_PREDL_CTL, 1, 0x7, + ARRAY_SIZE(twl4030_predrivel_texts), + twl4030_predrivel_texts, + twl4030_predrivel_values); + +static const struct snd_kcontrol_new twl4030_dapm_predrivel_control = +SOC_DAPM_VALUE_ENUM("Route", twl4030_predrivel_enum); /* PreDrive Right */ -static const struct snd_kcontrol_new twl4030_dapm_predriver_controls[] = { - SOC_DAPM_SINGLE("Voice", TWL4030_REG_PREDR_CTL, 0, 1, 0), - SOC_DAPM_SINGLE("AudioR1", TWL4030_REG_PREDR_CTL, 1, 1, 0), - SOC_DAPM_SINGLE("AudioR2", TWL4030_REG_PREDR_CTL, 2, 1, 0), - SOC_DAPM_SINGLE("AudioL2", TWL4030_REG_PREDR_CTL, 3, 1, 0), -}; +static const char *twl4030_predriver_texts[] = + {"Off", "DACR1", "DACR2", "DACL2"}; + +static const unsigned int twl4030_predriver_values[] = + {0x0, 0x1, 0x2, 0x4}; + +static const struct soc_enum twl4030_predriver_enum = + SOC_VALUE_ENUM_SINGLE(TWL4030_REG_PREDR_CTL, 1, 0x7, + ARRAY_SIZE(twl4030_predriver_texts), + twl4030_predriver_texts, + twl4030_predriver_values); + +static const struct snd_kcontrol_new twl4030_dapm_predriver_control = +SOC_DAPM_VALUE_ENUM("Route", twl4030_predriver_enum); /* Headset Left */ -static const struct snd_kcontrol_new twl4030_dapm_hsol_controls[] = { - SOC_DAPM_SINGLE("Voice", TWL4030_REG_HS_SEL, 0, 1, 0), - SOC_DAPM_SINGLE("AudioL1", TWL4030_REG_HS_SEL, 1, 1, 0), - SOC_DAPM_SINGLE("AudioL2", TWL4030_REG_HS_SEL, 2, 1, 0), -}; +static const char *twl4030_hsol_texts[] = + {"Off", "DACL1", "DACL2"}; + +static const struct soc_enum twl4030_hsol_enum = + SOC_ENUM_SINGLE(TWL4030_REG_HS_SEL, 1, + ARRAY_SIZE(twl4030_hsol_texts), + twl4030_hsol_texts); + +static const struct snd_kcontrol_new twl4030_dapm_hsol_control = +SOC_DAPM_ENUM("Route", twl4030_hsol_enum); /* Headset Right */ -static const struct snd_kcontrol_new twl4030_dapm_hsor_controls[] = { - SOC_DAPM_SINGLE("Voice", TWL4030_REG_HS_SEL, 3, 1, 0), - SOC_DAPM_SINGLE("AudioR1", TWL4030_REG_HS_SEL, 4, 1, 0), - SOC_DAPM_SINGLE("AudioR2", TWL4030_REG_HS_SEL, 5, 1, 0), -}; +static const char *twl4030_hsor_texts[] = + {"Off", "DACR1", "DACR2"}; + +static const struct soc_enum twl4030_hsor_enum = + SOC_ENUM_SINGLE(TWL4030_REG_HS_SEL, 4, + ARRAY_SIZE(twl4030_hsor_texts), + twl4030_hsor_texts); + +static const struct snd_kcontrol_new twl4030_dapm_hsor_control = +SOC_DAPM_ENUM("Route", twl4030_hsor_enum); /* Carkit Left */ -static const struct snd_kcontrol_new twl4030_dapm_carkitl_controls[] = { - SOC_DAPM_SINGLE("Voice", TWL4030_REG_PRECKL_CTL, 0, 1, 0), - SOC_DAPM_SINGLE("AudioL1", TWL4030_REG_PRECKL_CTL, 1, 1, 0), - SOC_DAPM_SINGLE("AudioL2", TWL4030_REG_PRECKL_CTL, 2, 1, 0), -}; +static const char *twl4030_carkitl_texts[] = + {"Off", "DACL1", "DACL2"}; + +static const struct soc_enum twl4030_carkitl_enum = + SOC_ENUM_SINGLE(TWL4030_REG_PRECKL_CTL, 1, + ARRAY_SIZE(twl4030_carkitl_texts), + twl4030_carkitl_texts); + +static const struct snd_kcontrol_new twl4030_dapm_carkitl_control = +SOC_DAPM_ENUM("Route", twl4030_carkitl_enum); /* Carkit Right */ -static const struct snd_kcontrol_new twl4030_dapm_carkitr_controls[] = { - SOC_DAPM_SINGLE("Voice", TWL4030_REG_PRECKR_CTL, 0, 1, 0), - SOC_DAPM_SINGLE("AudioR1", TWL4030_REG_PRECKR_CTL, 1, 1, 0), - SOC_DAPM_SINGLE("AudioR2", TWL4030_REG_PRECKR_CTL, 2, 1, 0), -}; +static const char *twl4030_carkitr_texts[] = + {"Off", "DACR1", "DACR2"}; + +static const struct soc_enum twl4030_carkitr_enum = + SOC_ENUM_SINGLE(TWL4030_REG_PRECKR_CTL, 1, + ARRAY_SIZE(twl4030_carkitr_texts), + twl4030_carkitr_texts); + +static const struct snd_kcontrol_new twl4030_dapm_carkitr_control = +SOC_DAPM_ENUM("Route", twl4030_carkitr_enum); /* Handsfree Left */ static const char *twl4030_handsfreel_texts[] = - {"Voice", "AudioL1", "AudioL2", "AudioR2"}; + {"Voice", "DACL1", "DACL2", "DACR2"}; static const struct soc_enum twl4030_handsfreel_enum = SOC_ENUM_SINGLE(TWL4030_REG_HFL_CTL, 0, @@ -396,13 +423,9 @@ static const struct soc_enum twl4030_handsfreel_enum = static const struct snd_kcontrol_new twl4030_dapm_handsfreel_control = SOC_DAPM_ENUM("Route", twl4030_handsfreel_enum); -/* Handsfree Left virtual mute */ -static const struct snd_kcontrol_new twl4030_dapm_handsfreelmute_control = - SOC_DAPM_SINGLE("Switch", TWL4030_REG_SW_SHADOW, 0, 1, 0); - /* Handsfree Right */ static const char *twl4030_handsfreer_texts[] = - {"Voice", "AudioR1", "AudioR2", "AudioL2"}; + {"Voice", "DACR1", "DACR2", "DACL2"}; static const struct soc_enum twl4030_handsfreer_enum = SOC_ENUM_SINGLE(TWL4030_REG_HFR_CTL, 0, @@ -412,48 +435,37 @@ static const struct soc_enum twl4030_handsfreer_enum = static const struct snd_kcontrol_new twl4030_dapm_handsfreer_control = SOC_DAPM_ENUM("Route", twl4030_handsfreer_enum); -/* Handsfree Right virtual mute */ -static const struct snd_kcontrol_new twl4030_dapm_handsfreermute_control = - SOC_DAPM_SINGLE("Switch", TWL4030_REG_SW_SHADOW, 1, 1, 0); +/* Left analog microphone selection */ +static const char *twl4030_analoglmic_texts[] = + {"Off", "Main mic", "Headset mic", "AUXL", "Carkit mic"}; -/* Vibra */ -/* Vibra audio path selection */ -static const char *twl4030_vibra_texts[] = - {"AudioL1", "AudioR1", "AudioL2", "AudioR2"}; +static const unsigned int twl4030_analoglmic_values[] = + {0x0, 0x1, 0x2, 0x4, 0x8}; -static const struct soc_enum twl4030_vibra_enum = - SOC_ENUM_SINGLE(TWL4030_REG_VIBRA_CTL, 2, - ARRAY_SIZE(twl4030_vibra_texts), - twl4030_vibra_texts); +static const struct soc_enum twl4030_analoglmic_enum = + SOC_VALUE_ENUM_SINGLE(TWL4030_REG_ANAMICL, 0, 0xf, + ARRAY_SIZE(twl4030_analoglmic_texts), + twl4030_analoglmic_texts, + twl4030_analoglmic_values); -static const struct snd_kcontrol_new twl4030_dapm_vibra_control = -SOC_DAPM_ENUM("Route", twl4030_vibra_enum); +static const struct snd_kcontrol_new twl4030_dapm_analoglmic_control = +SOC_DAPM_VALUE_ENUM("Route", twl4030_analoglmic_enum); -/* Vibra path selection: local vibrator (PWM) or audio driven */ -static const char *twl4030_vibrapath_texts[] = - {"Local vibrator", "Audio"}; +/* Right analog microphone selection */ +static const char *twl4030_analogrmic_texts[] = + {"Off", "Sub mic", "AUXR"}; -static const struct soc_enum twl4030_vibrapath_enum = - SOC_ENUM_SINGLE(TWL4030_REG_VIBRA_CTL, 4, - ARRAY_SIZE(twl4030_vibrapath_texts), - twl4030_vibrapath_texts); +static const unsigned int twl4030_analogrmic_values[] = + {0x0, 0x1, 0x4}; -static const struct snd_kcontrol_new twl4030_dapm_vibrapath_control = -SOC_DAPM_ENUM("Route", twl4030_vibrapath_enum); +static const struct soc_enum twl4030_analogrmic_enum = + SOC_VALUE_ENUM_SINGLE(TWL4030_REG_ANAMICR, 0, 0x5, + ARRAY_SIZE(twl4030_analogrmic_texts), + twl4030_analogrmic_texts, + twl4030_analogrmic_values); -/* Left analog microphone selection */ -static const struct snd_kcontrol_new twl4030_dapm_analoglmic_controls[] = { - SOC_DAPM_SINGLE("Main mic", TWL4030_REG_ANAMICL, 0, 1, 0), - SOC_DAPM_SINGLE("Headset mic", TWL4030_REG_ANAMICL, 1, 1, 0), - SOC_DAPM_SINGLE("AUXL", TWL4030_REG_ANAMICL, 2, 1, 0), - SOC_DAPM_SINGLE("Carkit mic", TWL4030_REG_ANAMICL, 3, 1, 0), -}; - -/* Right analog microphone selection */ -static const struct snd_kcontrol_new twl4030_dapm_analogrmic_controls[] = { - SOC_DAPM_SINGLE("Sub mic", TWL4030_REG_ANAMICR, 0, 1, 0), - SOC_DAPM_SINGLE("AUXR", TWL4030_REG_ANAMICR, 2, 1, 0), -}; +static const struct snd_kcontrol_new twl4030_dapm_analogrmic_control = +SOC_DAPM_VALUE_ENUM("Route", twl4030_analogrmic_enum); /* TX1 L/R Analog/Digital microphone selection */ static const char *twl4030_micpathtx1_texts[] = @@ -495,10 +507,6 @@ static const struct snd_kcontrol_new twl4030_dapm_abypassr2_control = static const struct snd_kcontrol_new twl4030_dapm_abypassl2_control = SOC_DAPM_SINGLE("Switch", TWL4030_REG_ARXL2_APGA_CTL, 2, 1, 0); -/* Analog bypass for Voice */ -static const struct snd_kcontrol_new twl4030_dapm_abypassv_control = - SOC_DAPM_SINGLE("Switch", TWL4030_REG_VDL_APGA_CTL, 2, 1, 0); - /* Digital bypass gain, 0 mutes the bypass */ static const unsigned int twl4030_dapm_dbypass_tlv[] = { TLV_DB_RANGE_HEAD(2), @@ -518,18 +526,6 @@ static const struct snd_kcontrol_new twl4030_dapm_dbypassr_control = TWL4030_REG_ATX2ARXPGA, 0, 7, 0, twl4030_dapm_dbypass_tlv); -/* - * Voice Sidetone GAIN volume control: - * from -51 to -10 dB in 1 dB steps (mute instead of -51 dB) - */ -static DECLARE_TLV_DB_SCALE(twl4030_dapm_dbypassv_tlv, -5100, 100, 1); - -/* Digital bypass voice: sidetone (VUL -> VDL)*/ -static const struct snd_kcontrol_new twl4030_dapm_dbypassv_control = - SOC_DAPM_SINGLE_TLV("Volume", - TWL4030_REG_VSTPGA, 0, 0x29, 0, - twl4030_dapm_dbypassv_tlv); - static int micpath_event(struct snd_soc_dapm_widget *w, struct snd_kcontrol *kcontrol, int event) { @@ -560,143 +556,63 @@ static int micpath_event(struct snd_soc_dapm_widget *w, return 0; } -static void handsfree_ramp(struct snd_soc_codec *codec, int reg, int ramp) +static int handsfree_event(struct snd_soc_dapm_widget *w, + struct snd_kcontrol *kcontrol, int event) { + struct soc_enum *e = (struct soc_enum *)w->kcontrols->private_value; unsigned char hs_ctl; - hs_ctl = twl4030_read_reg_cache(codec, reg); + hs_ctl = twl4030_read_reg_cache(w->codec, e->reg); - if (ramp) { - /* HF ramp-up */ - hs_ctl |= TWL4030_HF_CTL_REF_EN; - twl4030_write(codec, reg, hs_ctl); - udelay(10); + if (hs_ctl & TWL4030_HF_CTL_REF_EN) { hs_ctl |= TWL4030_HF_CTL_RAMP_EN; - twl4030_write(codec, reg, hs_ctl); - udelay(40); + twl4030_write(w->codec, e->reg, hs_ctl); hs_ctl |= TWL4030_HF_CTL_LOOP_EN; + twl4030_write(w->codec, e->reg, hs_ctl); hs_ctl |= TWL4030_HF_CTL_HB_EN; - twl4030_write(codec, reg, hs_ctl); + twl4030_write(w->codec, e->reg, hs_ctl); } else { - /* HF ramp-down */ - hs_ctl &= ~TWL4030_HF_CTL_LOOP_EN; - hs_ctl &= ~TWL4030_HF_CTL_HB_EN; - twl4030_write(codec, reg, hs_ctl); - hs_ctl &= ~TWL4030_HF_CTL_RAMP_EN; - twl4030_write(codec, reg, hs_ctl); - udelay(40); - hs_ctl &= ~TWL4030_HF_CTL_REF_EN; - twl4030_write(codec, reg, hs_ctl); + hs_ctl &= ~(TWL4030_HF_CTL_RAMP_EN | TWL4030_HF_CTL_LOOP_EN + | TWL4030_HF_CTL_HB_EN); + twl4030_write(w->codec, e->reg, hs_ctl); } -} -static int handsfreelpga_event(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) -{ - switch (event) { - case SND_SOC_DAPM_POST_PMU: - handsfree_ramp(w->codec, TWL4030_REG_HFL_CTL, 1); - break; - case SND_SOC_DAPM_POST_PMD: - handsfree_ramp(w->codec, TWL4030_REG_HFL_CTL, 0); - break; - } return 0; } -static int handsfreerpga_event(struct snd_soc_dapm_widget *w, +static int headsetl_event(struct snd_soc_dapm_widget *w, struct snd_kcontrol *kcontrol, int event) -{ - switch (event) { - case SND_SOC_DAPM_POST_PMU: - handsfree_ramp(w->codec, TWL4030_REG_HFR_CTL, 1); - break; - case SND_SOC_DAPM_POST_PMD: - handsfree_ramp(w->codec, TWL4030_REG_HFR_CTL, 0); - break; - } - return 0; -} - -static void headset_ramp(struct snd_soc_codec *codec, int ramp) { unsigned char hs_gain, hs_pop; - struct twl4030_priv *twl4030 = codec->private_data; - /* Base values for ramp delay calculation: 2^19 - 2^26 */ - unsigned int ramp_base[] = {524288, 1048576, 2097152, 4194304, - 8388608, 16777216, 33554432, 67108864}; - hs_gain = twl4030_read_reg_cache(codec, TWL4030_REG_HS_GAIN_SET); - hs_pop = twl4030_read_reg_cache(codec, TWL4030_REG_HS_POPN_SET); + /* Save the current volume */ + hs_gain = twl4030_read_reg_cache(w->codec, TWL4030_REG_HS_GAIN_SET); + hs_pop = twl4030_read_reg_cache(w->codec, TWL4030_REG_HS_POPN_SET); - if (ramp) { - /* Headset ramp-up according to the TRM */ + switch (event) { + case SND_SOC_DAPM_POST_PMU: + /* Do the anti-pop/bias ramp enable according to the TRM */ hs_pop |= TWL4030_VMID_EN; - twl4030_write(codec, TWL4030_REG_HS_POPN_SET, hs_pop); - twl4030_write(codec, TWL4030_REG_HS_GAIN_SET, hs_gain); + twl4030_write(w->codec, TWL4030_REG_HS_POPN_SET, hs_pop); + /* Is this needed? Can we just use whatever gain here? */ + twl4030_write(w->codec, TWL4030_REG_HS_GAIN_SET, + (hs_gain & (~0x0f)) | 0x0a); hs_pop |= TWL4030_RAMP_EN; - twl4030_write(codec, TWL4030_REG_HS_POPN_SET, hs_pop); - } else { - /* Headset ramp-down _not_ according to - * the TRM, but in a way that it is working */ + twl4030_write(w->codec, TWL4030_REG_HS_POPN_SET, hs_pop); + + /* Restore the original volume */ + twl4030_write(w->codec, TWL4030_REG_HS_GAIN_SET, hs_gain); + break; + case SND_SOC_DAPM_POST_PMD: + /* Do the anti-pop/bias ramp disable according to the TRM */ hs_pop &= ~TWL4030_RAMP_EN; - twl4030_write(codec, TWL4030_REG_HS_POPN_SET, hs_pop); - /* Wait ramp delay time + 1, so the VMID can settle */ - mdelay((ramp_base[(hs_pop & TWL4030_RAMP_DELAY) >> 2] / - twl4030->sysclk) + 1); + twl4030_write(w->codec, TWL4030_REG_HS_POPN_SET, hs_pop); /* Bypass the reg_cache to mute the headset */ twl4030_i2c_write_u8(TWL4030_MODULE_AUDIO_VOICE, hs_gain & (~0x0f), TWL4030_REG_HS_GAIN_SET); - hs_pop &= ~TWL4030_VMID_EN; - twl4030_write(codec, TWL4030_REG_HS_POPN_SET, hs_pop); - } -} - -static int headsetlpga_event(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) -{ - struct twl4030_priv *twl4030 = w->codec->private_data; - - switch (event) { - case SND_SOC_DAPM_POST_PMU: - /* Do the ramp-up only once */ - if (!twl4030->hsr_enabled) - headset_ramp(w->codec, 1); - - twl4030->hsl_enabled = 1; - break; - case SND_SOC_DAPM_POST_PMD: - /* Do the ramp-down only if both headsetL/R is disabled */ - if (!twl4030->hsr_enabled) - headset_ramp(w->codec, 0); - - twl4030->hsl_enabled = 0; - break; - } - return 0; -} - -static int headsetrpga_event(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) -{ - struct twl4030_priv *twl4030 = w->codec->private_data; - - switch (event) { - case SND_SOC_DAPM_POST_PMU: - /* Do the ramp-up only once */ - if (!twl4030->hsl_enabled) - headset_ramp(w->codec, 1); - - twl4030->hsr_enabled = 1; - break; - case SND_SOC_DAPM_POST_PMD: - /* Do the ramp-down only if both headsetL/R is disabled */ - if (!twl4030->hsl_enabled) - headset_ramp(w->codec, 0); - - twl4030->hsr_enabled = 0; + twl4030_write(w->codec, TWL4030_REG_HS_POPN_SET, hs_pop); break; } return 0; @@ -708,7 +624,7 @@ static int bypass_event(struct snd_soc_dapm_widget *w, struct soc_mixer_control *m = (struct soc_mixer_control *)w->kcontrols->private_value; struct twl4030_priv *twl4030 = w->codec->private_data; - unsigned char reg, misc; + unsigned char reg; reg = twl4030_read_reg_cache(w->codec, m->reg); @@ -720,34 +636,14 @@ static int bypass_event(struct snd_soc_dapm_widget *w, else twl4030->bypass_state &= ~(1 << (m->reg - TWL4030_REG_ARXL1_APGA_CTL)); - } else if (m->reg == TWL4030_REG_VDL_APGA_CTL) { - /* Analog voice bypass */ - if (reg & (1 << m->shift)) - twl4030->bypass_state |= (1 << 4); - else - twl4030->bypass_state &= ~(1 << 4); - } else if (m->reg == TWL4030_REG_VSTPGA) { - /* Voice digital bypass */ - if (reg) - twl4030->bypass_state |= (1 << 5); - else - twl4030->bypass_state &= ~(1 << 5); } else { /* Digital bypass */ if (reg & (0x7 << m->shift)) - twl4030->bypass_state |= (1 << (m->shift ? 7 : 6)); + twl4030->bypass_state |= (1 << (m->shift ? 5 : 4)); else - twl4030->bypass_state &= ~(1 << (m->shift ? 7 : 6)); + twl4030->bypass_state &= ~(1 << (m->shift ? 5 : 4)); } - /* Enable master analog loopback mode if any analog switch is enabled*/ - misc = twl4030_read_reg_cache(w->codec, TWL4030_REG_MISC_SET_1); - if (twl4030->bypass_state & 0x1F) - misc |= TWL4030_FMLOOP_EN; - else - misc &= ~TWL4030_FMLOOP_EN; - twl4030_write(w->codec, TWL4030_REG_MISC_SET_1, misc); - if (w->codec->bias_level == SND_SOC_BIAS_STANDBY) { if (twl4030->bypass_state) twl4030_codec_mute(w->codec, 0); @@ -914,48 +810,6 @@ static int snd_soc_put_volsw_r2_twl4030(struct snd_kcontrol *kcontrol, return err; } -/* Codec operation modes */ -static const char *twl4030_op_modes_texts[] = { - "Option 2 (voice/audio)", "Option 1 (audio)" -}; - -static const struct soc_enum twl4030_op_modes_enum = - SOC_ENUM_SINGLE(TWL4030_REG_CODEC_MODE, 0, - ARRAY_SIZE(twl4030_op_modes_texts), - twl4030_op_modes_texts); - -int snd_soc_put_twl4030_opmode_enum_double(struct snd_kcontrol *kcontrol, - struct snd_ctl_elem_value *ucontrol) -{ - struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol); - struct twl4030_priv *twl4030 = codec->private_data; - struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; - unsigned short val; - unsigned short mask, bitmask; - - if (twl4030->configured) { - printk(KERN_ERR "twl4030 operation mode cannot be " - "changed on-the-fly\n"); - return -EBUSY; - } - - for (bitmask = 1; bitmask < e->max; bitmask <<= 1) - ; - if (ucontrol->value.enumerated.item[0] > e->max - 1) - return -EINVAL; - - val = ucontrol->value.enumerated.item[0] << e->shift_l; - mask = (bitmask - 1) << e->shift_l; - if (e->shift_l != e->shift_r) { - if (ucontrol->value.enumerated.item[1] > e->max - 1) - return -EINVAL; - val |= ucontrol->value.enumerated.item[1] << e->shift_r; - mask |= (bitmask - 1) << e->shift_r; - } - - return snd_soc_update_bits(codec, e->reg, mask, val); -} - /* * FGAIN volume control: * from -62 to 0 dB in 1 dB steps (mute instead of -63 dB) @@ -969,12 +823,6 @@ static DECLARE_TLV_DB_SCALE(digital_fine_tlv, -6300, 100, 1); */ static DECLARE_TLV_DB_SCALE(digital_coarse_tlv, 0, 600, 0); -/* - * Voice Downlink GAIN volume control: - * from -37 to 12 dB in 1 dB steps (mute instead of -37 dB) - */ -static DECLARE_TLV_DB_SCALE(digital_voice_downlink_tlv, -3700, 100, 1); - /* * Analog playback gain * -24 dB to 12 dB in 2 dB steps @@ -1016,32 +864,7 @@ static const struct soc_enum twl4030_rampdelay_enum = ARRAY_SIZE(twl4030_rampdelay_texts), twl4030_rampdelay_texts); -/* Vibra H-bridge direction mode */ -static const char *twl4030_vibradirmode_texts[] = { - "Vibra H-bridge direction", "Audio data MSB", -}; - -static const struct soc_enum twl4030_vibradirmode_enum = - SOC_ENUM_SINGLE(TWL4030_REG_VIBRA_CTL, 5, - ARRAY_SIZE(twl4030_vibradirmode_texts), - twl4030_vibradirmode_texts); - -/* Vibra H-bridge direction */ -static const char *twl4030_vibradir_texts[] = { - "Positive polarity", "Negative polarity", -}; - -static const struct soc_enum twl4030_vibradir_enum = - SOC_ENUM_SINGLE(TWL4030_REG_VIBRA_CTL, 1, - ARRAY_SIZE(twl4030_vibradir_texts), - twl4030_vibradir_texts); - static const struct snd_kcontrol_new twl4030_snd_controls[] = { - /* Codec operation mode control */ - SOC_ENUM_EXT("Codec Operation Mode", twl4030_op_modes_enum, - snd_soc_get_enum_double, - snd_soc_put_twl4030_opmode_enum_double), - /* Common playback gain controls */ SOC_DOUBLE_R_TLV("DAC1 Digital Fine Playback Volume", TWL4030_REG_ARXL1PGA, TWL4030_REG_ARXR1PGA, @@ -1070,16 +893,6 @@ static const struct snd_kcontrol_new twl4030_snd_controls[] = { TWL4030_REG_ARXL2_APGA_CTL, TWL4030_REG_ARXR2_APGA_CTL, 1, 1, 0), - /* Common voice downlink gain controls */ - SOC_SINGLE_TLV("DAC Voice Digital Downlink Volume", - TWL4030_REG_VRXPGA, 0, 0x31, 0, digital_voice_downlink_tlv), - - SOC_SINGLE_TLV("DAC Voice Analog Downlink Volume", - TWL4030_REG_VDL_APGA_CTL, 3, 0x12, 1, analog_tlv), - - SOC_SINGLE("DAC Voice Analog Downlink Switch", - TWL4030_REG_VDL_APGA_CTL, 1, 1, 0), - /* Separate output gain controls */ SOC_DOUBLE_R_TLV_TWL4030("PreDriv Playback Volume", TWL4030_REG_PREDL_CTL, TWL4030_REG_PREDR_CTL, @@ -1107,9 +920,6 @@ static const struct snd_kcontrol_new twl4030_snd_controls[] = { 0, 3, 5, 0, input_gain_tlv), SOC_ENUM("HS ramp delay", twl4030_rampdelay_enum), - - SOC_ENUM("Vibra H-bridge mode", twl4030_vibradirmode_enum), - SOC_ENUM("Vibra H-bridge direction", twl4030_vibradir_enum), }; static const struct snd_soc_dapm_widget twl4030_dapm_widgets[] = { @@ -1137,20 +947,27 @@ static const struct snd_soc_dapm_widget twl4030_dapm_widgets[] = { SND_SOC_DAPM_OUTPUT("CARKITR"), SND_SOC_DAPM_OUTPUT("HFL"), SND_SOC_DAPM_OUTPUT("HFR"), - SND_SOC_DAPM_OUTPUT("VIBRA"), /* DACs */ - SND_SOC_DAPM_DAC("DAC Right1", "Right Front HiFi Playback", + SND_SOC_DAPM_DAC("DAC Right1", "Right Front Playback", SND_SOC_NOPM, 0, 0), - SND_SOC_DAPM_DAC("DAC Left1", "Left Front HiFi Playback", + SND_SOC_DAPM_DAC("DAC Left1", "Left Front Playback", SND_SOC_NOPM, 0, 0), - SND_SOC_DAPM_DAC("DAC Right2", "Right Rear HiFi Playback", + SND_SOC_DAPM_DAC("DAC Right2", "Right Rear Playback", SND_SOC_NOPM, 0, 0), - SND_SOC_DAPM_DAC("DAC Left2", "Left Rear HiFi Playback", - SND_SOC_NOPM, 0, 0), - SND_SOC_DAPM_DAC("DAC Voice", "Voice Playback", + SND_SOC_DAPM_DAC("DAC Left2", "Left Rear Playback", SND_SOC_NOPM, 0, 0), + /* Analog PGAs */ + SND_SOC_DAPM_PGA("ARXR1_APGA", TWL4030_REG_ARXR1_APGA_CTL, + 0, 0, NULL, 0), + SND_SOC_DAPM_PGA("ARXL1_APGA", TWL4030_REG_ARXL1_APGA_CTL, + 0, 0, NULL, 0), + SND_SOC_DAPM_PGA("ARXR2_APGA", TWL4030_REG_ARXR2_APGA_CTL, + 0, 0, NULL, 0), + SND_SOC_DAPM_PGA("ARXL2_APGA", TWL4030_REG_ARXL2_APGA_CTL, + 0, 0, NULL, 0), + /* Analog bypasses */ SND_SOC_DAPM_SWITCH_E("Right1 Analog Loopback", SND_SOC_NOPM, 0, 0, &twl4030_dapm_abypassr1_control, bypass_event, @@ -1164,9 +981,6 @@ static const struct snd_soc_dapm_widget twl4030_dapm_widgets[] = { SND_SOC_DAPM_SWITCH_E("Left2 Analog Loopback", SND_SOC_NOPM, 0, 0, &twl4030_dapm_abypassl2_control, bypass_event, SND_SOC_DAPM_POST_REG), - SND_SOC_DAPM_SWITCH_E("Voice Analog Loopback", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_abypassv_control, - bypass_event, SND_SOC_DAPM_POST_REG), /* Digital bypasses */ SND_SOC_DAPM_SWITCH_E("Left Digital Loopback", SND_SOC_NOPM, 0, 0, @@ -1175,88 +989,43 @@ static const struct snd_soc_dapm_widget twl4030_dapm_widgets[] = { SND_SOC_DAPM_SWITCH_E("Right Digital Loopback", SND_SOC_NOPM, 0, 0, &twl4030_dapm_dbypassr_control, bypass_event, SND_SOC_DAPM_POST_REG), - SND_SOC_DAPM_SWITCH_E("Voice Digital Loopback", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_dbypassv_control, bypass_event, - SND_SOC_DAPM_POST_REG), - /* Digital mixers, power control for the physical DACs */ - SND_SOC_DAPM_MIXER("Digital R1 Playback Mixer", - TWL4030_REG_AVDAC_CTL, 0, 0, NULL, 0), - SND_SOC_DAPM_MIXER("Digital L1 Playback Mixer", - TWL4030_REG_AVDAC_CTL, 1, 0, NULL, 0), - SND_SOC_DAPM_MIXER("Digital R2 Playback Mixer", - TWL4030_REG_AVDAC_CTL, 2, 0, NULL, 0), - SND_SOC_DAPM_MIXER("Digital L2 Playback Mixer", - TWL4030_REG_AVDAC_CTL, 3, 0, NULL, 0), - SND_SOC_DAPM_MIXER("Digital Voice Playback Mixer", - TWL4030_REG_AVDAC_CTL, 4, 0, NULL, 0), - - /* Analog mixers, power control for the physical PGAs */ - SND_SOC_DAPM_MIXER("Analog R1 Playback Mixer", - TWL4030_REG_ARXR1_APGA_CTL, 0, 0, NULL, 0), - SND_SOC_DAPM_MIXER("Analog L1 Playback Mixer", - TWL4030_REG_ARXL1_APGA_CTL, 0, 0, NULL, 0), - SND_SOC_DAPM_MIXER("Analog R2 Playback Mixer", - TWL4030_REG_ARXR2_APGA_CTL, 0, 0, NULL, 0), - SND_SOC_DAPM_MIXER("Analog L2 Playback Mixer", - TWL4030_REG_ARXL2_APGA_CTL, 0, 0, NULL, 0), - SND_SOC_DAPM_MIXER("Analog Voice Playback Mixer", - TWL4030_REG_VDL_APGA_CTL, 0, 0, NULL, 0), - - /* Output MIXER controls */ + SND_SOC_DAPM_MIXER("Analog R1 Playback Mixer", TWL4030_REG_AVDAC_CTL, + 0, 0, NULL, 0), + SND_SOC_DAPM_MIXER("Analog L1 Playback Mixer", TWL4030_REG_AVDAC_CTL, + 1, 0, NULL, 0), + SND_SOC_DAPM_MIXER("Analog R2 Playback Mixer", TWL4030_REG_AVDAC_CTL, + 2, 0, NULL, 0), + SND_SOC_DAPM_MIXER("Analog L2 Playback Mixer", TWL4030_REG_AVDAC_CTL, + 3, 0, NULL, 0), + + /* Output MUX controls */ /* Earpiece */ - SND_SOC_DAPM_MIXER("Earpiece Mixer", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_earpiece_controls[0], - ARRAY_SIZE(twl4030_dapm_earpiece_controls)), + SND_SOC_DAPM_VALUE_MUX("Earpiece Mux", SND_SOC_NOPM, 0, 0, + &twl4030_dapm_earpiece_control), /* PreDrivL/R */ - SND_SOC_DAPM_MIXER("PredriveL Mixer", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_predrivel_controls[0], - ARRAY_SIZE(twl4030_dapm_predrivel_controls)), - SND_SOC_DAPM_MIXER("PredriveR Mixer", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_predriver_controls[0], - ARRAY_SIZE(twl4030_dapm_predriver_controls)), + SND_SOC_DAPM_VALUE_MUX("PredriveL Mux", SND_SOC_NOPM, 0, 0, + &twl4030_dapm_predrivel_control), + SND_SOC_DAPM_VALUE_MUX("PredriveR Mux", SND_SOC_NOPM, 0, 0, + &twl4030_dapm_predriver_control), /* HeadsetL/R */ - SND_SOC_DAPM_MIXER("HeadsetL Mixer", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_hsol_controls[0], - ARRAY_SIZE(twl4030_dapm_hsol_controls)), - SND_SOC_DAPM_PGA_E("HeadsetL PGA", SND_SOC_NOPM, - 0, 0, NULL, 0, headsetlpga_event, - SND_SOC_DAPM_POST_PMU|SND_SOC_DAPM_POST_PMD), - SND_SOC_DAPM_MIXER("HeadsetR Mixer", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_hsor_controls[0], - ARRAY_SIZE(twl4030_dapm_hsor_controls)), - SND_SOC_DAPM_PGA_E("HeadsetR PGA", SND_SOC_NOPM, - 0, 0, NULL, 0, headsetrpga_event, - SND_SOC_DAPM_POST_PMU|SND_SOC_DAPM_POST_PMD), + SND_SOC_DAPM_MUX_E("HeadsetL Mux", SND_SOC_NOPM, 0, 0, + &twl4030_dapm_hsol_control, headsetl_event, + SND_SOC_DAPM_POST_PMU|SND_SOC_DAPM_POST_PMD), + SND_SOC_DAPM_MUX("HeadsetR Mux", SND_SOC_NOPM, 0, 0, + &twl4030_dapm_hsor_control), /* CarkitL/R */ - SND_SOC_DAPM_MIXER("CarkitL Mixer", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_carkitl_controls[0], - ARRAY_SIZE(twl4030_dapm_carkitl_controls)), - SND_SOC_DAPM_MIXER("CarkitR Mixer", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_carkitr_controls[0], - ARRAY_SIZE(twl4030_dapm_carkitr_controls)), - - /* Output MUX controls */ + SND_SOC_DAPM_MUX("CarkitL Mux", SND_SOC_NOPM, 0, 0, + &twl4030_dapm_carkitl_control), + SND_SOC_DAPM_MUX("CarkitR Mux", SND_SOC_NOPM, 0, 0, + &twl4030_dapm_carkitr_control), /* HandsfreeL/R */ - SND_SOC_DAPM_MUX("HandsfreeL Mux", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_handsfreel_control), - SND_SOC_DAPM_SWITCH("HandsfreeL Switch", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_handsfreelmute_control), - SND_SOC_DAPM_PGA_E("HandsfreeL PGA", SND_SOC_NOPM, - 0, 0, NULL, 0, handsfreelpga_event, - SND_SOC_DAPM_POST_PMU|SND_SOC_DAPM_POST_PMD), - SND_SOC_DAPM_MUX("HandsfreeR Mux", SND_SOC_NOPM, 5, 0, - &twl4030_dapm_handsfreer_control), - SND_SOC_DAPM_SWITCH("HandsfreeR Switch", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_handsfreermute_control), - SND_SOC_DAPM_PGA_E("HandsfreeR PGA", SND_SOC_NOPM, - 0, 0, NULL, 0, handsfreerpga_event, - SND_SOC_DAPM_POST_PMU|SND_SOC_DAPM_POST_PMD), - /* Vibra */ - SND_SOC_DAPM_MUX("Vibra Mux", TWL4030_REG_VIBRA_CTL, 0, 0, - &twl4030_dapm_vibra_control), - SND_SOC_DAPM_MUX("Vibra Route", SND_SOC_NOPM, 0, 0, - &twl4030_dapm_vibrapath_control), + SND_SOC_DAPM_MUX_E("HandsfreeL Mux", TWL4030_REG_HFL_CTL, 5, 0, + &twl4030_dapm_handsfreel_control, handsfree_event, + SND_SOC_DAPM_POST_PMU|SND_SOC_DAPM_POST_PMD), + SND_SOC_DAPM_MUX_E("HandsfreeR Mux", TWL4030_REG_HFR_CTL, 5, 0, + &twl4030_dapm_handsfreer_control, handsfree_event, + SND_SOC_DAPM_POST_PMU|SND_SOC_DAPM_POST_PMD), /* Introducing four virtual ADC, since TWL4030 have four channel for capture */ @@ -1281,15 +1050,11 @@ static const struct snd_soc_dapm_widget twl4030_dapm_widgets[] = { SND_SOC_DAPM_POST_PMU|SND_SOC_DAPM_POST_PMD| SND_SOC_DAPM_POST_REG), - /* Analog input mixers for the capture amplifiers */ - SND_SOC_DAPM_MIXER("Analog Left Capture Route", - TWL4030_REG_ANAMICL, 4, 0, - &twl4030_dapm_analoglmic_controls[0], - ARRAY_SIZE(twl4030_dapm_analoglmic_controls)), - SND_SOC_DAPM_MIXER("Analog Right Capture Route", - TWL4030_REG_ANAMICR, 4, 0, - &twl4030_dapm_analogrmic_controls[0], - ARRAY_SIZE(twl4030_dapm_analogrmic_controls)), + /* Analog input muxes with switch for the capture amplifiers */ + SND_SOC_DAPM_VALUE_MUX("Analog Left Capture Route", + TWL4030_REG_ANAMICL, 4, 0, &twl4030_dapm_analoglmic_control), + SND_SOC_DAPM_VALUE_MUX("Analog Right Capture Route", + TWL4030_REG_ANAMICR, 4, 0, &twl4030_dapm_analogrmic_control), SND_SOC_DAPM_PGA("ADC Physical Left", TWL4030_REG_AVADC_CTL, 3, 0, NULL, 0), @@ -1308,86 +1073,62 @@ static const struct snd_soc_dapm_widget twl4030_dapm_widgets[] = { }; static const struct snd_soc_dapm_route intercon[] = { - {"Digital L1 Playback Mixer", NULL, "DAC Left1"}, - {"Digital R1 Playback Mixer", NULL, "DAC Right1"}, - {"Digital L2 Playback Mixer", NULL, "DAC Left2"}, - {"Digital R2 Playback Mixer", NULL, "DAC Right2"}, - {"Digital Voice Playback Mixer", NULL, "DAC Voice"}, - - {"Analog L1 Playback Mixer", NULL, "Digital L1 Playback Mixer"}, - {"Analog R1 Playback Mixer", NULL, "Digital R1 Playback Mixer"}, - {"Analog L2 Playback Mixer", NULL, "Digital L2 Playback Mixer"}, - {"Analog R2 Playback Mixer", NULL, "Digital R2 Playback Mixer"}, - {"Analog Voice Playback Mixer", NULL, "Digital Voice Playback Mixer"}, + {"Analog L1 Playback Mixer", NULL, "DAC Left1"}, + {"Analog R1 Playback Mixer", NULL, "DAC Right1"}, + {"Analog L2 Playback Mixer", NULL, "DAC Left2"}, + {"Analog R2 Playback Mixer", NULL, "DAC Right2"}, + + {"ARXL1_APGA", NULL, "Analog L1 Playback Mixer"}, + {"ARXR1_APGA", NULL, "Analog R1 Playback Mixer"}, + {"ARXL2_APGA", NULL, "Analog L2 Playback Mixer"}, + {"ARXR2_APGA", NULL, "Analog R2 Playback Mixer"}, /* Internal playback routings */ /* Earpiece */ - {"Earpiece Mixer", "Voice", "Analog Voice Playback Mixer"}, - {"Earpiece Mixer", "AudioL1", "Analog L1 Playback Mixer"}, - {"Earpiece Mixer", "AudioL2", "Analog L2 Playback Mixer"}, - {"Earpiece Mixer", "AudioR1", "Analog R1 Playback Mixer"}, + {"Earpiece Mux", "DACL1", "ARXL1_APGA"}, + {"Earpiece Mux", "DACL2", "ARXL2_APGA"}, + {"Earpiece Mux", "DACR1", "ARXR1_APGA"}, /* PreDrivL */ - {"PredriveL Mixer", "Voice", "Analog Voice Playback Mixer"}, - {"PredriveL Mixer", "AudioL1", "Analog L1 Playback Mixer"}, - {"PredriveL Mixer", "AudioL2", "Analog L2 Playback Mixer"}, - {"PredriveL Mixer", "AudioR2", "Analog R2 Playback Mixer"}, + {"PredriveL Mux", "DACL1", "ARXL1_APGA"}, + {"PredriveL Mux", "DACL2", "ARXL2_APGA"}, + {"PredriveL Mux", "DACR2", "ARXR2_APGA"}, /* PreDrivR */ - {"PredriveR Mixer", "Voice", "Analog Voice Playback Mixer"}, - {"PredriveR Mixer", "AudioR1", "Analog R1 Playback Mixer"}, - {"PredriveR Mixer", "AudioR2", "Analog R2 Playback Mixer"}, - {"PredriveR Mixer", "AudioL2", "Analog L2 Playback Mixer"}, + {"PredriveR Mux", "DACR1", "ARXR1_APGA"}, + {"PredriveR Mux", "DACR2", "ARXR2_APGA"}, + {"PredriveR Mux", "DACL2", "ARXL2_APGA"}, /* HeadsetL */ - {"HeadsetL Mixer", "Voice", "Analog Voice Playback Mixer"}, - {"HeadsetL Mixer", "AudioL1", "Analog L1 Playback Mixer"}, - {"HeadsetL Mixer", "AudioL2", "Analog L2 Playback Mixer"}, - {"HeadsetL PGA", NULL, "HeadsetL Mixer"}, + {"HeadsetL Mux", "DACL1", "ARXL1_APGA"}, + {"HeadsetL Mux", "DACL2", "ARXL2_APGA"}, /* HeadsetR */ - {"HeadsetR Mixer", "Voice", "Analog Voice Playback Mixer"}, - {"HeadsetR Mixer", "AudioR1", "Analog R1 Playback Mixer"}, - {"HeadsetR Mixer", "AudioR2", "Analog R2 Playback Mixer"}, - {"HeadsetR PGA", NULL, "HeadsetR Mixer"}, + {"HeadsetR Mux", "DACR1", "ARXR1_APGA"}, + {"HeadsetR Mux", "DACR2", "ARXR2_APGA"}, /* CarkitL */ - {"CarkitL Mixer", "Voice", "Analog Voice Playback Mixer"}, - {"CarkitL Mixer", "AudioL1", "Analog L1 Playback Mixer"}, - {"CarkitL Mixer", "AudioL2", "Analog L2 Playback Mixer"}, + {"CarkitL Mux", "DACL1", "ARXL1_APGA"}, + {"CarkitL Mux", "DACL2", "ARXL2_APGA"}, /* CarkitR */ - {"CarkitR Mixer", "Voice", "Analog Voice Playback Mixer"}, - {"CarkitR Mixer", "AudioR1", "Analog R1 Playback Mixer"}, - {"CarkitR Mixer", "AudioR2", "Analog R2 Playback Mixer"}, + {"CarkitR Mux", "DACR1", "ARXR1_APGA"}, + {"CarkitR Mux", "DACR2", "ARXR2_APGA"}, /* HandsfreeL */ - {"HandsfreeL Mux", "Voice", "Analog Voice Playback Mixer"}, - {"HandsfreeL Mux", "AudioL1", "Analog L1 Playback Mixer"}, - {"HandsfreeL Mux", "AudioL2", "Analog L2 Playback Mixer"}, - {"HandsfreeL Mux", "AudioR2", "Analog R2 Playback Mixer"}, - {"HandsfreeL Switch", "Switch", "HandsfreeL Mux"}, - {"HandsfreeL PGA", NULL, "HandsfreeL Switch"}, + {"HandsfreeL Mux", "DACL1", "ARXL1_APGA"}, + {"HandsfreeL Mux", "DACL2", "ARXL2_APGA"}, + {"HandsfreeL Mux", "DACR2", "ARXR2_APGA"}, /* HandsfreeR */ - {"HandsfreeR Mux", "Voice", "Analog Voice Playback Mixer"}, - {"HandsfreeR Mux", "AudioR1", "Analog R1 Playback Mixer"}, - {"HandsfreeR Mux", "AudioR2", "Analog R2 Playback Mixer"}, - {"HandsfreeR Mux", "AudioL2", "Analog L2 Playback Mixer"}, - {"HandsfreeR Switch", "Switch", "HandsfreeR Mux"}, - {"HandsfreeR PGA", NULL, "HandsfreeR Switch"}, - /* Vibra */ - {"Vibra Mux", "AudioL1", "DAC Left1"}, - {"Vibra Mux", "AudioR1", "DAC Right1"}, - {"Vibra Mux", "AudioL2", "DAC Left2"}, - {"Vibra Mux", "AudioR2", "DAC Right2"}, + {"HandsfreeR Mux", "DACR1", "ARXR1_APGA"}, + {"HandsfreeR Mux", "DACR2", "ARXR2_APGA"}, + {"HandsfreeR Mux", "DACL2", "ARXL2_APGA"}, /* outputs */ - {"OUTL", NULL, "Analog L2 Playback Mixer"}, - {"OUTR", NULL, "Analog R2 Playback Mixer"}, - {"EARPIECE", NULL, "Earpiece Mixer"}, - {"PREDRIVEL", NULL, "PredriveL Mixer"}, - {"PREDRIVER", NULL, "PredriveR Mixer"}, - {"HSOL", NULL, "HeadsetL PGA"}, - {"HSOR", NULL, "HeadsetR PGA"}, - {"CARKITL", NULL, "CarkitL Mixer"}, - {"CARKITR", NULL, "CarkitR Mixer"}, - {"HFL", NULL, "HandsfreeL PGA"}, - {"HFR", NULL, "HandsfreeR PGA"}, - {"Vibra Route", "Audio", "Vibra Mux"}, - {"VIBRA", NULL, "Vibra Route"}, + {"OUTL", NULL, "ARXL2_APGA"}, + {"OUTR", NULL, "ARXR2_APGA"}, + {"EARPIECE", NULL, "Earpiece Mux"}, + {"PREDRIVEL", NULL, "PredriveL Mux"}, + {"PREDRIVER", NULL, "PredriveR Mux"}, + {"HSOL", NULL, "HeadsetL Mux"}, + {"HSOR", NULL, "HeadsetR Mux"}, + {"CARKITL", NULL, "CarkitL Mux"}, + {"CARKITR", NULL, "CarkitR Mux"}, + {"HFL", NULL, "HandsfreeL Mux"}, + {"HFR", NULL, "HandsfreeR Mux"}, /* Capture path */ {"Analog Left Capture Route", "Main mic", "MAINMIC"}, @@ -1427,22 +1168,18 @@ static const struct snd_soc_dapm_route intercon[] = { {"Left1 Analog Loopback", "Switch", "Analog Left Capture Route"}, {"Right2 Analog Loopback", "Switch", "Analog Right Capture Route"}, {"Left2 Analog Loopback", "Switch", "Analog Left Capture Route"}, - {"Voice Analog Loopback", "Switch", "Analog Left Capture Route"}, {"Analog R1 Playback Mixer", NULL, "Right1 Analog Loopback"}, {"Analog L1 Playback Mixer", NULL, "Left1 Analog Loopback"}, {"Analog R2 Playback Mixer", NULL, "Right2 Analog Loopback"}, {"Analog L2 Playback Mixer", NULL, "Left2 Analog Loopback"}, - {"Analog Voice Playback Mixer", NULL, "Voice Analog Loopback"}, /* Digital bypass routes */ {"Right Digital Loopback", "Volume", "TX1 Capture Route"}, {"Left Digital Loopback", "Volume", "TX1 Capture Route"}, - {"Voice Digital Loopback", "Volume", "TX2 Capture Route"}, - {"Digital R2 Playback Mixer", NULL, "Right Digital Loopback"}, - {"Digital L2 Playback Mixer", NULL, "Left Digital Loopback"}, - {"Digital Voice Playback Mixer", NULL, "Voice Digital Loopback"}, + {"Analog R2 Playback Mixer", NULL, "Right Digital Loopback"}, + {"Analog L2 Playback Mixer", NULL, "Left Digital Loopback"}, }; @@ -1489,58 +1226,6 @@ static int twl4030_set_bias_level(struct snd_soc_codec *codec, return 0; } -static void twl4030_constraints(struct twl4030_priv *twl4030, - struct snd_pcm_substream *mst_substream) -{ - struct snd_pcm_substream *slv_substream; - - /* Pick the stream, which need to be constrained */ - if (mst_substream == twl4030->master_substream) - slv_substream = twl4030->slave_substream; - else if (mst_substream == twl4030->slave_substream) - slv_substream = twl4030->master_substream; - else /* This should not happen.. */ - return; - - /* Set the constraints according to the already configured stream */ - snd_pcm_hw_constraint_minmax(slv_substream->runtime, - SNDRV_PCM_HW_PARAM_RATE, - twl4030->rate, - twl4030->rate); - - snd_pcm_hw_constraint_minmax(slv_substream->runtime, - SNDRV_PCM_HW_PARAM_SAMPLE_BITS, - twl4030->sample_bits, - twl4030->sample_bits); - - snd_pcm_hw_constraint_minmax(slv_substream->runtime, - SNDRV_PCM_HW_PARAM_CHANNELS, - twl4030->channels, - twl4030->channels); -} - -/* In case of 4 channel mode, the RX1 L/R for playback and the TX2 L/R for - * capture has to be enabled/disabled. */ -static void twl4030_tdm_enable(struct snd_soc_codec *codec, int direction, - int enable) -{ - u8 reg, mask; - - reg = twl4030_read_reg_cache(codec, TWL4030_REG_OPTION); - - if (direction == SNDRV_PCM_STREAM_PLAYBACK) - mask = TWL4030_ARXL1_VRX_EN | TWL4030_ARXR1_EN; - else - mask = TWL4030_ATXL2_VTXL_EN | TWL4030_ATXR2_VTXR_EN; - - if (enable) - reg |= mask; - else - reg &= ~mask; - - twl4030_write(codec, TWL4030_REG_OPTION, reg); -} - static int twl4030_startup(struct snd_pcm_substream *substream, struct snd_soc_dai *dai) { @@ -1549,25 +1234,26 @@ static int twl4030_startup(struct snd_pcm_substream *substream, struct snd_soc_codec *codec = socdev->card->codec; struct twl4030_priv *twl4030 = codec->private_data; + /* If we already have a playback or capture going then constrain + * this substream to match it. + */ if (twl4030->master_substream) { + struct snd_pcm_runtime *master_runtime; + master_runtime = twl4030->master_substream->runtime; + + snd_pcm_hw_constraint_minmax(substream->runtime, + SNDRV_PCM_HW_PARAM_RATE, + master_runtime->rate, + master_runtime->rate); + + snd_pcm_hw_constraint_minmax(substream->runtime, + SNDRV_PCM_HW_PARAM_SAMPLE_BITS, + master_runtime->sample_bits, + master_runtime->sample_bits); + twl4030->slave_substream = substream; - /* The DAI has one configuration for playback and capture, so - * if the DAI has been already configured then constrain this - * substream to match it. */ - if (twl4030->configured) - twl4030_constraints(twl4030, twl4030->master_substream); - } else { - if (!(twl4030_read_reg_cache(codec, TWL4030_REG_CODEC_MODE) & - TWL4030_OPTION_1)) { - /* In option2 4 channel is not supported, set the - * constraint for the first stream for channels, the - * second stream will 'inherit' this cosntraint */ - snd_pcm_hw_constraint_minmax(substream->runtime, - SNDRV_PCM_HW_PARAM_CHANNELS, - 2, 2); - } + } else twl4030->master_substream = substream; - } return 0; } @@ -1584,17 +1270,6 @@ static void twl4030_shutdown(struct snd_pcm_substream *substream, twl4030->master_substream = twl4030->slave_substream; twl4030->slave_substream = NULL; - - /* If all streams are closed, or the remaining stream has not yet - * been configured than set the DAI as not configured. */ - if (!twl4030->master_substream) - twl4030->configured = 0; - else if (!twl4030->master_substream->runtime->channels) - twl4030->configured = 0; - - /* If the closing substream had 4 channel, do the necessary cleanup */ - if (substream->runtime->channels == 4) - twl4030_tdm_enable(codec, substream->stream, 0); } static int twl4030_hw_params(struct snd_pcm_substream *substream, @@ -1607,24 +1282,8 @@ static int twl4030_hw_params(struct snd_pcm_substream *substream, struct twl4030_priv *twl4030 = codec->private_data; u8 mode, old_mode, format, old_format; - /* If the substream has 4 channel, do the necessary setup */ - if (params_channels(params) == 4) { - u8 format, mode; - - format = twl4030_read_reg_cache(codec, TWL4030_REG_AUDIO_IF); - mode = twl4030_read_reg_cache(codec, TWL4030_REG_CODEC_MODE); - - /* Safety check: are we in the correct operating mode and - * the interface is in TDM mode? */ - if ((mode & TWL4030_OPTION_1) && - ((format & TWL4030_AIF_FORMAT) == TWL4030_AIF_FORMAT_TDM)) - twl4030_tdm_enable(codec, substream->stream, 1); - else - return -EINVAL; - } - - if (twl4030->configured) - /* Ignoring hw_params for already configured DAI */ + if (substream == twl4030->slave_substream) + /* Ignoring hw_params for slave substream */ return 0; /* bit rate */ @@ -1704,21 +1363,6 @@ static int twl4030_hw_params(struct snd_pcm_substream *substream, /* set CODECPDZ afterwards */ twl4030_codec_enable(codec, 1); } - - /* Store the important parameters for the DAI configuration and set - * the DAI as configured */ - twl4030->configured = 1; - twl4030->rate = params_rate(params); - twl4030->sample_bits = hw_param_interval(params, - SNDRV_PCM_HW_PARAM_SAMPLE_BITS)->min; - twl4030->channels = params_channels(params); - - /* If both playback and capture streams are open, and one of them - * is setting the hw parameters right now (since we are here), set - * constraints to the other stream to match the current one. */ - if (twl4030->slave_substream) - twl4030_constraints(twl4030, substream); - return 0; } @@ -1726,21 +1370,17 @@ static int twl4030_set_dai_sysclk(struct snd_soc_dai *codec_dai, int clk_id, unsigned int freq, int dir) { struct snd_soc_codec *codec = codec_dai->codec; - struct twl4030_priv *twl4030 = codec->private_data; u8 infreq; switch (freq) { case 19200000: infreq = TWL4030_APLL_INFREQ_19200KHZ; - twl4030->sysclk = 19200; break; case 26000000: infreq = TWL4030_APLL_INFREQ_26000KHZ; - twl4030->sysclk = 26000; break; case 38400000: infreq = TWL4030_APLL_INFREQ_38400KHZ; - twl4030->sysclk = 38400; break; default: printk(KERN_ERR "TWL4030 set sysclk: unknown rate %d\n", @@ -1784,9 +1424,6 @@ static int twl4030_set_dai_fmt(struct snd_soc_dai *codec_dai, case SND_SOC_DAIFMT_I2S: format |= TWL4030_AIF_FORMAT_CODEC; break; - case SND_SOC_DAIFMT_DSP_A: - format |= TWL4030_AIF_FORMAT_TDM; - break; default: return -EINVAL; } @@ -1806,180 +1443,6 @@ static int twl4030_set_dai_fmt(struct snd_soc_dai *codec_dai, return 0; } -/* In case of voice mode, the RX1 L(VRX) for downlink and the TX2 L/R - * (VTXL, VTXR) for uplink has to be enabled/disabled. */ -static void twl4030_voice_enable(struct snd_soc_codec *codec, int direction, - int enable) -{ - u8 reg, mask; - - reg = twl4030_read_reg_cache(codec, TWL4030_REG_OPTION); - - if (direction == SNDRV_PCM_STREAM_PLAYBACK) - mask = TWL4030_ARXL1_VRX_EN; - else - mask = TWL4030_ATXL2_VTXL_EN | TWL4030_ATXR2_VTXR_EN; - - if (enable) - reg |= mask; - else - reg &= ~mask; - - twl4030_write(codec, TWL4030_REG_OPTION, reg); -} - -static int twl4030_voice_startup(struct snd_pcm_substream *substream, - struct snd_soc_dai *dai) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_device *socdev = rtd->socdev; - struct snd_soc_codec *codec = socdev->card->codec; - u8 infreq; - u8 mode; - - /* If the system master clock is not 26MHz, the voice PCM interface is - * not avilable. - */ - infreq = twl4030_read_reg_cache(codec, TWL4030_REG_APLL_CTL) - & TWL4030_APLL_INFREQ; - - if (infreq != TWL4030_APLL_INFREQ_26000KHZ) { - printk(KERN_ERR "TWL4030 voice startup: " - "MCLK is not 26MHz, call set_sysclk() on init\n"); - return -EINVAL; - } - - /* If the codec mode is not option2, the voice PCM interface is not - * avilable. - */ - mode = twl4030_read_reg_cache(codec, TWL4030_REG_CODEC_MODE) - & TWL4030_OPT_MODE; - - if (mode != TWL4030_OPTION_2) { - printk(KERN_ERR "TWL4030 voice startup: " - "the codec mode is not option2\n"); - return -EINVAL; - } - - return 0; -} - -static void twl4030_voice_shutdown(struct snd_pcm_substream *substream, - struct snd_soc_dai *dai) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_device *socdev = rtd->socdev; - struct snd_soc_codec *codec = socdev->card->codec; - - /* Enable voice digital filters */ - twl4030_voice_enable(codec, substream->stream, 0); -} - -static int twl4030_voice_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params, struct snd_soc_dai *dai) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_device *socdev = rtd->socdev; - struct snd_soc_codec *codec = socdev->card->codec; - u8 old_mode, mode; - - /* Enable voice digital filters */ - twl4030_voice_enable(codec, substream->stream, 1); - - /* bit rate */ - old_mode = twl4030_read_reg_cache(codec, TWL4030_REG_CODEC_MODE) - & ~(TWL4030_CODECPDZ); - mode = old_mode; - - switch (params_rate(params)) { - case 8000: - mode &= ~(TWL4030_SEL_16K); - break; - case 16000: - mode |= TWL4030_SEL_16K; - break; - default: - printk(KERN_ERR "TWL4030 voice hw params: unknown rate %d\n", - params_rate(params)); - return -EINVAL; - } - - if (mode != old_mode) { - /* change rate and set CODECPDZ */ - twl4030_codec_enable(codec, 0); - twl4030_write(codec, TWL4030_REG_CODEC_MODE, mode); - twl4030_codec_enable(codec, 1); - } - - return 0; -} - -static int twl4030_voice_set_dai_sysclk(struct snd_soc_dai *codec_dai, - int clk_id, unsigned int freq, int dir) -{ - struct snd_soc_codec *codec = codec_dai->codec; - u8 infreq; - - switch (freq) { - case 26000000: - infreq = TWL4030_APLL_INFREQ_26000KHZ; - break; - default: - printk(KERN_ERR "TWL4030 voice set sysclk: unknown rate %d\n", - freq); - return -EINVAL; - } - - infreq |= TWL4030_APLL_EN; - twl4030_write(codec, TWL4030_REG_APLL_CTL, infreq); - - return 0; -} - -static int twl4030_voice_set_dai_fmt(struct snd_soc_dai *codec_dai, - unsigned int fmt) -{ - struct snd_soc_codec *codec = codec_dai->codec; - u8 old_format, format; - - /* get format */ - old_format = twl4030_read_reg_cache(codec, TWL4030_REG_VOICE_IF); - format = old_format; - - /* set master/slave audio interface */ - switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { - case SND_SOC_DAIFMT_CBS_CFM: - format &= ~(TWL4030_VIF_SLAVE_EN); - break; - case SND_SOC_DAIFMT_CBS_CFS: - format |= TWL4030_VIF_SLAVE_EN; - break; - default: - return -EINVAL; - } - - /* clock inversion */ - switch (fmt & SND_SOC_DAIFMT_INV_MASK) { - case SND_SOC_DAIFMT_IB_NF: - format &= ~(TWL4030_VIF_FORMAT); - break; - case SND_SOC_DAIFMT_NB_IF: - format |= TWL4030_VIF_FORMAT; - break; - default: - return -EINVAL; - } - - if (format != old_format) { - /* change format and set CODECPDZ */ - twl4030_codec_enable(codec, 0); - twl4030_write(codec, TWL4030_REG_VOICE_IF, format); - twl4030_codec_enable(codec, 1); - } - - return 0; -} - #define TWL4030_RATES (SNDRV_PCM_RATE_8000_48000) #define TWL4030_FORMATS (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FORMAT_S24_LE) @@ -1991,47 +1454,21 @@ static struct snd_soc_dai_ops twl4030_dai_ops = { .set_fmt = twl4030_set_dai_fmt, }; -static struct snd_soc_dai_ops twl4030_dai_voice_ops = { - .startup = twl4030_voice_startup, - .shutdown = twl4030_voice_shutdown, - .hw_params = twl4030_voice_hw_params, - .set_sysclk = twl4030_voice_set_dai_sysclk, - .set_fmt = twl4030_voice_set_dai_fmt, -}; - -struct snd_soc_dai twl4030_dai[] = { -{ +struct snd_soc_dai twl4030_dai = { .name = "twl4030", .playback = { - .stream_name = "HiFi Playback", + .stream_name = "Playback", .channels_min = 2, - .channels_max = 4, + .channels_max = 2, .rates = TWL4030_RATES | SNDRV_PCM_RATE_96000, .formats = TWL4030_FORMATS,}, .capture = { .stream_name = "Capture", .channels_min = 2, - .channels_max = 4, + .channels_max = 2, .rates = TWL4030_RATES, .formats = TWL4030_FORMATS,}, .ops = &twl4030_dai_ops, -}, -{ - .name = "twl4030 Voice", - .playback = { - .stream_name = "Voice Playback", - .channels_min = 1, - .channels_max = 1, - .rates = SNDRV_PCM_RATE_8000 | SNDRV_PCM_RATE_16000, - .formats = SNDRV_PCM_FMTBIT_S16_LE,}, - .capture = { - .stream_name = "Capture", - .channels_min = 1, - .channels_max = 2, - .rates = SNDRV_PCM_RATE_8000 | SNDRV_PCM_RATE_16000, - .formats = SNDRV_PCM_FMTBIT_S16_LE,}, - .ops = &twl4030_dai_voice_ops, -}, }; EXPORT_SYMBOL_GPL(twl4030_dai); @@ -2063,8 +1500,6 @@ static int twl4030_resume(struct platform_device *pdev) static int twl4030_init(struct snd_soc_device *socdev) { struct snd_soc_codec *codec = socdev->card->codec; - struct twl4030_setup_data *setup = socdev->codec_data; - struct twl4030_priv *twl4030 = codec->private_data; int ret = 0; printk(KERN_INFO "TWL4030 Audio Codec init \n"); @@ -2074,31 +1509,14 @@ static int twl4030_init(struct snd_soc_device *socdev) codec->read = twl4030_read_reg_cache; codec->write = twl4030_write; codec->set_bias_level = twl4030_set_bias_level; - codec->dai = twl4030_dai; - codec->num_dai = ARRAY_SIZE(twl4030_dai), + codec->dai = &twl4030_dai; + codec->num_dai = 1; codec->reg_cache_size = sizeof(twl4030_reg); codec->reg_cache = kmemdup(twl4030_reg, sizeof(twl4030_reg), GFP_KERNEL); if (codec->reg_cache == NULL) return -ENOMEM; - /* Configuration for headset ramp delay from setup data */ - if (setup) { - unsigned char hs_pop; - - if (setup->sysclk) - twl4030->sysclk = setup->sysclk; - else - twl4030->sysclk = 26000; - - hs_pop = twl4030_read_reg_cache(codec, TWL4030_REG_HS_POPN_SET); - hs_pop &= ~TWL4030_RAMP_DELAY; - hs_pop |= (setup->ramp_delay_value << 2); - twl4030_write_reg_cache(codec, TWL4030_REG_HS_POPN_SET, hs_pop); - } else { - twl4030->sysclk = 26000; - } - /* register pcms */ ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1); if (ret < 0) { @@ -2186,13 +1604,13 @@ EXPORT_SYMBOL_GPL(soc_codec_dev_twl4030); static int __init twl4030_modinit(void) { - return snd_soc_register_dais(&twl4030_dai[0], ARRAY_SIZE(twl4030_dai)); + return snd_soc_register_dai(&twl4030_dai); } module_init(twl4030_modinit); static void __exit twl4030_exit(void) { - snd_soc_unregister_dais(&twl4030_dai[0], ARRAY_SIZE(twl4030_dai)); + snd_soc_unregister_dai(&twl4030_dai); } module_exit(twl4030_exit); diff --git a/trunk/sound/soc/codecs/twl4030.h b/trunk/sound/soc/codecs/twl4030.h index fe5f395d9e4f..cb63765db1df 100644 --- a/trunk/sound/soc/codecs/twl4030.h +++ b/trunk/sound/soc/codecs/twl4030.h @@ -92,9 +92,8 @@ #define TWL4030_REG_VIBRA_PWM_SET 0x47 #define TWL4030_REG_ANAMIC_GAIN 0x48 #define TWL4030_REG_MISC_SET_2 0x49 -#define TWL4030_REG_SW_SHADOW 0x4A -#define TWL4030_CACHEREGNUM (TWL4030_REG_SW_SHADOW + 1) +#define TWL4030_CACHEREGNUM (TWL4030_REG_MISC_SET_2 + 1) /* Bitfield Definitions */ @@ -111,22 +110,9 @@ #define TWL4030_APLL_RATE_44100 0x90 #define TWL4030_APLL_RATE_48000 0xA0 #define TWL4030_APLL_RATE_96000 0xE0 -#define TWL4030_SEL_16K 0x08 +#define TWL4030_SEL_16K 0x04 #define TWL4030_CODECPDZ 0x02 #define TWL4030_OPT_MODE 0x01 -#define TWL4030_OPTION_1 (1 << 0) -#define TWL4030_OPTION_2 (0 << 0) - -/* TWL4030_OPTION (0x02) Fields */ - -#define TWL4030_ATXL1_EN (1 << 0) -#define TWL4030_ATXR1_EN (1 << 1) -#define TWL4030_ATXL2_VTXL_EN (1 << 2) -#define TWL4030_ATXR2_VTXR_EN (1 << 3) -#define TWL4030_ARXL1_VRX_EN (1 << 4) -#define TWL4030_ARXR1_EN (1 << 5) -#define TWL4030_ARXL2_EN (1 << 6) -#define TWL4030_ARXR2_EN (1 << 7) /* TWL4030_REG_MICBIAS_CTL (0x04) Fields */ @@ -185,17 +171,6 @@ #define TWL4030_CLK256FS_EN 0x02 #define TWL4030_AIF_EN 0x01 -/* VOICE_IF (0x0F) Fields */ - -#define TWL4030_VIF_SLAVE_EN 0x80 -#define TWL4030_VIF_DIN_EN 0x40 -#define TWL4030_VIF_DOUT_EN 0x20 -#define TWL4030_VIF_SWAP 0x10 -#define TWL4030_VIF_FORMAT 0x08 -#define TWL4030_VIF_TRI_EN 0x04 -#define TWL4030_VIF_SUB_EN 0x02 -#define TWL4030_VIF_EN 0x01 - /* EAR_CTL (0x21) */ #define TWL4030_EAR_GAIN 0x30 @@ -261,19 +236,7 @@ #define TWL4030_SMOOTH_ANAVOL_EN 0x02 #define TWL4030_DIGMIC_LR_SWAP_EN 0x01 -/* TWL4030_REG_SW_SHADOW (0x4A) Fields */ -#define TWL4030_HFL_EN 0x01 -#define TWL4030_HFR_EN 0x02 - -#define TWL4030_DAI_HIFI 0 -#define TWL4030_DAI_VOICE 1 - -extern struct snd_soc_dai twl4030_dai[2]; +extern struct snd_soc_dai twl4030_dai; extern struct snd_soc_codec_device soc_codec_dev_twl4030; -struct twl4030_setup_data { - unsigned int ramp_delay_value; - unsigned int sysclk; -}; - #endif /* End of __TWL4030_AUDIO_H__ */ diff --git a/trunk/sound/soc/codecs/uda134x.c b/trunk/sound/soc/codecs/uda134x.c index 269b108e1de6..ddefb8f80145 100644 --- a/trunk/sound/soc/codecs/uda134x.c +++ b/trunk/sound/soc/codecs/uda134x.c @@ -101,7 +101,7 @@ static int uda134x_write(struct snd_soc_codec *codec, unsigned int reg, pr_debug("%s reg: %02X, value:%02X\n", __func__, reg, value); if (reg >= UDA134X_REGS_NUM) { - printk(KERN_ERR "%s unkown register: reg: %u", + printk(KERN_ERR "%s unkown register: reg: %d", __func__, reg); return -EINVAL; } @@ -296,7 +296,7 @@ static int uda134x_set_dai_sysclk(struct snd_soc_dai *codec_dai, struct snd_soc_codec *codec = codec_dai->codec; struct uda134x_priv *uda134x = codec->private_data; - pr_debug("%s clk_id: %d, freq: %u, dir: %d\n", __func__, + pr_debug("%s clk_id: %d, freq: %d, dir: %d\n", __func__, clk_id, freq, dir); /* Anything between 256fs*8Khz and 512fs*48Khz should be acceptable diff --git a/trunk/sound/soc/codecs/wm8350.c b/trunk/sound/soc/codecs/wm8350.c index e7348d341b76..0275321ff8ab 100644 --- a/trunk/sound/soc/codecs/wm8350.c +++ b/trunk/sound/soc/codecs/wm8350.c @@ -1108,7 +1108,7 @@ static int wm8350_set_fll(struct snd_soc_dai *codec_dai, if (ret < 0) return ret; dev_dbg(wm8350->dev, - "FLL in %u FLL out %u N 0x%x K 0x%x div %d ratio %d", + "FLL in %d FLL out %d N 0x%x K 0x%x div %d ratio %d", freq_in, freq_out, fll_div.n, fll_div.k, fll_div.div, fll_div.ratio); diff --git a/trunk/sound/soc/codecs/wm8350.h b/trunk/sound/soc/codecs/wm8350.h index d088eb4b88bb..d11bd9288cf9 100644 --- a/trunk/sound/soc/codecs/wm8350.h +++ b/trunk/sound/soc/codecs/wm8350.h @@ -13,7 +13,6 @@ #define _WM8350_H #include -#include extern struct snd_soc_dai wm8350_dai; extern struct snd_soc_codec_device soc_codec_dev_wm8350; diff --git a/trunk/sound/soc/codecs/wm8400.c b/trunk/sound/soc/codecs/wm8400.c index 502eefac1ecd..510efa604008 100644 --- a/trunk/sound/soc/codecs/wm8400.c +++ b/trunk/sound/soc/codecs/wm8400.c @@ -954,7 +954,7 @@ static int fll_factors(struct wm8400_priv *wm8400, struct fll_factors *factors, factors->outdiv *= 2; if (factors->outdiv > 32) { dev_err(wm8400->wm8400->dev, - "Unsupported FLL output frequency %uHz\n", + "Unsupported FLL output frequency %dHz\n", Fout); return -EINVAL; } @@ -1003,7 +1003,7 @@ static int fll_factors(struct wm8400_priv *wm8400, struct fll_factors *factors, factors->k = K / 10; dev_dbg(wm8400->wm8400->dev, - "FLL: Fref=%u Fout=%u N=%x K=%x, FRATIO=%x OUTDIV=%x\n", + "FLL: Fref=%d Fout=%d N=%x K=%x, FRATIO=%x OUTDIV=%x\n", Fref, Fout, factors->n, factors->k, factors->fratio, factors->outdiv); @@ -1473,8 +1473,8 @@ static int wm8400_codec_probe(struct platform_device *dev) codec = &priv->codec; codec->private_data = priv; - codec->control_data = dev_get_drvdata(&dev->dev); - priv->wm8400 = dev_get_drvdata(&dev->dev); + codec->control_data = dev->dev.driver_data; + priv->wm8400 = dev->dev.driver_data; ret = regulator_bulk_get(priv->wm8400->dev, ARRAY_SIZE(power), &power[0]); diff --git a/trunk/sound/soc/codecs/wm8510.c b/trunk/sound/soc/codecs/wm8510.c index c8b8dba85890..6a4cea09c45d 100644 --- a/trunk/sound/soc/codecs/wm8510.c +++ b/trunk/sound/soc/codecs/wm8510.c @@ -298,7 +298,7 @@ static void pll_factors(unsigned int target, unsigned int source) if ((Ndiv < 6) || (Ndiv > 12)) printk(KERN_WARNING - "WM8510 N value %u outwith recommended range!d\n", + "WM8510 N value %d outwith recommended range!d\n", Ndiv); pll_div.n = Ndiv; diff --git a/trunk/sound/soc/codecs/wm8580.c b/trunk/sound/soc/codecs/wm8580.c index 86c4b24db817..9f6be3d31ac0 100644 --- a/trunk/sound/soc/codecs/wm8580.c +++ b/trunk/sound/soc/codecs/wm8580.c @@ -415,7 +415,7 @@ static int pll_factors(struct _pll_div *pll_div, unsigned int target, unsigned int K, Ndiv, Nmod; int i; - pr_debug("wm8580: PLL %uHz->%uHz\n", source, target); + pr_debug("wm8580: PLL %dHz->%dHz\n", source, target); /* Scale the output frequency up; the PLL should run in the * region of 90-100MHz. @@ -447,7 +447,7 @@ static int pll_factors(struct _pll_div *pll_div, unsigned int target, if ((Ndiv < 5) || (Ndiv > 13)) { printk(KERN_ERR - "WM8580 N=%u outside supported range\n", Ndiv); + "WM8580 N=%d outside supported range\n", Ndiv); return -EINVAL; } diff --git a/trunk/sound/soc/codecs/wm8731.c b/trunk/sound/soc/codecs/wm8731.c index 7a205876ef4f..e043e3f60008 100644 --- a/trunk/sound/soc/codecs/wm8731.c +++ b/trunk/sound/soc/codecs/wm8731.c @@ -666,14 +666,14 @@ static int __devinit wm8731_spi_probe(struct spi_device *spi) codec->hw_write = (hw_write_t)wm8731_spi_write; codec->dev = &spi->dev; - dev_set_drvdata(&spi->dev, wm8731); + spi->dev.driver_data = wm8731; return wm8731_register(wm8731); } static int __devexit wm8731_spi_remove(struct spi_device *spi) { - struct wm8731_priv *wm8731 = dev_get_drvdata(&spi->dev); + struct wm8731_priv *wm8731 = spi->dev.driver_data; wm8731_unregister(wm8731); diff --git a/trunk/sound/soc/codecs/wm8753.c b/trunk/sound/soc/codecs/wm8753.c index d28eeaceb857..a6e8f3f7f052 100644 --- a/trunk/sound/soc/codecs/wm8753.c +++ b/trunk/sound/soc/codecs/wm8753.c @@ -703,7 +703,7 @@ static void pll_factors(struct _pll_div *pll_div, unsigned int target, if ((Ndiv < 6) || (Ndiv > 12)) printk(KERN_WARNING - "wm8753: unsupported N = %u\n", Ndiv); + "wm8753: unsupported N = %d\n", Ndiv); pll_div->n = Ndiv; Nmod = target % source; @@ -1822,14 +1822,14 @@ static int __devinit wm8753_spi_probe(struct spi_device *spi) codec->hw_write = (hw_write_t)wm8753_spi_write; codec->dev = &spi->dev; - dev_set_drvdata(&spi->dev, wm8753); + spi->dev.driver_data = wm8753; return wm8753_register(wm8753); } static int __devexit wm8753_spi_remove(struct spi_device *spi) { - struct wm8753_priv *wm8753 = dev_get_drvdata(&spi->dev); + struct wm8753_priv *wm8753 = spi->dev.driver_data; wm8753_unregister(wm8753); return 0; } diff --git a/trunk/sound/soc/codecs/wm8900.c b/trunk/sound/soc/codecs/wm8900.c index 3c78945244b8..46c5ea1ff921 100644 --- a/trunk/sound/soc/codecs/wm8900.c +++ b/trunk/sound/soc/codecs/wm8900.c @@ -778,11 +778,11 @@ static int fll_factors(struct _fll_div *fll_div, unsigned int Fref, } if (target > 100000000) - printk(KERN_WARNING "wm8900: FLL rate %u out of range, Fref=%u" - " Fout=%u\n", target, Fref, Fout); + printk(KERN_WARNING "wm8900: FLL rate %d out of range, Fref=%d" + " Fout=%d\n", target, Fref, Fout); if (div > 32) { printk(KERN_ERR "wm8900: Invalid FLL division rate %u, " - "Fref=%u, Fout=%u, target=%u\n", + "Fref=%d, Fout=%d, target=%d\n", div, Fref, Fout, target); return -EINVAL; } diff --git a/trunk/sound/soc/codecs/wm8903.c b/trunk/sound/soc/codecs/wm8903.c index d8a9222fbf74..8cf571f1a803 100644 --- a/trunk/sound/soc/codecs/wm8903.c +++ b/trunk/sound/soc/codecs/wm8903.c @@ -217,6 +217,7 @@ struct wm8903_priv { int sysclk; /* Reference counts */ + int charge_pump_users; int class_w_users; int playback_active; int capture_active; @@ -372,15 +373,6 @@ static void wm8903_reset(struct snd_soc_codec *codec) #define WM8903_OUTPUT_INT 0x2 #define WM8903_OUTPUT_IN 0x1 -static int wm8903_cp_event(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) -{ - WARN_ON(event != SND_SOC_DAPM_POST_PMU); - mdelay(4); - - return 0; -} - /* * Event for headphone and line out amplifier power changes. Special * power up/down sequences are required in order to maximise pop/click @@ -390,20 +382,19 @@ static int wm8903_output_event(struct snd_soc_dapm_widget *w, struct snd_kcontrol *kcontrol, int event) { struct snd_soc_codec *codec = w->codec; + struct wm8903_priv *wm8903 = codec->private_data; + struct i2c_client *i2c = codec->control_data; u16 val; u16 reg; - u16 dcs_reg; - u16 dcs_bit; int shift; + u16 cp_reg = wm8903_read(codec, WM8903_CHARGE_PUMP_0); switch (w->reg) { case WM8903_POWER_MANAGEMENT_2: reg = WM8903_ANALOGUE_HP_0; - dcs_bit = 0 + w->shift; break; case WM8903_POWER_MANAGEMENT_3: reg = WM8903_ANALOGUE_LINEOUT_0; - dcs_bit = 2 + w->shift; break; default: BUG(); @@ -428,6 +419,18 @@ static int wm8903_output_event(struct snd_soc_dapm_widget *w, /* Short the output */ val &= ~(WM8903_OUTPUT_SHORT << shift); wm8903_write(codec, reg, val); + + wm8903->charge_pump_users++; + + dev_dbg(&i2c->dev, "Charge pump use count now %d\n", + wm8903->charge_pump_users); + + if (wm8903->charge_pump_users == 1) { + dev_dbg(&i2c->dev, "Enabling charge pump\n"); + wm8903_write(codec, WM8903_CHARGE_PUMP_0, + cp_reg | WM8903_CP_ENA); + mdelay(4); + } } if (event & SND_SOC_DAPM_POST_PMU) { @@ -443,11 +446,6 @@ static int wm8903_output_event(struct snd_soc_dapm_widget *w, val |= (WM8903_OUTPUT_OUT << shift); wm8903_write(codec, reg, val); - /* Enable the DC servo */ - dcs_reg = wm8903_read(codec, WM8903_DC_SERVO_0); - dcs_reg |= dcs_bit; - wm8903_write(codec, WM8903_DC_SERVO_0, dcs_reg); - /* Remove the short */ val |= (WM8903_OUTPUT_SHORT << shift); wm8903_write(codec, reg, val); @@ -460,17 +458,25 @@ static int wm8903_output_event(struct snd_soc_dapm_widget *w, val &= ~(WM8903_OUTPUT_SHORT << shift); wm8903_write(codec, reg, val); - /* Disable the DC servo */ - dcs_reg = wm8903_read(codec, WM8903_DC_SERVO_0); - dcs_reg &= ~dcs_bit; - wm8903_write(codec, WM8903_DC_SERVO_0, dcs_reg); - /* Then disable the intermediate and output stages */ val &= ~((WM8903_OUTPUT_OUT | WM8903_OUTPUT_INT | WM8903_OUTPUT_IN) << shift); wm8903_write(codec, reg, val); } + if (event & SND_SOC_DAPM_POST_PMD) { + wm8903->charge_pump_users--; + + dev_dbg(&i2c->dev, "Charge pump use count now %d\n", + wm8903->charge_pump_users); + + if (wm8903->charge_pump_users == 0) { + dev_dbg(&i2c->dev, "Disabling charge pump\n"); + wm8903_write(codec, WM8903_CHARGE_PUMP_0, + cp_reg & ~WM8903_CP_ENA); + } + } + return 0; } @@ -533,7 +539,6 @@ static int wm8903_class_w_put(struct snd_kcontrol *kcontrol, /* ALSA can only do steps of .01dB */ static const DECLARE_TLV_DB_SCALE(digital_tlv, -7200, 75, 1); -static const DECLARE_TLV_DB_SCALE(digital_sidetone_tlv, -3600, 300, 0); static const DECLARE_TLV_DB_SCALE(out_tlv, -5700, 100, 0); static const DECLARE_TLV_DB_SCALE(drc_tlv_thresh, 0, 75, 0); @@ -652,16 +657,6 @@ static const struct soc_enum rinput_inv_enum = SOC_ENUM_SINGLE(WM8903_ANALOGUE_RIGHT_INPUT_1, 4, 3, rinput_mux_text); -static const char *sidetone_text[] = { - "None", "Left", "Right" -}; - -static const struct soc_enum lsidetone_enum = - SOC_ENUM_SINGLE(WM8903_DAC_DIGITAL_0, 2, 3, sidetone_text); - -static const struct soc_enum rsidetone_enum = - SOC_ENUM_SINGLE(WM8903_DAC_DIGITAL_0, 0, 3, sidetone_text); - static const struct snd_kcontrol_new wm8903_snd_controls[] = { /* Input PGAs - No TLV since the scale depends on PGA mode */ @@ -705,9 +700,6 @@ SOC_DOUBLE_R_TLV("Digital Capture Volume", WM8903_ADC_DIGITAL_VOLUME_LEFT, SOC_ENUM("ADC Companding Mode", adc_companding), SOC_SINGLE("ADC Companding Switch", WM8903_AUDIO_INTERFACE_0, 3, 1, 0), -SOC_DOUBLE_TLV("Digital Sidetone Volume", WM8903_DAC_DIGITAL_0, 4, 8, - 12, 0, digital_sidetone_tlv), - /* DAC */ SOC_DOUBLE_R_TLV("Digital Playback Volume", WM8903_DAC_DIGITAL_VOLUME_LEFT, WM8903_DAC_DIGITAL_VOLUME_RIGHT, 1, 120, 0, digital_tlv), @@ -770,12 +762,6 @@ static const struct snd_kcontrol_new rinput_mux = static const struct snd_kcontrol_new rinput_inv_mux = SOC_DAPM_ENUM("Right Inverting Input Mux", rinput_inv_enum); -static const struct snd_kcontrol_new lsidetone_mux = - SOC_DAPM_ENUM("DACL Sidetone Mux", lsidetone_enum); - -static const struct snd_kcontrol_new rsidetone_mux = - SOC_DAPM_ENUM("DACR Sidetone Mux", rsidetone_enum); - static const struct snd_kcontrol_new left_output_mixer[] = { SOC_DAPM_SINGLE("DACL Switch", WM8903_ANALOGUE_LEFT_MIX_0, 3, 1, 0), SOC_DAPM_SINGLE("DACR Switch", WM8903_ANALOGUE_LEFT_MIX_0, 2, 1, 0), @@ -842,9 +828,6 @@ SND_SOC_DAPM_PGA("Right Input PGA", WM8903_POWER_MANAGEMENT_0, 0, 0, NULL, 0), SND_SOC_DAPM_ADC("ADCL", "Left HiFi Capture", WM8903_POWER_MANAGEMENT_6, 1, 0), SND_SOC_DAPM_ADC("ADCR", "Right HiFi Capture", WM8903_POWER_MANAGEMENT_6, 0, 0), -SND_SOC_DAPM_MUX("DACL Sidetone", SND_SOC_NOPM, 0, 0, &lsidetone_mux), -SND_SOC_DAPM_MUX("DACR Sidetone", SND_SOC_NOPM, 0, 0, &rsidetone_mux), - SND_SOC_DAPM_DAC("DACL", "Left Playback", WM8903_POWER_MANAGEMENT_6, 3, 0), SND_SOC_DAPM_DAC("DACR", "Right Playback", WM8903_POWER_MANAGEMENT_6, 2, 0), @@ -861,29 +844,26 @@ SND_SOC_DAPM_MIXER("Right Speaker Mixer", WM8903_POWER_MANAGEMENT_4, 0, 0, SND_SOC_DAPM_PGA_E("Left Headphone Output PGA", WM8903_POWER_MANAGEMENT_2, 1, 0, NULL, 0, wm8903_output_event, SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU | - SND_SOC_DAPM_PRE_PMD), + SND_SOC_DAPM_PRE_PMD | SND_SOC_DAPM_POST_PMD), SND_SOC_DAPM_PGA_E("Right Headphone Output PGA", WM8903_POWER_MANAGEMENT_2, 0, 0, NULL, 0, wm8903_output_event, SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU | - SND_SOC_DAPM_PRE_PMD), + SND_SOC_DAPM_PRE_PMD | SND_SOC_DAPM_POST_PMD), SND_SOC_DAPM_PGA_E("Left Line Output PGA", WM8903_POWER_MANAGEMENT_3, 1, 0, NULL, 0, wm8903_output_event, SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU | - SND_SOC_DAPM_PRE_PMD), + SND_SOC_DAPM_PRE_PMD | SND_SOC_DAPM_POST_PMD), SND_SOC_DAPM_PGA_E("Right Line Output PGA", WM8903_POWER_MANAGEMENT_3, 0, 0, NULL, 0, wm8903_output_event, SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU | - SND_SOC_DAPM_PRE_PMD), + SND_SOC_DAPM_PRE_PMD | SND_SOC_DAPM_POST_PMD), SND_SOC_DAPM_PGA("Left Speaker PGA", WM8903_POWER_MANAGEMENT_5, 1, 0, NULL, 0), SND_SOC_DAPM_PGA("Right Speaker PGA", WM8903_POWER_MANAGEMENT_5, 0, 0, NULL, 0), -SND_SOC_DAPM_SUPPLY("Charge Pump", WM8903_CHARGE_PUMP_0, 0, 0, - wm8903_cp_event, SND_SOC_DAPM_POST_PMU), -SND_SOC_DAPM_SUPPLY("CLK_DSP", WM8903_CLOCK_RATES_2, 1, 0, NULL, 0), }; static const struct snd_soc_dapm_route intercon[] = { @@ -929,19 +909,7 @@ static const struct snd_soc_dapm_route intercon[] = { { "Right Input PGA", NULL, "Right Input Mode Mux" }, { "ADCL", NULL, "Left Input PGA" }, - { "ADCL", NULL, "CLK_DSP" }, { "ADCR", NULL, "Right Input PGA" }, - { "ADCR", NULL, "CLK_DSP" }, - - { "DACL Sidetone", "Left", "ADCL" }, - { "DACL Sidetone", "Right", "ADCR" }, - { "DACR Sidetone", "Left", "ADCL" }, - { "DACR Sidetone", "Right", "ADCR" }, - - { "DACL", NULL, "DACL Sidetone" }, - { "DACL", NULL, "CLK_DSP" }, - { "DACR", NULL, "DACR Sidetone" }, - { "DACR", NULL, "CLK_DSP" }, { "Left Output Mixer", "Left Bypass Switch", "Left Input PGA" }, { "Left Output Mixer", "Right Bypass Switch", "Right Input PGA" }, @@ -983,11 +951,6 @@ static const struct snd_soc_dapm_route intercon[] = { { "ROP", NULL, "Right Speaker PGA" }, { "RON", NULL, "Right Speaker PGA" }, - - { "Left Headphone Output PGA", NULL, "Charge Pump" }, - { "Right Headphone Output PGA", NULL, "Charge Pump" }, - { "Left Line Output PGA", NULL, "Charge Pump" }, - { "Right Line Output PGA", NULL, "Charge Pump" }, }; static int wm8903_add_widgets(struct snd_soc_codec *codec) @@ -1022,11 +985,6 @@ static int wm8903_set_bias_level(struct snd_soc_codec *codec, wm8903_write(codec, WM8903_CLOCK_RATES_2, WM8903_CLK_SYS_ENA); - /* Change DC servo dither level in startup sequence */ - wm8903_write(codec, WM8903_WRITE_SEQUENCER_0, 0x11); - wm8903_write(codec, WM8903_WRITE_SEQUENCER_1, 0x1257); - wm8903_write(codec, WM8903_WRITE_SEQUENCER_2, 0x2); - wm8903_run_sequence(codec, 0); wm8903_sync_reg_cache(codec, codec->reg_cache); @@ -1319,8 +1277,14 @@ static int wm8903_startup(struct snd_pcm_substream *substream, if (wm8903->master_substream) { master_runtime = wm8903->master_substream->runtime; - dev_dbg(&i2c->dev, "Constraining to %d bits\n", - master_runtime->sample_bits); + dev_dbg(&i2c->dev, "Constraining to %d bits at %dHz\n", + master_runtime->sample_bits, + master_runtime->rate); + + snd_pcm_hw_constraint_minmax(substream->runtime, + SNDRV_PCM_HW_PARAM_RATE, + master_runtime->rate, + master_runtime->rate); snd_pcm_hw_constraint_minmax(substream->runtime, SNDRV_PCM_HW_PARAM_SAMPLE_BITS, @@ -1559,7 +1523,6 @@ struct snd_soc_dai wm8903_dai = { .formats = WM8903_FORMATS, }, .ops = &wm8903_dai_ops, - .symmetric_rates = 1, }; EXPORT_SYMBOL_GPL(wm8903_dai); diff --git a/trunk/sound/soc/codecs/wm8940.c b/trunk/sound/soc/codecs/wm8940.c deleted file mode 100644 index b8e17d6bc1f7..000000000000 --- a/trunk/sound/soc/codecs/wm8940.c +++ /dev/null @@ -1,955 +0,0 @@ -/* - * wm8940.c -- WM8940 ALSA Soc Audio driver - * - * Author: Jonathan Cameron - * - * Based on wm8510.c - * Copyright 2006 Wolfson Microelectronics PLC. - * Author: Liam Girdwood - * - * 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. - * - * Not currently handled: - * Notch filter control - * AUXMode (inverting vs mixer) - * No means to obtain current gain if alc enabled. - * No use made of gpio - * Fast VMID discharge for power down - * Soft Start - * DLR and ALR Swaps not enabled - * Digital Sidetone not supported - */ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "wm8940.h" - -struct wm8940_priv { - unsigned int sysclk; - u16 reg_cache[WM8940_CACHEREGNUM]; - struct snd_soc_codec codec; -}; - -static u16 wm8940_reg_defaults[] = { - 0x8940, /* Soft Reset */ - 0x0000, /* Power 1 */ - 0x0000, /* Power 2 */ - 0x0000, /* Power 3 */ - 0x0010, /* Interface Control */ - 0x0000, /* Companding Control */ - 0x0140, /* Clock Control */ - 0x0000, /* Additional Controls */ - 0x0000, /* GPIO Control */ - 0x0002, /* Auto Increment Control */ - 0x0000, /* DAC Control */ - 0x00FF, /* DAC Volume */ - 0, - 0, - 0x0100, /* ADC Control */ - 0x00FF, /* ADC Volume */ - 0x0000, /* Notch Filter 1 Control 1 */ - 0x0000, /* Notch Filter 1 Control 2 */ - 0x0000, /* Notch Filter 2 Control 1 */ - 0x0000, /* Notch Filter 2 Control 2 */ - 0x0000, /* Notch Filter 3 Control 1 */ - 0x0000, /* Notch Filter 3 Control 2 */ - 0x0000, /* Notch Filter 4 Control 1 */ - 0x0000, /* Notch Filter 4 Control 2 */ - 0x0032, /* DAC Limit Control 1 */ - 0x0000, /* DAC Limit Control 2 */ - 0, - 0, - 0, - 0, - 0, - 0, - 0x0038, /* ALC Control 1 */ - 0x000B, /* ALC Control 2 */ - 0x0032, /* ALC Control 3 */ - 0x0000, /* Noise Gate */ - 0x0041, /* PLLN */ - 0x000C, /* PLLK1 */ - 0x0093, /* PLLK2 */ - 0x00E9, /* PLLK3 */ - 0, - 0, - 0x0030, /* ALC Control 4 */ - 0, - 0x0002, /* Input Control */ - 0x0050, /* PGA Gain */ - 0, - 0x0002, /* ADC Boost Control */ - 0, - 0x0002, /* Output Control */ - 0x0000, /* Speaker Mixer Control */ - 0, - 0, - 0, - 0x0079, /* Speaker Volume */ - 0, - 0x0000, /* Mono Mixer Control */ -}; - -static inline unsigned int wm8940_read_reg_cache(struct snd_soc_codec *codec, - unsigned int reg) -{ - u16 *cache = codec->reg_cache; - - if (reg >= ARRAY_SIZE(wm8940_reg_defaults)) - return -1; - - return cache[reg]; -} - -static inline int wm8940_write_reg_cache(struct snd_soc_codec *codec, - u16 reg, unsigned int value) -{ - u16 *cache = codec->reg_cache; - - if (reg >= ARRAY_SIZE(wm8940_reg_defaults)) - return -1; - - cache[reg] = value; - - return 0; -} - -static int wm8940_write(struct snd_soc_codec *codec, unsigned int reg, - unsigned int value) -{ - int ret; - u8 data[3] = { reg, - (value & 0xff00) >> 8, - (value & 0x00ff) - }; - - wm8940_write_reg_cache(codec, reg, value); - - ret = codec->hw_write(codec->control_data, data, 3); - - if (ret < 0) - return ret; - else if (ret != 3) - return -EIO; - return 0; -} - -static const char *wm8940_companding[] = { "Off", "NC", "u-law", "A-law" }; -static const struct soc_enum wm8940_adc_companding_enum -= SOC_ENUM_SINGLE(WM8940_COMPANDINGCTL, 1, 4, wm8940_companding); -static const struct soc_enum wm8940_dac_companding_enum -= SOC_ENUM_SINGLE(WM8940_COMPANDINGCTL, 3, 4, wm8940_companding); - -static const char *wm8940_alc_mode_text[] = {"ALC", "Limiter"}; -static const struct soc_enum wm8940_alc_mode_enum -= SOC_ENUM_SINGLE(WM8940_ALC3, 8, 2, wm8940_alc_mode_text); - -static const char *wm8940_mic_bias_level_text[] = {"0.9", "0.65"}; -static const struct soc_enum wm8940_mic_bias_level_enum -= SOC_ENUM_SINGLE(WM8940_INPUTCTL, 8, 2, wm8940_mic_bias_level_text); - -static const char *wm8940_filter_mode_text[] = {"Audio", "Application"}; -static const struct soc_enum wm8940_filter_mode_enum -= SOC_ENUM_SINGLE(WM8940_ADC, 7, 2, wm8940_filter_mode_text); - -static DECLARE_TLV_DB_SCALE(wm8940_spk_vol_tlv, -5700, 100, 1); -static DECLARE_TLV_DB_SCALE(wm8940_att_tlv, -1000, 1000, 0); -static DECLARE_TLV_DB_SCALE(wm8940_pga_vol_tlv, -1200, 75, 0); -static DECLARE_TLV_DB_SCALE(wm8940_alc_min_tlv, -1200, 600, 0); -static DECLARE_TLV_DB_SCALE(wm8940_alc_max_tlv, 675, 600, 0); -static DECLARE_TLV_DB_SCALE(wm8940_alc_tar_tlv, -2250, 50, 0); -static DECLARE_TLV_DB_SCALE(wm8940_lim_boost_tlv, 0, 100, 0); -static DECLARE_TLV_DB_SCALE(wm8940_lim_thresh_tlv, -600, 100, 0); -static DECLARE_TLV_DB_SCALE(wm8940_adc_tlv, -12750, 50, 1); -static DECLARE_TLV_DB_SCALE(wm8940_capture_boost_vol_tlv, 0, 2000, 0); - -static const struct snd_kcontrol_new wm8940_snd_controls[] = { - SOC_SINGLE("Digital Loopback Switch", WM8940_COMPANDINGCTL, - 6, 1, 0), - SOC_ENUM("DAC Companding", wm8940_dac_companding_enum), - SOC_ENUM("ADC Companding", wm8940_adc_companding_enum), - - SOC_ENUM("ALC Mode", wm8940_alc_mode_enum), - SOC_SINGLE("ALC Switch", WM8940_ALC1, 8, 1, 0), - SOC_SINGLE_TLV("ALC Capture Max Gain", WM8940_ALC1, - 3, 7, 1, wm8940_alc_max_tlv), - SOC_SINGLE_TLV("ALC Capture Min Gain", WM8940_ALC1, - 0, 7, 0, wm8940_alc_min_tlv), - SOC_SINGLE_TLV("ALC Capture Target", WM8940_ALC2, - 0, 14, 0, wm8940_alc_tar_tlv), - SOC_SINGLE("ALC Capture Hold", WM8940_ALC2, 4, 10, 0), - SOC_SINGLE("ALC Capture Decay", WM8940_ALC3, 4, 10, 0), - SOC_SINGLE("ALC Capture Attach", WM8940_ALC3, 0, 10, 0), - SOC_SINGLE("ALC ZC Switch", WM8940_ALC4, 1, 1, 0), - SOC_SINGLE("ALC Capture Noise Gate Switch", WM8940_NOISEGATE, - 3, 1, 0), - SOC_SINGLE("ALC Capture Noise Gate Threshold", WM8940_NOISEGATE, - 0, 7, 0), - - SOC_SINGLE("DAC Playback Limiter Switch", WM8940_DACLIM1, 8, 1, 0), - SOC_SINGLE("DAC Playback Limiter Attack", WM8940_DACLIM1, 0, 9, 0), - SOC_SINGLE("DAC Playback Limiter Decay", WM8940_DACLIM1, 4, 11, 0), - SOC_SINGLE_TLV("DAC Playback Limiter Threshold", WM8940_DACLIM2, - 4, 9, 1, wm8940_lim_thresh_tlv), - SOC_SINGLE_TLV("DAC Playback Limiter Boost", WM8940_DACLIM2, - 0, 12, 0, wm8940_lim_boost_tlv), - - SOC_SINGLE("Capture PGA ZC Switch", WM8940_PGAGAIN, 7, 1, 0), - SOC_SINGLE_TLV("Capture PGA Volume", WM8940_PGAGAIN, - 0, 63, 0, wm8940_pga_vol_tlv), - SOC_SINGLE_TLV("Digital Playback Volume", WM8940_DACVOL, - 0, 255, 0, wm8940_adc_tlv), - SOC_SINGLE_TLV("Digital Capture Volume", WM8940_ADCVOL, - 0, 255, 0, wm8940_adc_tlv), - SOC_ENUM("Mic Bias Level", wm8940_mic_bias_level_enum), - SOC_SINGLE_TLV("Capture Boost Volue", WM8940_ADCBOOST, - 8, 1, 0, wm8940_capture_boost_vol_tlv), - SOC_SINGLE_TLV("Speaker Playback Volume", WM8940_SPKVOL, - 0, 63, 0, wm8940_spk_vol_tlv), - SOC_SINGLE("Speaker Playback Switch", WM8940_SPKVOL, 6, 1, 1), - - SOC_SINGLE_TLV("Speaker Mixer Line Bypass Volume", WM8940_SPKVOL, - 8, 1, 1, wm8940_att_tlv), - SOC_SINGLE("Speaker Playback ZC Switch", WM8940_SPKVOL, 7, 1, 0), - - SOC_SINGLE("Mono Out Switch", WM8940_MONOMIX, 6, 1, 1), - SOC_SINGLE_TLV("Mono Mixer Line Bypass Volume", WM8940_MONOMIX, - 7, 1, 1, wm8940_att_tlv), - - SOC_SINGLE("High Pass Filter Switch", WM8940_ADC, 8, 1, 0), - SOC_ENUM("High Pass Filter Mode", wm8940_filter_mode_enum), - SOC_SINGLE("High Pass Filter Cut Off", WM8940_ADC, 4, 7, 0), - SOC_SINGLE("ADC Inversion Switch", WM8940_ADC, 0, 1, 0), - SOC_SINGLE("DAC Inversion Switch", WM8940_DAC, 0, 1, 0), - SOC_SINGLE("DAC Auto Mute Switch", WM8940_DAC, 2, 1, 0), - SOC_SINGLE("ZC Timeout Clock Switch", WM8940_ADDCNTRL, 0, 1, 0), -}; - -static const struct snd_kcontrol_new wm8940_speaker_mixer_controls[] = { - SOC_DAPM_SINGLE("Line Bypass Switch", WM8940_SPKMIX, 1, 1, 0), - SOC_DAPM_SINGLE("Aux Playback Switch", WM8940_SPKMIX, 5, 1, 0), - SOC_DAPM_SINGLE("PCM Playback Switch", WM8940_SPKMIX, 0, 1, 0), -}; - -static const struct snd_kcontrol_new wm8940_mono_mixer_controls[] = { - SOC_DAPM_SINGLE("Line Bypass Switch", WM8940_MONOMIX, 1, 1, 0), - SOC_DAPM_SINGLE("Aux Playback Switch", WM8940_MONOMIX, 2, 1, 0), - SOC_DAPM_SINGLE("PCM Playback Switch", WM8940_MONOMIX, 0, 1, 0), -}; - -static DECLARE_TLV_DB_SCALE(wm8940_boost_vol_tlv, -1500, 300, 1); -static const struct snd_kcontrol_new wm8940_input_boost_controls[] = { - SOC_DAPM_SINGLE("Mic PGA Switch", WM8940_PGAGAIN, 6, 1, 1), - SOC_DAPM_SINGLE_TLV("Aux Volume", WM8940_ADCBOOST, - 0, 7, 0, wm8940_boost_vol_tlv), - SOC_DAPM_SINGLE_TLV("Mic Volume", WM8940_ADCBOOST, - 4, 7, 0, wm8940_boost_vol_tlv), -}; - -static const struct snd_kcontrol_new wm8940_micpga_controls[] = { - SOC_DAPM_SINGLE("AUX Switch", WM8940_INPUTCTL, 2, 1, 0), - SOC_DAPM_SINGLE("MICP Switch", WM8940_INPUTCTL, 0, 1, 0), - SOC_DAPM_SINGLE("MICN Switch", WM8940_INPUTCTL, 1, 1, 0), -}; - -static const struct snd_soc_dapm_widget wm8940_dapm_widgets[] = { - SND_SOC_DAPM_MIXER("Speaker Mixer", WM8940_POWER3, 2, 0, - &wm8940_speaker_mixer_controls[0], - ARRAY_SIZE(wm8940_speaker_mixer_controls)), - SND_SOC_DAPM_MIXER("Mono Mixer", WM8940_POWER3, 3, 0, - &wm8940_mono_mixer_controls[0], - ARRAY_SIZE(wm8940_mono_mixer_controls)), - SND_SOC_DAPM_DAC("DAC", "HiFi Playback", WM8940_POWER3, 0, 0), - - SND_SOC_DAPM_PGA("SpkN Out", WM8940_POWER3, 5, 0, NULL, 0), - SND_SOC_DAPM_PGA("SpkP Out", WM8940_POWER3, 6, 0, NULL, 0), - SND_SOC_DAPM_PGA("Mono Out", WM8940_POWER3, 7, 0, NULL, 0), - SND_SOC_DAPM_OUTPUT("MONOOUT"), - SND_SOC_DAPM_OUTPUT("SPKOUTP"), - SND_SOC_DAPM_OUTPUT("SPKOUTN"), - - SND_SOC_DAPM_PGA("Aux Input", WM8940_POWER1, 6, 0, NULL, 0), - SND_SOC_DAPM_ADC("ADC", "HiFi Capture", WM8940_POWER2, 0, 0), - SND_SOC_DAPM_MIXER("Mic PGA", WM8940_POWER2, 2, 0, - &wm8940_micpga_controls[0], - ARRAY_SIZE(wm8940_micpga_controls)), - SND_SOC_DAPM_MIXER("Boost Mixer", WM8940_POWER2, 4, 0, - &wm8940_input_boost_controls[0], - ARRAY_SIZE(wm8940_input_boost_controls)), - SND_SOC_DAPM_MICBIAS("Mic Bias", WM8940_POWER1, 4, 0), - - SND_SOC_DAPM_INPUT("MICN"), - SND_SOC_DAPM_INPUT("MICP"), - SND_SOC_DAPM_INPUT("AUX"), -}; - -static const struct snd_soc_dapm_route audio_map[] = { - /* Mono output mixer */ - {"Mono Mixer", "PCM Playback Switch", "DAC"}, - {"Mono Mixer", "Aux Playback Switch", "Aux Input"}, - {"Mono Mixer", "Line Bypass Switch", "Boost Mixer"}, - - /* Speaker output mixer */ - {"Speaker Mixer", "PCM Playback Switch", "DAC"}, - {"Speaker Mixer", "Aux Playback Switch", "Aux Input"}, - {"Speaker Mixer", "Line Bypass Switch", "Boost Mixer"}, - - /* Outputs */ - {"Mono Out", NULL, "Mono Mixer"}, - {"MONOOUT", NULL, "Mono Out"}, - {"SpkN Out", NULL, "Speaker Mixer"}, - {"SpkP Out", NULL, "Speaker Mixer"}, - {"SPKOUTN", NULL, "SpkN Out"}, - {"SPKOUTP", NULL, "SpkP Out"}, - - /* Microphone PGA */ - {"Mic PGA", "MICN Switch", "MICN"}, - {"Mic PGA", "MICP Switch", "MICP"}, - {"Mic PGA", "AUX Switch", "AUX"}, - - /* Boost Mixer */ - {"Boost Mixer", "Mic PGA Switch", "Mic PGA"}, - {"Boost Mixer", "Mic Volume", "MICP"}, - {"Boost Mixer", "Aux Volume", "Aux Input"}, - - {"ADC", NULL, "Boost Mixer"}, -}; - -static int wm8940_add_widgets(struct snd_soc_codec *codec) -{ - int ret; - - ret = snd_soc_dapm_new_controls(codec, wm8940_dapm_widgets, - ARRAY_SIZE(wm8940_dapm_widgets)); - if (ret) - goto error_ret; - ret = snd_soc_dapm_add_routes(codec, audio_map, ARRAY_SIZE(audio_map)); - if (ret) - goto error_ret; - ret = snd_soc_dapm_new_widgets(codec); - -error_ret: - return ret; -} - -#define wm8940_reset(c) wm8940_write(c, WM8940_SOFTRESET, 0); - -static int wm8940_set_dai_fmt(struct snd_soc_dai *codec_dai, - unsigned int fmt) -{ - struct snd_soc_codec *codec = codec_dai->codec; - u16 iface = wm8940_read_reg_cache(codec, WM8940_IFACE) & 0xFE67; - u16 clk = wm8940_read_reg_cache(codec, WM8940_CLOCK) & 0x1fe; - - switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { - case SND_SOC_DAIFMT_CBM_CFM: - clk |= 1; - break; - case SND_SOC_DAIFMT_CBS_CFS: - break; - default: - return -EINVAL; - } - wm8940_write(codec, WM8940_CLOCK, clk); - - switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { - case SND_SOC_DAIFMT_I2S: - iface |= (2 << 3); - break; - case SND_SOC_DAIFMT_LEFT_J: - iface |= (1 << 3); - break; - case SND_SOC_DAIFMT_RIGHT_J: - break; - case SND_SOC_DAIFMT_DSP_A: - iface |= (3 << 3); - break; - case SND_SOC_DAIFMT_DSP_B: - iface |= (3 << 3) | (1 << 7); - break; - } - - switch (fmt & SND_SOC_DAIFMT_INV_MASK) { - case SND_SOC_DAIFMT_NB_NF: - break; - case SND_SOC_DAIFMT_NB_IF: - iface |= (1 << 7); - break; - case SND_SOC_DAIFMT_IB_NF: - iface |= (1 << 8); - break; - case SND_SOC_DAIFMT_IB_IF: - iface |= (1 << 8) | (1 << 7); - break; - } - - wm8940_write(codec, WM8940_IFACE, iface); - - return 0; -} - -static int wm8940_i2s_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params, - struct snd_soc_dai *dai) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_device *socdev = rtd->socdev; - struct snd_soc_codec *codec = socdev->card->codec; - u16 iface = wm8940_read_reg_cache(codec, WM8940_IFACE) & 0xFD9F; - u16 addcntrl = wm8940_read_reg_cache(codec, WM8940_ADDCNTRL) & 0xFFF1; - u16 companding = wm8940_read_reg_cache(codec, - WM8940_COMPANDINGCTL) & 0xFFDF; - int ret; - - /* LoutR control */ - if (substream->stream == SNDRV_PCM_STREAM_CAPTURE - && params_channels(params) == 2) - iface |= (1 << 9); - - switch (params_rate(params)) { - case SNDRV_PCM_RATE_8000: - addcntrl |= (0x5 << 1); - break; - case SNDRV_PCM_RATE_11025: - addcntrl |= (0x4 << 1); - break; - case SNDRV_PCM_RATE_16000: - addcntrl |= (0x3 << 1); - break; - case SNDRV_PCM_RATE_22050: - addcntrl |= (0x2 << 1); - break; - case SNDRV_PCM_RATE_32000: - addcntrl |= (0x1 << 1); - break; - case SNDRV_PCM_RATE_44100: - case SNDRV_PCM_RATE_48000: - break; - } - ret = wm8940_write(codec, WM8940_ADDCNTRL, addcntrl); - if (ret) - goto error_ret; - - switch (params_format(params)) { - case SNDRV_PCM_FORMAT_S8: - companding = companding | (1 << 5); - break; - case SNDRV_PCM_FORMAT_S16_LE: - break; - case SNDRV_PCM_FORMAT_S20_3LE: - iface |= (1 << 5); - break; - case SNDRV_PCM_FORMAT_S24_LE: - iface |= (2 << 5); - break; - case SNDRV_PCM_FORMAT_S32_LE: - iface |= (3 << 5); - break; - } - ret = wm8940_write(codec, WM8940_COMPANDINGCTL, companding); - if (ret) - goto error_ret; - ret = wm8940_write(codec, WM8940_IFACE, iface); - -error_ret: - return ret; -} - -static int wm8940_mute(struct snd_soc_dai *dai, int mute) -{ - struct snd_soc_codec *codec = dai->codec; - u16 mute_reg = wm8940_read_reg_cache(codec, WM8940_DAC) & 0xffbf; - - if (mute) - mute_reg |= 0x40; - - return wm8940_write(codec, WM8940_DAC, mute_reg); -} - -static int wm8940_set_bias_level(struct snd_soc_codec *codec, - enum snd_soc_bias_level level) -{ - u16 val; - u16 pwr_reg = wm8940_read_reg_cache(codec, WM8940_POWER1) & 0x1F0; - int ret = 0; - - switch (level) { - case SND_SOC_BIAS_ON: - /* ensure bufioen and biasen */ - pwr_reg |= (1 << 2) | (1 << 3); - /* Enable thermal shutdown */ - val = wm8940_read_reg_cache(codec, WM8940_OUTPUTCTL); - ret = wm8940_write(codec, WM8940_OUTPUTCTL, val | 0x2); - if (ret) - break; - /* set vmid to 75k */ - ret = wm8940_write(codec, WM8940_POWER1, pwr_reg | 0x1); - break; - case SND_SOC_BIAS_PREPARE: - /* ensure bufioen and biasen */ - pwr_reg |= (1 << 2) | (1 << 3); - ret = wm8940_write(codec, WM8940_POWER1, pwr_reg | 0x1); - break; - case SND_SOC_BIAS_STANDBY: - /* ensure bufioen and biasen */ - pwr_reg |= (1 << 2) | (1 << 3); - /* set vmid to 300k for standby */ - ret = wm8940_write(codec, WM8940_POWER1, pwr_reg | 0x2); - break; - case SND_SOC_BIAS_OFF: - ret = wm8940_write(codec, WM8940_POWER1, pwr_reg); - break; - } - - return ret; -} - -struct pll_ { - unsigned int pre_scale:2; - unsigned int n:4; - unsigned int k; -}; - -static struct pll_ pll_div; - -/* The size in bits of the pll divide multiplied by 10 - * to allow rounding later */ -#define FIXED_PLL_SIZE ((1 << 24) * 10) -static void pll_factors(unsigned int target, unsigned int source) -{ - unsigned long long Kpart; - unsigned int K, Ndiv, Nmod; - /* The left shift ist to avoid accuracy loss when right shifting */ - Ndiv = target / source; - - if (Ndiv > 12) { - source <<= 1; - /* Multiply by 2 */ - pll_div.pre_scale = 0; - Ndiv = target / source; - } else if (Ndiv < 3) { - source >>= 2; - /* Divide by 4 */ - pll_div.pre_scale = 3; - Ndiv = target / source; - } else if (Ndiv < 6) { - source >>= 1; - /* divide by 2 */ - pll_div.pre_scale = 2; - Ndiv = target / source; - } else - pll_div.pre_scale = 1; - - if ((Ndiv < 6) || (Ndiv > 12)) - printk(KERN_WARNING - "WM8940 N value %d outwith recommended range!d\n", - Ndiv); - - pll_div.n = Ndiv; - Nmod = target % source; - Kpart = FIXED_PLL_SIZE * (long long)Nmod; - - do_div(Kpart, source); - - K = Kpart & 0xFFFFFFFF; - - /* Check if we need to round */ - if ((K % 10) >= 5) - K += 5; - - /* Move down to proper range now rounding is done */ - K /= 10; - - pll_div.k = K; -} - -/* Untested at the moment */ -static int wm8940_set_dai_pll(struct snd_soc_dai *codec_dai, - int pll_id, unsigned int freq_in, unsigned int freq_out) -{ - struct snd_soc_codec *codec = codec_dai->codec; - u16 reg; - - /* Turn off PLL */ - reg = wm8940_read_reg_cache(codec, WM8940_POWER1); - wm8940_write(codec, WM8940_POWER1, reg & 0x1df); - - if (freq_in == 0 || freq_out == 0) { - /* Clock CODEC directly from MCLK */ - reg = wm8940_read_reg_cache(codec, WM8940_CLOCK); - wm8940_write(codec, WM8940_CLOCK, reg & 0x0ff); - /* Pll power down */ - wm8940_write(codec, WM8940_PLLN, (1 << 7)); - return 0; - } - - /* Pll is followed by a frequency divide by 4 */ - pll_factors(freq_out*4, freq_in); - if (pll_div.k) - wm8940_write(codec, WM8940_PLLN, - (pll_div.pre_scale << 4) | pll_div.n | (1 << 6)); - else /* No factional component */ - wm8940_write(codec, WM8940_PLLN, - (pll_div.pre_scale << 4) | pll_div.n); - wm8940_write(codec, WM8940_PLLK1, pll_div.k >> 18); - wm8940_write(codec, WM8940_PLLK2, (pll_div.k >> 9) & 0x1ff); - wm8940_write(codec, WM8940_PLLK3, pll_div.k & 0x1ff); - /* Enable the PLL */ - reg = wm8940_read_reg_cache(codec, WM8940_POWER1); - wm8940_write(codec, WM8940_POWER1, reg | 0x020); - - /* Run CODEC from PLL instead of MCLK */ - reg = wm8940_read_reg_cache(codec, WM8940_CLOCK); - wm8940_write(codec, WM8940_CLOCK, reg | 0x100); - - return 0; -} - -static int wm8940_set_dai_sysclk(struct snd_soc_dai *codec_dai, - int clk_id, unsigned int freq, int dir) -{ - struct snd_soc_codec *codec = codec_dai->codec; - struct wm8940_priv *wm8940 = codec->private_data; - - switch (freq) { - case 11289600: - case 12000000: - case 12288000: - case 16934400: - case 18432000: - wm8940->sysclk = freq; - return 0; - } - return -EINVAL; -} - -static int wm8940_set_dai_clkdiv(struct snd_soc_dai *codec_dai, - int div_id, int div) -{ - struct snd_soc_codec *codec = codec_dai->codec; - u16 reg; - int ret = 0; - - switch (div_id) { - case WM8940_BCLKDIV: - reg = wm8940_read_reg_cache(codec, WM8940_CLOCK) & 0xFFEF3; - ret = wm8940_write(codec, WM8940_CLOCK, reg | (div << 2)); - break; - case WM8940_MCLKDIV: - reg = wm8940_read_reg_cache(codec, WM8940_CLOCK) & 0xFF1F; - ret = wm8940_write(codec, WM8940_CLOCK, reg | (div << 5)); - break; - case WM8940_OPCLKDIV: - reg = wm8940_read_reg_cache(codec, WM8940_ADDCNTRL) & 0xFFCF; - ret = wm8940_write(codec, WM8940_ADDCNTRL, reg | (div << 4)); - break; - } - return ret; -} - -#define WM8940_RATES SNDRV_PCM_RATE_8000_48000 - -#define WM8940_FORMATS (SNDRV_PCM_FMTBIT_S8 | \ - SNDRV_PCM_FMTBIT_S16_LE | \ - SNDRV_PCM_FMTBIT_S20_3LE | \ - SNDRV_PCM_FMTBIT_S24_LE | \ - SNDRV_PCM_FMTBIT_S32_LE) - -static struct snd_soc_dai_ops wm8940_dai_ops = { - .hw_params = wm8940_i2s_hw_params, - .set_sysclk = wm8940_set_dai_sysclk, - .digital_mute = wm8940_mute, - .set_fmt = wm8940_set_dai_fmt, - .set_clkdiv = wm8940_set_dai_clkdiv, - .set_pll = wm8940_set_dai_pll, -}; - -struct snd_soc_dai wm8940_dai = { - .name = "WM8940", - .playback = { - .stream_name = "Playback", - .channels_min = 1, - .channels_max = 2, - .rates = WM8940_RATES, - .formats = WM8940_FORMATS, - }, - .capture = { - .stream_name = "Capture", - .channels_min = 1, - .channels_max = 2, - .rates = WM8940_RATES, - .formats = WM8940_FORMATS, - }, - .ops = &wm8940_dai_ops, - .symmetric_rates = 1, -}; -EXPORT_SYMBOL_GPL(wm8940_dai); - -static int wm8940_suspend(struct platform_device *pdev, pm_message_t state) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - - return wm8940_set_bias_level(codec, SND_SOC_BIAS_OFF); -} - -static int wm8940_resume(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - int i; - int ret; - u8 data[3]; - u16 *cache = codec->reg_cache; - - /* Sync reg_cache with the hardware - * Could use auto incremented writes to speed this up - */ - for (i = 0; i < ARRAY_SIZE(wm8940_reg_defaults); i++) { - data[0] = i; - data[1] = (cache[i] & 0xFF00) >> 8; - data[2] = cache[i] & 0x00FF; - ret = codec->hw_write(codec->control_data, data, 3); - if (ret < 0) - goto error_ret; - else if (ret != 3) { - ret = -EIO; - goto error_ret; - } - } - ret = wm8940_set_bias_level(codec, SND_SOC_BIAS_STANDBY); - if (ret) - goto error_ret; - ret = wm8940_set_bias_level(codec, codec->suspend_bias_level); - -error_ret: - return ret; -} - -static struct snd_soc_codec *wm8940_codec; - -static int wm8940_probe(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec; - - int ret = 0; - - if (wm8940_codec == NULL) { - dev_err(&pdev->dev, "Codec device not registered\n"); - return -ENODEV; - } - - socdev->card->codec = wm8940_codec; - codec = wm8940_codec; - - mutex_init(&codec->mutex); - /* register pcms */ - ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1); - if (ret < 0) { - dev_err(codec->dev, "failed to create pcms: %d\n", ret); - goto pcm_err; - } - - ret = snd_soc_add_controls(codec, wm8940_snd_controls, - ARRAY_SIZE(wm8940_snd_controls)); - if (ret) - goto error_free_pcms; - ret = wm8940_add_widgets(codec); - if (ret) - goto error_free_pcms; - - ret = snd_soc_init_card(socdev); - if (ret < 0) { - dev_err(codec->dev, "failed to register card: %d\n", ret); - goto error_free_pcms; - } - - return ret; - -error_free_pcms: - snd_soc_free_pcms(socdev); - snd_soc_dapm_free(socdev); -pcm_err: - return ret; -} - -static int wm8940_remove(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - - snd_soc_free_pcms(socdev); - snd_soc_dapm_free(socdev); - - return 0; -} - -struct snd_soc_codec_device soc_codec_dev_wm8940 = { - .probe = wm8940_probe, - .remove = wm8940_remove, - .suspend = wm8940_suspend, - .resume = wm8940_resume, -}; -EXPORT_SYMBOL_GPL(soc_codec_dev_wm8940); - -static int wm8940_register(struct wm8940_priv *wm8940) -{ - struct wm8940_setup_data *pdata = wm8940->codec.dev->platform_data; - struct snd_soc_codec *codec = &wm8940->codec; - int ret; - u16 reg; - if (wm8940_codec) { - dev_err(codec->dev, "Another WM8940 is registered\n"); - return -EINVAL; - } - - INIT_LIST_HEAD(&codec->dapm_widgets); - INIT_LIST_HEAD(&codec->dapm_paths); - - codec->private_data = wm8940; - codec->name = "WM8940"; - codec->owner = THIS_MODULE; - codec->read = wm8940_read_reg_cache; - codec->write = wm8940_write; - codec->bias_level = SND_SOC_BIAS_OFF; - codec->set_bias_level = wm8940_set_bias_level; - codec->dai = &wm8940_dai; - codec->num_dai = 1; - codec->reg_cache_size = ARRAY_SIZE(wm8940_reg_defaults); - codec->reg_cache = &wm8940->reg_cache; - - memcpy(codec->reg_cache, wm8940_reg_defaults, - sizeof(wm8940_reg_defaults)); - - ret = wm8940_reset(codec); - if (ret < 0) { - dev_err(codec->dev, "Failed to issue reset\n"); - return ret; - } - - wm8940_dai.dev = codec->dev; - - wm8940_set_bias_level(codec, SND_SOC_BIAS_STANDBY); - - ret = wm8940_write(codec, WM8940_POWER1, 0x180); - if (ret < 0) - return ret; - - if (!pdata) - dev_warn(codec->dev, "No platform data supplied\n"); - else { - reg = wm8940_read_reg_cache(codec, WM8940_OUTPUTCTL); - ret = wm8940_write(codec, WM8940_OUTPUTCTL, reg | pdata->vroi); - if (ret < 0) - return ret; - } - - - wm8940_codec = codec; - - ret = snd_soc_register_codec(codec); - if (ret) { - dev_err(codec->dev, "Failed to register codec: %d\n", ret); - return ret; - } - - ret = snd_soc_register_dai(&wm8940_dai); - if (ret) { - dev_err(codec->dev, "Failed to register DAI: %d\n", ret); - snd_soc_unregister_codec(codec); - return ret; - } - - return 0; -} - -static void wm8940_unregister(struct wm8940_priv *wm8940) -{ - wm8940_set_bias_level(&wm8940->codec, SND_SOC_BIAS_OFF); - snd_soc_unregister_dai(&wm8940_dai); - snd_soc_unregister_codec(&wm8940->codec); - kfree(wm8940); - wm8940_codec = NULL; -} - -static int wm8940_i2c_probe(struct i2c_client *i2c, - const struct i2c_device_id *id) -{ - struct wm8940_priv *wm8940; - struct snd_soc_codec *codec; - - wm8940 = kzalloc(sizeof *wm8940, GFP_KERNEL); - if (wm8940 == NULL) - return -ENOMEM; - - codec = &wm8940->codec; - codec->hw_write = (hw_write_t)i2c_master_send; - i2c_set_clientdata(i2c, wm8940); - codec->control_data = i2c; - codec->dev = &i2c->dev; - - return wm8940_register(wm8940); -} - -static int __devexit wm8940_i2c_remove(struct i2c_client *client) -{ - struct wm8940_priv *wm8940 = i2c_get_clientdata(client); - - wm8940_unregister(wm8940); - - return 0; -} - -static const struct i2c_device_id wm8940_i2c_id[] = { - { "wm8940", 0 }, - { } -}; -MODULE_DEVICE_TABLE(i2c, wm8940_i2c_id); - -static struct i2c_driver wm8940_i2c_driver = { - .driver = { - .name = "WM8940 I2C Codec", - .owner = THIS_MODULE, - }, - .probe = wm8940_i2c_probe, - .remove = __devexit_p(wm8940_i2c_remove), - .id_table = wm8940_i2c_id, -}; - -static int __init wm8940_modinit(void) -{ - int ret; - - ret = i2c_add_driver(&wm8940_i2c_driver); - if (ret) - printk(KERN_ERR "Failed to register WM8940 I2C driver: %d\n", - ret); - return ret; -} -module_init(wm8940_modinit); - -static void __exit wm8940_exit(void) -{ - i2c_del_driver(&wm8940_i2c_driver); -} -module_exit(wm8940_exit); - -MODULE_DESCRIPTION("ASoC WM8940 driver"); -MODULE_AUTHOR("Jonathan Cameron"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/codecs/wm8940.h b/trunk/sound/soc/codecs/wm8940.h deleted file mode 100644 index 8410eed3ef84..000000000000 --- a/trunk/sound/soc/codecs/wm8940.h +++ /dev/null @@ -1,104 +0,0 @@ -/* - * wm8940.h -- WM8940 Soc Audio driver - * - * 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 _WM8940_H -#define _WM8940_H - -struct wm8940_setup_data { - /* Vref to analogue output resistance */ -#define WM8940_VROI_1K 0 -#define WM8940_VROI_30K 1 - unsigned int vroi:1; -}; -extern struct snd_soc_dai wm8940_dai; -extern struct snd_soc_codec_device soc_codec_dev_wm8940; - -/* WM8940 register space */ -#define WM8940_SOFTRESET 0x00 -#define WM8940_POWER1 0x01 -#define WM8940_POWER2 0x02 -#define WM8940_POWER3 0x03 -#define WM8940_IFACE 0x04 -#define WM8940_COMPANDINGCTL 0x05 -#define WM8940_CLOCK 0x06 -#define WM8940_ADDCNTRL 0x07 -#define WM8940_GPIO 0x08 -#define WM8940_CTLINT 0x09 -#define WM8940_DAC 0x0A -#define WM8940_DACVOL 0x0B - -#define WM8940_ADC 0x0E -#define WM8940_ADCVOL 0x0F -#define WM8940_NOTCH1 0x10 -#define WM8940_NOTCH2 0x11 -#define WM8940_NOTCH3 0x12 -#define WM8940_NOTCH4 0x13 -#define WM8940_NOTCH5 0x14 -#define WM8940_NOTCH6 0x15 -#define WM8940_NOTCH7 0x16 -#define WM8940_NOTCH8 0x17 -#define WM8940_DACLIM1 0x18 -#define WM8940_DACLIM2 0x19 - -#define WM8940_ALC1 0x20 -#define WM8940_ALC2 0x21 -#define WM8940_ALC3 0x22 -#define WM8940_NOISEGATE 0x23 -#define WM8940_PLLN 0x24 -#define WM8940_PLLK1 0x25 -#define WM8940_PLLK2 0x26 -#define WM8940_PLLK3 0x27 - -#define WM8940_ALC4 0x2A - -#define WM8940_INPUTCTL 0x2C -#define WM8940_PGAGAIN 0x2D - -#define WM8940_ADCBOOST 0x2F - -#define WM8940_OUTPUTCTL 0x31 -#define WM8940_SPKMIX 0x32 - -#define WM8940_SPKVOL 0x36 - -#define WM8940_MONOMIX 0x38 - -#define WM8940_CACHEREGNUM 0x57 - - -/* Clock divider Id's */ -#define WM8940_BCLKDIV 0 -#define WM8940_MCLKDIV 1 -#define WM8940_OPCLKDIV 2 - -/* MCLK clock dividers */ -#define WM8940_MCLKDIV_1 0 -#define WM8940_MCLKDIV_1_5 1 -#define WM8940_MCLKDIV_2 2 -#define WM8940_MCLKDIV_3 3 -#define WM8940_MCLKDIV_4 4 -#define WM8940_MCLKDIV_6 5 -#define WM8940_MCLKDIV_8 6 -#define WM8940_MCLKDIV_12 7 - -/* BCLK clock dividers */ -#define WM8940_BCLKDIV_1 0 -#define WM8940_BCLKDIV_2 1 -#define WM8940_BCLKDIV_4 2 -#define WM8940_BCLKDIV_8 3 -#define WM8940_BCLKDIV_16 4 -#define WM8940_BCLKDIV_32 5 - -/* PLL Out Dividers */ -#define WM8940_OPCLKDIV_1 0 -#define WM8940_OPCLKDIV_2 1 -#define WM8940_OPCLKDIV_3 2 -#define WM8940_OPCLKDIV_4 3 - -#endif /* _WM8940_H */ - diff --git a/trunk/sound/soc/codecs/wm8960.c b/trunk/sound/soc/codecs/wm8960.c deleted file mode 100644 index e224d8add170..000000000000 --- a/trunk/sound/soc/codecs/wm8960.c +++ /dev/null @@ -1,969 +0,0 @@ -/* - * wm8960.c -- WM8960 ALSA SoC Audio driver - * - * Author: Liam Girdwood - * - * 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. - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "wm8960.h" - -#define AUDIO_NAME "wm8960" - -struct snd_soc_codec_device soc_codec_dev_wm8960; - -/* R25 - Power 1 */ -#define WM8960_VREF 0x40 - -/* R28 - Anti-pop 1 */ -#define WM8960_POBCTRL 0x80 -#define WM8960_BUFDCOPEN 0x10 -#define WM8960_BUFIOEN 0x08 -#define WM8960_SOFT_ST 0x04 -#define WM8960_HPSTBY 0x01 - -/* R29 - Anti-pop 2 */ -#define WM8960_DISOP 0x40 - -/* - * wm8960 register cache - * We can't read the WM8960 register space when we are - * using 2 wire for device control, so we cache them instead. - */ -static const u16 wm8960_reg[WM8960_CACHEREGNUM] = { - 0x0097, 0x0097, 0x0000, 0x0000, - 0x0000, 0x0008, 0x0000, 0x000a, - 0x01c0, 0x0000, 0x00ff, 0x00ff, - 0x0000, 0x0000, 0x0000, 0x0000, - 0x0000, 0x007b, 0x0100, 0x0032, - 0x0000, 0x00c3, 0x00c3, 0x01c0, - 0x0000, 0x0000, 0x0000, 0x0000, - 0x0000, 0x0000, 0x0000, 0x0000, - 0x0100, 0x0100, 0x0050, 0x0050, - 0x0050, 0x0050, 0x0000, 0x0000, - 0x0000, 0x0000, 0x0040, 0x0000, - 0x0000, 0x0050, 0x0050, 0x0000, - 0x0002, 0x0037, 0x004d, 0x0080, - 0x0008, 0x0031, 0x0026, 0x00e9, -}; - -struct wm8960_priv { - u16 reg_cache[WM8960_CACHEREGNUM]; - struct snd_soc_codec codec; -}; - -/* - * read wm8960 register cache - */ -static inline unsigned int wm8960_read_reg_cache(struct snd_soc_codec *codec, - unsigned int reg) -{ - u16 *cache = codec->reg_cache; - if (reg == WM8960_RESET) - return 0; - if (reg >= WM8960_CACHEREGNUM) - return -1; - return cache[reg]; -} - -/* - * write wm8960 register cache - */ -static inline void wm8960_write_reg_cache(struct snd_soc_codec *codec, - u16 reg, unsigned int value) -{ - u16 *cache = codec->reg_cache; - if (reg >= WM8960_CACHEREGNUM) - return; - cache[reg] = value; -} - -static inline unsigned int wm8960_read(struct snd_soc_codec *codec, - unsigned int reg) -{ - return wm8960_read_reg_cache(codec, reg); -} - -/* - * write to the WM8960 register space - */ -static int wm8960_write(struct snd_soc_codec *codec, unsigned int reg, - unsigned int value) -{ - u8 data[2]; - - /* data is - * D15..D9 WM8960 register offset - * D8...D0 register data - */ - data[0] = (reg << 1) | ((value >> 8) & 0x0001); - data[1] = value & 0x00ff; - - wm8960_write_reg_cache(codec, reg, value); - if (codec->hw_write(codec->control_data, data, 2) == 2) - return 0; - else - return -EIO; -} - -#define wm8960_reset(c) wm8960_write(c, WM8960_RESET, 0) - -/* enumerated controls */ -static const char *wm8960_deemph[] = {"None", "32Khz", "44.1Khz", "48Khz"}; -static const char *wm8960_polarity[] = {"No Inversion", "Left Inverted", - "Right Inverted", "Stereo Inversion"}; -static const char *wm8960_3d_upper_cutoff[] = {"High", "Low"}; -static const char *wm8960_3d_lower_cutoff[] = {"Low", "High"}; -static const char *wm8960_alcfunc[] = {"Off", "Right", "Left", "Stereo"}; -static const char *wm8960_alcmode[] = {"ALC", "Limiter"}; - -static const struct soc_enum wm8960_enum[] = { - SOC_ENUM_SINGLE(WM8960_DACCTL1, 1, 4, wm8960_deemph), - SOC_ENUM_SINGLE(WM8960_DACCTL1, 5, 4, wm8960_polarity), - SOC_ENUM_SINGLE(WM8960_DACCTL2, 5, 4, wm8960_polarity), - SOC_ENUM_SINGLE(WM8960_3D, 6, 2, wm8960_3d_upper_cutoff), - SOC_ENUM_SINGLE(WM8960_3D, 5, 2, wm8960_3d_lower_cutoff), - SOC_ENUM_SINGLE(WM8960_ALC1, 7, 4, wm8960_alcfunc), - SOC_ENUM_SINGLE(WM8960_ALC3, 8, 2, wm8960_alcmode), -}; - -static const DECLARE_TLV_DB_SCALE(adc_tlv, -9700, 50, 0); -static const DECLARE_TLV_DB_SCALE(dac_tlv, -12700, 50, 1); -static const DECLARE_TLV_DB_SCALE(bypass_tlv, -2100, 300, 0); -static const DECLARE_TLV_DB_SCALE(out_tlv, -12100, 100, 1); - -static const struct snd_kcontrol_new wm8960_snd_controls[] = { -SOC_DOUBLE_R_TLV("Capture Volume", WM8960_LINVOL, WM8960_RINVOL, - 0, 63, 0, adc_tlv), -SOC_DOUBLE_R("Capture Volume ZC Switch", WM8960_LINVOL, WM8960_RINVOL, - 6, 1, 0), -SOC_DOUBLE_R("Capture Switch", WM8960_LINVOL, WM8960_RINVOL, - 7, 1, 0), - -SOC_DOUBLE_R_TLV("Playback Volume", WM8960_LDAC, WM8960_RDAC, - 0, 255, 0, dac_tlv), - -SOC_DOUBLE_R_TLV("Headphone Playback Volume", WM8960_LOUT1, WM8960_ROUT1, - 0, 127, 0, out_tlv), -SOC_DOUBLE_R("Headphone Playback ZC Switch", WM8960_LOUT1, WM8960_ROUT1, - 7, 1, 0), - -SOC_DOUBLE_R_TLV("Speaker Playback Volume", WM8960_LOUT2, WM8960_ROUT2, - 0, 127, 0, out_tlv), -SOC_DOUBLE_R("Speaker Playback ZC Switch", WM8960_LOUT2, WM8960_ROUT2, - 7, 1, 0), -SOC_SINGLE("Speaker DC Volume", WM8960_CLASSD3, 3, 5, 0), -SOC_SINGLE("Speaker AC Volume", WM8960_CLASSD3, 0, 5, 0), - -SOC_SINGLE("PCM Playback -6dB Switch", WM8960_DACCTL1, 7, 1, 0), -SOC_ENUM("ADC Polarity", wm8960_enum[1]), -SOC_ENUM("Playback De-emphasis", wm8960_enum[0]), -SOC_SINGLE("ADC High Pass Filter Switch", WM8960_DACCTL1, 0, 1, 0), - -SOC_ENUM("DAC Polarity", wm8960_enum[2]), - -SOC_ENUM("3D Filter Upper Cut-Off", wm8960_enum[3]), -SOC_ENUM("3D Filter Lower Cut-Off", wm8960_enum[4]), -SOC_SINGLE("3D Volume", WM8960_3D, 1, 15, 0), -SOC_SINGLE("3D Switch", WM8960_3D, 0, 1, 0), - -SOC_ENUM("ALC Function", wm8960_enum[5]), -SOC_SINGLE("ALC Max Gain", WM8960_ALC1, 4, 7, 0), -SOC_SINGLE("ALC Target", WM8960_ALC1, 0, 15, 1), -SOC_SINGLE("ALC Min Gain", WM8960_ALC2, 4, 7, 0), -SOC_SINGLE("ALC Hold Time", WM8960_ALC2, 0, 15, 0), -SOC_ENUM("ALC Mode", wm8960_enum[6]), -SOC_SINGLE("ALC Decay", WM8960_ALC3, 4, 15, 0), -SOC_SINGLE("ALC Attack", WM8960_ALC3, 0, 15, 0), - -SOC_SINGLE("Noise Gate Threshold", WM8960_NOISEG, 3, 31, 0), -SOC_SINGLE("Noise Gate Switch", WM8960_NOISEG, 0, 1, 0), - -SOC_DOUBLE_R("ADC PCM Capture Volume", WM8960_LINPATH, WM8960_RINPATH, - 0, 127, 0), - -SOC_SINGLE_TLV("Left Output Mixer Boost Bypass Volume", - WM8960_BYPASS1, 4, 7, 1, bypass_tlv), -SOC_SINGLE_TLV("Left Output Mixer LINPUT3 Volume", - WM8960_LOUTMIX, 4, 7, 1, bypass_tlv), -SOC_SINGLE_TLV("Right Output Mixer Boost Bypass Volume", - WM8960_BYPASS2, 4, 7, 1, bypass_tlv), -SOC_SINGLE_TLV("Right Output Mixer RINPUT3 Volume", - WM8960_ROUTMIX, 4, 7, 1, bypass_tlv), -}; - -static const struct snd_kcontrol_new wm8960_lin_boost[] = { -SOC_DAPM_SINGLE("LINPUT2 Switch", WM8960_LINPATH, 6, 1, 0), -SOC_DAPM_SINGLE("LINPUT3 Switch", WM8960_LINPATH, 7, 1, 0), -SOC_DAPM_SINGLE("LINPUT1 Switch", WM8960_LINPATH, 8, 1, 0), -}; - -static const struct snd_kcontrol_new wm8960_lin[] = { -SOC_DAPM_SINGLE("Boost Switch", WM8960_LINPATH, 3, 1, 0), -}; - -static const struct snd_kcontrol_new wm8960_rin_boost[] = { -SOC_DAPM_SINGLE("RINPUT2 Switch", WM8960_RINPATH, 6, 1, 0), -SOC_DAPM_SINGLE("RINPUT3 Switch", WM8960_RINPATH, 7, 1, 0), -SOC_DAPM_SINGLE("RINPUT1 Switch", WM8960_RINPATH, 8, 1, 0), -}; - -static const struct snd_kcontrol_new wm8960_rin[] = { -SOC_DAPM_SINGLE("Boost Switch", WM8960_RINPATH, 3, 1, 0), -}; - -static const struct snd_kcontrol_new wm8960_loutput_mixer[] = { -SOC_DAPM_SINGLE("PCM Playback Switch", WM8960_LOUTMIX, 8, 1, 0), -SOC_DAPM_SINGLE("LINPUT3 Switch", WM8960_LOUTMIX, 7, 1, 0), -SOC_DAPM_SINGLE("Boost Bypass Switch", WM8960_BYPASS1, 7, 1, 0), -}; - -static const struct snd_kcontrol_new wm8960_routput_mixer[] = { -SOC_DAPM_SINGLE("PCM Playback Switch", WM8960_ROUTMIX, 8, 1, 0), -SOC_DAPM_SINGLE("RINPUT3 Switch", WM8960_ROUTMIX, 7, 1, 0), -SOC_DAPM_SINGLE("Boost Bypass Switch", WM8960_BYPASS2, 7, 1, 0), -}; - -static const struct snd_kcontrol_new wm8960_mono_out[] = { -SOC_DAPM_SINGLE("Left Switch", WM8960_MONOMIX1, 7, 1, 0), -SOC_DAPM_SINGLE("Right Switch", WM8960_MONOMIX2, 7, 1, 0), -}; - -static const struct snd_soc_dapm_widget wm8960_dapm_widgets[] = { -SND_SOC_DAPM_INPUT("LINPUT1"), -SND_SOC_DAPM_INPUT("RINPUT1"), -SND_SOC_DAPM_INPUT("LINPUT2"), -SND_SOC_DAPM_INPUT("RINPUT2"), -SND_SOC_DAPM_INPUT("LINPUT3"), -SND_SOC_DAPM_INPUT("RINPUT3"), - -SND_SOC_DAPM_MICBIAS("MICB", WM8960_POWER1, 1, 0), - -SND_SOC_DAPM_MIXER("Left Boost Mixer", WM8960_POWER1, 5, 0, - wm8960_lin_boost, ARRAY_SIZE(wm8960_lin_boost)), -SND_SOC_DAPM_MIXER("Right Boost Mixer", WM8960_POWER1, 4, 0, - wm8960_rin_boost, ARRAY_SIZE(wm8960_rin_boost)), - -SND_SOC_DAPM_MIXER("Left Input Mixer", WM8960_POWER3, 5, 0, - wm8960_lin, ARRAY_SIZE(wm8960_lin)), -SND_SOC_DAPM_MIXER("Right Input Mixer", WM8960_POWER3, 4, 0, - wm8960_rin, ARRAY_SIZE(wm8960_rin)), - -SND_SOC_DAPM_ADC("Left ADC", "Capture", WM8960_POWER2, 3, 0), -SND_SOC_DAPM_ADC("Right ADC", "Capture", WM8960_POWER2, 2, 0), - -SND_SOC_DAPM_DAC("Left DAC", "Playback", WM8960_POWER2, 8, 0), -SND_SOC_DAPM_DAC("Right DAC", "Playback", WM8960_POWER2, 7, 0), - -SND_SOC_DAPM_MIXER("Left Output Mixer", WM8960_POWER3, 3, 0, - &wm8960_loutput_mixer[0], - ARRAY_SIZE(wm8960_loutput_mixer)), -SND_SOC_DAPM_MIXER("Right Output Mixer", WM8960_POWER3, 2, 0, - &wm8960_routput_mixer[0], - ARRAY_SIZE(wm8960_routput_mixer)), - -SND_SOC_DAPM_MIXER("Mono Output Mixer", WM8960_POWER2, 1, 0, - &wm8960_mono_out[0], - ARRAY_SIZE(wm8960_mono_out)), - -SND_SOC_DAPM_PGA("LOUT1 PGA", WM8960_POWER2, 6, 0, NULL, 0), -SND_SOC_DAPM_PGA("ROUT1 PGA", WM8960_POWER2, 5, 0, NULL, 0), - -SND_SOC_DAPM_PGA("Left Speaker PGA", WM8960_POWER2, 4, 0, NULL, 0), -SND_SOC_DAPM_PGA("Right Speaker PGA", WM8960_POWER2, 3, 0, NULL, 0), - -SND_SOC_DAPM_PGA("Right Speaker Output", WM8960_CLASSD1, 7, 0, NULL, 0), -SND_SOC_DAPM_PGA("Left Speaker Output", WM8960_CLASSD1, 6, 0, NULL, 0), - -SND_SOC_DAPM_OUTPUT("SPK_LP"), -SND_SOC_DAPM_OUTPUT("SPK_LN"), -SND_SOC_DAPM_OUTPUT("HP_L"), -SND_SOC_DAPM_OUTPUT("HP_R"), -SND_SOC_DAPM_OUTPUT("SPK_RP"), -SND_SOC_DAPM_OUTPUT("SPK_RN"), -SND_SOC_DAPM_OUTPUT("OUT3"), -}; - -static const struct snd_soc_dapm_route audio_paths[] = { - { "Left Boost Mixer", "LINPUT1 Switch", "LINPUT1" }, - { "Left Boost Mixer", "LINPUT2 Switch", "LINPUT2" }, - { "Left Boost Mixer", "LINPUT3 Switch", "LINPUT3" }, - - { "Left Input Mixer", "Boost Switch", "Left Boost Mixer", }, - { "Left Input Mixer", NULL, "LINPUT1", }, /* Really Boost Switch */ - { "Left Input Mixer", NULL, "LINPUT2" }, - { "Left Input Mixer", NULL, "LINPUT3" }, - - { "Right Boost Mixer", "RINPUT1 Switch", "RINPUT1" }, - { "Right Boost Mixer", "RINPUT2 Switch", "RINPUT2" }, - { "Right Boost Mixer", "RINPUT3 Switch", "RINPUT3" }, - - { "Right Input Mixer", "Boost Switch", "Right Boost Mixer", }, - { "Right Input Mixer", NULL, "RINPUT1", }, /* Really Boost Switch */ - { "Right Input Mixer", NULL, "RINPUT2" }, - { "Right Input Mixer", NULL, "LINPUT3" }, - - { "Left ADC", NULL, "Left Input Mixer" }, - { "Right ADC", NULL, "Right Input Mixer" }, - - { "Left Output Mixer", "LINPUT3 Switch", "LINPUT3" }, - { "Left Output Mixer", "Boost Bypass Switch", "Left Boost Mixer"} , - { "Left Output Mixer", "PCM Playback Switch", "Left DAC" }, - - { "Right Output Mixer", "RINPUT3 Switch", "RINPUT3" }, - { "Right Output Mixer", "Boost Bypass Switch", "Right Boost Mixer" } , - { "Right Output Mixer", "PCM Playback Switch", "Right DAC" }, - - { "Mono Output Mixer", "Left Switch", "Left Output Mixer" }, - { "Mono Output Mixer", "Right Switch", "Right Output Mixer" }, - - { "LOUT1 PGA", NULL, "Left Output Mixer" }, - { "ROUT1 PGA", NULL, "Right Output Mixer" }, - - { "HP_L", NULL, "LOUT1 PGA" }, - { "HP_R", NULL, "ROUT1 PGA" }, - - { "Left Speaker PGA", NULL, "Left Output Mixer" }, - { "Right Speaker PGA", NULL, "Right Output Mixer" }, - - { "Left Speaker Output", NULL, "Left Speaker PGA" }, - { "Right Speaker Output", NULL, "Right Speaker PGA" }, - - { "SPK_LN", NULL, "Left Speaker Output" }, - { "SPK_LP", NULL, "Left Speaker Output" }, - { "SPK_RN", NULL, "Right Speaker Output" }, - { "SPK_RP", NULL, "Right Speaker Output" }, - - { "OUT3", NULL, "Mono Output Mixer", } -}; - -static int wm8960_add_widgets(struct snd_soc_codec *codec) -{ - snd_soc_dapm_new_controls(codec, wm8960_dapm_widgets, - ARRAY_SIZE(wm8960_dapm_widgets)); - - snd_soc_dapm_add_routes(codec, audio_paths, ARRAY_SIZE(audio_paths)); - - snd_soc_dapm_new_widgets(codec); - return 0; -} - -static int wm8960_set_dai_fmt(struct snd_soc_dai *codec_dai, - unsigned int fmt) -{ - struct snd_soc_codec *codec = codec_dai->codec; - u16 iface = 0; - - /* set master/slave audio interface */ - switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { - case SND_SOC_DAIFMT_CBM_CFM: - iface |= 0x0040; - break; - case SND_SOC_DAIFMT_CBS_CFS: - break; - default: - return -EINVAL; - } - - /* interface format */ - switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { - case SND_SOC_DAIFMT_I2S: - iface |= 0x0002; - break; - case SND_SOC_DAIFMT_RIGHT_J: - break; - case SND_SOC_DAIFMT_LEFT_J: - iface |= 0x0001; - break; - case SND_SOC_DAIFMT_DSP_A: - iface |= 0x0003; - break; - case SND_SOC_DAIFMT_DSP_B: - iface |= 0x0013; - break; - default: - return -EINVAL; - } - - /* clock inversion */ - switch (fmt & SND_SOC_DAIFMT_INV_MASK) { - case SND_SOC_DAIFMT_NB_NF: - break; - case SND_SOC_DAIFMT_IB_IF: - iface |= 0x0090; - break; - case SND_SOC_DAIFMT_IB_NF: - iface |= 0x0080; - break; - case SND_SOC_DAIFMT_NB_IF: - iface |= 0x0010; - break; - default: - return -EINVAL; - } - - /* set iface */ - wm8960_write(codec, WM8960_IFACE1, iface); - return 0; -} - -static int wm8960_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params, - struct snd_soc_dai *dai) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_device *socdev = rtd->socdev; - struct snd_soc_codec *codec = socdev->card->codec; - u16 iface = wm8960_read(codec, WM8960_IFACE1) & 0xfff3; - - /* bit size */ - switch (params_format(params)) { - case SNDRV_PCM_FORMAT_S16_LE: - break; - case SNDRV_PCM_FORMAT_S20_3LE: - iface |= 0x0004; - break; - case SNDRV_PCM_FORMAT_S24_LE: - iface |= 0x0008; - break; - } - - /* set iface */ - wm8960_write(codec, WM8960_IFACE1, iface); - return 0; -} - -static int wm8960_mute(struct snd_soc_dai *dai, int mute) -{ - struct snd_soc_codec *codec = dai->codec; - u16 mute_reg = wm8960_read(codec, WM8960_DACCTL1) & 0xfff7; - - if (mute) - wm8960_write(codec, WM8960_DACCTL1, mute_reg | 0x8); - else - wm8960_write(codec, WM8960_DACCTL1, mute_reg); - return 0; -} - -static int wm8960_set_bias_level(struct snd_soc_codec *codec, - enum snd_soc_bias_level level) -{ - struct wm8960_data *pdata = codec->dev->platform_data; - u16 reg; - - switch (level) { - case SND_SOC_BIAS_ON: - break; - - case SND_SOC_BIAS_PREPARE: - /* Set VMID to 2x50k */ - reg = wm8960_read(codec, WM8960_POWER1); - reg &= ~0x180; - reg |= 0x80; - wm8960_write(codec, WM8960_POWER1, reg); - break; - - case SND_SOC_BIAS_STANDBY: - if (codec->bias_level == SND_SOC_BIAS_OFF) { - /* Enable anti-pop features */ - wm8960_write(codec, WM8960_APOP1, - WM8960_POBCTRL | WM8960_SOFT_ST | - WM8960_BUFDCOPEN | WM8960_BUFIOEN); - - /* Discharge HP output */ - reg = WM8960_DISOP; - if (pdata) - reg |= pdata->dres << 4; - wm8960_write(codec, WM8960_APOP2, reg); - - msleep(400); - - wm8960_write(codec, WM8960_APOP2, 0); - - /* Enable & ramp VMID at 2x50k */ - reg = wm8960_read(codec, WM8960_POWER1); - reg |= 0x80; - wm8960_write(codec, WM8960_POWER1, reg); - msleep(100); - - /* Enable VREF */ - wm8960_write(codec, WM8960_POWER1, reg | WM8960_VREF); - - /* Disable anti-pop features */ - wm8960_write(codec, WM8960_APOP1, WM8960_BUFIOEN); - } - - /* Set VMID to 2x250k */ - reg = wm8960_read(codec, WM8960_POWER1); - reg &= ~0x180; - reg |= 0x100; - wm8960_write(codec, WM8960_POWER1, reg); - break; - - case SND_SOC_BIAS_OFF: - /* Enable anti-pop features */ - wm8960_write(codec, WM8960_APOP1, - WM8960_POBCTRL | WM8960_SOFT_ST | - WM8960_BUFDCOPEN | WM8960_BUFIOEN); - - /* Disable VMID and VREF, let them discharge */ - wm8960_write(codec, WM8960_POWER1, 0); - msleep(600); - - wm8960_write(codec, WM8960_APOP1, 0); - break; - } - - codec->bias_level = level; - - return 0; -} - -/* PLL divisors */ -struct _pll_div { - u32 pre_div:1; - u32 n:4; - u32 k:24; -}; - -/* The size in bits of the pll divide multiplied by 10 - * to allow rounding later */ -#define FIXED_PLL_SIZE ((1 << 24) * 10) - -static int pll_factors(unsigned int source, unsigned int target, - struct _pll_div *pll_div) -{ - unsigned long long Kpart; - unsigned int K, Ndiv, Nmod; - - pr_debug("WM8960 PLL: setting %dHz->%dHz\n", source, target); - - /* Scale up target to PLL operating frequency */ - target *= 4; - - Ndiv = target / source; - if (Ndiv < 6) { - source >>= 1; - pll_div->pre_div = 1; - Ndiv = target / source; - } else - pll_div->pre_div = 0; - - if ((Ndiv < 6) || (Ndiv > 12)) { - pr_err("WM8960 PLL: Unsupported N=%d\n", Ndiv); - return -EINVAL; - } - - pll_div->n = Ndiv; - Nmod = target % source; - Kpart = FIXED_PLL_SIZE * (long long)Nmod; - - do_div(Kpart, source); - - K = Kpart & 0xFFFFFFFF; - - /* Check if we need to round */ - if ((K % 10) >= 5) - K += 5; - - /* Move down to proper range now rounding is done */ - K /= 10; - - pll_div->k = K; - - pr_debug("WM8960 PLL: N=%x K=%x pre_div=%d\n", - pll_div->n, pll_div->k, pll_div->pre_div); - - return 0; -} - -static int wm8960_set_dai_pll(struct snd_soc_dai *codec_dai, - int pll_id, unsigned int freq_in, unsigned int freq_out) -{ - struct snd_soc_codec *codec = codec_dai->codec; - u16 reg; - static struct _pll_div pll_div; - int ret; - - if (freq_in && freq_out) { - ret = pll_factors(freq_in, freq_out, &pll_div); - if (ret != 0) - return ret; - } - - /* Disable the PLL: even if we are changing the frequency the - * PLL needs to be disabled while we do so. */ - wm8960_write(codec, WM8960_CLOCK1, - wm8960_read(codec, WM8960_CLOCK1) & ~1); - wm8960_write(codec, WM8960_POWER2, - wm8960_read(codec, WM8960_POWER2) & ~1); - - if (!freq_in || !freq_out) - return 0; - - reg = wm8960_read(codec, WM8960_PLL1) & ~0x3f; - reg |= pll_div.pre_div << 4; - reg |= pll_div.n; - - if (pll_div.k) { - reg |= 0x20; - - wm8960_write(codec, WM8960_PLL2, (pll_div.k >> 18) & 0x3f); - wm8960_write(codec, WM8960_PLL3, (pll_div.k >> 9) & 0x1ff); - wm8960_write(codec, WM8960_PLL4, pll_div.k & 0x1ff); - } - wm8960_write(codec, WM8960_PLL1, reg); - - /* Turn it on */ - wm8960_write(codec, WM8960_POWER2, - wm8960_read(codec, WM8960_POWER2) | 1); - msleep(250); - wm8960_write(codec, WM8960_CLOCK1, - wm8960_read(codec, WM8960_CLOCK1) | 1); - - return 0; -} - -static int wm8960_set_dai_clkdiv(struct snd_soc_dai *codec_dai, - int div_id, int div) -{ - struct snd_soc_codec *codec = codec_dai->codec; - u16 reg; - - switch (div_id) { - case WM8960_SYSCLKSEL: - reg = wm8960_read(codec, WM8960_CLOCK1) & 0x1fe; - wm8960_write(codec, WM8960_CLOCK1, reg | div); - break; - case WM8960_SYSCLKDIV: - reg = wm8960_read(codec, WM8960_CLOCK1) & 0x1f9; - wm8960_write(codec, WM8960_CLOCK1, reg | div); - break; - case WM8960_DACDIV: - reg = wm8960_read(codec, WM8960_CLOCK1) & 0x1c7; - wm8960_write(codec, WM8960_CLOCK1, reg | div); - break; - case WM8960_OPCLKDIV: - reg = wm8960_read(codec, WM8960_PLL1) & 0x03f; - wm8960_write(codec, WM8960_PLL1, reg | div); - break; - case WM8960_DCLKDIV: - reg = wm8960_read(codec, WM8960_CLOCK2) & 0x03f; - wm8960_write(codec, WM8960_CLOCK2, reg | div); - break; - case WM8960_TOCLKSEL: - reg = wm8960_read(codec, WM8960_ADDCTL1) & 0x1fd; - wm8960_write(codec, WM8960_ADDCTL1, reg | div); - break; - default: - return -EINVAL; - } - - return 0; -} - -#define WM8960_RATES SNDRV_PCM_RATE_8000_48000 - -#define WM8960_FORMATS \ - (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S20_3LE | \ - SNDRV_PCM_FMTBIT_S24_LE) - -static struct snd_soc_dai_ops wm8960_dai_ops = { - .hw_params = wm8960_hw_params, - .digital_mute = wm8960_mute, - .set_fmt = wm8960_set_dai_fmt, - .set_clkdiv = wm8960_set_dai_clkdiv, - .set_pll = wm8960_set_dai_pll, -}; - -struct snd_soc_dai wm8960_dai = { - .name = "WM8960", - .playback = { - .stream_name = "Playback", - .channels_min = 1, - .channels_max = 2, - .rates = WM8960_RATES, - .formats = WM8960_FORMATS,}, - .capture = { - .stream_name = "Capture", - .channels_min = 1, - .channels_max = 2, - .rates = WM8960_RATES, - .formats = WM8960_FORMATS,}, - .ops = &wm8960_dai_ops, - .symmetric_rates = 1, -}; -EXPORT_SYMBOL_GPL(wm8960_dai); - -static int wm8960_suspend(struct platform_device *pdev, pm_message_t state) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - - wm8960_set_bias_level(codec, SND_SOC_BIAS_OFF); - return 0; -} - -static int wm8960_resume(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - int i; - u8 data[2]; - u16 *cache = codec->reg_cache; - - /* Sync reg_cache with the hardware */ - for (i = 0; i < ARRAY_SIZE(wm8960_reg); i++) { - data[0] = (i << 1) | ((cache[i] >> 8) & 0x0001); - data[1] = cache[i] & 0x00ff; - codec->hw_write(codec->control_data, data, 2); - } - - wm8960_set_bias_level(codec, SND_SOC_BIAS_STANDBY); - wm8960_set_bias_level(codec, codec->suspend_bias_level); - return 0; -} - -static struct snd_soc_codec *wm8960_codec; - -static int wm8960_probe(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec; - int ret = 0; - - if (wm8960_codec == NULL) { - dev_err(&pdev->dev, "Codec device not registered\n"); - return -ENODEV; - } - - socdev->card->codec = wm8960_codec; - codec = wm8960_codec; - - /* register pcms */ - ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1); - if (ret < 0) { - dev_err(codec->dev, "failed to create pcms: %d\n", ret); - goto pcm_err; - } - - snd_soc_add_controls(codec, wm8960_snd_controls, - ARRAY_SIZE(wm8960_snd_controls)); - wm8960_add_widgets(codec); - ret = snd_soc_init_card(socdev); - if (ret < 0) { - dev_err(codec->dev, "failed to register card: %d\n", ret); - goto card_err; - } - - return ret; - -card_err: - snd_soc_free_pcms(socdev); - snd_soc_dapm_free(socdev); -pcm_err: - return ret; -} - -/* power down chip */ -static int wm8960_remove(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - - snd_soc_free_pcms(socdev); - snd_soc_dapm_free(socdev); - - return 0; -} - -struct snd_soc_codec_device soc_codec_dev_wm8960 = { - .probe = wm8960_probe, - .remove = wm8960_remove, - .suspend = wm8960_suspend, - .resume = wm8960_resume, -}; -EXPORT_SYMBOL_GPL(soc_codec_dev_wm8960); - -static int wm8960_register(struct wm8960_priv *wm8960) -{ - struct wm8960_data *pdata = wm8960->codec.dev->platform_data; - struct snd_soc_codec *codec = &wm8960->codec; - int ret; - u16 reg; - - if (wm8960_codec) { - dev_err(codec->dev, "Another WM8960 is registered\n"); - return -EINVAL; - } - - if (!pdata) { - dev_warn(codec->dev, "No platform data supplied\n"); - } else { - if (pdata->dres > WM8960_DRES_MAX) { - dev_err(codec->dev, "Invalid DRES: %d\n", pdata->dres); - pdata->dres = 0; - } - } - - mutex_init(&codec->mutex); - INIT_LIST_HEAD(&codec->dapm_widgets); - INIT_LIST_HEAD(&codec->dapm_paths); - - codec->private_data = wm8960; - codec->name = "WM8960"; - codec->owner = THIS_MODULE; - codec->read = wm8960_read_reg_cache; - codec->write = wm8960_write; - codec->bias_level = SND_SOC_BIAS_OFF; - codec->set_bias_level = wm8960_set_bias_level; - codec->dai = &wm8960_dai; - codec->num_dai = 1; - codec->reg_cache_size = WM8960_CACHEREGNUM; - codec->reg_cache = &wm8960->reg_cache; - - memcpy(codec->reg_cache, wm8960_reg, sizeof(wm8960_reg)); - - ret = wm8960_reset(codec); - if (ret < 0) { - dev_err(codec->dev, "Failed to issue reset\n"); - return ret; - } - - wm8960_dai.dev = codec->dev; - - wm8960_set_bias_level(codec, SND_SOC_BIAS_STANDBY); - - /* Latch the update bits */ - reg = wm8960_read(codec, WM8960_LINVOL); - wm8960_write(codec, WM8960_LINVOL, reg | 0x100); - reg = wm8960_read(codec, WM8960_RINVOL); - wm8960_write(codec, WM8960_RINVOL, reg | 0x100); - reg = wm8960_read(codec, WM8960_LADC); - wm8960_write(codec, WM8960_LADC, reg | 0x100); - reg = wm8960_read(codec, WM8960_RADC); - wm8960_write(codec, WM8960_RADC, reg | 0x100); - reg = wm8960_read(codec, WM8960_LDAC); - wm8960_write(codec, WM8960_LDAC, reg | 0x100); - reg = wm8960_read(codec, WM8960_RDAC); - wm8960_write(codec, WM8960_RDAC, reg | 0x100); - reg = wm8960_read(codec, WM8960_LOUT1); - wm8960_write(codec, WM8960_LOUT1, reg | 0x100); - reg = wm8960_read(codec, WM8960_ROUT1); - wm8960_write(codec, WM8960_ROUT1, reg | 0x100); - reg = wm8960_read(codec, WM8960_LOUT2); - wm8960_write(codec, WM8960_LOUT2, reg | 0x100); - reg = wm8960_read(codec, WM8960_ROUT2); - wm8960_write(codec, WM8960_ROUT2, reg | 0x100); - - wm8960_codec = codec; - - ret = snd_soc_register_codec(codec); - if (ret != 0) { - dev_err(codec->dev, "Failed to register codec: %d\n", ret); - return ret; - } - - ret = snd_soc_register_dai(&wm8960_dai); - if (ret != 0) { - dev_err(codec->dev, "Failed to register DAI: %d\n", ret); - snd_soc_unregister_codec(codec); - return ret; - } - - return 0; -} - -static void wm8960_unregister(struct wm8960_priv *wm8960) -{ - wm8960_set_bias_level(&wm8960->codec, SND_SOC_BIAS_OFF); - snd_soc_unregister_dai(&wm8960_dai); - snd_soc_unregister_codec(&wm8960->codec); - kfree(wm8960); - wm8960_codec = NULL; -} - -static __devinit int wm8960_i2c_probe(struct i2c_client *i2c, - const struct i2c_device_id *id) -{ - struct wm8960_priv *wm8960; - struct snd_soc_codec *codec; - - wm8960 = kzalloc(sizeof(struct wm8960_priv), GFP_KERNEL); - if (wm8960 == NULL) - return -ENOMEM; - - codec = &wm8960->codec; - codec->hw_write = (hw_write_t)i2c_master_send; - - i2c_set_clientdata(i2c, wm8960); - codec->control_data = i2c; - - codec->dev = &i2c->dev; - - return wm8960_register(wm8960); -} - -static __devexit int wm8960_i2c_remove(struct i2c_client *client) -{ - struct wm8960_priv *wm8960 = i2c_get_clientdata(client); - wm8960_unregister(wm8960); - return 0; -} - -static const struct i2c_device_id wm8960_i2c_id[] = { - { "wm8960", 0 }, - { } -}; -MODULE_DEVICE_TABLE(i2c, wm8960_i2c_id); - -static struct i2c_driver wm8960_i2c_driver = { - .driver = { - .name = "WM8960 I2C Codec", - .owner = THIS_MODULE, - }, - .probe = wm8960_i2c_probe, - .remove = __devexit_p(wm8960_i2c_remove), - .id_table = wm8960_i2c_id, -}; - -static int __init wm8960_modinit(void) -{ - int ret; - - ret = i2c_add_driver(&wm8960_i2c_driver); - if (ret != 0) { - printk(KERN_ERR "Failed to register WM8960 I2C driver: %d\n", - ret); - } - - return ret; -} -module_init(wm8960_modinit); - -static void __exit wm8960_exit(void) -{ - i2c_del_driver(&wm8960_i2c_driver); -} -module_exit(wm8960_exit); - - -MODULE_DESCRIPTION("ASoC WM8960 driver"); -MODULE_AUTHOR("Liam Girdwood"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/codecs/wm8960.h b/trunk/sound/soc/codecs/wm8960.h deleted file mode 100644 index c9af56c9d9d4..000000000000 --- a/trunk/sound/soc/codecs/wm8960.h +++ /dev/null @@ -1,127 +0,0 @@ -/* - * wm8960.h -- WM8960 Soc Audio driver - * - * 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 _WM8960_H -#define _WM8960_H - -/* WM8960 register space */ - - -#define WM8960_CACHEREGNUM 56 - -#define WM8960_LINVOL 0x0 -#define WM8960_RINVOL 0x1 -#define WM8960_LOUT1 0x2 -#define WM8960_ROUT1 0x3 -#define WM8960_CLOCK1 0x4 -#define WM8960_DACCTL1 0x5 -#define WM8960_DACCTL2 0x6 -#define WM8960_IFACE1 0x7 -#define WM8960_CLOCK2 0x8 -#define WM8960_IFACE2 0x9 -#define WM8960_LDAC 0xa -#define WM8960_RDAC 0xb - -#define WM8960_RESET 0xf -#define WM8960_3D 0x10 -#define WM8960_ALC1 0x11 -#define WM8960_ALC2 0x12 -#define WM8960_ALC3 0x13 -#define WM8960_NOISEG 0x14 -#define WM8960_LADC 0x15 -#define WM8960_RADC 0x16 -#define WM8960_ADDCTL1 0x17 -#define WM8960_ADDCTL2 0x18 -#define WM8960_POWER1 0x19 -#define WM8960_POWER2 0x1a -#define WM8960_ADDCTL3 0x1b -#define WM8960_APOP1 0x1c -#define WM8960_APOP2 0x1d - -#define WM8960_LINPATH 0x20 -#define WM8960_RINPATH 0x21 -#define WM8960_LOUTMIX 0x22 - -#define WM8960_ROUTMIX 0x25 -#define WM8960_MONOMIX1 0x26 -#define WM8960_MONOMIX2 0x27 -#define WM8960_LOUT2 0x28 -#define WM8960_ROUT2 0x29 -#define WM8960_MONO 0x2a -#define WM8960_INBMIX1 0x2b -#define WM8960_INBMIX2 0x2c -#define WM8960_BYPASS1 0x2d -#define WM8960_BYPASS2 0x2e -#define WM8960_POWER3 0x2f -#define WM8960_ADDCTL4 0x30 -#define WM8960_CLASSD1 0x31 - -#define WM8960_CLASSD3 0x33 -#define WM8960_PLL1 0x34 -#define WM8960_PLL2 0x35 -#define WM8960_PLL3 0x36 -#define WM8960_PLL4 0x37 - - -/* - * WM8960 Clock dividers - */ -#define WM8960_SYSCLKDIV 0 -#define WM8960_DACDIV 1 -#define WM8960_OPCLKDIV 2 -#define WM8960_DCLKDIV 3 -#define WM8960_TOCLKSEL 4 -#define WM8960_SYSCLKSEL 5 - -#define WM8960_SYSCLK_DIV_1 (0 << 1) -#define WM8960_SYSCLK_DIV_2 (2 << 1) - -#define WM8960_SYSCLK_MCLK (0 << 0) -#define WM8960_SYSCLK_PLL (1 << 0) - -#define WM8960_DAC_DIV_1 (0 << 3) -#define WM8960_DAC_DIV_1_5 (1 << 3) -#define WM8960_DAC_DIV_2 (2 << 3) -#define WM8960_DAC_DIV_3 (3 << 3) -#define WM8960_DAC_DIV_4 (4 << 3) -#define WM8960_DAC_DIV_5_5 (5 << 3) -#define WM8960_DAC_DIV_6 (6 << 3) - -#define WM8960_DCLK_DIV_1_5 (0 << 6) -#define WM8960_DCLK_DIV_2 (1 << 6) -#define WM8960_DCLK_DIV_3 (2 << 6) -#define WM8960_DCLK_DIV_4 (3 << 6) -#define WM8960_DCLK_DIV_6 (4 << 6) -#define WM8960_DCLK_DIV_8 (5 << 6) -#define WM8960_DCLK_DIV_12 (6 << 6) -#define WM8960_DCLK_DIV_16 (7 << 6) - -#define WM8960_TOCLK_F19 (0 << 1) -#define WM8960_TOCLK_F21 (1 << 1) - -#define WM8960_OPCLK_DIV_1 (0 << 0) -#define WM8960_OPCLK_DIV_2 (1 << 0) -#define WM8960_OPCLK_DIV_3 (2 << 0) -#define WM8960_OPCLK_DIV_4 (3 << 0) -#define WM8960_OPCLK_DIV_5_5 (4 << 0) -#define WM8960_OPCLK_DIV_6 (5 << 0) - -extern struct snd_soc_dai wm8960_dai; -extern struct snd_soc_codec_device soc_codec_dev_wm8960; - -#define WM8960_DRES_400R 0 -#define WM8960_DRES_200R 1 -#define WM8960_DRES_600R 2 -#define WM8960_DRES_150R 3 -#define WM8960_DRES_MAX 3 - -struct wm8960_data { - int dres; -}; - -#endif diff --git a/trunk/sound/soc/codecs/wm8988.c b/trunk/sound/soc/codecs/wm8988.c deleted file mode 100644 index c05f71803aa8..000000000000 --- a/trunk/sound/soc/codecs/wm8988.c +++ /dev/null @@ -1,1097 +0,0 @@ -/* - * wm8988.c -- WM8988 ALSA SoC audio driver - * - * Copyright 2009 Wolfson Microelectronics plc - * Copyright 2005 Openedhand Ltd. - * - * Author: Mark Brown - * - * 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. - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "wm8988.h" - -/* - * wm8988 register cache - * We can't read the WM8988 register space when we - * are using 2 wire for device control, so we cache them instead. - */ -static const u16 wm8988_reg[] = { - 0x0097, 0x0097, 0x0079, 0x0079, /* 0 */ - 0x0000, 0x0008, 0x0000, 0x000a, /* 4 */ - 0x0000, 0x0000, 0x00ff, 0x00ff, /* 8 */ - 0x000f, 0x000f, 0x0000, 0x0000, /* 12 */ - 0x0000, 0x007b, 0x0000, 0x0032, /* 16 */ - 0x0000, 0x00c3, 0x00c3, 0x00c0, /* 20 */ - 0x0000, 0x0000, 0x0000, 0x0000, /* 24 */ - 0x0000, 0x0000, 0x0000, 0x0000, /* 28 */ - 0x0000, 0x0000, 0x0050, 0x0050, /* 32 */ - 0x0050, 0x0050, 0x0050, 0x0050, /* 36 */ - 0x0079, 0x0079, 0x0079, /* 40 */ -}; - -/* codec private data */ -struct wm8988_priv { - unsigned int sysclk; - struct snd_soc_codec codec; - struct snd_pcm_hw_constraint_list *sysclk_constraints; - u16 reg_cache[WM8988_NUM_REG]; -}; - - -/* - * read wm8988 register cache - */ -static inline unsigned int wm8988_read_reg_cache(struct snd_soc_codec *codec, - unsigned int reg) -{ - u16 *cache = codec->reg_cache; - if (reg > WM8988_NUM_REG) - return -1; - return cache[reg]; -} - -/* - * write wm8988 register cache - */ -static inline void wm8988_write_reg_cache(struct snd_soc_codec *codec, - unsigned int reg, unsigned int value) -{ - u16 *cache = codec->reg_cache; - if (reg > WM8988_NUM_REG) - return; - cache[reg] = value; -} - -static int wm8988_write(struct snd_soc_codec *codec, unsigned int reg, - unsigned int value) -{ - u8 data[2]; - - /* data is - * D15..D9 WM8753 register offset - * D8...D0 register data - */ - data[0] = (reg << 1) | ((value >> 8) & 0x0001); - data[1] = value & 0x00ff; - - wm8988_write_reg_cache(codec, reg, value); - if (codec->hw_write(codec->control_data, data, 2) == 2) - return 0; - else - return -EIO; -} - -#define wm8988_reset(c) wm8988_write(c, WM8988_RESET, 0) - -/* - * WM8988 Controls - */ - -static const char *bass_boost_txt[] = {"Linear Control", "Adaptive Boost"}; -static const struct soc_enum bass_boost = - SOC_ENUM_SINGLE(WM8988_BASS, 7, 2, bass_boost_txt); - -static const char *bass_filter_txt[] = { "130Hz @ 48kHz", "200Hz @ 48kHz" }; -static const struct soc_enum bass_filter = - SOC_ENUM_SINGLE(WM8988_BASS, 6, 2, bass_filter_txt); - -static const char *treble_txt[] = {"8kHz", "4kHz"}; -static const struct soc_enum treble = - SOC_ENUM_SINGLE(WM8988_TREBLE, 6, 2, treble_txt); - -static const char *stereo_3d_lc_txt[] = {"200Hz", "500Hz"}; -static const struct soc_enum stereo_3d_lc = - SOC_ENUM_SINGLE(WM8988_3D, 5, 2, stereo_3d_lc_txt); - -static const char *stereo_3d_uc_txt[] = {"2.2kHz", "1.5kHz"}; -static const struct soc_enum stereo_3d_uc = - SOC_ENUM_SINGLE(WM8988_3D, 6, 2, stereo_3d_uc_txt); - -static const char *stereo_3d_func_txt[] = {"Capture", "Playback"}; -static const struct soc_enum stereo_3d_func = - SOC_ENUM_SINGLE(WM8988_3D, 7, 2, stereo_3d_func_txt); - -static const char *alc_func_txt[] = {"Off", "Right", "Left", "Stereo"}; -static const struct soc_enum alc_func = - SOC_ENUM_SINGLE(WM8988_ALC1, 7, 4, alc_func_txt); - -static const char *ng_type_txt[] = {"Constant PGA Gain", - "Mute ADC Output"}; -static const struct soc_enum ng_type = - SOC_ENUM_SINGLE(WM8988_NGATE, 1, 2, ng_type_txt); - -static const char *deemph_txt[] = {"None", "32Khz", "44.1Khz", "48Khz"}; -static const struct soc_enum deemph = - SOC_ENUM_SINGLE(WM8988_ADCDAC, 1, 4, deemph_txt); - -static const char *adcpol_txt[] = {"Normal", "L Invert", "R Invert", - "L + R Invert"}; -static const struct soc_enum adcpol = - SOC_ENUM_SINGLE(WM8988_ADCDAC, 5, 4, adcpol_txt); - -static const DECLARE_TLV_DB_SCALE(pga_tlv, -1725, 75, 0); -static const DECLARE_TLV_DB_SCALE(adc_tlv, -9750, 50, 1); -static const DECLARE_TLV_DB_SCALE(dac_tlv, -12750, 50, 1); -static const DECLARE_TLV_DB_SCALE(out_tlv, -12100, 100, 1); -static const DECLARE_TLV_DB_SCALE(bypass_tlv, -1500, 300, 0); - -static const struct snd_kcontrol_new wm8988_snd_controls[] = { - -SOC_ENUM("Bass Boost", bass_boost), -SOC_ENUM("Bass Filter", bass_filter), -SOC_SINGLE("Bass Volume", WM8988_BASS, 0, 15, 1), - -SOC_SINGLE("Treble Volume", WM8988_TREBLE, 0, 15, 0), -SOC_ENUM("Treble Cut-off", treble), - -SOC_SINGLE("3D Switch", WM8988_3D, 0, 1, 0), -SOC_SINGLE("3D Volume", WM8988_3D, 1, 15, 0), -SOC_ENUM("3D Lower Cut-off", stereo_3d_lc), -SOC_ENUM("3D Upper Cut-off", stereo_3d_uc), -SOC_ENUM("3D Mode", stereo_3d_func), - -SOC_SINGLE("ALC Capture Target Volume", WM8988_ALC1, 0, 7, 0), -SOC_SINGLE("ALC Capture Max Volume", WM8988_ALC1, 4, 7, 0), -SOC_ENUM("ALC Capture Function", alc_func), -SOC_SINGLE("ALC Capture ZC Switch", WM8988_ALC2, 7, 1, 0), -SOC_SINGLE("ALC Capture Hold Time", WM8988_ALC2, 0, 15, 0), -SOC_SINGLE("ALC Capture Decay Time", WM8988_ALC3, 4, 15, 0), -SOC_SINGLE("ALC Capture Attack Time", WM8988_ALC3, 0, 15, 0), -SOC_SINGLE("ALC Capture NG Threshold", WM8988_NGATE, 3, 31, 0), -SOC_ENUM("ALC Capture NG Type", ng_type), -SOC_SINGLE("ALC Capture NG Switch", WM8988_NGATE, 0, 1, 0), - -SOC_SINGLE("ZC Timeout Switch", WM8988_ADCTL1, 0, 1, 0), - -SOC_DOUBLE_R_TLV("Capture Digital Volume", WM8988_LADC, WM8988_RADC, - 0, 255, 0, adc_tlv), -SOC_DOUBLE_R_TLV("Capture Volume", WM8988_LINVOL, WM8988_RINVOL, - 0, 63, 0, pga_tlv), -SOC_DOUBLE_R("Capture ZC Switch", WM8988_LINVOL, WM8988_RINVOL, 6, 1, 0), -SOC_DOUBLE_R("Capture Switch", WM8988_LINVOL, WM8988_RINVOL, 7, 1, 1), - -SOC_ENUM("Playback De-emphasis", deemph), - -SOC_ENUM("Capture Polarity", adcpol), -SOC_SINGLE("Playback 6dB Attenuate", WM8988_ADCDAC, 7, 1, 0), -SOC_SINGLE("Capture 6dB Attenuate", WM8988_ADCDAC, 8, 1, 0), - -SOC_DOUBLE_R_TLV("PCM Volume", WM8988_LDAC, WM8988_RDAC, 0, 255, 0, dac_tlv), - -SOC_SINGLE_TLV("Left Mixer Left Bypass Volume", WM8988_LOUTM1, 4, 7, 1, - bypass_tlv), -SOC_SINGLE_TLV("Left Mixer Right Bypass Volume", WM8988_LOUTM2, 4, 7, 1, - bypass_tlv), -SOC_SINGLE_TLV("Right Mixer Left Bypass Volume", WM8988_ROUTM1, 4, 7, 1, - bypass_tlv), -SOC_SINGLE_TLV("Right Mixer Right Bypass Volume", WM8988_ROUTM2, 4, 7, 1, - bypass_tlv), - -SOC_DOUBLE_R("Output 1 Playback ZC Switch", WM8988_LOUT1V, - WM8988_ROUT1V, 7, 1, 0), -SOC_DOUBLE_R_TLV("Output 1 Playback Volume", WM8988_LOUT1V, WM8988_ROUT1V, - 0, 127, 0, out_tlv), - -SOC_DOUBLE_R("Output 2 Playback ZC Switch", WM8988_LOUT2V, - WM8988_ROUT2V, 7, 1, 0), -SOC_DOUBLE_R_TLV("Output 2 Playback Volume", WM8988_LOUT2V, WM8988_ROUT2V, - 0, 127, 0, out_tlv), - -}; - -/* - * DAPM Controls - */ - -static int wm8988_lrc_control(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) -{ - struct snd_soc_codec *codec = w->codec; - u16 adctl2 = wm8988_read_reg_cache(codec, WM8988_ADCTL2); - - /* Use the DAC to gate LRC if active, otherwise use ADC */ - if (wm8988_read_reg_cache(codec, WM8988_PWR2) & 0x180) - adctl2 &= ~0x4; - else - adctl2 |= 0x4; - - return wm8988_write(codec, WM8988_ADCTL2, adctl2); -} - -static const char *wm8988_line_texts[] = { - "Line 1", "Line 2", "PGA", "Differential"}; - -static const unsigned int wm8988_line_values[] = { - 0, 1, 3, 4}; - -static const struct soc_enum wm8988_lline_enum = - SOC_VALUE_ENUM_SINGLE(WM8988_LOUTM1, 0, 7, - ARRAY_SIZE(wm8988_line_texts), - wm8988_line_texts, - wm8988_line_values); -static const struct snd_kcontrol_new wm8988_left_line_controls = - SOC_DAPM_VALUE_ENUM("Route", wm8988_lline_enum); - -static const struct soc_enum wm8988_rline_enum = - SOC_VALUE_ENUM_SINGLE(WM8988_ROUTM1, 0, 7, - ARRAY_SIZE(wm8988_line_texts), - wm8988_line_texts, - wm8988_line_values); -static const struct snd_kcontrol_new wm8988_right_line_controls = - SOC_DAPM_VALUE_ENUM("Route", wm8988_lline_enum); - -/* Left Mixer */ -static const struct snd_kcontrol_new wm8988_left_mixer_controls[] = { - SOC_DAPM_SINGLE("Playback Switch", WM8988_LOUTM1, 8, 1, 0), - SOC_DAPM_SINGLE("Left Bypass Switch", WM8988_LOUTM1, 7, 1, 0), - SOC_DAPM_SINGLE("Right Playback Switch", WM8988_LOUTM2, 8, 1, 0), - SOC_DAPM_SINGLE("Right Bypass Switch", WM8988_LOUTM2, 7, 1, 0), -}; - -/* Right Mixer */ -static const struct snd_kcontrol_new wm8988_right_mixer_controls[] = { - SOC_DAPM_SINGLE("Left Playback Switch", WM8988_ROUTM1, 8, 1, 0), - SOC_DAPM_SINGLE("Left Bypass Switch", WM8988_ROUTM1, 7, 1, 0), - SOC_DAPM_SINGLE("Playback Switch", WM8988_ROUTM2, 8, 1, 0), - SOC_DAPM_SINGLE("Right Bypass Switch", WM8988_ROUTM2, 7, 1, 0), -}; - -static const char *wm8988_pga_sel[] = {"Line 1", "Line 2", "Differential"}; -static const unsigned int wm8988_pga_val[] = { 0, 1, 3 }; - -/* Left PGA Mux */ -static const struct soc_enum wm8988_lpga_enum = - SOC_VALUE_ENUM_SINGLE(WM8988_LADCIN, 6, 3, - ARRAY_SIZE(wm8988_pga_sel), - wm8988_pga_sel, - wm8988_pga_val); -static const struct snd_kcontrol_new wm8988_left_pga_controls = - SOC_DAPM_VALUE_ENUM("Route", wm8988_lpga_enum); - -/* Right PGA Mux */ -static const struct soc_enum wm8988_rpga_enum = - SOC_VALUE_ENUM_SINGLE(WM8988_RADCIN, 6, 3, - ARRAY_SIZE(wm8988_pga_sel), - wm8988_pga_sel, - wm8988_pga_val); -static const struct snd_kcontrol_new wm8988_right_pga_controls = - SOC_DAPM_VALUE_ENUM("Route", wm8988_rpga_enum); - -/* Differential Mux */ -static const char *wm8988_diff_sel[] = {"Line 1", "Line 2"}; -static const struct soc_enum diffmux = - SOC_ENUM_SINGLE(WM8988_ADCIN, 8, 2, wm8988_diff_sel); -static const struct snd_kcontrol_new wm8988_diffmux_controls = - SOC_DAPM_ENUM("Route", diffmux); - -/* Mono ADC Mux */ -static const char *wm8988_mono_mux[] = {"Stereo", "Mono (Left)", - "Mono (Right)", "Digital Mono"}; -static const struct soc_enum monomux = - SOC_ENUM_SINGLE(WM8988_ADCIN, 6, 4, wm8988_mono_mux); -static const struct snd_kcontrol_new wm8988_monomux_controls = - SOC_DAPM_ENUM("Route", monomux); - -static const struct snd_soc_dapm_widget wm8988_dapm_widgets[] = { - SND_SOC_DAPM_MICBIAS("Mic Bias", WM8988_PWR1, 1, 0), - - SND_SOC_DAPM_MUX("Differential Mux", SND_SOC_NOPM, 0, 0, - &wm8988_diffmux_controls), - SND_SOC_DAPM_MUX("Left ADC Mux", SND_SOC_NOPM, 0, 0, - &wm8988_monomux_controls), - SND_SOC_DAPM_MUX("Right ADC Mux", SND_SOC_NOPM, 0, 0, - &wm8988_monomux_controls), - - SND_SOC_DAPM_MUX("Left PGA Mux", WM8988_PWR1, 5, 0, - &wm8988_left_pga_controls), - SND_SOC_DAPM_MUX("Right PGA Mux", WM8988_PWR1, 4, 0, - &wm8988_right_pga_controls), - - SND_SOC_DAPM_MUX("Left Line Mux", SND_SOC_NOPM, 0, 0, - &wm8988_left_line_controls), - SND_SOC_DAPM_MUX("Right Line Mux", SND_SOC_NOPM, 0, 0, - &wm8988_right_line_controls), - - SND_SOC_DAPM_ADC("Right ADC", "Right Capture", WM8988_PWR1, 2, 0), - SND_SOC_DAPM_ADC("Left ADC", "Left Capture", WM8988_PWR1, 3, 0), - - SND_SOC_DAPM_DAC("Right DAC", "Right Playback", WM8988_PWR2, 7, 0), - SND_SOC_DAPM_DAC("Left DAC", "Left Playback", WM8988_PWR2, 8, 0), - - SND_SOC_DAPM_MIXER("Left Mixer", SND_SOC_NOPM, 0, 0, - &wm8988_left_mixer_controls[0], - ARRAY_SIZE(wm8988_left_mixer_controls)), - SND_SOC_DAPM_MIXER("Right Mixer", SND_SOC_NOPM, 0, 0, - &wm8988_right_mixer_controls[0], - ARRAY_SIZE(wm8988_right_mixer_controls)), - - SND_SOC_DAPM_PGA("Right Out 2", WM8988_PWR2, 3, 0, NULL, 0), - SND_SOC_DAPM_PGA("Left Out 2", WM8988_PWR2, 4, 0, NULL, 0), - SND_SOC_DAPM_PGA("Right Out 1", WM8988_PWR2, 5, 0, NULL, 0), - SND_SOC_DAPM_PGA("Left Out 1", WM8988_PWR2, 6, 0, NULL, 0), - - SND_SOC_DAPM_POST("LRC control", wm8988_lrc_control), - - SND_SOC_DAPM_OUTPUT("LOUT1"), - SND_SOC_DAPM_OUTPUT("ROUT1"), - SND_SOC_DAPM_OUTPUT("LOUT2"), - SND_SOC_DAPM_OUTPUT("ROUT2"), - SND_SOC_DAPM_OUTPUT("VREF"), - - SND_SOC_DAPM_INPUT("LINPUT1"), - SND_SOC_DAPM_INPUT("LINPUT2"), - SND_SOC_DAPM_INPUT("RINPUT1"), - SND_SOC_DAPM_INPUT("RINPUT2"), -}; - -static const struct snd_soc_dapm_route audio_map[] = { - - { "Left Line Mux", "Line 1", "LINPUT1" }, - { "Left Line Mux", "Line 2", "LINPUT2" }, - { "Left Line Mux", "PGA", "Left PGA Mux" }, - { "Left Line Mux", "Differential", "Differential Mux" }, - - { "Right Line Mux", "Line 1", "RINPUT1" }, - { "Right Line Mux", "Line 2", "RINPUT2" }, - { "Right Line Mux", "PGA", "Right PGA Mux" }, - { "Right Line Mux", "Differential", "Differential Mux" }, - - { "Left PGA Mux", "Line 1", "LINPUT1" }, - { "Left PGA Mux", "Line 2", "LINPUT2" }, - { "Left PGA Mux", "Differential", "Differential Mux" }, - - { "Right PGA Mux", "Line 1", "RINPUT1" }, - { "Right PGA Mux", "Line 2", "RINPUT2" }, - { "Right PGA Mux", "Differential", "Differential Mux" }, - - { "Differential Mux", "Line 1", "LINPUT1" }, - { "Differential Mux", "Line 1", "RINPUT1" }, - { "Differential Mux", "Line 2", "LINPUT2" }, - { "Differential Mux", "Line 2", "RINPUT2" }, - - { "Left ADC Mux", "Stereo", "Left PGA Mux" }, - { "Left ADC Mux", "Mono (Left)", "Left PGA Mux" }, - { "Left ADC Mux", "Digital Mono", "Left PGA Mux" }, - - { "Right ADC Mux", "Stereo", "Right PGA Mux" }, - { "Right ADC Mux", "Mono (Right)", "Right PGA Mux" }, - { "Right ADC Mux", "Digital Mono", "Right PGA Mux" }, - - { "Left ADC", NULL, "Left ADC Mux" }, - { "Right ADC", NULL, "Right ADC Mux" }, - - { "Left Line Mux", "Line 1", "LINPUT1" }, - { "Left Line Mux", "Line 2", "LINPUT2" }, - { "Left Line Mux", "PGA", "Left PGA Mux" }, - { "Left Line Mux", "Differential", "Differential Mux" }, - - { "Right Line Mux", "Line 1", "RINPUT1" }, - { "Right Line Mux", "Line 2", "RINPUT2" }, - { "Right Line Mux", "PGA", "Right PGA Mux" }, - { "Right Line Mux", "Differential", "Differential Mux" }, - - { "Left Mixer", "Playback Switch", "Left DAC" }, - { "Left Mixer", "Left Bypass Switch", "Left Line Mux" }, - { "Left Mixer", "Right Playback Switch", "Right DAC" }, - { "Left Mixer", "Right Bypass Switch", "Right Line Mux" }, - - { "Right Mixer", "Left Playback Switch", "Left DAC" }, - { "Right Mixer", "Left Bypass Switch", "Left Line Mux" }, - { "Right Mixer", "Playback Switch", "Right DAC" }, - { "Right Mixer", "Right Bypass Switch", "Right Line Mux" }, - - { "Left Out 1", NULL, "Left Mixer" }, - { "LOUT1", NULL, "Left Out 1" }, - { "Right Out 1", NULL, "Right Mixer" }, - { "ROUT1", NULL, "Right Out 1" }, - - { "Left Out 2", NULL, "Left Mixer" }, - { "LOUT2", NULL, "Left Out 2" }, - { "Right Out 2", NULL, "Right Mixer" }, - { "ROUT2", NULL, "Right Out 2" }, -}; - -struct _coeff_div { - u32 mclk; - u32 rate; - u16 fs; - u8 sr:5; - u8 usb:1; -}; - -/* codec hifi mclk clock divider coefficients */ -static const struct _coeff_div coeff_div[] = { - /* 8k */ - {12288000, 8000, 1536, 0x6, 0x0}, - {11289600, 8000, 1408, 0x16, 0x0}, - {18432000, 8000, 2304, 0x7, 0x0}, - {16934400, 8000, 2112, 0x17, 0x0}, - {12000000, 8000, 1500, 0x6, 0x1}, - - /* 11.025k */ - {11289600, 11025, 1024, 0x18, 0x0}, - {16934400, 11025, 1536, 0x19, 0x0}, - {12000000, 11025, 1088, 0x19, 0x1}, - - /* 16k */ - {12288000, 16000, 768, 0xa, 0x0}, - {18432000, 16000, 1152, 0xb, 0x0}, - {12000000, 16000, 750, 0xa, 0x1}, - - /* 22.05k */ - {11289600, 22050, 512, 0x1a, 0x0}, - {16934400, 22050, 768, 0x1b, 0x0}, - {12000000, 22050, 544, 0x1b, 0x1}, - - /* 32k */ - {12288000, 32000, 384, 0xc, 0x0}, - {18432000, 32000, 576, 0xd, 0x0}, - {12000000, 32000, 375, 0xa, 0x1}, - - /* 44.1k */ - {11289600, 44100, 256, 0x10, 0x0}, - {16934400, 44100, 384, 0x11, 0x0}, - {12000000, 44100, 272, 0x11, 0x1}, - - /* 48k */ - {12288000, 48000, 256, 0x0, 0x0}, - {18432000, 48000, 384, 0x1, 0x0}, - {12000000, 48000, 250, 0x0, 0x1}, - - /* 88.2k */ - {11289600, 88200, 128, 0x1e, 0x0}, - {16934400, 88200, 192, 0x1f, 0x0}, - {12000000, 88200, 136, 0x1f, 0x1}, - - /* 96k */ - {12288000, 96000, 128, 0xe, 0x0}, - {18432000, 96000, 192, 0xf, 0x0}, - {12000000, 96000, 125, 0xe, 0x1}, -}; - -static inline int get_coeff(int mclk, int rate) -{ - int i; - - for (i = 0; i < ARRAY_SIZE(coeff_div); i++) { - if (coeff_div[i].rate == rate && coeff_div[i].mclk == mclk) - return i; - } - - return -EINVAL; -} - -/* The set of rates we can generate from the above for each SYSCLK */ - -static unsigned int rates_12288[] = { - 8000, 12000, 16000, 24000, 24000, 32000, 48000, 96000, -}; - -static struct snd_pcm_hw_constraint_list constraints_12288 = { - .count = ARRAY_SIZE(rates_12288), - .list = rates_12288, -}; - -static unsigned int rates_112896[] = { - 8000, 11025, 22050, 44100, -}; - -static struct snd_pcm_hw_constraint_list constraints_112896 = { - .count = ARRAY_SIZE(rates_112896), - .list = rates_112896, -}; - -static unsigned int rates_12[] = { - 8000, 11025, 12000, 16000, 22050, 2400, 32000, 41100, 48000, - 48000, 88235, 96000, -}; - -static struct snd_pcm_hw_constraint_list constraints_12 = { - .count = ARRAY_SIZE(rates_12), - .list = rates_12, -}; - -/* - * Note that this should be called from init rather than from hw_params. - */ -static int wm8988_set_dai_sysclk(struct snd_soc_dai *codec_dai, - int clk_id, unsigned int freq, int dir) -{ - struct snd_soc_codec *codec = codec_dai->codec; - struct wm8988_priv *wm8988 = codec->private_data; - - switch (freq) { - case 11289600: - case 18432000: - case 22579200: - case 36864000: - wm8988->sysclk_constraints = &constraints_112896; - wm8988->sysclk = freq; - return 0; - - case 12288000: - case 16934400: - case 24576000: - case 33868800: - wm8988->sysclk_constraints = &constraints_12288; - wm8988->sysclk = freq; - return 0; - - case 12000000: - case 24000000: - wm8988->sysclk_constraints = &constraints_12; - wm8988->sysclk = freq; - return 0; - } - return -EINVAL; -} - -static int wm8988_set_dai_fmt(struct snd_soc_dai *codec_dai, - unsigned int fmt) -{ - struct snd_soc_codec *codec = codec_dai->codec; - u16 iface = 0; - - /* set master/slave audio interface */ - switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { - case SND_SOC_DAIFMT_CBM_CFM: - iface = 0x0040; - break; - case SND_SOC_DAIFMT_CBS_CFS: - break; - default: - return -EINVAL; - } - - /* interface format */ - switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { - case SND_SOC_DAIFMT_I2S: - iface |= 0x0002; - break; - case SND_SOC_DAIFMT_RIGHT_J: - break; - case SND_SOC_DAIFMT_LEFT_J: - iface |= 0x0001; - break; - case SND_SOC_DAIFMT_DSP_A: - iface |= 0x0003; - break; - case SND_SOC_DAIFMT_DSP_B: - iface |= 0x0013; - break; - default: - return -EINVAL; - } - - /* clock inversion */ - switch (fmt & SND_SOC_DAIFMT_INV_MASK) { - case SND_SOC_DAIFMT_NB_NF: - break; - case SND_SOC_DAIFMT_IB_IF: - iface |= 0x0090; - break; - case SND_SOC_DAIFMT_IB_NF: - iface |= 0x0080; - break; - case SND_SOC_DAIFMT_NB_IF: - iface |= 0x0010; - break; - default: - return -EINVAL; - } - - wm8988_write(codec, WM8988_IFACE, iface); - return 0; -} - -static int wm8988_pcm_startup(struct snd_pcm_substream *substream, - struct snd_soc_dai *dai) -{ - struct snd_soc_codec *codec = dai->codec; - struct wm8988_priv *wm8988 = codec->private_data; - - /* The set of sample rates that can be supported depends on the - * MCLK supplied to the CODEC - enforce this. - */ - if (!wm8988->sysclk) { - dev_err(codec->dev, - "No MCLK configured, call set_sysclk() on init\n"); - return -EINVAL; - } - - snd_pcm_hw_constraint_list(substream->runtime, 0, - SNDRV_PCM_HW_PARAM_RATE, - wm8988->sysclk_constraints); - - return 0; -} - -static int wm8988_pcm_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params, - struct snd_soc_dai *dai) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_device *socdev = rtd->socdev; - struct snd_soc_codec *codec = socdev->card->codec; - struct wm8988_priv *wm8988 = codec->private_data; - u16 iface = wm8988_read_reg_cache(codec, WM8988_IFACE) & 0x1f3; - u16 srate = wm8988_read_reg_cache(codec, WM8988_SRATE) & 0x180; - int coeff; - - coeff = get_coeff(wm8988->sysclk, params_rate(params)); - if (coeff < 0) { - coeff = get_coeff(wm8988->sysclk / 2, params_rate(params)); - srate |= 0x40; - } - if (coeff < 0) { - dev_err(codec->dev, - "Unable to configure sample rate %dHz with %dHz MCLK\n", - params_rate(params), wm8988->sysclk); - return coeff; - } - - /* bit size */ - switch (params_format(params)) { - case SNDRV_PCM_FORMAT_S16_LE: - break; - case SNDRV_PCM_FORMAT_S20_3LE: - iface |= 0x0004; - break; - case SNDRV_PCM_FORMAT_S24_LE: - iface |= 0x0008; - break; - case SNDRV_PCM_FORMAT_S32_LE: - iface |= 0x000c; - break; - } - - /* set iface & srate */ - wm8988_write(codec, WM8988_IFACE, iface); - if (coeff >= 0) - wm8988_write(codec, WM8988_SRATE, srate | - (coeff_div[coeff].sr << 1) | coeff_div[coeff].usb); - - return 0; -} - -static int wm8988_mute(struct snd_soc_dai *dai, int mute) -{ - struct snd_soc_codec *codec = dai->codec; - u16 mute_reg = wm8988_read_reg_cache(codec, WM8988_ADCDAC) & 0xfff7; - - if (mute) - wm8988_write(codec, WM8988_ADCDAC, mute_reg | 0x8); - else - wm8988_write(codec, WM8988_ADCDAC, mute_reg); - return 0; -} - -static int wm8988_set_bias_level(struct snd_soc_codec *codec, - enum snd_soc_bias_level level) -{ - u16 pwr_reg = wm8988_read_reg_cache(codec, WM8988_PWR1) & ~0x1c1; - - switch (level) { - case SND_SOC_BIAS_ON: - break; - - case SND_SOC_BIAS_PREPARE: - /* VREF, VMID=2x50k, digital enabled */ - wm8988_write(codec, WM8988_PWR1, pwr_reg | 0x00c0); - break; - - case SND_SOC_BIAS_STANDBY: - if (codec->bias_level == SND_SOC_BIAS_OFF) { - /* VREF, VMID=2x5k */ - wm8988_write(codec, WM8988_PWR1, pwr_reg | 0x1c1); - - /* Charge caps */ - msleep(100); - } - - /* VREF, VMID=2*500k, digital stopped */ - wm8988_write(codec, WM8988_PWR1, pwr_reg | 0x0141); - break; - - case SND_SOC_BIAS_OFF: - wm8988_write(codec, WM8988_PWR1, 0x0000); - break; - } - codec->bias_level = level; - return 0; -} - -#define WM8988_RATES SNDRV_PCM_RATE_8000_96000 - -#define WM8988_FORMATS (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S20_3LE |\ - SNDRV_PCM_FMTBIT_S24_LE) - -static struct snd_soc_dai_ops wm8988_ops = { - .startup = wm8988_pcm_startup, - .hw_params = wm8988_pcm_hw_params, - .set_fmt = wm8988_set_dai_fmt, - .set_sysclk = wm8988_set_dai_sysclk, - .digital_mute = wm8988_mute, -}; - -struct snd_soc_dai wm8988_dai = { - .name = "WM8988", - .playback = { - .stream_name = "Playback", - .channels_min = 1, - .channels_max = 2, - .rates = WM8988_RATES, - .formats = WM8988_FORMATS, - }, - .capture = { - .stream_name = "Capture", - .channels_min = 1, - .channels_max = 2, - .rates = WM8988_RATES, - .formats = WM8988_FORMATS, - }, - .ops = &wm8988_ops, - .symmetric_rates = 1, -}; -EXPORT_SYMBOL_GPL(wm8988_dai); - -static int wm8988_suspend(struct platform_device *pdev, pm_message_t state) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - - wm8988_set_bias_level(codec, SND_SOC_BIAS_OFF); - return 0; -} - -static int wm8988_resume(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - int i; - u8 data[2]; - u16 *cache = codec->reg_cache; - - /* Sync reg_cache with the hardware */ - for (i = 0; i < WM8988_NUM_REG; i++) { - if (i == WM8988_RESET) - continue; - data[0] = (i << 1) | ((cache[i] >> 8) & 0x0001); - data[1] = cache[i] & 0x00ff; - codec->hw_write(codec->control_data, data, 2); - } - - wm8988_set_bias_level(codec, SND_SOC_BIAS_STANDBY); - - return 0; -} - -static struct snd_soc_codec *wm8988_codec; - -static int wm8988_probe(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec; - int ret = 0; - - if (wm8988_codec == NULL) { - dev_err(&pdev->dev, "Codec device not registered\n"); - return -ENODEV; - } - - socdev->card->codec = wm8988_codec; - codec = wm8988_codec; - - /* register pcms */ - ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1); - if (ret < 0) { - dev_err(codec->dev, "failed to create pcms: %d\n", ret); - goto pcm_err; - } - - snd_soc_add_controls(codec, wm8988_snd_controls, - ARRAY_SIZE(wm8988_snd_controls)); - snd_soc_dapm_new_controls(codec, wm8988_dapm_widgets, - ARRAY_SIZE(wm8988_dapm_widgets)); - snd_soc_dapm_add_routes(codec, audio_map, ARRAY_SIZE(audio_map)); - snd_soc_dapm_new_widgets(codec); - - ret = snd_soc_init_card(socdev); - if (ret < 0) { - dev_err(codec->dev, "failed to register card: %d\n", ret); - goto card_err; - } - - return ret; - -card_err: - snd_soc_free_pcms(socdev); - snd_soc_dapm_free(socdev); -pcm_err: - return ret; -} - -static int wm8988_remove(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - - snd_soc_free_pcms(socdev); - snd_soc_dapm_free(socdev); - - return 0; -} - -struct snd_soc_codec_device soc_codec_dev_wm8988 = { - .probe = wm8988_probe, - .remove = wm8988_remove, - .suspend = wm8988_suspend, - .resume = wm8988_resume, -}; -EXPORT_SYMBOL_GPL(soc_codec_dev_wm8988); - -static int wm8988_register(struct wm8988_priv *wm8988) -{ - struct snd_soc_codec *codec = &wm8988->codec; - int ret; - u16 reg; - - if (wm8988_codec) { - dev_err(codec->dev, "Another WM8988 is registered\n"); - ret = -EINVAL; - goto err; - } - - mutex_init(&codec->mutex); - INIT_LIST_HEAD(&codec->dapm_widgets); - INIT_LIST_HEAD(&codec->dapm_paths); - - codec->private_data = wm8988; - codec->name = "WM8988"; - codec->owner = THIS_MODULE; - codec->read = wm8988_read_reg_cache; - codec->write = wm8988_write; - codec->dai = &wm8988_dai; - codec->num_dai = 1; - codec->reg_cache_size = ARRAY_SIZE(wm8988->reg_cache); - codec->reg_cache = &wm8988->reg_cache; - codec->bias_level = SND_SOC_BIAS_OFF; - codec->set_bias_level = wm8988_set_bias_level; - - memcpy(codec->reg_cache, wm8988_reg, - sizeof(wm8988_reg)); - - ret = wm8988_reset(codec); - if (ret < 0) { - dev_err(codec->dev, "Failed to issue reset\n"); - return ret; - } - - /* set the update bits (we always update left then right) */ - reg = wm8988_read_reg_cache(codec, WM8988_RADC); - wm8988_write(codec, WM8988_RADC, reg | 0x100); - reg = wm8988_read_reg_cache(codec, WM8988_RDAC); - wm8988_write(codec, WM8988_RDAC, reg | 0x0100); - reg = wm8988_read_reg_cache(codec, WM8988_ROUT1V); - wm8988_write(codec, WM8988_ROUT1V, reg | 0x0100); - reg = wm8988_read_reg_cache(codec, WM8988_ROUT2V); - wm8988_write(codec, WM8988_ROUT2V, reg | 0x0100); - reg = wm8988_read_reg_cache(codec, WM8988_RINVOL); - wm8988_write(codec, WM8988_RINVOL, reg | 0x0100); - - wm8988_set_bias_level(&wm8988->codec, SND_SOC_BIAS_STANDBY); - - wm8988_dai.dev = codec->dev; - - wm8988_codec = codec; - - ret = snd_soc_register_codec(codec); - if (ret != 0) { - dev_err(codec->dev, "Failed to register codec: %d\n", ret); - return ret; - } - - ret = snd_soc_register_dai(&wm8988_dai); - if (ret != 0) { - dev_err(codec->dev, "Failed to register DAI: %d\n", ret); - snd_soc_unregister_codec(codec); - return ret; - } - - return 0; - -err: - kfree(wm8988); - return ret; -} - -static void wm8988_unregister(struct wm8988_priv *wm8988) -{ - wm8988_set_bias_level(&wm8988->codec, SND_SOC_BIAS_OFF); - snd_soc_unregister_dai(&wm8988_dai); - snd_soc_unregister_codec(&wm8988->codec); - kfree(wm8988); - wm8988_codec = NULL; -} - -#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE) -static int wm8988_i2c_probe(struct i2c_client *i2c, - const struct i2c_device_id *id) -{ - struct wm8988_priv *wm8988; - struct snd_soc_codec *codec; - - wm8988 = kzalloc(sizeof(struct wm8988_priv), GFP_KERNEL); - if (wm8988 == NULL) - return -ENOMEM; - - codec = &wm8988->codec; - codec->hw_write = (hw_write_t)i2c_master_send; - - i2c_set_clientdata(i2c, wm8988); - codec->control_data = i2c; - - codec->dev = &i2c->dev; - - return wm8988_register(wm8988); -} - -static int wm8988_i2c_remove(struct i2c_client *client) -{ - struct wm8988_priv *wm8988 = i2c_get_clientdata(client); - wm8988_unregister(wm8988); - return 0; -} - -static const struct i2c_device_id wm8988_i2c_id[] = { - { "wm8988", 0 }, - { } -}; -MODULE_DEVICE_TABLE(i2c, wm8988_i2c_id); - -static struct i2c_driver wm8988_i2c_driver = { - .driver = { - .name = "WM8988", - .owner = THIS_MODULE, - }, - .probe = wm8988_i2c_probe, - .remove = wm8988_i2c_remove, - .id_table = wm8988_i2c_id, -}; -#endif - -#if defined(CONFIG_SPI_MASTER) -static int wm8988_spi_write(struct spi_device *spi, const char *data, int len) -{ - struct spi_transfer t; - struct spi_message m; - u8 msg[2]; - - if (len <= 0) - return 0; - - msg[0] = data[0]; - msg[1] = data[1]; - - spi_message_init(&m); - memset(&t, 0, (sizeof t)); - - t.tx_buf = &msg[0]; - t.len = len; - - spi_message_add_tail(&t, &m); - spi_sync(spi, &m); - - return len; -} - -static int __devinit wm8988_spi_probe(struct spi_device *spi) -{ - struct wm8988_priv *wm8988; - struct snd_soc_codec *codec; - - wm8988 = kzalloc(sizeof(struct wm8988_priv), GFP_KERNEL); - if (wm8988 == NULL) - return -ENOMEM; - - codec = &wm8988->codec; - codec->hw_write = (hw_write_t)wm8988_spi_write; - codec->control_data = spi; - codec->dev = &spi->dev; - - spi->dev.driver_data = wm8988; - - return wm8988_register(wm8988); -} - -static int __devexit wm8988_spi_remove(struct spi_device *spi) -{ - struct wm8988_priv *wm8988 = spi->dev.driver_data; - - wm8988_unregister(wm8988); - - return 0; -} - -static struct spi_driver wm8988_spi_driver = { - .driver = { - .name = "wm8988", - .bus = &spi_bus_type, - .owner = THIS_MODULE, - }, - .probe = wm8988_spi_probe, - .remove = __devexit_p(wm8988_spi_remove), -}; -#endif - -static int __init wm8988_modinit(void) -{ - int ret; - -#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE) - ret = i2c_add_driver(&wm8988_i2c_driver); - if (ret != 0) - pr_err("WM8988: Unable to register I2C driver: %d\n", ret); -#endif -#if defined(CONFIG_SPI_MASTER) - ret = spi_register_driver(&wm8988_spi_driver); - if (ret != 0) - pr_err("WM8988: Unable to register SPI driver: %d\n", ret); -#endif - return ret; -} -module_init(wm8988_modinit); - -static void __exit wm8988_exit(void) -{ -#if defined(CONFIG_I2C) || defined(CONFIG_I2C_MODULE) - i2c_del_driver(&wm8988_i2c_driver); -#endif -#if defined(CONFIG_SPI_MASTER) - spi_unregister_driver(&wm8988_spi_driver); -#endif -} -module_exit(wm8988_exit); - - -MODULE_DESCRIPTION("ASoC WM8988 driver"); -MODULE_AUTHOR("Mark Brown "); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/codecs/wm8988.h b/trunk/sound/soc/codecs/wm8988.h deleted file mode 100644 index 4552d37fdd41..000000000000 --- a/trunk/sound/soc/codecs/wm8988.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - * Copyright 2005 Openedhand Ltd. - * - * Author: Richard Purdie - * - * Based on WM8753.h - * - * 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 _WM8988_H -#define _WM8988_H - -/* WM8988 register space */ - -#define WM8988_LINVOL 0x00 -#define WM8988_RINVOL 0x01 -#define WM8988_LOUT1V 0x02 -#define WM8988_ROUT1V 0x03 -#define WM8988_ADCDAC 0x05 -#define WM8988_IFACE 0x07 -#define WM8988_SRATE 0x08 -#define WM8988_LDAC 0x0a -#define WM8988_RDAC 0x0b -#define WM8988_BASS 0x0c -#define WM8988_TREBLE 0x0d -#define WM8988_RESET 0x0f -#define WM8988_3D 0x10 -#define WM8988_ALC1 0x11 -#define WM8988_ALC2 0x12 -#define WM8988_ALC3 0x13 -#define WM8988_NGATE 0x14 -#define WM8988_LADC 0x15 -#define WM8988_RADC 0x16 -#define WM8988_ADCTL1 0x17 -#define WM8988_ADCTL2 0x18 -#define WM8988_PWR1 0x19 -#define WM8988_PWR2 0x1a -#define WM8988_ADCTL3 0x1b -#define WM8988_ADCIN 0x1f -#define WM8988_LADCIN 0x20 -#define WM8988_RADCIN 0x21 -#define WM8988_LOUTM1 0x22 -#define WM8988_LOUTM2 0x23 -#define WM8988_ROUTM1 0x24 -#define WM8988_ROUTM2 0x25 -#define WM8988_LOUT2V 0x28 -#define WM8988_ROUT2V 0x29 -#define WM8988_LPPB 0x43 -#define WM8988_NUM_REG 0x44 - -#define WM8988_SYSCLK 0 - -extern struct snd_soc_dai wm8988_dai; -extern struct snd_soc_codec_device soc_codec_dev_wm8988; - -#endif diff --git a/trunk/sound/soc/codecs/wm8990.c b/trunk/sound/soc/codecs/wm8990.c index d029818350e9..40cd274eb1ef 100644 --- a/trunk/sound/soc/codecs/wm8990.c +++ b/trunk/sound/soc/codecs/wm8990.c @@ -998,7 +998,7 @@ static void pll_factors(struct _pll_div *pll_div, unsigned int target, if ((Ndiv < 6) || (Ndiv > 12)) printk(KERN_WARNING - "WM8990 N value outwith recommended range! N = %u\n", Ndiv); + "WM8990 N value outwith recommended range! N = %d\n", Ndiv); pll_div->n = Ndiv; Nmod = target % source; diff --git a/trunk/sound/soc/codecs/wm9081.c b/trunk/sound/soc/codecs/wm9081.c deleted file mode 100644 index 86fc57e25f97..000000000000 --- a/trunk/sound/soc/codecs/wm9081.c +++ /dev/null @@ -1,1534 +0,0 @@ -/* - * wm9081.c -- WM9081 ALSA SoC Audio driver - * - * Author: Mark Brown - * - * Copyright 2009 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. - * - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include "wm9081.h" - -static u16 wm9081_reg_defaults[] = { - 0x0000, /* R0 - Software Reset */ - 0x0000, /* R1 */ - 0x00B9, /* R2 - Analogue Lineout */ - 0x00B9, /* R3 - Analogue Speaker PGA */ - 0x0001, /* R4 - VMID Control */ - 0x0068, /* R5 - Bias Control 1 */ - 0x0000, /* R6 */ - 0x0000, /* R7 - Analogue Mixer */ - 0x0000, /* R8 - Anti Pop Control */ - 0x01DB, /* R9 - Analogue Speaker 1 */ - 0x0018, /* R10 - Analogue Speaker 2 */ - 0x0180, /* R11 - Power Management */ - 0x0000, /* R12 - Clock Control 1 */ - 0x0038, /* R13 - Clock Control 2 */ - 0x4000, /* R14 - Clock Control 3 */ - 0x0000, /* R15 */ - 0x0000, /* R16 - FLL Control 1 */ - 0x0200, /* R17 - FLL Control 2 */ - 0x0000, /* R18 - FLL Control 3 */ - 0x0204, /* R19 - FLL Control 4 */ - 0x0000, /* R20 - FLL Control 5 */ - 0x0000, /* R21 */ - 0x0000, /* R22 - Audio Interface 1 */ - 0x0002, /* R23 - Audio Interface 2 */ - 0x0008, /* R24 - Audio Interface 3 */ - 0x0022, /* R25 - Audio Interface 4 */ - 0x0000, /* R26 - Interrupt Status */ - 0x0006, /* R27 - Interrupt Status Mask */ - 0x0000, /* R28 - Interrupt Polarity */ - 0x0000, /* R29 - Interrupt Control */ - 0x00C0, /* R30 - DAC Digital 1 */ - 0x0008, /* R31 - DAC Digital 2 */ - 0x09AF, /* R32 - DRC 1 */ - 0x4201, /* R33 - DRC 2 */ - 0x0000, /* R34 - DRC 3 */ - 0x0000, /* R35 - DRC 4 */ - 0x0000, /* R36 */ - 0x0000, /* R37 */ - 0x0000, /* R38 - Write Sequencer 1 */ - 0x0000, /* R39 - Write Sequencer 2 */ - 0x0002, /* R40 - MW Slave 1 */ - 0x0000, /* R41 */ - 0x0000, /* R42 - EQ 1 */ - 0x0000, /* R43 - EQ 2 */ - 0x0FCA, /* R44 - EQ 3 */ - 0x0400, /* R45 - EQ 4 */ - 0x00B8, /* R46 - EQ 5 */ - 0x1EB5, /* R47 - EQ 6 */ - 0xF145, /* R48 - EQ 7 */ - 0x0B75, /* R49 - EQ 8 */ - 0x01C5, /* R50 - EQ 9 */ - 0x169E, /* R51 - EQ 10 */ - 0xF829, /* R52 - EQ 11 */ - 0x07AD, /* R53 - EQ 12 */ - 0x1103, /* R54 - EQ 13 */ - 0x1C58, /* R55 - EQ 14 */ - 0xF373, /* R56 - EQ 15 */ - 0x0A54, /* R57 - EQ 16 */ - 0x0558, /* R58 - EQ 17 */ - 0x0564, /* R59 - EQ 18 */ - 0x0559, /* R60 - EQ 19 */ - 0x4000, /* R61 - EQ 20 */ -}; - -static struct { - int ratio; - int clk_sys_rate; -} clk_sys_rates[] = { - { 64, 0 }, - { 128, 1 }, - { 192, 2 }, - { 256, 3 }, - { 384, 4 }, - { 512, 5 }, - { 768, 6 }, - { 1024, 7 }, - { 1408, 8 }, - { 1536, 9 }, -}; - -static struct { - int rate; - int sample_rate; -} sample_rates[] = { - { 8000, 0 }, - { 11025, 1 }, - { 12000, 2 }, - { 16000, 3 }, - { 22050, 4 }, - { 24000, 5 }, - { 32000, 6 }, - { 44100, 7 }, - { 48000, 8 }, - { 88200, 9 }, - { 96000, 10 }, -}; - -static struct { - int div; /* *10 due to .5s */ - int bclk_div; -} bclk_divs[] = { - { 10, 0 }, - { 15, 1 }, - { 20, 2 }, - { 30, 3 }, - { 40, 4 }, - { 50, 5 }, - { 55, 6 }, - { 60, 7 }, - { 80, 8 }, - { 100, 9 }, - { 110, 10 }, - { 120, 11 }, - { 160, 12 }, - { 200, 13 }, - { 220, 14 }, - { 240, 15 }, - { 250, 16 }, - { 300, 17 }, - { 320, 18 }, - { 440, 19 }, - { 480, 20 }, -}; - -struct wm9081_priv { - struct snd_soc_codec codec; - u16 reg_cache[WM9081_MAX_REGISTER + 1]; - int sysclk_source; - int mclk_rate; - int sysclk_rate; - int fs; - int bclk; - int master; - int fll_fref; - int fll_fout; - struct wm9081_retune_mobile_config *retune; -}; - -static int wm9081_reg_is_volatile(int reg) -{ - switch (reg) { - default: - return 0; - } -} - -static unsigned int wm9081_read_reg_cache(struct snd_soc_codec *codec, - unsigned int reg) -{ - u16 *cache = codec->reg_cache; - BUG_ON(reg > WM9081_MAX_REGISTER); - return cache[reg]; -} - -static unsigned int wm9081_read_hw(struct snd_soc_codec *codec, u8 reg) -{ - struct i2c_msg xfer[2]; - u16 data; - int ret; - struct i2c_client *client = codec->control_data; - - BUG_ON(reg > WM9081_MAX_REGISTER); - - /* Write register */ - xfer[0].addr = client->addr; - xfer[0].flags = 0; - xfer[0].len = 1; - xfer[0].buf = ® - - /* Read data */ - xfer[1].addr = client->addr; - xfer[1].flags = I2C_M_RD; - xfer[1].len = 2; - xfer[1].buf = (u8 *)&data; - - ret = i2c_transfer(client->adapter, xfer, 2); - if (ret != 2) { - dev_err(&client->dev, "i2c_transfer() returned %d\n", ret); - return 0; - } - - return (data >> 8) | ((data & 0xff) << 8); -} - -static unsigned int wm9081_read(struct snd_soc_codec *codec, unsigned int reg) -{ - if (wm9081_reg_is_volatile(reg)) - return wm9081_read_hw(codec, reg); - else - return wm9081_read_reg_cache(codec, reg); -} - -static int wm9081_write(struct snd_soc_codec *codec, unsigned int reg, - unsigned int value) -{ - u16 *cache = codec->reg_cache; - u8 data[3]; - - BUG_ON(reg > WM9081_MAX_REGISTER); - - if (!wm9081_reg_is_volatile(reg)) - cache[reg] = value; - - data[0] = reg; - data[1] = value >> 8; - data[2] = value & 0x00ff; - - if (codec->hw_write(codec->control_data, data, 3) == 3) - return 0; - else - return -EIO; -} - -static int wm9081_reset(struct snd_soc_codec *codec) -{ - return wm9081_write(codec, WM9081_SOFTWARE_RESET, 0); -} - -static const DECLARE_TLV_DB_SCALE(drc_in_tlv, -4500, 75, 0); -static const DECLARE_TLV_DB_SCALE(drc_out_tlv, -2250, 75, 0); -static const DECLARE_TLV_DB_SCALE(drc_min_tlv, -1800, 600, 0); -static unsigned int drc_max_tlv[] = { - TLV_DB_RANGE_HEAD(4), - 0, 0, TLV_DB_SCALE_ITEM(1200, 0, 0), - 1, 1, TLV_DB_SCALE_ITEM(1800, 0, 0), - 2, 2, TLV_DB_SCALE_ITEM(2400, 0, 0), - 3, 3, TLV_DB_SCALE_ITEM(3600, 0, 0), -}; -static const DECLARE_TLV_DB_SCALE(drc_qr_tlv, 1200, 600, 0); -static const DECLARE_TLV_DB_SCALE(drc_startup_tlv, -300, 50, 0); - -static const DECLARE_TLV_DB_SCALE(eq_tlv, -1200, 100, 0); - -static const DECLARE_TLV_DB_SCALE(in_tlv, -600, 600, 0); -static const DECLARE_TLV_DB_SCALE(dac_tlv, -7200, 75, 1); -static const DECLARE_TLV_DB_SCALE(out_tlv, -5700, 100, 0); - -static const char *drc_high_text[] = { - "1", - "1/2", - "1/4", - "1/8", - "1/16", - "0", -}; - -static const struct soc_enum drc_high = - SOC_ENUM_SINGLE(WM9081_DRC_3, 3, 6, drc_high_text); - -static const char *drc_low_text[] = { - "1", - "1/2", - "1/4", - "1/8", - "0", -}; - -static const struct soc_enum drc_low = - SOC_ENUM_SINGLE(WM9081_DRC_3, 0, 5, drc_low_text); - -static const char *drc_atk_text[] = { - "181us", - "181us", - "363us", - "726us", - "1.45ms", - "2.9ms", - "5.8ms", - "11.6ms", - "23.2ms", - "46.4ms", - "92.8ms", - "185.6ms", -}; - -static const struct soc_enum drc_atk = - SOC_ENUM_SINGLE(WM9081_DRC_2, 12, 12, drc_atk_text); - -static const char *drc_dcy_text[] = { - "186ms", - "372ms", - "743ms", - "1.49s", - "2.97s", - "5.94s", - "11.89s", - "23.78s", - "47.56s", -}; - -static const struct soc_enum drc_dcy = - SOC_ENUM_SINGLE(WM9081_DRC_2, 8, 9, drc_dcy_text); - -static const char *drc_qr_dcy_text[] = { - "0.725ms", - "1.45ms", - "5.8ms", -}; - -static const struct soc_enum drc_qr_dcy = - SOC_ENUM_SINGLE(WM9081_DRC_2, 4, 3, drc_qr_dcy_text); - -static const char *dac_deemph_text[] = { - "None", - "32kHz", - "44.1kHz", - "48kHz", -}; - -static const struct soc_enum dac_deemph = - SOC_ENUM_SINGLE(WM9081_DAC_DIGITAL_2, 1, 4, dac_deemph_text); - -static const char *speaker_mode_text[] = { - "Class D", - "Class AB", -}; - -static const struct soc_enum speaker_mode = - SOC_ENUM_SINGLE(WM9081_ANALOGUE_SPEAKER_2, 6, 2, speaker_mode_text); - -static int speaker_mode_get(struct snd_kcontrol *kcontrol, - struct snd_ctl_elem_value *ucontrol) -{ - struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol); - unsigned int reg; - - reg = wm9081_read(codec, WM9081_ANALOGUE_SPEAKER_2); - if (reg & WM9081_SPK_MODE) - ucontrol->value.integer.value[0] = 1; - else - ucontrol->value.integer.value[0] = 0; - - return 0; -} - -/* - * Stop any attempts to change speaker mode while the speaker is enabled. - * - * We also have some special anti-pop controls dependant on speaker - * mode which must be changed along with the mode. - */ -static int speaker_mode_put(struct snd_kcontrol *kcontrol, - struct snd_ctl_elem_value *ucontrol) -{ - struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol); - unsigned int reg_pwr = wm9081_read(codec, WM9081_POWER_MANAGEMENT); - unsigned int reg2 = wm9081_read(codec, WM9081_ANALOGUE_SPEAKER_2); - - /* Are we changing anything? */ - if (ucontrol->value.integer.value[0] == - ((reg2 & WM9081_SPK_MODE) != 0)) - return 0; - - /* Don't try to change modes while enabled */ - if (reg_pwr & WM9081_SPK_ENA) - return -EINVAL; - - if (ucontrol->value.integer.value[0]) { - /* Class AB */ - reg2 &= ~(WM9081_SPK_INV_MUTE | WM9081_OUT_SPK_CTRL); - reg2 |= WM9081_SPK_MODE; - } else { - /* Class D */ - reg2 |= WM9081_SPK_INV_MUTE | WM9081_OUT_SPK_CTRL; - reg2 &= ~WM9081_SPK_MODE; - } - - wm9081_write(codec, WM9081_ANALOGUE_SPEAKER_2, reg2); - - return 0; -} - -static const struct snd_kcontrol_new wm9081_snd_controls[] = { -SOC_SINGLE_TLV("IN1 Volume", WM9081_ANALOGUE_MIXER, 1, 1, 1, in_tlv), -SOC_SINGLE_TLV("IN2 Volume", WM9081_ANALOGUE_MIXER, 3, 1, 1, in_tlv), - -SOC_SINGLE_TLV("Playback Volume", WM9081_DAC_DIGITAL_1, 1, 96, 0, dac_tlv), - -SOC_SINGLE("LINEOUT Switch", WM9081_ANALOGUE_LINEOUT, 7, 1, 1), -SOC_SINGLE("LINEOUT ZC Switch", WM9081_ANALOGUE_LINEOUT, 6, 1, 0), -SOC_SINGLE_TLV("LINEOUT Volume", WM9081_ANALOGUE_LINEOUT, 0, 63, 0, out_tlv), - -SOC_SINGLE("DRC Switch", WM9081_DRC_1, 15, 1, 0), -SOC_ENUM("DRC High Slope", drc_high), -SOC_ENUM("DRC Low Slope", drc_low), -SOC_SINGLE_TLV("DRC Input Volume", WM9081_DRC_4, 5, 60, 1, drc_in_tlv), -SOC_SINGLE_TLV("DRC Output Volume", WM9081_DRC_4, 0, 30, 1, drc_out_tlv), -SOC_SINGLE_TLV("DRC Minimum Volume", WM9081_DRC_2, 2, 3, 1, drc_min_tlv), -SOC_SINGLE_TLV("DRC Maximum Volume", WM9081_DRC_2, 0, 3, 0, drc_max_tlv), -SOC_ENUM("DRC Attack", drc_atk), -SOC_ENUM("DRC Decay", drc_dcy), -SOC_SINGLE("DRC Quick Release Switch", WM9081_DRC_1, 2, 1, 0), -SOC_SINGLE_TLV("DRC Quick Release Volume", WM9081_DRC_2, 6, 3, 0, drc_qr_tlv), -SOC_ENUM("DRC Quick Release Decay", drc_qr_dcy), -SOC_SINGLE_TLV("DRC Startup Volume", WM9081_DRC_1, 6, 18, 0, drc_startup_tlv), - -SOC_SINGLE("EQ Switch", WM9081_EQ_1, 0, 1, 0), - -SOC_SINGLE("Speaker DC Volume", WM9081_ANALOGUE_SPEAKER_1, 3, 5, 0), -SOC_SINGLE("Speaker AC Volume", WM9081_ANALOGUE_SPEAKER_1, 0, 5, 0), -SOC_SINGLE("Speaker Switch", WM9081_ANALOGUE_SPEAKER_PGA, 7, 1, 1), -SOC_SINGLE("Speaker ZC Switch", WM9081_ANALOGUE_SPEAKER_PGA, 6, 1, 0), -SOC_SINGLE_TLV("Speaker Volume", WM9081_ANALOGUE_SPEAKER_PGA, 0, 63, 0, - out_tlv), -SOC_ENUM("DAC Deemphasis", dac_deemph), -SOC_ENUM_EXT("Speaker Mode", speaker_mode, speaker_mode_get, speaker_mode_put), -}; - -static const struct snd_kcontrol_new wm9081_eq_controls[] = { -SOC_SINGLE_TLV("EQ1 Volume", WM9081_EQ_1, 11, 24, 0, eq_tlv), -SOC_SINGLE_TLV("EQ2 Volume", WM9081_EQ_1, 6, 24, 0, eq_tlv), -SOC_SINGLE_TLV("EQ3 Volume", WM9081_EQ_1, 1, 24, 0, eq_tlv), -SOC_SINGLE_TLV("EQ4 Volume", WM9081_EQ_2, 11, 24, 0, eq_tlv), -SOC_SINGLE_TLV("EQ5 Volume", WM9081_EQ_2, 6, 24, 0, eq_tlv), -}; - -static const struct snd_kcontrol_new mixer[] = { -SOC_DAPM_SINGLE("IN1 Switch", WM9081_ANALOGUE_MIXER, 0, 1, 0), -SOC_DAPM_SINGLE("IN2 Switch", WM9081_ANALOGUE_MIXER, 2, 1, 0), -SOC_DAPM_SINGLE("Playback Switch", WM9081_ANALOGUE_MIXER, 4, 1, 0), -}; - -static int speaker_event(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) -{ - struct snd_soc_codec *codec = w->codec; - unsigned int reg = wm9081_read(codec, WM9081_POWER_MANAGEMENT); - - switch (event) { - case SND_SOC_DAPM_POST_PMU: - reg |= WM9081_SPK_ENA; - break; - - case SND_SOC_DAPM_PRE_PMD: - reg &= ~WM9081_SPK_ENA; - break; - } - - wm9081_write(codec, WM9081_POWER_MANAGEMENT, reg); - - return 0; -} - -struct _fll_div { - u16 fll_fratio; - u16 fll_outdiv; - u16 fll_clk_ref_div; - u16 n; - u16 k; -}; - -/* The size in bits of the FLL divide multiplied by 10 - * to allow rounding later */ -#define FIXED_FLL_SIZE ((1 << 16) * 10) - -static struct { - unsigned int min; - unsigned int max; - u16 fll_fratio; - int ratio; -} fll_fratios[] = { - { 0, 64000, 4, 16 }, - { 64000, 128000, 3, 8 }, - { 128000, 256000, 2, 4 }, - { 256000, 1000000, 1, 2 }, - { 1000000, 13500000, 0, 1 }, -}; - -static int fll_factors(struct _fll_div *fll_div, unsigned int Fref, - unsigned int Fout) -{ - u64 Kpart; - unsigned int K, Ndiv, Nmod, target; - unsigned int div; - int i; - - /* Fref must be <=13.5MHz */ - div = 1; - while ((Fref / div) > 13500000) { - div *= 2; - - if (div > 8) { - pr_err("Can't scale %dMHz input down to <=13.5MHz\n", - Fref); - return -EINVAL; - } - } - fll_div->fll_clk_ref_div = div / 2; - - pr_debug("Fref=%u Fout=%u\n", Fref, Fout); - - /* Apply the division for our remaining calculations */ - Fref /= div; - - /* Fvco should be 90-100MHz; don't check the upper bound */ - div = 0; - target = Fout * 2; - while (target < 90000000) { - div++; - target *= 2; - if (div > 7) { - pr_err("Unable to find FLL_OUTDIV for Fout=%uHz\n", - Fout); - return -EINVAL; - } - } - fll_div->fll_outdiv = div; - - pr_debug("Fvco=%dHz\n", target); - - /* Find an appropraite FLL_FRATIO and factor it out of the target */ - for (i = 0; i < ARRAY_SIZE(fll_fratios); i++) { - if (fll_fratios[i].min <= Fref && Fref <= fll_fratios[i].max) { - fll_div->fll_fratio = fll_fratios[i].fll_fratio; - target /= fll_fratios[i].ratio; - break; - } - } - if (i == ARRAY_SIZE(fll_fratios)) { - pr_err("Unable to find FLL_FRATIO for Fref=%uHz\n", Fref); - return -EINVAL; - } - - /* Now, calculate N.K */ - Ndiv = target / Fref; - - fll_div->n = Ndiv; - Nmod = target % Fref; - pr_debug("Nmod=%d\n", Nmod); - - /* Calculate fractional part - scale up so we can round. */ - Kpart = FIXED_FLL_SIZE * (long long)Nmod; - - do_div(Kpart, Fref); - - K = Kpart & 0xFFFFFFFF; - - if ((K % 10) >= 5) - K += 5; - - /* Move down to proper range now rounding is done */ - fll_div->k = K / 10; - - pr_debug("N=%x K=%x FLL_FRATIO=%x FLL_OUTDIV=%x FLL_CLK_REF_DIV=%x\n", - fll_div->n, fll_div->k, - fll_div->fll_fratio, fll_div->fll_outdiv, - fll_div->fll_clk_ref_div); - - return 0; -} - -static int wm9081_set_fll(struct snd_soc_codec *codec, int fll_id, - unsigned int Fref, unsigned int Fout) -{ - struct wm9081_priv *wm9081 = codec->private_data; - u16 reg1, reg4, reg5; - struct _fll_div fll_div; - int ret; - int clk_sys_reg; - - /* Any change? */ - if (Fref == wm9081->fll_fref && Fout == wm9081->fll_fout) - return 0; - - /* Disable the FLL */ - if (Fout == 0) { - dev_dbg(codec->dev, "FLL disabled\n"); - wm9081->fll_fref = 0; - wm9081->fll_fout = 0; - - return 0; - } - - ret = fll_factors(&fll_div, Fref, Fout); - if (ret != 0) - return ret; - - reg5 = wm9081_read(codec, WM9081_FLL_CONTROL_5); - reg5 &= ~WM9081_FLL_CLK_SRC_MASK; - - switch (fll_id) { - case WM9081_SYSCLK_FLL_MCLK: - reg5 |= 0x1; - break; - - default: - dev_err(codec->dev, "Unknown FLL ID %d\n", fll_id); - return -EINVAL; - } - - /* Disable CLK_SYS while we reconfigure */ - clk_sys_reg = wm9081_read(codec, WM9081_CLOCK_CONTROL_3); - if (clk_sys_reg & WM9081_CLK_SYS_ENA) - wm9081_write(codec, WM9081_CLOCK_CONTROL_3, - clk_sys_reg & ~WM9081_CLK_SYS_ENA); - - /* Any FLL configuration change requires that the FLL be - * disabled first. */ - reg1 = wm9081_read(codec, WM9081_FLL_CONTROL_1); - reg1 &= ~WM9081_FLL_ENA; - wm9081_write(codec, WM9081_FLL_CONTROL_1, reg1); - - /* Apply the configuration */ - if (fll_div.k) - reg1 |= WM9081_FLL_FRAC_MASK; - else - reg1 &= ~WM9081_FLL_FRAC_MASK; - wm9081_write(codec, WM9081_FLL_CONTROL_1, reg1); - - wm9081_write(codec, WM9081_FLL_CONTROL_2, - (fll_div.fll_outdiv << WM9081_FLL_OUTDIV_SHIFT) | - (fll_div.fll_fratio << WM9081_FLL_FRATIO_SHIFT)); - wm9081_write(codec, WM9081_FLL_CONTROL_3, fll_div.k); - - reg4 = wm9081_read(codec, WM9081_FLL_CONTROL_4); - reg4 &= ~WM9081_FLL_N_MASK; - reg4 |= fll_div.n << WM9081_FLL_N_SHIFT; - wm9081_write(codec, WM9081_FLL_CONTROL_4, reg4); - - reg5 &= ~WM9081_FLL_CLK_REF_DIV_MASK; - reg5 |= fll_div.fll_clk_ref_div << WM9081_FLL_CLK_REF_DIV_SHIFT; - wm9081_write(codec, WM9081_FLL_CONTROL_5, reg5); - - /* Enable the FLL */ - wm9081_write(codec, WM9081_FLL_CONTROL_1, reg1 | WM9081_FLL_ENA); - - /* Then bring CLK_SYS up again if it was disabled */ - if (clk_sys_reg & WM9081_CLK_SYS_ENA) - wm9081_write(codec, WM9081_CLOCK_CONTROL_3, clk_sys_reg); - - dev_dbg(codec->dev, "FLL enabled at %dHz->%dHz\n", Fref, Fout); - - wm9081->fll_fref = Fref; - wm9081->fll_fout = Fout; - - return 0; -} - -static int configure_clock(struct snd_soc_codec *codec) -{ - struct wm9081_priv *wm9081 = codec->private_data; - int new_sysclk, i, target; - unsigned int reg; - int ret = 0; - int mclkdiv = 0; - int fll = 0; - - switch (wm9081->sysclk_source) { - case WM9081_SYSCLK_MCLK: - if (wm9081->mclk_rate > 12225000) { - mclkdiv = 1; - wm9081->sysclk_rate = wm9081->mclk_rate / 2; - } else { - wm9081->sysclk_rate = wm9081->mclk_rate; - } - wm9081_set_fll(codec, WM9081_SYSCLK_FLL_MCLK, 0, 0); - break; - - case WM9081_SYSCLK_FLL_MCLK: - /* If we have a sample rate calculate a CLK_SYS that - * gives us a suitable DAC configuration, plus BCLK. - * Ideally we would check to see if we can clock - * directly from MCLK and only use the FLL if this is - * not the case, though care must be taken with free - * running mode. - */ - if (wm9081->master && wm9081->bclk) { - /* Make sure we can generate CLK_SYS and BCLK - * and that we've got 3MHz for optimal - * performance. */ - for (i = 0; i < ARRAY_SIZE(clk_sys_rates); i++) { - target = wm9081->fs * clk_sys_rates[i].ratio; - new_sysclk = target; - if (target >= wm9081->bclk && - target > 3000000) - break; - } - } else if (wm9081->fs) { - for (i = 0; i < ARRAY_SIZE(clk_sys_rates); i++) { - new_sysclk = clk_sys_rates[i].ratio - * wm9081->fs; - if (new_sysclk > 3000000) - break; - } - } else { - new_sysclk = 12288000; - } - - ret = wm9081_set_fll(codec, WM9081_SYSCLK_FLL_MCLK, - wm9081->mclk_rate, new_sysclk); - if (ret == 0) { - wm9081->sysclk_rate = new_sysclk; - - /* Switch SYSCLK over to FLL */ - fll = 1; - } else { - wm9081->sysclk_rate = wm9081->mclk_rate; - } - break; - - default: - return -EINVAL; - } - - reg = wm9081_read(codec, WM9081_CLOCK_CONTROL_1); - if (mclkdiv) - reg |= WM9081_MCLKDIV2; - else - reg &= ~WM9081_MCLKDIV2; - wm9081_write(codec, WM9081_CLOCK_CONTROL_1, reg); - - reg = wm9081_read(codec, WM9081_CLOCK_CONTROL_3); - if (fll) - reg |= WM9081_CLK_SRC_SEL; - else - reg &= ~WM9081_CLK_SRC_SEL; - wm9081_write(codec, WM9081_CLOCK_CONTROL_3, reg); - - dev_dbg(codec->dev, "CLK_SYS is %dHz\n", wm9081->sysclk_rate); - - return ret; -} - -static int clk_sys_event(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) -{ - struct snd_soc_codec *codec = w->codec; - struct wm9081_priv *wm9081 = codec->private_data; - - /* This should be done on init() for bypass paths */ - switch (wm9081->sysclk_source) { - case WM9081_SYSCLK_MCLK: - dev_dbg(codec->dev, "Using %dHz MCLK\n", wm9081->mclk_rate); - break; - case WM9081_SYSCLK_FLL_MCLK: - dev_dbg(codec->dev, "Using %dHz MCLK with FLL\n", - wm9081->mclk_rate); - break; - default: - dev_err(codec->dev, "System clock not configured\n"); - return -EINVAL; - } - - switch (event) { - case SND_SOC_DAPM_PRE_PMU: - configure_clock(codec); - break; - - case SND_SOC_DAPM_POST_PMD: - /* Disable the FLL if it's running */ - wm9081_set_fll(codec, 0, 0, 0); - break; - } - - return 0; -} - -static const struct snd_soc_dapm_widget wm9081_dapm_widgets[] = { -SND_SOC_DAPM_INPUT("IN1"), -SND_SOC_DAPM_INPUT("IN2"), - -SND_SOC_DAPM_DAC("DAC", "HiFi Playback", WM9081_POWER_MANAGEMENT, 0, 0), - -SND_SOC_DAPM_MIXER_NAMED_CTL("Mixer", SND_SOC_NOPM, 0, 0, - mixer, ARRAY_SIZE(mixer)), - -SND_SOC_DAPM_PGA("LINEOUT PGA", WM9081_POWER_MANAGEMENT, 4, 0, NULL, 0), - -SND_SOC_DAPM_PGA_E("Speaker PGA", WM9081_POWER_MANAGEMENT, 2, 0, NULL, 0, - speaker_event, - SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_PRE_PMD), - -SND_SOC_DAPM_OUTPUT("LINEOUT"), -SND_SOC_DAPM_OUTPUT("SPKN"), -SND_SOC_DAPM_OUTPUT("SPKP"), - -SND_SOC_DAPM_SUPPLY("CLK_SYS", WM9081_CLOCK_CONTROL_3, 0, 0, clk_sys_event, - SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMD), -SND_SOC_DAPM_SUPPLY("CLK_DSP", WM9081_CLOCK_CONTROL_3, 1, 0, NULL, 0), -SND_SOC_DAPM_SUPPLY("TOCLK", WM9081_CLOCK_CONTROL_3, 2, 0, NULL, 0), -}; - - -static const struct snd_soc_dapm_route audio_paths[] = { - { "DAC", NULL, "CLK_SYS" }, - { "DAC", NULL, "CLK_DSP" }, - - { "Mixer", "IN1 Switch", "IN1" }, - { "Mixer", "IN2 Switch", "IN2" }, - { "Mixer", "Playback Switch", "DAC" }, - - { "LINEOUT PGA", NULL, "Mixer" }, - { "LINEOUT PGA", NULL, "TOCLK" }, - { "LINEOUT PGA", NULL, "CLK_SYS" }, - - { "LINEOUT", NULL, "LINEOUT PGA" }, - - { "Speaker PGA", NULL, "Mixer" }, - { "Speaker PGA", NULL, "TOCLK" }, - { "Speaker PGA", NULL, "CLK_SYS" }, - - { "SPKN", NULL, "Speaker PGA" }, - { "SPKP", NULL, "Speaker PGA" }, -}; - -static int wm9081_set_bias_level(struct snd_soc_codec *codec, - enum snd_soc_bias_level level) -{ - u16 reg; - - switch (level) { - case SND_SOC_BIAS_ON: - break; - - case SND_SOC_BIAS_PREPARE: - /* VMID=2*40k */ - reg = wm9081_read(codec, WM9081_VMID_CONTROL); - reg &= ~WM9081_VMID_SEL_MASK; - reg |= 0x2; - wm9081_write(codec, WM9081_VMID_CONTROL, reg); - - /* Normal bias current */ - reg = wm9081_read(codec, WM9081_BIAS_CONTROL_1); - reg &= ~WM9081_STBY_BIAS_ENA; - wm9081_write(codec, WM9081_BIAS_CONTROL_1, reg); - break; - - case SND_SOC_BIAS_STANDBY: - /* Initial cold start */ - if (codec->bias_level == SND_SOC_BIAS_OFF) { - /* Disable LINEOUT discharge */ - reg = wm9081_read(codec, WM9081_ANTI_POP_CONTROL); - reg &= ~WM9081_LINEOUT_DISCH; - wm9081_write(codec, WM9081_ANTI_POP_CONTROL, reg); - - /* Select startup bias source */ - reg = wm9081_read(codec, WM9081_BIAS_CONTROL_1); - reg |= WM9081_BIAS_SRC | WM9081_BIAS_ENA; - wm9081_write(codec, WM9081_BIAS_CONTROL_1, reg); - - /* VMID 2*4k; Soft VMID ramp enable */ - reg = wm9081_read(codec, WM9081_VMID_CONTROL); - reg |= WM9081_VMID_RAMP | 0x6; - wm9081_write(codec, WM9081_VMID_CONTROL, reg); - - mdelay(100); - - /* Normal bias enable & soft start off */ - reg |= WM9081_BIAS_ENA; - reg &= ~WM9081_VMID_RAMP; - wm9081_write(codec, WM9081_VMID_CONTROL, reg); - - /* Standard bias source */ - reg = wm9081_read(codec, WM9081_BIAS_CONTROL_1); - reg &= ~WM9081_BIAS_SRC; - wm9081_write(codec, WM9081_BIAS_CONTROL_1, reg); - } - - /* VMID 2*240k */ - reg = wm9081_read(codec, WM9081_BIAS_CONTROL_1); - reg &= ~WM9081_VMID_SEL_MASK; - reg |= 0x40; - wm9081_write(codec, WM9081_VMID_CONTROL, reg); - - /* Standby bias current on */ - reg = wm9081_read(codec, WM9081_BIAS_CONTROL_1); - reg |= WM9081_STBY_BIAS_ENA; - wm9081_write(codec, WM9081_BIAS_CONTROL_1, reg); - break; - - case SND_SOC_BIAS_OFF: - /* Startup bias source */ - reg = wm9081_read(codec, WM9081_BIAS_CONTROL_1); - reg |= WM9081_BIAS_SRC; - wm9081_write(codec, WM9081_BIAS_CONTROL_1, reg); - - /* Disable VMID and biases with soft ramping */ - reg = wm9081_read(codec, WM9081_VMID_CONTROL); - reg &= ~(WM9081_VMID_SEL_MASK | WM9081_BIAS_ENA); - reg |= WM9081_VMID_RAMP; - wm9081_write(codec, WM9081_VMID_CONTROL, reg); - - /* Actively discharge LINEOUT */ - reg = wm9081_read(codec, WM9081_ANTI_POP_CONTROL); - reg |= WM9081_LINEOUT_DISCH; - wm9081_write(codec, WM9081_ANTI_POP_CONTROL, reg); - break; - } - - codec->bias_level = level; - - return 0; -} - -static int wm9081_set_dai_fmt(struct snd_soc_dai *dai, - unsigned int fmt) -{ - struct snd_soc_codec *codec = dai->codec; - struct wm9081_priv *wm9081 = codec->private_data; - unsigned int aif2 = wm9081_read(codec, WM9081_AUDIO_INTERFACE_2); - - aif2 &= ~(WM9081_AIF_BCLK_INV | WM9081_AIF_LRCLK_INV | - WM9081_BCLK_DIR | WM9081_LRCLK_DIR | WM9081_AIF_FMT_MASK); - - switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { - case SND_SOC_DAIFMT_CBS_CFS: - wm9081->master = 0; - break; - case SND_SOC_DAIFMT_CBS_CFM: - aif2 |= WM9081_LRCLK_DIR; - wm9081->master = 1; - break; - case SND_SOC_DAIFMT_CBM_CFS: - aif2 |= WM9081_BCLK_DIR; - wm9081->master = 1; - break; - case SND_SOC_DAIFMT_CBM_CFM: - aif2 |= WM9081_LRCLK_DIR | WM9081_BCLK_DIR; - wm9081->master = 1; - break; - default: - return -EINVAL; - } - - switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { - case SND_SOC_DAIFMT_DSP_B: - aif2 |= WM9081_AIF_LRCLK_INV; - case SND_SOC_DAIFMT_DSP_A: - aif2 |= 0x3; - break; - case SND_SOC_DAIFMT_I2S: - aif2 |= 0x2; - break; - case SND_SOC_DAIFMT_RIGHT_J: - break; - case SND_SOC_DAIFMT_LEFT_J: - aif2 |= 0x1; - break; - default: - return -EINVAL; - } - - switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { - case SND_SOC_DAIFMT_DSP_A: - case SND_SOC_DAIFMT_DSP_B: - /* frame inversion not valid for DSP modes */ - switch (fmt & SND_SOC_DAIFMT_INV_MASK) { - case SND_SOC_DAIFMT_NB_NF: - break; - case SND_SOC_DAIFMT_IB_NF: - aif2 |= WM9081_AIF_BCLK_INV; - break; - default: - return -EINVAL; - } - break; - - case SND_SOC_DAIFMT_I2S: - case SND_SOC_DAIFMT_RIGHT_J: - case SND_SOC_DAIFMT_LEFT_J: - switch (fmt & SND_SOC_DAIFMT_INV_MASK) { - case SND_SOC_DAIFMT_NB_NF: - break; - case SND_SOC_DAIFMT_IB_IF: - aif2 |= WM9081_AIF_BCLK_INV | WM9081_AIF_LRCLK_INV; - break; - case SND_SOC_DAIFMT_IB_NF: - aif2 |= WM9081_AIF_BCLK_INV; - break; - case SND_SOC_DAIFMT_NB_IF: - aif2 |= WM9081_AIF_LRCLK_INV; - break; - default: - return -EINVAL; - } - break; - default: - return -EINVAL; - } - - wm9081_write(codec, WM9081_AUDIO_INTERFACE_2, aif2); - - return 0; -} - -static int wm9081_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params, - struct snd_soc_dai *dai) -{ - struct snd_soc_codec *codec = dai->codec; - struct wm9081_priv *wm9081 = codec->private_data; - int ret, i, best, best_val, cur_val; - unsigned int clk_ctrl2, aif1, aif2, aif3, aif4; - - clk_ctrl2 = wm9081_read(codec, WM9081_CLOCK_CONTROL_2); - clk_ctrl2 &= ~(WM9081_CLK_SYS_RATE_MASK | WM9081_SAMPLE_RATE_MASK); - - aif1 = wm9081_read(codec, WM9081_AUDIO_INTERFACE_1); - - aif2 = wm9081_read(codec, WM9081_AUDIO_INTERFACE_2); - aif2 &= ~WM9081_AIF_WL_MASK; - - aif3 = wm9081_read(codec, WM9081_AUDIO_INTERFACE_3); - aif3 &= ~WM9081_BCLK_DIV_MASK; - - aif4 = wm9081_read(codec, WM9081_AUDIO_INTERFACE_4); - aif4 &= ~WM9081_LRCLK_RATE_MASK; - - /* What BCLK do we need? */ - wm9081->fs = params_rate(params); - wm9081->bclk = 2 * wm9081->fs; - switch (params_format(params)) { - case SNDRV_PCM_FORMAT_S16_LE: - wm9081->bclk *= 16; - break; - case SNDRV_PCM_FORMAT_S20_3LE: - wm9081->bclk *= 20; - aif2 |= 0x4; - break; - case SNDRV_PCM_FORMAT_S24_LE: - wm9081->bclk *= 24; - aif2 |= 0x8; - break; - case SNDRV_PCM_FORMAT_S32_LE: - wm9081->bclk *= 32; - aif2 |= 0xc; - break; - default: - return -EINVAL; - } - - if (aif1 & WM9081_AIFDAC_TDM_MODE_MASK) { - int slots = ((aif1 & WM9081_AIFDAC_TDM_MODE_MASK) >> - WM9081_AIFDAC_TDM_MODE_SHIFT) + 1; - wm9081->bclk *= slots; - } - - dev_dbg(codec->dev, "Target BCLK is %dHz\n", wm9081->bclk); - - ret = configure_clock(codec); - if (ret != 0) - return ret; - - /* Select nearest CLK_SYS_RATE */ - best = 0; - best_val = abs((wm9081->sysclk_rate / clk_sys_rates[0].ratio) - - wm9081->fs); - for (i = 1; i < ARRAY_SIZE(clk_sys_rates); i++) { - cur_val = abs((wm9081->sysclk_rate / - clk_sys_rates[i].ratio) - wm9081->fs);; - if (cur_val < best_val) { - best = i; - best_val = cur_val; - } - } - dev_dbg(codec->dev, "Selected CLK_SYS_RATIO of %d\n", - clk_sys_rates[best].ratio); - clk_ctrl2 |= (clk_sys_rates[best].clk_sys_rate - << WM9081_CLK_SYS_RATE_SHIFT); - - /* SAMPLE_RATE */ - best = 0; - best_val = abs(wm9081->fs - sample_rates[0].rate); - for (i = 1; i < ARRAY_SIZE(sample_rates); i++) { - /* Closest match */ - cur_val = abs(wm9081->fs - sample_rates[i].rate); - if (cur_val < best_val) { - best = i; - best_val = cur_val; - } - } - dev_dbg(codec->dev, "Selected SAMPLE_RATE of %dHz\n", - sample_rates[best].rate); - clk_ctrl2 |= (sample_rates[best].sample_rate - << WM9081_SAMPLE_RATE_SHIFT); - - /* BCLK_DIV */ - best = 0; - best_val = INT_MAX; - for (i = 0; i < ARRAY_SIZE(bclk_divs); i++) { - cur_val = ((wm9081->sysclk_rate * 10) / bclk_divs[i].div) - - wm9081->bclk; - if (cur_val < 0) /* Table is sorted */ - break; - if (cur_val < best_val) { - best = i; - best_val = cur_val; - } - } - wm9081->bclk = (wm9081->sysclk_rate * 10) / bclk_divs[best].div; - dev_dbg(codec->dev, "Selected BCLK_DIV of %d for %dHz BCLK\n", - bclk_divs[best].div, wm9081->bclk); - aif3 |= bclk_divs[best].bclk_div; - - /* LRCLK is a simple fraction of BCLK */ - dev_dbg(codec->dev, "LRCLK_RATE is %d\n", wm9081->bclk / wm9081->fs); - aif4 |= wm9081->bclk / wm9081->fs; - - /* Apply a ReTune Mobile configuration if it's in use */ - if (wm9081->retune) { - struct wm9081_retune_mobile_config *retune = wm9081->retune; - struct wm9081_retune_mobile_setting *s; - int eq1; - - best = 0; - best_val = abs(retune->configs[0].rate - wm9081->fs); - for (i = 0; i < retune->num_configs; i++) { - cur_val = abs(retune->configs[i].rate - wm9081->fs); - if (cur_val < best_val) { - best_val = cur_val; - best = i; - } - } - s = &retune->configs[best]; - - dev_dbg(codec->dev, "ReTune Mobile %s tuned for %dHz\n", - s->name, s->rate); - - /* If the EQ is enabled then disable it while we write out */ - eq1 = wm9081_read(codec, WM9081_EQ_1) & WM9081_EQ_ENA; - if (eq1 & WM9081_EQ_ENA) - wm9081_write(codec, WM9081_EQ_1, 0); - - /* Write out the other values */ - for (i = 1; i < ARRAY_SIZE(s->config); i++) - wm9081_write(codec, WM9081_EQ_1 + i, s->config[i]); - - eq1 |= (s->config[0] & ~WM9081_EQ_ENA); - wm9081_write(codec, WM9081_EQ_1, eq1); - } - - wm9081_write(codec, WM9081_CLOCK_CONTROL_2, clk_ctrl2); - wm9081_write(codec, WM9081_AUDIO_INTERFACE_2, aif2); - wm9081_write(codec, WM9081_AUDIO_INTERFACE_3, aif3); - wm9081_write(codec, WM9081_AUDIO_INTERFACE_4, aif4); - - return 0; -} - -static int wm9081_digital_mute(struct snd_soc_dai *codec_dai, int mute) -{ - struct snd_soc_codec *codec = codec_dai->codec; - unsigned int reg; - - reg = wm9081_read(codec, WM9081_DAC_DIGITAL_2); - - if (mute) - reg |= WM9081_DAC_MUTE; - else - reg &= ~WM9081_DAC_MUTE; - - wm9081_write(codec, WM9081_DAC_DIGITAL_2, reg); - - return 0; -} - -static int wm9081_set_sysclk(struct snd_soc_dai *codec_dai, - int clk_id, unsigned int freq, int dir) -{ - struct snd_soc_codec *codec = codec_dai->codec; - struct wm9081_priv *wm9081 = codec->private_data; - - switch (clk_id) { - case WM9081_SYSCLK_MCLK: - case WM9081_SYSCLK_FLL_MCLK: - wm9081->sysclk_source = clk_id; - wm9081->mclk_rate = freq; - break; - - default: - return -EINVAL; - } - - return 0; -} - -static int wm9081_set_tdm_slot(struct snd_soc_dai *dai, - unsigned int mask, int slots) -{ - struct snd_soc_codec *codec = dai->codec; - unsigned int aif1 = wm9081_read(codec, WM9081_AUDIO_INTERFACE_1); - - aif1 &= ~(WM9081_AIFDAC_TDM_SLOT_MASK | WM9081_AIFDAC_TDM_MODE_MASK); - - if (slots < 1 || slots > 4) - return -EINVAL; - - aif1 |= (slots - 1) << WM9081_AIFDAC_TDM_MODE_SHIFT; - - switch (mask) { - case 1: - break; - case 2: - aif1 |= 0x10; - break; - case 4: - aif1 |= 0x20; - break; - case 8: - aif1 |= 0x30; - break; - default: - return -EINVAL; - } - - wm9081_write(codec, WM9081_AUDIO_INTERFACE_1, aif1); - - return 0; -} - -#define WM9081_RATES SNDRV_PCM_RATE_8000_96000 - -#define WM9081_FORMATS \ - (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S20_3LE | \ - SNDRV_PCM_FMTBIT_S24_LE | SNDRV_PCM_FMTBIT_S32_LE) - -static struct snd_soc_dai_ops wm9081_dai_ops = { - .hw_params = wm9081_hw_params, - .set_sysclk = wm9081_set_sysclk, - .set_fmt = wm9081_set_dai_fmt, - .digital_mute = wm9081_digital_mute, - .set_tdm_slot = wm9081_set_tdm_slot, -}; - -/* We report two channels because the CODEC processes a stereo signal, even - * though it is only capable of handling a mono output. - */ -struct snd_soc_dai wm9081_dai = { - .name = "WM9081", - .playback = { - .stream_name = "HiFi Playback", - .channels_min = 1, - .channels_max = 2, - .rates = WM9081_RATES, - .formats = WM9081_FORMATS, - }, - .ops = &wm9081_dai_ops, -}; -EXPORT_SYMBOL_GPL(wm9081_dai); - - -static struct snd_soc_codec *wm9081_codec; - -static int wm9081_probe(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec; - struct wm9081_priv *wm9081; - int ret = 0; - - if (wm9081_codec == NULL) { - dev_err(&pdev->dev, "Codec device not registered\n"); - return -ENODEV; - } - - socdev->card->codec = wm9081_codec; - codec = wm9081_codec; - wm9081 = codec->private_data; - - /* register pcms */ - ret = snd_soc_new_pcms(socdev, SNDRV_DEFAULT_IDX1, SNDRV_DEFAULT_STR1); - if (ret < 0) { - dev_err(codec->dev, "failed to create pcms: %d\n", ret); - goto pcm_err; - } - - snd_soc_add_controls(codec, wm9081_snd_controls, - ARRAY_SIZE(wm9081_snd_controls)); - if (!wm9081->retune) { - dev_dbg(codec->dev, - "No ReTune Mobile data, using normal EQ\n"); - snd_soc_add_controls(codec, wm9081_eq_controls, - ARRAY_SIZE(wm9081_eq_controls)); - } - - snd_soc_dapm_new_controls(codec, wm9081_dapm_widgets, - ARRAY_SIZE(wm9081_dapm_widgets)); - snd_soc_dapm_add_routes(codec, audio_paths, ARRAY_SIZE(audio_paths)); - snd_soc_dapm_new_widgets(codec); - - ret = snd_soc_init_card(socdev); - if (ret < 0) { - dev_err(codec->dev, "failed to register card: %d\n", ret); - goto card_err; - } - - return ret; - -card_err: - snd_soc_free_pcms(socdev); - snd_soc_dapm_free(socdev); -pcm_err: - return ret; -} - -static int wm9081_remove(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - - snd_soc_free_pcms(socdev); - snd_soc_dapm_free(socdev); - - return 0; -} - -#ifdef CONFIG_PM -static int wm9081_suspend(struct platform_device *pdev, pm_message_t state) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - - wm9081_set_bias_level(codec, SND_SOC_BIAS_OFF); - - return 0; -} - -static int wm9081_resume(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct snd_soc_codec *codec = socdev->card->codec; - u16 *reg_cache = codec->reg_cache; - int i; - - for (i = 0; i < codec->reg_cache_size; i++) { - if (i == WM9081_SOFTWARE_RESET) - continue; - - wm9081_write(codec, i, reg_cache[i]); - } - - wm9081_set_bias_level(codec, SND_SOC_BIAS_STANDBY); - - return 0; -} -#else -#define wm9081_suspend NULL -#define wm9081_resume NULL -#endif - -struct snd_soc_codec_device soc_codec_dev_wm9081 = { - .probe = wm9081_probe, - .remove = wm9081_remove, - .suspend = wm9081_suspend, - .resume = wm9081_resume, -}; -EXPORT_SYMBOL_GPL(soc_codec_dev_wm9081); - -static int wm9081_register(struct wm9081_priv *wm9081) -{ - struct snd_soc_codec *codec = &wm9081->codec; - int ret; - u16 reg; - - if (wm9081_codec) { - dev_err(codec->dev, "Another WM9081 is registered\n"); - ret = -EINVAL; - goto err; - } - - mutex_init(&codec->mutex); - INIT_LIST_HEAD(&codec->dapm_widgets); - INIT_LIST_HEAD(&codec->dapm_paths); - - codec->private_data = wm9081; - codec->name = "WM9081"; - codec->owner = THIS_MODULE; - codec->read = wm9081_read; - codec->write = wm9081_write; - codec->dai = &wm9081_dai; - codec->num_dai = 1; - codec->reg_cache_size = ARRAY_SIZE(wm9081->reg_cache); - codec->reg_cache = &wm9081->reg_cache; - codec->bias_level = SND_SOC_BIAS_OFF; - codec->set_bias_level = wm9081_set_bias_level; - - memcpy(codec->reg_cache, wm9081_reg_defaults, - sizeof(wm9081_reg_defaults)); - - reg = wm9081_read_hw(codec, WM9081_SOFTWARE_RESET); - if (reg != 0x9081) { - dev_err(codec->dev, "Device is not a WM9081: ID=0x%x\n", reg); - ret = -EINVAL; - goto err; - } - - ret = wm9081_reset(codec); - if (ret < 0) { - dev_err(codec->dev, "Failed to issue reset\n"); - return ret; - } - - wm9081_set_bias_level(codec, SND_SOC_BIAS_STANDBY); - - /* Enable zero cross by default */ - reg = wm9081_read(codec, WM9081_ANALOGUE_LINEOUT); - wm9081_write(codec, WM9081_ANALOGUE_LINEOUT, reg | WM9081_LINEOUTZC); - reg = wm9081_read(codec, WM9081_ANALOGUE_SPEAKER_PGA); - wm9081_write(codec, WM9081_ANALOGUE_SPEAKER_PGA, - reg | WM9081_SPKPGAZC); - - wm9081_dai.dev = codec->dev; - - wm9081_codec = codec; - - ret = snd_soc_register_codec(codec); - if (ret != 0) { - dev_err(codec->dev, "Failed to register codec: %d\n", ret); - return ret; - } - - ret = snd_soc_register_dai(&wm9081_dai); - if (ret != 0) { - dev_err(codec->dev, "Failed to register DAI: %d\n", ret); - snd_soc_unregister_codec(codec); - return ret; - } - - return 0; - -err: - kfree(wm9081); - return ret; -} - -static void wm9081_unregister(struct wm9081_priv *wm9081) -{ - wm9081_set_bias_level(&wm9081->codec, SND_SOC_BIAS_OFF); - snd_soc_unregister_dai(&wm9081_dai); - snd_soc_unregister_codec(&wm9081->codec); - kfree(wm9081); - wm9081_codec = NULL; -} - -static __devinit int wm9081_i2c_probe(struct i2c_client *i2c, - const struct i2c_device_id *id) -{ - struct wm9081_priv *wm9081; - struct snd_soc_codec *codec; - - wm9081 = kzalloc(sizeof(struct wm9081_priv), GFP_KERNEL); - if (wm9081 == NULL) - return -ENOMEM; - - codec = &wm9081->codec; - codec->hw_write = (hw_write_t)i2c_master_send; - wm9081->retune = i2c->dev.platform_data; - - i2c_set_clientdata(i2c, wm9081); - codec->control_data = i2c; - - codec->dev = &i2c->dev; - - return wm9081_register(wm9081); -} - -static __devexit int wm9081_i2c_remove(struct i2c_client *client) -{ - struct wm9081_priv *wm9081 = i2c_get_clientdata(client); - wm9081_unregister(wm9081); - return 0; -} - -static const struct i2c_device_id wm9081_i2c_id[] = { - { "wm9081", 0 }, - { } -}; -MODULE_DEVICE_TABLE(i2c, wm9081_i2c_id); - -static struct i2c_driver wm9081_i2c_driver = { - .driver = { - .name = "wm9081", - .owner = THIS_MODULE, - }, - .probe = wm9081_i2c_probe, - .remove = __devexit_p(wm9081_i2c_remove), - .id_table = wm9081_i2c_id, -}; - -static int __init wm9081_modinit(void) -{ - int ret; - - ret = i2c_add_driver(&wm9081_i2c_driver); - if (ret != 0) { - printk(KERN_ERR "Failed to register WM9081 I2C driver: %d\n", - ret); - } - - return ret; -} -module_init(wm9081_modinit); - -static void __exit wm9081_exit(void) -{ - i2c_del_driver(&wm9081_i2c_driver); -} -module_exit(wm9081_exit); - - -MODULE_DESCRIPTION("ASoC WM9081 driver"); -MODULE_AUTHOR("Mark Brown "); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/codecs/wm9081.h b/trunk/sound/soc/codecs/wm9081.h deleted file mode 100644 index 42d3bc757021..000000000000 --- a/trunk/sound/soc/codecs/wm9081.h +++ /dev/null @@ -1,787 +0,0 @@ -#ifndef WM9081_H -#define WM9081_H - -/* - * wm9081.c -- WM9081 ALSA SoC Audio driver - * - * Author: Mark Brown - * - * Copyright 2009 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. - */ - -#include - -extern struct snd_soc_dai wm9081_dai; -extern struct snd_soc_codec_device soc_codec_dev_wm9081; - -/* - * SYSCLK sources - */ -#define WM9081_SYSCLK_MCLK 1 /* Use MCLK without FLL */ -#define WM9081_SYSCLK_FLL_MCLK 2 /* Use MCLK, enabling FLL if required */ - -/* - * Register values. - */ -#define WM9081_SOFTWARE_RESET 0x00 -#define WM9081_ANALOGUE_LINEOUT 0x02 -#define WM9081_ANALOGUE_SPEAKER_PGA 0x03 -#define WM9081_VMID_CONTROL 0x04 -#define WM9081_BIAS_CONTROL_1 0x05 -#define WM9081_ANALOGUE_MIXER 0x07 -#define WM9081_ANTI_POP_CONTROL 0x08 -#define WM9081_ANALOGUE_SPEAKER_1 0x09 -#define WM9081_ANALOGUE_SPEAKER_2 0x0A -#define WM9081_POWER_MANAGEMENT 0x0B -#define WM9081_CLOCK_CONTROL_1 0x0C -#define WM9081_CLOCK_CONTROL_2 0x0D -#define WM9081_CLOCK_CONTROL_3 0x0E -#define WM9081_FLL_CONTROL_1 0x10 -#define WM9081_FLL_CONTROL_2 0x11 -#define WM9081_FLL_CONTROL_3 0x12 -#define WM9081_FLL_CONTROL_4 0x13 -#define WM9081_FLL_CONTROL_5 0x14 -#define WM9081_AUDIO_INTERFACE_1 0x16 -#define WM9081_AUDIO_INTERFACE_2 0x17 -#define WM9081_AUDIO_INTERFACE_3 0x18 -#define WM9081_AUDIO_INTERFACE_4 0x19 -#define WM9081_INTERRUPT_STATUS 0x1A -#define WM9081_INTERRUPT_STATUS_MASK 0x1B -#define WM9081_INTERRUPT_POLARITY 0x1C -#define WM9081_INTERRUPT_CONTROL 0x1D -#define WM9081_DAC_DIGITAL_1 0x1E -#define WM9081_DAC_DIGITAL_2 0x1F -#define WM9081_DRC_1 0x20 -#define WM9081_DRC_2 0x21 -#define WM9081_DRC_3 0x22 -#define WM9081_DRC_4 0x23 -#define WM9081_WRITE_SEQUENCER_1 0x26 -#define WM9081_WRITE_SEQUENCER_2 0x27 -#define WM9081_MW_SLAVE_1 0x28 -#define WM9081_EQ_1 0x2A -#define WM9081_EQ_2 0x2B -#define WM9081_EQ_3 0x2C -#define WM9081_EQ_4 0x2D -#define WM9081_EQ_5 0x2E -#define WM9081_EQ_6 0x2F -#define WM9081_EQ_7 0x30 -#define WM9081_EQ_8 0x31 -#define WM9081_EQ_9 0x32 -#define WM9081_EQ_10 0x33 -#define WM9081_EQ_11 0x34 -#define WM9081_EQ_12 0x35 -#define WM9081_EQ_13 0x36 -#define WM9081_EQ_14 0x37 -#define WM9081_EQ_15 0x38 -#define WM9081_EQ_16 0x39 -#define WM9081_EQ_17 0x3A -#define WM9081_EQ_18 0x3B -#define WM9081_EQ_19 0x3C -#define WM9081_EQ_20 0x3D - -#define WM9081_REGISTER_COUNT 55 -#define WM9081_MAX_REGISTER 0x3D - -/* - * Field Definitions. - */ - -/* - * R0 (0x00) - Software Reset - */ -#define WM9081_SW_RST_DEV_ID1_MASK 0xFFFF /* SW_RST_DEV_ID1 - [15:0] */ -#define WM9081_SW_RST_DEV_ID1_SHIFT 0 /* SW_RST_DEV_ID1 - [15:0] */ -#define WM9081_SW_RST_DEV_ID1_WIDTH 16 /* SW_RST_DEV_ID1 - [15:0] */ - -/* - * R2 (0x02) - Analogue Lineout - */ -#define WM9081_LINEOUT_MUTE 0x0080 /* LINEOUT_MUTE */ -#define WM9081_LINEOUT_MUTE_MASK 0x0080 /* LINEOUT_MUTE */ -#define WM9081_LINEOUT_MUTE_SHIFT 7 /* LINEOUT_MUTE */ -#define WM9081_LINEOUT_MUTE_WIDTH 1 /* LINEOUT_MUTE */ -#define WM9081_LINEOUTZC 0x0040 /* LINEOUTZC */ -#define WM9081_LINEOUTZC_MASK 0x0040 /* LINEOUTZC */ -#define WM9081_LINEOUTZC_SHIFT 6 /* LINEOUTZC */ -#define WM9081_LINEOUTZC_WIDTH 1 /* LINEOUTZC */ -#define WM9081_LINEOUT_VOL_MASK 0x003F /* LINEOUT_VOL - [5:0] */ -#define WM9081_LINEOUT_VOL_SHIFT 0 /* LINEOUT_VOL - [5:0] */ -#define WM9081_LINEOUT_VOL_WIDTH 6 /* LINEOUT_VOL - [5:0] */ - -/* - * R3 (0x03) - Analogue Speaker PGA - */ -#define WM9081_SPKPGA_MUTE 0x0080 /* SPKPGA_MUTE */ -#define WM9081_SPKPGA_MUTE_MASK 0x0080 /* SPKPGA_MUTE */ -#define WM9081_SPKPGA_MUTE_SHIFT 7 /* SPKPGA_MUTE */ -#define WM9081_SPKPGA_MUTE_WIDTH 1 /* SPKPGA_MUTE */ -#define WM9081_SPKPGAZC 0x0040 /* SPKPGAZC */ -#define WM9081_SPKPGAZC_MASK 0x0040 /* SPKPGAZC */ -#define WM9081_SPKPGAZC_SHIFT 6 /* SPKPGAZC */ -#define WM9081_SPKPGAZC_WIDTH 1 /* SPKPGAZC */ -#define WM9081_SPKPGA_VOL_MASK 0x003F /* SPKPGA_VOL - [5:0] */ -#define WM9081_SPKPGA_VOL_SHIFT 0 /* SPKPGA_VOL - [5:0] */ -#define WM9081_SPKPGA_VOL_WIDTH 6 /* SPKPGA_VOL - [5:0] */ - -/* - * R4 (0x04) - VMID Control - */ -#define WM9081_VMID_BUF_ENA 0x0020 /* VMID_BUF_ENA */ -#define WM9081_VMID_BUF_ENA_MASK 0x0020 /* VMID_BUF_ENA */ -#define WM9081_VMID_BUF_ENA_SHIFT 5 /* VMID_BUF_ENA */ -#define WM9081_VMID_BUF_ENA_WIDTH 1 /* VMID_BUF_ENA */ -#define WM9081_VMID_RAMP 0x0008 /* VMID_RAMP */ -#define WM9081_VMID_RAMP_MASK 0x0008 /* VMID_RAMP */ -#define WM9081_VMID_RAMP_SHIFT 3 /* VMID_RAMP */ -#define WM9081_VMID_RAMP_WIDTH 1 /* VMID_RAMP */ -#define WM9081_VMID_SEL_MASK 0x0006 /* VMID_SEL - [2:1] */ -#define WM9081_VMID_SEL_SHIFT 1 /* VMID_SEL - [2:1] */ -#define WM9081_VMID_SEL_WIDTH 2 /* VMID_SEL - [2:1] */ -#define WM9081_VMID_FAST_ST 0x0001 /* VMID_FAST_ST */ -#define WM9081_VMID_FAST_ST_MASK 0x0001 /* VMID_FAST_ST */ -#define WM9081_VMID_FAST_ST_SHIFT 0 /* VMID_FAST_ST */ -#define WM9081_VMID_FAST_ST_WIDTH 1 /* VMID_FAST_ST */ - -/* - * R5 (0x05) - Bias Control 1 - */ -#define WM9081_BIAS_SRC 0x0040 /* BIAS_SRC */ -#define WM9081_BIAS_SRC_MASK 0x0040 /* BIAS_SRC */ -#define WM9081_BIAS_SRC_SHIFT 6 /* BIAS_SRC */ -#define WM9081_BIAS_SRC_WIDTH 1 /* BIAS_SRC */ -#define WM9081_STBY_BIAS_LVL 0x0020 /* STBY_BIAS_LVL */ -#define WM9081_STBY_BIAS_LVL_MASK 0x0020 /* STBY_BIAS_LVL */ -#define WM9081_STBY_BIAS_LVL_SHIFT 5 /* STBY_BIAS_LVL */ -#define WM9081_STBY_BIAS_LVL_WIDTH 1 /* STBY_BIAS_LVL */ -#define WM9081_STBY_BIAS_ENA 0x0010 /* STBY_BIAS_ENA */ -#define WM9081_STBY_BIAS_ENA_MASK 0x0010 /* STBY_BIAS_ENA */ -#define WM9081_STBY_BIAS_ENA_SHIFT 4 /* STBY_BIAS_ENA */ -#define WM9081_STBY_BIAS_ENA_WIDTH 1 /* STBY_BIAS_ENA */ -#define WM9081_BIAS_LVL_MASK 0x000C /* BIAS_LVL - [3:2] */ -#define WM9081_BIAS_LVL_SHIFT 2 /* BIAS_LVL - [3:2] */ -#define WM9081_BIAS_LVL_WIDTH 2 /* BIAS_LVL - [3:2] */ -#define WM9081_BIAS_ENA 0x0002 /* BIAS_ENA */ -#define WM9081_BIAS_ENA_MASK 0x0002 /* BIAS_ENA */ -#define WM9081_BIAS_ENA_SHIFT 1 /* BIAS_ENA */ -#define WM9081_BIAS_ENA_WIDTH 1 /* BIAS_ENA */ -#define WM9081_STARTUP_BIAS_ENA 0x0001 /* STARTUP_BIAS_ENA */ -#define WM9081_STARTUP_BIAS_ENA_MASK 0x0001 /* STARTUP_BIAS_ENA */ -#define WM9081_STARTUP_BIAS_ENA_SHIFT 0 /* STARTUP_BIAS_ENA */ -#define WM9081_STARTUP_BIAS_ENA_WIDTH 1 /* STARTUP_BIAS_ENA */ - -/* - * R7 (0x07) - Analogue Mixer - */ -#define WM9081_DAC_SEL 0x0010 /* DAC_SEL */ -#define WM9081_DAC_SEL_MASK 0x0010 /* DAC_SEL */ -#define WM9081_DAC_SEL_SHIFT 4 /* DAC_SEL */ -#define WM9081_DAC_SEL_WIDTH 1 /* DAC_SEL */ -#define WM9081_IN2_VOL 0x0008 /* IN2_VOL */ -#define WM9081_IN2_VOL_MASK 0x0008 /* IN2_VOL */ -#define WM9081_IN2_VOL_SHIFT 3 /* IN2_VOL */ -#define WM9081_IN2_VOL_WIDTH 1 /* IN2_VOL */ -#define WM9081_IN2_ENA 0x0004 /* IN2_ENA */ -#define WM9081_IN2_ENA_MASK 0x0004 /* IN2_ENA */ -#define WM9081_IN2_ENA_SHIFT 2 /* IN2_ENA */ -#define WM9081_IN2_ENA_WIDTH 1 /* IN2_ENA */ -#define WM9081_IN1_VOL 0x0002 /* IN1_VOL */ -#define WM9081_IN1_VOL_MASK 0x0002 /* IN1_VOL */ -#define WM9081_IN1_VOL_SHIFT 1 /* IN1_VOL */ -#define WM9081_IN1_VOL_WIDTH 1 /* IN1_VOL */ -#define WM9081_IN1_ENA 0x0001 /* IN1_ENA */ -#define WM9081_IN1_ENA_MASK 0x0001 /* IN1_ENA */ -#define WM9081_IN1_ENA_SHIFT 0 /* IN1_ENA */ -#define WM9081_IN1_ENA_WIDTH 1 /* IN1_ENA */ - -/* - * R8 (0x08) - Anti Pop Control - */ -#define WM9081_LINEOUT_DISCH 0x0004 /* LINEOUT_DISCH */ -#define WM9081_LINEOUT_DISCH_MASK 0x0004 /* LINEOUT_DISCH */ -#define WM9081_LINEOUT_DISCH_SHIFT 2 /* LINEOUT_DISCH */ -#define WM9081_LINEOUT_DISCH_WIDTH 1 /* LINEOUT_DISCH */ -#define WM9081_LINEOUT_VROI 0x0002 /* LINEOUT_VROI */ -#define WM9081_LINEOUT_VROI_MASK 0x0002 /* LINEOUT_VROI */ -#define WM9081_LINEOUT_VROI_SHIFT 1 /* LINEOUT_VROI */ -#define WM9081_LINEOUT_VROI_WIDTH 1 /* LINEOUT_VROI */ -#define WM9081_LINEOUT_CLAMP 0x0001 /* LINEOUT_CLAMP */ -#define WM9081_LINEOUT_CLAMP_MASK 0x0001 /* LINEOUT_CLAMP */ -#define WM9081_LINEOUT_CLAMP_SHIFT 0 /* LINEOUT_CLAMP */ -#define WM9081_LINEOUT_CLAMP_WIDTH 1 /* LINEOUT_CLAMP */ - -/* - * R9 (0x09) - Analogue Speaker 1 - */ -#define WM9081_SPK_DCGAIN_MASK 0x0038 /* SPK_DCGAIN - [5:3] */ -#define WM9081_SPK_DCGAIN_SHIFT 3 /* SPK_DCGAIN - [5:3] */ -#define WM9081_SPK_DCGAIN_WIDTH 3 /* SPK_DCGAIN - [5:3] */ -#define WM9081_SPK_ACGAIN_MASK 0x0007 /* SPK_ACGAIN - [2:0] */ -#define WM9081_SPK_ACGAIN_SHIFT 0 /* SPK_ACGAIN - [2:0] */ -#define WM9081_SPK_ACGAIN_WIDTH 3 /* SPK_ACGAIN - [2:0] */ - -/* - * R10 (0x0A) - Analogue Speaker 2 - */ -#define WM9081_SPK_MODE 0x0040 /* SPK_MODE */ -#define WM9081_SPK_MODE_MASK 0x0040 /* SPK_MODE */ -#define WM9081_SPK_MODE_SHIFT 6 /* SPK_MODE */ -#define WM9081_SPK_MODE_WIDTH 1 /* SPK_MODE */ -#define WM9081_SPK_INV_MUTE 0x0010 /* SPK_INV_MUTE */ -#define WM9081_SPK_INV_MUTE_MASK 0x0010 /* SPK_INV_MUTE */ -#define WM9081_SPK_INV_MUTE_SHIFT 4 /* SPK_INV_MUTE */ -#define WM9081_SPK_INV_MUTE_WIDTH 1 /* SPK_INV_MUTE */ -#define WM9081_OUT_SPK_CTRL 0x0008 /* OUT_SPK_CTRL */ -#define WM9081_OUT_SPK_CTRL_MASK 0x0008 /* OUT_SPK_CTRL */ -#define WM9081_OUT_SPK_CTRL_SHIFT 3 /* OUT_SPK_CTRL */ -#define WM9081_OUT_SPK_CTRL_WIDTH 1 /* OUT_SPK_CTRL */ - -/* - * R11 (0x0B) - Power Management - */ -#define WM9081_TSHUT_ENA 0x0100 /* TSHUT_ENA */ -#define WM9081_TSHUT_ENA_MASK 0x0100 /* TSHUT_ENA */ -#define WM9081_TSHUT_ENA_SHIFT 8 /* TSHUT_ENA */ -#define WM9081_TSHUT_ENA_WIDTH 1 /* TSHUT_ENA */ -#define WM9081_TSENSE_ENA 0x0080 /* TSENSE_ENA */ -#define WM9081_TSENSE_ENA_MASK 0x0080 /* TSENSE_ENA */ -#define WM9081_TSENSE_ENA_SHIFT 7 /* TSENSE_ENA */ -#define WM9081_TSENSE_ENA_WIDTH 1 /* TSENSE_ENA */ -#define WM9081_TEMP_SHUT 0x0040 /* TEMP_SHUT */ -#define WM9081_TEMP_SHUT_MASK 0x0040 /* TEMP_SHUT */ -#define WM9081_TEMP_SHUT_SHIFT 6 /* TEMP_SHUT */ -#define WM9081_TEMP_SHUT_WIDTH 1 /* TEMP_SHUT */ -#define WM9081_LINEOUT_ENA 0x0010 /* LINEOUT_ENA */ -#define WM9081_LINEOUT_ENA_MASK 0x0010 /* LINEOUT_ENA */ -#define WM9081_LINEOUT_ENA_SHIFT 4 /* LINEOUT_ENA */ -#define WM9081_LINEOUT_ENA_WIDTH 1 /* LINEOUT_ENA */ -#define WM9081_SPKPGA_ENA 0x0004 /* SPKPGA_ENA */ -#define WM9081_SPKPGA_ENA_MASK 0x0004 /* SPKPGA_ENA */ -#define WM9081_SPKPGA_ENA_SHIFT 2 /* SPKPGA_ENA */ -#define WM9081_SPKPGA_ENA_WIDTH 1 /* SPKPGA_ENA */ -#define WM9081_SPK_ENA 0x0002 /* SPK_ENA */ -#define WM9081_SPK_ENA_MASK 0x0002 /* SPK_ENA */ -#define WM9081_SPK_ENA_SHIFT 1 /* SPK_ENA */ -#define WM9081_SPK_ENA_WIDTH 1 /* SPK_ENA */ -#define WM9081_DAC_ENA 0x0001 /* DAC_ENA */ -#define WM9081_DAC_ENA_MASK 0x0001 /* DAC_ENA */ -#define WM9081_DAC_ENA_SHIFT 0 /* DAC_ENA */ -#define WM9081_DAC_ENA_WIDTH 1 /* DAC_ENA */ - -/* - * R12 (0x0C) - Clock Control 1 - */ -#define WM9081_CLK_OP_DIV_MASK 0x1C00 /* CLK_OP_DIV - [12:10] */ -#define WM9081_CLK_OP_DIV_SHIFT 10 /* CLK_OP_DIV - [12:10] */ -#define WM9081_CLK_OP_DIV_WIDTH 3 /* CLK_OP_DIV - [12:10] */ -#define WM9081_CLK_TO_DIV_MASK 0x0300 /* CLK_TO_DIV - [9:8] */ -#define WM9081_CLK_TO_DIV_SHIFT 8 /* CLK_TO_DIV - [9:8] */ -#define WM9081_CLK_TO_DIV_WIDTH 2 /* CLK_TO_DIV - [9:8] */ -#define WM9081_MCLKDIV2 0x0080 /* MCLKDIV2 */ -#define WM9081_MCLKDIV2_MASK 0x0080 /* MCLKDIV2 */ -#define WM9081_MCLKDIV2_SHIFT 7 /* MCLKDIV2 */ -#define WM9081_MCLKDIV2_WIDTH 1 /* MCLKDIV2 */ - -/* - * R13 (0x0D) - Clock Control 2 - */ -#define WM9081_CLK_SYS_RATE_MASK 0x00F0 /* CLK_SYS_RATE - [7:4] */ -#define WM9081_CLK_SYS_RATE_SHIFT 4 /* CLK_SYS_RATE - [7:4] */ -#define WM9081_CLK_SYS_RATE_WIDTH 4 /* CLK_SYS_RATE - [7:4] */ -#define WM9081_SAMPLE_RATE_MASK 0x000F /* SAMPLE_RATE - [3:0] */ -#define WM9081_SAMPLE_RATE_SHIFT 0 /* SAMPLE_RATE - [3:0] */ -#define WM9081_SAMPLE_RATE_WIDTH 4 /* SAMPLE_RATE - [3:0] */ - -/* - * R14 (0x0E) - Clock Control 3 - */ -#define WM9081_CLK_SRC_SEL 0x2000 /* CLK_SRC_SEL */ -#define WM9081_CLK_SRC_SEL_MASK 0x2000 /* CLK_SRC_SEL */ -#define WM9081_CLK_SRC_SEL_SHIFT 13 /* CLK_SRC_SEL */ -#define WM9081_CLK_SRC_SEL_WIDTH 1 /* CLK_SRC_SEL */ -#define WM9081_CLK_OP_ENA 0x0020 /* CLK_OP_ENA */ -#define WM9081_CLK_OP_ENA_MASK 0x0020 /* CLK_OP_ENA */ -#define WM9081_CLK_OP_ENA_SHIFT 5 /* CLK_OP_ENA */ -#define WM9081_CLK_OP_ENA_WIDTH 1 /* CLK_OP_ENA */ -#define WM9081_CLK_TO_ENA 0x0004 /* CLK_TO_ENA */ -#define WM9081_CLK_TO_ENA_MASK 0x0004 /* CLK_TO_ENA */ -#define WM9081_CLK_TO_ENA_SHIFT 2 /* CLK_TO_ENA */ -#define WM9081_CLK_TO_ENA_WIDTH 1 /* CLK_TO_ENA */ -#define WM9081_CLK_DSP_ENA 0x0002 /* CLK_DSP_ENA */ -#define WM9081_CLK_DSP_ENA_MASK 0x0002 /* CLK_DSP_ENA */ -#define WM9081_CLK_DSP_ENA_SHIFT 1 /* CLK_DSP_ENA */ -#define WM9081_CLK_DSP_ENA_WIDTH 1 /* CLK_DSP_ENA */ -#define WM9081_CLK_SYS_ENA 0x0001 /* CLK_SYS_ENA */ -#define WM9081_CLK_SYS_ENA_MASK 0x0001 /* CLK_SYS_ENA */ -#define WM9081_CLK_SYS_ENA_SHIFT 0 /* CLK_SYS_ENA */ -#define WM9081_CLK_SYS_ENA_WIDTH 1 /* CLK_SYS_ENA */ - -/* - * R16 (0x10) - FLL Control 1 - */ -#define WM9081_FLL_HOLD 0x0008 /* FLL_HOLD */ -#define WM9081_FLL_HOLD_MASK 0x0008 /* FLL_HOLD */ -#define WM9081_FLL_HOLD_SHIFT 3 /* FLL_HOLD */ -#define WM9081_FLL_HOLD_WIDTH 1 /* FLL_HOLD */ -#define WM9081_FLL_FRAC 0x0004 /* FLL_FRAC */ -#define WM9081_FLL_FRAC_MASK 0x0004 /* FLL_FRAC */ -#define WM9081_FLL_FRAC_SHIFT 2 /* FLL_FRAC */ -#define WM9081_FLL_FRAC_WIDTH 1 /* FLL_FRAC */ -#define WM9081_FLL_ENA 0x0001 /* FLL_ENA */ -#define WM9081_FLL_ENA_MASK 0x0001 /* FLL_ENA */ -#define WM9081_FLL_ENA_SHIFT 0 /* FLL_ENA */ -#define WM9081_FLL_ENA_WIDTH 1 /* FLL_ENA */ - -/* - * R17 (0x11) - FLL Control 2 - */ -#define WM9081_FLL_OUTDIV_MASK 0x0700 /* FLL_OUTDIV - [10:8] */ -#define WM9081_FLL_OUTDIV_SHIFT 8 /* FLL_OUTDIV - [10:8] */ -#define WM9081_FLL_OUTDIV_WIDTH 3 /* FLL_OUTDIV - [10:8] */ -#define WM9081_FLL_CTRL_RATE_MASK 0x0070 /* FLL_CTRL_RATE - [6:4] */ -#define WM9081_FLL_CTRL_RATE_SHIFT 4 /* FLL_CTRL_RATE - [6:4] */ -#define WM9081_FLL_CTRL_RATE_WIDTH 3 /* FLL_CTRL_RATE - [6:4] */ -#define WM9081_FLL_FRATIO_MASK 0x0007 /* FLL_FRATIO - [2:0] */ -#define WM9081_FLL_FRATIO_SHIFT 0 /* FLL_FRATIO - [2:0] */ -#define WM9081_FLL_FRATIO_WIDTH 3 /* FLL_FRATIO - [2:0] */ - -/* - * R18 (0x12) - FLL Control 3 - */ -#define WM9081_FLL_K_MASK 0xFFFF /* FLL_K - [15:0] */ -#define WM9081_FLL_K_SHIFT 0 /* FLL_K - [15:0] */ -#define WM9081_FLL_K_WIDTH 16 /* FLL_K - [15:0] */ - -/* - * R19 (0x13) - FLL Control 4 - */ -#define WM9081_FLL_N_MASK 0x7FE0 /* FLL_N - [14:5] */ -#define WM9081_FLL_N_SHIFT 5 /* FLL_N - [14:5] */ -#define WM9081_FLL_N_WIDTH 10 /* FLL_N - [14:5] */ -#define WM9081_FLL_GAIN_MASK 0x000F /* FLL_GAIN - [3:0] */ -#define WM9081_FLL_GAIN_SHIFT 0 /* FLL_GAIN - [3:0] */ -#define WM9081_FLL_GAIN_WIDTH 4 /* FLL_GAIN - [3:0] */ - -/* - * R20 (0x14) - FLL Control 5 - */ -#define WM9081_FLL_CLK_REF_DIV_MASK 0x0018 /* FLL_CLK_REF_DIV - [4:3] */ -#define WM9081_FLL_CLK_REF_DIV_SHIFT 3 /* FLL_CLK_REF_DIV - [4:3] */ -#define WM9081_FLL_CLK_REF_DIV_WIDTH 2 /* FLL_CLK_REF_DIV - [4:3] */ -#define WM9081_FLL_CLK_SRC_MASK 0x0003 /* FLL_CLK_SRC - [1:0] */ -#define WM9081_FLL_CLK_SRC_SHIFT 0 /* FLL_CLK_SRC - [1:0] */ -#define WM9081_FLL_CLK_SRC_WIDTH 2 /* FLL_CLK_SRC - [1:0] */ - -/* - * R22 (0x16) - Audio Interface 1 - */ -#define WM9081_AIFDAC_CHAN 0x0040 /* AIFDAC_CHAN */ -#define WM9081_AIFDAC_CHAN_MASK 0x0040 /* AIFDAC_CHAN */ -#define WM9081_AIFDAC_CHAN_SHIFT 6 /* AIFDAC_CHAN */ -#define WM9081_AIFDAC_CHAN_WIDTH 1 /* AIFDAC_CHAN */ -#define WM9081_AIFDAC_TDM_SLOT_MASK 0x0030 /* AIFDAC_TDM_SLOT - [5:4] */ -#define WM9081_AIFDAC_TDM_SLOT_SHIFT 4 /* AIFDAC_TDM_SLOT - [5:4] */ -#define WM9081_AIFDAC_TDM_SLOT_WIDTH 2 /* AIFDAC_TDM_SLOT - [5:4] */ -#define WM9081_AIFDAC_TDM_MODE_MASK 0x000C /* AIFDAC_TDM_MODE - [3:2] */ -#define WM9081_AIFDAC_TDM_MODE_SHIFT 2 /* AIFDAC_TDM_MODE - [3:2] */ -#define WM9081_AIFDAC_TDM_MODE_WIDTH 2 /* AIFDAC_TDM_MODE - [3:2] */ -#define WM9081_DAC_COMP 0x0002 /* DAC_COMP */ -#define WM9081_DAC_COMP_MASK 0x0002 /* DAC_COMP */ -#define WM9081_DAC_COMP_SHIFT 1 /* DAC_COMP */ -#define WM9081_DAC_COMP_WIDTH 1 /* DAC_COMP */ -#define WM9081_DAC_COMPMODE 0x0001 /* DAC_COMPMODE */ -#define WM9081_DAC_COMPMODE_MASK 0x0001 /* DAC_COMPMODE */ -#define WM9081_DAC_COMPMODE_SHIFT 0 /* DAC_COMPMODE */ -#define WM9081_DAC_COMPMODE_WIDTH 1 /* DAC_COMPMODE */ - -/* - * R23 (0x17) - Audio Interface 2 - */ -#define WM9081_AIF_TRIS 0x0200 /* AIF_TRIS */ -#define WM9081_AIF_TRIS_MASK 0x0200 /* AIF_TRIS */ -#define WM9081_AIF_TRIS_SHIFT 9 /* AIF_TRIS */ -#define WM9081_AIF_TRIS_WIDTH 1 /* AIF_TRIS */ -#define WM9081_DAC_DAT_INV 0x0100 /* DAC_DAT_INV */ -#define WM9081_DAC_DAT_INV_MASK 0x0100 /* DAC_DAT_INV */ -#define WM9081_DAC_DAT_INV_SHIFT 8 /* DAC_DAT_INV */ -#define WM9081_DAC_DAT_INV_WIDTH 1 /* DAC_DAT_INV */ -#define WM9081_AIF_BCLK_INV 0x0080 /* AIF_BCLK_INV */ -#define WM9081_AIF_BCLK_INV_MASK 0x0080 /* AIF_BCLK_INV */ -#define WM9081_AIF_BCLK_INV_SHIFT 7 /* AIF_BCLK_INV */ -#define WM9081_AIF_BCLK_INV_WIDTH 1 /* AIF_BCLK_INV */ -#define WM9081_BCLK_DIR 0x0040 /* BCLK_DIR */ -#define WM9081_BCLK_DIR_MASK 0x0040 /* BCLK_DIR */ -#define WM9081_BCLK_DIR_SHIFT 6 /* BCLK_DIR */ -#define WM9081_BCLK_DIR_WIDTH 1 /* BCLK_DIR */ -#define WM9081_LRCLK_DIR 0x0020 /* LRCLK_DIR */ -#define WM9081_LRCLK_DIR_MASK 0x0020 /* LRCLK_DIR */ -#define WM9081_LRCLK_DIR_SHIFT 5 /* LRCLK_DIR */ -#define WM9081_LRCLK_DIR_WIDTH 1 /* LRCLK_DIR */ -#define WM9081_AIF_LRCLK_INV 0x0010 /* AIF_LRCLK_INV */ -#define WM9081_AIF_LRCLK_INV_MASK 0x0010 /* AIF_LRCLK_INV */ -#define WM9081_AIF_LRCLK_INV_SHIFT 4 /* AIF_LRCLK_INV */ -#define WM9081_AIF_LRCLK_INV_WIDTH 1 /* AIF_LRCLK_INV */ -#define WM9081_AIF_WL_MASK 0x000C /* AIF_WL - [3:2] */ -#define WM9081_AIF_WL_SHIFT 2 /* AIF_WL - [3:2] */ -#define WM9081_AIF_WL_WIDTH 2 /* AIF_WL - [3:2] */ -#define WM9081_AIF_FMT_MASK 0x0003 /* AIF_FMT - [1:0] */ -#define WM9081_AIF_FMT_SHIFT 0 /* AIF_FMT - [1:0] */ -#define WM9081_AIF_FMT_WIDTH 2 /* AIF_FMT - [1:0] */ - -/* - * R24 (0x18) - Audio Interface 3 - */ -#define WM9081_BCLK_DIV_MASK 0x001F /* BCLK_DIV - [4:0] */ -#define WM9081_BCLK_DIV_SHIFT 0 /* BCLK_DIV - [4:0] */ -#define WM9081_BCLK_DIV_WIDTH 5 /* BCLK_DIV - [4:0] */ - -/* - * R25 (0x19) - Audio Interface 4 - */ -#define WM9081_LRCLK_RATE_MASK 0x07FF /* LRCLK_RATE - [10:0] */ -#define WM9081_LRCLK_RATE_SHIFT 0 /* LRCLK_RATE - [10:0] */ -#define WM9081_LRCLK_RATE_WIDTH 11 /* LRCLK_RATE - [10:0] */ - -/* - * R26 (0x1A) - Interrupt Status - */ -#define WM9081_WSEQ_BUSY_EINT 0x0004 /* WSEQ_BUSY_EINT */ -#define WM9081_WSEQ_BUSY_EINT_MASK 0x0004 /* WSEQ_BUSY_EINT */ -#define WM9081_WSEQ_BUSY_EINT_SHIFT 2 /* WSEQ_BUSY_EINT */ -#define WM9081_WSEQ_BUSY_EINT_WIDTH 1 /* WSEQ_BUSY_EINT */ -#define WM9081_TSHUT_EINT 0x0001 /* TSHUT_EINT */ -#define WM9081_TSHUT_EINT_MASK 0x0001 /* TSHUT_EINT */ -#define WM9081_TSHUT_EINT_SHIFT 0 /* TSHUT_EINT */ -#define WM9081_TSHUT_EINT_WIDTH 1 /* TSHUT_EINT */ - -/* - * R27 (0x1B) - Interrupt Status Mask - */ -#define WM9081_IM_WSEQ_BUSY_EINT 0x0004 /* IM_WSEQ_BUSY_EINT */ -#define WM9081_IM_WSEQ_BUSY_EINT_MASK 0x0004 /* IM_WSEQ_BUSY_EINT */ -#define WM9081_IM_WSEQ_BUSY_EINT_SHIFT 2 /* IM_WSEQ_BUSY_EINT */ -#define WM9081_IM_WSEQ_BUSY_EINT_WIDTH 1 /* IM_WSEQ_BUSY_EINT */ -#define WM9081_IM_TSHUT_EINT 0x0001 /* IM_TSHUT_EINT */ -#define WM9081_IM_TSHUT_EINT_MASK 0x0001 /* IM_TSHUT_EINT */ -#define WM9081_IM_TSHUT_EINT_SHIFT 0 /* IM_TSHUT_EINT */ -#define WM9081_IM_TSHUT_EINT_WIDTH 1 /* IM_TSHUT_EINT */ - -/* - * R28 (0x1C) - Interrupt Polarity - */ -#define WM9081_TSHUT_INV 0x0001 /* TSHUT_INV */ -#define WM9081_TSHUT_INV_MASK 0x0001 /* TSHUT_INV */ -#define WM9081_TSHUT_INV_SHIFT 0 /* TSHUT_INV */ -#define WM9081_TSHUT_INV_WIDTH 1 /* TSHUT_INV */ - -/* - * R29 (0x1D) - Interrupt Control - */ -#define WM9081_IRQ_POL 0x8000 /* IRQ_POL */ -#define WM9081_IRQ_POL_MASK 0x8000 /* IRQ_POL */ -#define WM9081_IRQ_POL_SHIFT 15 /* IRQ_POL */ -#define WM9081_IRQ_POL_WIDTH 1 /* IRQ_POL */ -#define WM9081_IRQ_OP_CTRL 0x0001 /* IRQ_OP_CTRL */ -#define WM9081_IRQ_OP_CTRL_MASK 0x0001 /* IRQ_OP_CTRL */ -#define WM9081_IRQ_OP_CTRL_SHIFT 0 /* IRQ_OP_CTRL */ -#define WM9081_IRQ_OP_CTRL_WIDTH 1 /* IRQ_OP_CTRL */ - -/* - * R30 (0x1E) - DAC Digital 1 - */ -#define WM9081_DAC_VOL_MASK 0x00FF /* DAC_VOL - [7:0] */ -#define WM9081_DAC_VOL_SHIFT 0 /* DAC_VOL - [7:0] */ -#define WM9081_DAC_VOL_WIDTH 8 /* DAC_VOL - [7:0] */ - -/* - * R31 (0x1F) - DAC Digital 2 - */ -#define WM9081_DAC_MUTERATE 0x0400 /* DAC_MUTERATE */ -#define WM9081_DAC_MUTERATE_MASK 0x0400 /* DAC_MUTERATE */ -#define WM9081_DAC_MUTERATE_SHIFT 10 /* DAC_MUTERATE */ -#define WM9081_DAC_MUTERATE_WIDTH 1 /* DAC_MUTERATE */ -#define WM9081_DAC_MUTEMODE 0x0200 /* DAC_MUTEMODE */ -#define WM9081_DAC_MUTEMODE_MASK 0x0200 /* DAC_MUTEMODE */ -#define WM9081_DAC_MUTEMODE_SHIFT 9 /* DAC_MUTEMODE */ -#define WM9081_DAC_MUTEMODE_WIDTH 1 /* DAC_MUTEMODE */ -#define WM9081_DAC_MUTE 0x0008 /* DAC_MUTE */ -#define WM9081_DAC_MUTE_MASK 0x0008 /* DAC_MUTE */ -#define WM9081_DAC_MUTE_SHIFT 3 /* DAC_MUTE */ -#define WM9081_DAC_MUTE_WIDTH 1 /* DAC_MUTE */ -#define WM9081_DEEMPH_MASK 0x0006 /* DEEMPH - [2:1] */ -#define WM9081_DEEMPH_SHIFT 1 /* DEEMPH - [2:1] */ -#define WM9081_DEEMPH_WIDTH 2 /* DEEMPH - [2:1] */ - -/* - * R32 (0x20) - DRC 1 - */ -#define WM9081_DRC_ENA 0x8000 /* DRC_ENA */ -#define WM9081_DRC_ENA_MASK 0x8000 /* DRC_ENA */ -#define WM9081_DRC_ENA_SHIFT 15 /* DRC_ENA */ -#define WM9081_DRC_ENA_WIDTH 1 /* DRC_ENA */ -#define WM9081_DRC_STARTUP_GAIN_MASK 0x07C0 /* DRC_STARTUP_GAIN - [10:6] */ -#define WM9081_DRC_STARTUP_GAIN_SHIFT 6 /* DRC_STARTUP_GAIN - [10:6] */ -#define WM9081_DRC_STARTUP_GAIN_WIDTH 5 /* DRC_STARTUP_GAIN - [10:6] */ -#define WM9081_DRC_FF_DLY 0x0020 /* DRC_FF_DLY */ -#define WM9081_DRC_FF_DLY_MASK 0x0020 /* DRC_FF_DLY */ -#define WM9081_DRC_FF_DLY_SHIFT 5 /* DRC_FF_DLY */ -#define WM9081_DRC_FF_DLY_WIDTH 1 /* DRC_FF_DLY */ -#define WM9081_DRC_QR 0x0004 /* DRC_QR */ -#define WM9081_DRC_QR_MASK 0x0004 /* DRC_QR */ -#define WM9081_DRC_QR_SHIFT 2 /* DRC_QR */ -#define WM9081_DRC_QR_WIDTH 1 /* DRC_QR */ -#define WM9081_DRC_ANTICLIP 0x0002 /* DRC_ANTICLIP */ -#define WM9081_DRC_ANTICLIP_MASK 0x0002 /* DRC_ANTICLIP */ -#define WM9081_DRC_ANTICLIP_SHIFT 1 /* DRC_ANTICLIP */ -#define WM9081_DRC_ANTICLIP_WIDTH 1 /* DRC_ANTICLIP */ - -/* - * R33 (0x21) - DRC 2 - */ -#define WM9081_DRC_ATK_MASK 0xF000 /* DRC_ATK - [15:12] */ -#define WM9081_DRC_ATK_SHIFT 12 /* DRC_ATK - [15:12] */ -#define WM9081_DRC_ATK_WIDTH 4 /* DRC_ATK - [15:12] */ -#define WM9081_DRC_DCY_MASK 0x0F00 /* DRC_DCY - [11:8] */ -#define WM9081_DRC_DCY_SHIFT 8 /* DRC_DCY - [11:8] */ -#define WM9081_DRC_DCY_WIDTH 4 /* DRC_DCY - [11:8] */ -#define WM9081_DRC_QR_THR_MASK 0x00C0 /* DRC_QR_THR - [7:6] */ -#define WM9081_DRC_QR_THR_SHIFT 6 /* DRC_QR_THR - [7:6] */ -#define WM9081_DRC_QR_THR_WIDTH 2 /* DRC_QR_THR - [7:6] */ -#define WM9081_DRC_QR_DCY_MASK 0x0030 /* DRC_QR_DCY - [5:4] */ -#define WM9081_DRC_QR_DCY_SHIFT 4 /* DRC_QR_DCY - [5:4] */ -#define WM9081_DRC_QR_DCY_WIDTH 2 /* DRC_QR_DCY - [5:4] */ -#define WM9081_DRC_MINGAIN_MASK 0x000C /* DRC_MINGAIN - [3:2] */ -#define WM9081_DRC_MINGAIN_SHIFT 2 /* DRC_MINGAIN - [3:2] */ -#define WM9081_DRC_MINGAIN_WIDTH 2 /* DRC_MINGAIN - [3:2] */ -#define WM9081_DRC_MAXGAIN_MASK 0x0003 /* DRC_MAXGAIN - [1:0] */ -#define WM9081_DRC_MAXGAIN_SHIFT 0 /* DRC_MAXGAIN - [1:0] */ -#define WM9081_DRC_MAXGAIN_WIDTH 2 /* DRC_MAXGAIN - [1:0] */ - -/* - * R34 (0x22) - DRC 3 - */ -#define WM9081_DRC_HI_COMP_MASK 0x0038 /* DRC_HI_COMP - [5:3] */ -#define WM9081_DRC_HI_COMP_SHIFT 3 /* DRC_HI_COMP - [5:3] */ -#define WM9081_DRC_HI_COMP_WIDTH 3 /* DRC_HI_COMP - [5:3] */ -#define WM9081_DRC_LO_COMP_MASK 0x0007 /* DRC_LO_COMP - [2:0] */ -#define WM9081_DRC_LO_COMP_SHIFT 0 /* DRC_LO_COMP - [2:0] */ -#define WM9081_DRC_LO_COMP_WIDTH 3 /* DRC_LO_COMP - [2:0] */ - -/* - * R35 (0x23) - DRC 4 - */ -#define WM9081_DRC_KNEE_IP_MASK 0x07E0 /* DRC_KNEE_IP - [10:5] */ -#define WM9081_DRC_KNEE_IP_SHIFT 5 /* DRC_KNEE_IP - [10:5] */ -#define WM9081_DRC_KNEE_IP_WIDTH 6 /* DRC_KNEE_IP - [10:5] */ -#define WM9081_DRC_KNEE_OP_MASK 0x001F /* DRC_KNEE_OP - [4:0] */ -#define WM9081_DRC_KNEE_OP_SHIFT 0 /* DRC_KNEE_OP - [4:0] */ -#define WM9081_DRC_KNEE_OP_WIDTH 5 /* DRC_KNEE_OP - [4:0] */ - -/* - * R38 (0x26) - Write Sequencer 1 - */ -#define WM9081_WSEQ_ENA 0x8000 /* WSEQ_ENA */ -#define WM9081_WSEQ_ENA_MASK 0x8000 /* WSEQ_ENA */ -#define WM9081_WSEQ_ENA_SHIFT 15 /* WSEQ_ENA */ -#define WM9081_WSEQ_ENA_WIDTH 1 /* WSEQ_ENA */ -#define WM9081_WSEQ_ABORT 0x0200 /* WSEQ_ABORT */ -#define WM9081_WSEQ_ABORT_MASK 0x0200 /* WSEQ_ABORT */ -#define WM9081_WSEQ_ABORT_SHIFT 9 /* WSEQ_ABORT */ -#define WM9081_WSEQ_ABORT_WIDTH 1 /* WSEQ_ABORT */ -#define WM9081_WSEQ_START 0x0100 /* WSEQ_START */ -#define WM9081_WSEQ_START_MASK 0x0100 /* WSEQ_START */ -#define WM9081_WSEQ_START_SHIFT 8 /* WSEQ_START */ -#define WM9081_WSEQ_START_WIDTH 1 /* WSEQ_START */ -#define WM9081_WSEQ_START_INDEX_MASK 0x007F /* WSEQ_START_INDEX - [6:0] */ -#define WM9081_WSEQ_START_INDEX_SHIFT 0 /* WSEQ_START_INDEX - [6:0] */ -#define WM9081_WSEQ_START_INDEX_WIDTH 7 /* WSEQ_START_INDEX - [6:0] */ - -/* - * R39 (0x27) - Write Sequencer 2 - */ -#define WM9081_WSEQ_CURRENT_INDEX_MASK 0x07F0 /* WSEQ_CURRENT_INDEX - [10:4] */ -#define WM9081_WSEQ_CURRENT_INDEX_SHIFT 4 /* WSEQ_CURRENT_INDEX - [10:4] */ -#define WM9081_WSEQ_CURRENT_INDEX_WIDTH 7 /* WSEQ_CURRENT_INDEX - [10:4] */ -#define WM9081_WSEQ_BUSY 0x0001 /* WSEQ_BUSY */ -#define WM9081_WSEQ_BUSY_MASK 0x0001 /* WSEQ_BUSY */ -#define WM9081_WSEQ_BUSY_SHIFT 0 /* WSEQ_BUSY */ -#define WM9081_WSEQ_BUSY_WIDTH 1 /* WSEQ_BUSY */ - -/* - * R40 (0x28) - MW Slave 1 - */ -#define WM9081_SPI_CFG 0x0020 /* SPI_CFG */ -#define WM9081_SPI_CFG_MASK 0x0020 /* SPI_CFG */ -#define WM9081_SPI_CFG_SHIFT 5 /* SPI_CFG */ -#define WM9081_SPI_CFG_WIDTH 1 /* SPI_CFG */ -#define WM9081_SPI_4WIRE 0x0010 /* SPI_4WIRE */ -#define WM9081_SPI_4WIRE_MASK 0x0010 /* SPI_4WIRE */ -#define WM9081_SPI_4WIRE_SHIFT 4 /* SPI_4WIRE */ -#define WM9081_SPI_4WIRE_WIDTH 1 /* SPI_4WIRE */ -#define WM9081_ARA_ENA 0x0008 /* ARA_ENA */ -#define WM9081_ARA_ENA_MASK 0x0008 /* ARA_ENA */ -#define WM9081_ARA_ENA_SHIFT 3 /* ARA_ENA */ -#define WM9081_ARA_ENA_WIDTH 1 /* ARA_ENA */ -#define WM9081_AUTO_INC 0x0002 /* AUTO_INC */ -#define WM9081_AUTO_INC_MASK 0x0002 /* AUTO_INC */ -#define WM9081_AUTO_INC_SHIFT 1 /* AUTO_INC */ -#define WM9081_AUTO_INC_WIDTH 1 /* AUTO_INC */ - -/* - * R42 (0x2A) - EQ 1 - */ -#define WM9081_EQ_B1_GAIN_MASK 0xF800 /* EQ_B1_GAIN - [15:11] */ -#define WM9081_EQ_B1_GAIN_SHIFT 11 /* EQ_B1_GAIN - [15:11] */ -#define WM9081_EQ_B1_GAIN_WIDTH 5 /* EQ_B1_GAIN - [15:11] */ -#define WM9081_EQ_B2_GAIN_MASK 0x07C0 /* EQ_B2_GAIN - [10:6] */ -#define WM9081_EQ_B2_GAIN_SHIFT 6 /* EQ_B2_GAIN - [10:6] */ -#define WM9081_EQ_B2_GAIN_WIDTH 5 /* EQ_B2_GAIN - [10:6] */ -#define WM9081_EQ_B4_GAIN_MASK 0x003E /* EQ_B4_GAIN - [5:1] */ -#define WM9081_EQ_B4_GAIN_SHIFT 1 /* EQ_B4_GAIN - [5:1] */ -#define WM9081_EQ_B4_GAIN_WIDTH 5 /* EQ_B4_GAIN - [5:1] */ -#define WM9081_EQ_ENA 0x0001 /* EQ_ENA */ -#define WM9081_EQ_ENA_MASK 0x0001 /* EQ_ENA */ -#define WM9081_EQ_ENA_SHIFT 0 /* EQ_ENA */ -#define WM9081_EQ_ENA_WIDTH 1 /* EQ_ENA */ - -/* - * R43 (0x2B) - EQ 2 - */ -#define WM9081_EQ_B3_GAIN_MASK 0xF800 /* EQ_B3_GAIN - [15:11] */ -#define WM9081_EQ_B3_GAIN_SHIFT 11 /* EQ_B3_GAIN - [15:11] */ -#define WM9081_EQ_B3_GAIN_WIDTH 5 /* EQ_B3_GAIN - [15:11] */ -#define WM9081_EQ_B5_GAIN_MASK 0x07C0 /* EQ_B5_GAIN - [10:6] */ -#define WM9081_EQ_B5_GAIN_SHIFT 6 /* EQ_B5_GAIN - [10:6] */ -#define WM9081_EQ_B5_GAIN_WIDTH 5 /* EQ_B5_GAIN - [10:6] */ - -/* - * R44 (0x2C) - EQ 3 - */ -#define WM9081_EQ_B1_A_MASK 0xFFFF /* EQ_B1_A - [15:0] */ -#define WM9081_EQ_B1_A_SHIFT 0 /* EQ_B1_A - [15:0] */ -#define WM9081_EQ_B1_A_WIDTH 16 /* EQ_B1_A - [15:0] */ - -/* - * R45 (0x2D) - EQ 4 - */ -#define WM9081_EQ_B1_B_MASK 0xFFFF /* EQ_B1_B - [15:0] */ -#define WM9081_EQ_B1_B_SHIFT 0 /* EQ_B1_B - [15:0] */ -#define WM9081_EQ_B1_B_WIDTH 16 /* EQ_B1_B - [15:0] */ - -/* - * R46 (0x2E) - EQ 5 - */ -#define WM9081_EQ_B1_PG_MASK 0xFFFF /* EQ_B1_PG - [15:0] */ -#define WM9081_EQ_B1_PG_SHIFT 0 /* EQ_B1_PG - [15:0] */ -#define WM9081_EQ_B1_PG_WIDTH 16 /* EQ_B1_PG - [15:0] */ - -/* - * R47 (0x2F) - EQ 6 - */ -#define WM9081_EQ_B2_A_MASK 0xFFFF /* EQ_B2_A - [15:0] */ -#define WM9081_EQ_B2_A_SHIFT 0 /* EQ_B2_A - [15:0] */ -#define WM9081_EQ_B2_A_WIDTH 16 /* EQ_B2_A - [15:0] */ - -/* - * R48 (0x30) - EQ 7 - */ -#define WM9081_EQ_B2_B_MASK 0xFFFF /* EQ_B2_B - [15:0] */ -#define WM9081_EQ_B2_B_SHIFT 0 /* EQ_B2_B - [15:0] */ -#define WM9081_EQ_B2_B_WIDTH 16 /* EQ_B2_B - [15:0] */ - -/* - * R49 (0x31) - EQ 8 - */ -#define WM9081_EQ_B2_C_MASK 0xFFFF /* EQ_B2_C - [15:0] */ -#define WM9081_EQ_B2_C_SHIFT 0 /* EQ_B2_C - [15:0] */ -#define WM9081_EQ_B2_C_WIDTH 16 /* EQ_B2_C - [15:0] */ - -/* - * R50 (0x32) - EQ 9 - */ -#define WM9081_EQ_B2_PG_MASK 0xFFFF /* EQ_B2_PG - [15:0] */ -#define WM9081_EQ_B2_PG_SHIFT 0 /* EQ_B2_PG - [15:0] */ -#define WM9081_EQ_B2_PG_WIDTH 16 /* EQ_B2_PG - [15:0] */ - -/* - * R51 (0x33) - EQ 10 - */ -#define WM9081_EQ_B4_A_MASK 0xFFFF /* EQ_B4_A - [15:0] */ -#define WM9081_EQ_B4_A_SHIFT 0 /* EQ_B4_A - [15:0] */ -#define WM9081_EQ_B4_A_WIDTH 16 /* EQ_B4_A - [15:0] */ - -/* - * R52 (0x34) - EQ 11 - */ -#define WM9081_EQ_B4_B_MASK 0xFFFF /* EQ_B4_B - [15:0] */ -#define WM9081_EQ_B4_B_SHIFT 0 /* EQ_B4_B - [15:0] */ -#define WM9081_EQ_B4_B_WIDTH 16 /* EQ_B4_B - [15:0] */ - -/* - * R53 (0x35) - EQ 12 - */ -#define WM9081_EQ_B4_C_MASK 0xFFFF /* EQ_B4_C - [15:0] */ -#define WM9081_EQ_B4_C_SHIFT 0 /* EQ_B4_C - [15:0] */ -#define WM9081_EQ_B4_C_WIDTH 16 /* EQ_B4_C - [15:0] */ - -/* - * R54 (0x36) - EQ 13 - */ -#define WM9081_EQ_B4_PG_MASK 0xFFFF /* EQ_B4_PG - [15:0] */ -#define WM9081_EQ_B4_PG_SHIFT 0 /* EQ_B4_PG - [15:0] */ -#define WM9081_EQ_B4_PG_WIDTH 16 /* EQ_B4_PG - [15:0] */ - -/* - * R55 (0x37) - EQ 14 - */ -#define WM9081_EQ_B3_A_MASK 0xFFFF /* EQ_B3_A - [15:0] */ -#define WM9081_EQ_B3_A_SHIFT 0 /* EQ_B3_A - [15:0] */ -#define WM9081_EQ_B3_A_WIDTH 16 /* EQ_B3_A - [15:0] */ - -/* - * R56 (0x38) - EQ 15 - */ -#define WM9081_EQ_B3_B_MASK 0xFFFF /* EQ_B3_B - [15:0] */ -#define WM9081_EQ_B3_B_SHIFT 0 /* EQ_B3_B - [15:0] */ -#define WM9081_EQ_B3_B_WIDTH 16 /* EQ_B3_B - [15:0] */ - -/* - * R57 (0x39) - EQ 16 - */ -#define WM9081_EQ_B3_C_MASK 0xFFFF /* EQ_B3_C - [15:0] */ -#define WM9081_EQ_B3_C_SHIFT 0 /* EQ_B3_C - [15:0] */ -#define WM9081_EQ_B3_C_WIDTH 16 /* EQ_B3_C - [15:0] */ - -/* - * R58 (0x3A) - EQ 17 - */ -#define WM9081_EQ_B3_PG_MASK 0xFFFF /* EQ_B3_PG - [15:0] */ -#define WM9081_EQ_B3_PG_SHIFT 0 /* EQ_B3_PG - [15:0] */ -#define WM9081_EQ_B3_PG_WIDTH 16 /* EQ_B3_PG - [15:0] */ - -/* - * R59 (0x3B) - EQ 18 - */ -#define WM9081_EQ_B5_A_MASK 0xFFFF /* EQ_B5_A - [15:0] */ -#define WM9081_EQ_B5_A_SHIFT 0 /* EQ_B5_A - [15:0] */ -#define WM9081_EQ_B5_A_WIDTH 16 /* EQ_B5_A - [15:0] */ - -/* - * R60 (0x3C) - EQ 19 - */ -#define WM9081_EQ_B5_B_MASK 0xFFFF /* EQ_B5_B - [15:0] */ -#define WM9081_EQ_B5_B_SHIFT 0 /* EQ_B5_B - [15:0] */ -#define WM9081_EQ_B5_B_WIDTH 16 /* EQ_B5_B - [15:0] */ - -/* - * R61 (0x3D) - EQ 20 - */ -#define WM9081_EQ_B5_PG_MASK 0xFFFF /* EQ_B5_PG - [15:0] */ -#define WM9081_EQ_B5_PG_SHIFT 0 /* EQ_B5_PG - [15:0] */ -#define WM9081_EQ_B5_PG_WIDTH 16 /* EQ_B5_PG - [15:0] */ - - -#endif diff --git a/trunk/sound/soc/codecs/wm9705.c b/trunk/sound/soc/codecs/wm9705.c index fa88b463e71f..c2d1a7a18fa3 100644 --- a/trunk/sound/soc/codecs/wm9705.c +++ b/trunk/sound/soc/codecs/wm9705.c @@ -282,14 +282,14 @@ struct snd_soc_dai wm9705_dai[] = { .channels_min = 1, .channels_max = 2, .rates = WM9705_AC97_RATES, - .formats = SND_SOC_STD_AC97_FMTS, + .formats = SNDRV_PCM_FMTBIT_S16_LE, }, .capture = { .stream_name = "HiFi Capture", .channels_min = 1, .channels_max = 2, .rates = WM9705_AC97_RATES, - .formats = SND_SOC_STD_AC97_FMTS, + .formats = SNDRV_PCM_FMTBIT_S16_LE, }, .ops = &wm9705_dai_ops, }, diff --git a/trunk/sound/soc/codecs/wm9712.c b/trunk/sound/soc/codecs/wm9712.c index 1fd4e88f50cf..765cf1e7369e 100644 --- a/trunk/sound/soc/codecs/wm9712.c +++ b/trunk/sound/soc/codecs/wm9712.c @@ -534,13 +534,13 @@ struct snd_soc_dai wm9712_dai[] = { .channels_min = 1, .channels_max = 2, .rates = WM9712_AC97_RATES, - .formats = SND_SOC_STD_AC97_FMTS,}, + .formats = SNDRV_PCM_FMTBIT_S16_LE,}, .capture = { .stream_name = "HiFi Capture", .channels_min = 1, .channels_max = 2, .rates = WM9712_AC97_RATES, - .formats = SND_SOC_STD_AC97_FMTS,}, + .formats = SNDRV_PCM_FMTBIT_S16_LE,}, .ops = &wm9712_dai_ops_hifi, }, { @@ -550,7 +550,7 @@ struct snd_soc_dai wm9712_dai[] = { .channels_min = 1, .channels_max = 1, .rates = WM9712_AC97_RATES, - .formats = SND_SOC_STD_AC97_FMTS,}, + .formats = SNDRV_PCM_FMTBIT_S16_LE,}, .ops = &wm9712_dai_ops_aux, } }; @@ -585,8 +585,6 @@ static int wm9712_reset(struct snd_soc_codec *codec, int try_warm) } soc_ac97_ops.reset(codec->ac97); - if (soc_ac97_ops.warm_reset) - soc_ac97_ops.warm_reset(codec->ac97); if (ac97_read(codec, 0) != wm9712_reg[0]) goto err; return 0; diff --git a/trunk/sound/soc/codecs/wm9713.c b/trunk/sound/soc/codecs/wm9713.c index abed37acf787..523bad077fa0 100644 --- a/trunk/sound/soc/codecs/wm9713.c +++ b/trunk/sound/soc/codecs/wm9713.c @@ -189,26 +189,6 @@ SOC_SINGLE("3D Lower Cut-off Switch", AC97_REC_GAIN_MIC, 4, 1, 0), SOC_SINGLE("3D Depth", AC97_REC_GAIN_MIC, 0, 15, 1), }; -static int wm9713_voice_shutdown(struct snd_soc_dapm_widget *w, - struct snd_kcontrol *kcontrol, int event) -{ - struct snd_soc_codec *codec = w->codec; - u16 status, rate; - - BUG_ON(event != SND_SOC_DAPM_PRE_PMD); - - /* Gracefully shut down the voice interface. */ - status = ac97_read(codec, AC97_EXTENDED_MID) | 0x1000; - rate = ac97_read(codec, AC97_HANDSET_RATE) & 0xF0FF; - ac97_write(codec, AC97_HANDSET_RATE, rate | 0x0200); - schedule_timeout_interruptible(msecs_to_jiffies(1)); - ac97_write(codec, AC97_HANDSET_RATE, rate | 0x0F00); - ac97_write(codec, AC97_EXTENDED_MID, status); - - return 0; -} - - /* We have to create a fake left and right HP mixers because * the codec only has a single control that is shared by both channels. * This makes it impossible to determine the audio path using the current @@ -420,8 +400,7 @@ SND_SOC_DAPM_MIXER("AC97 Mixer", SND_SOC_NOPM, 0, 0, NULL, 0), SND_SOC_DAPM_MIXER("HP Mixer", SND_SOC_NOPM, 0, 0, NULL, 0), SND_SOC_DAPM_MIXER("Line Mixer", SND_SOC_NOPM, 0, 0, NULL, 0), SND_SOC_DAPM_MIXER("Capture Mixer", SND_SOC_NOPM, 0, 0, NULL, 0), -SND_SOC_DAPM_DAC_E("Voice DAC", "Voice Playback", AC97_EXTENDED_MID, 12, 1, - wm9713_voice_shutdown, SND_SOC_DAPM_PRE_PMD), +SND_SOC_DAPM_DAC("Voice DAC", "Voice Playback", AC97_EXTENDED_MID, 12, 1), SND_SOC_DAPM_DAC("Aux DAC", "Aux Playback", AC97_EXTENDED_MID, 11, 1), SND_SOC_DAPM_PGA("Left ADC", AC97_EXTENDED_MID, 5, 1, NULL, 0), SND_SOC_DAPM_PGA("Right ADC", AC97_EXTENDED_MID, 4, 1, NULL, 0), @@ -710,7 +689,7 @@ static void pll_factors(struct _pll_div *pll_div, unsigned int source) Ndiv = target / source; if ((Ndiv < 5) || (Ndiv > 12)) printk(KERN_WARNING - "WM9713 PLL N value %u out of recommended range!\n", + "WM9713 PLL N value %d out of recommended range!\n", Ndiv); pll_div->n = Ndiv; @@ -957,6 +936,21 @@ static int wm9713_pcm_hw_params(struct snd_pcm_substream *substream, return 0; } +static void wm9713_voiceshutdown(struct snd_pcm_substream *substream, + struct snd_soc_dai *dai) +{ + struct snd_soc_codec *codec = dai->codec; + u16 status, rate; + + /* Gracefully shut down the voice interface. */ + status = ac97_read(codec, AC97_EXTENDED_STATUS) | 0x1000; + rate = ac97_read(codec, AC97_HANDSET_RATE) & 0xF0FF; + ac97_write(codec, AC97_HANDSET_RATE, rate | 0x0200); + schedule_timeout_interruptible(msecs_to_jiffies(1)); + ac97_write(codec, AC97_HANDSET_RATE, rate | 0x0F00); + ac97_write(codec, AC97_EXTENDED_MID, status); +} + static int ac97_hifi_prepare(struct snd_pcm_substream *substream, struct snd_soc_dai *dai) { @@ -1025,6 +1019,7 @@ static struct snd_soc_dai_ops wm9713_dai_ops_aux = { static struct snd_soc_dai_ops wm9713_dai_ops_voice = { .hw_params = wm9713_pcm_hw_params, + .shutdown = wm9713_voiceshutdown, .set_clkdiv = wm9713_set_dai_clkdiv, .set_pll = wm9713_set_dai_pll, .set_fmt = wm9713_set_dai_fmt, @@ -1040,13 +1035,13 @@ struct snd_soc_dai wm9713_dai[] = { .channels_min = 1, .channels_max = 2, .rates = WM9713_RATES, - .formats = SND_SOC_STD_AC97_FMTS,}, + .formats = SNDRV_PCM_FMTBIT_S16_LE,}, .capture = { .stream_name = "HiFi Capture", .channels_min = 1, .channels_max = 2, .rates = WM9713_RATES, - .formats = SND_SOC_STD_AC97_FMTS,}, + .formats = SNDRV_PCM_FMTBIT_S16_LE,}, .ops = &wm9713_dai_ops_hifi, }, { @@ -1056,7 +1051,7 @@ struct snd_soc_dai wm9713_dai[] = { .channels_min = 1, .channels_max = 1, .rates = WM9713_RATES, - .formats = SND_SOC_STD_AC97_FMTS,}, + .formats = SNDRV_PCM_FMTBIT_S16_LE,}, .ops = &wm9713_dai_ops_aux, }, { @@ -1074,7 +1069,6 @@ struct snd_soc_dai wm9713_dai[] = { .rates = WM9713_PCM_RATES, .formats = WM9713_PCM_FORMATS,}, .ops = &wm9713_dai_ops_voice, - .symmetric_rates = 1, }, }; EXPORT_SYMBOL_GPL(wm9713_dai); diff --git a/trunk/sound/soc/fsl/Kconfig b/trunk/sound/soc/fsl/Kconfig index 5dbebf82249c..9fc908283371 100644 --- a/trunk/sound/soc/fsl/Kconfig +++ b/trunk/sound/soc/fsl/Kconfig @@ -1,8 +1,5 @@ config SND_SOC_OF_SIMPLE tristate - -config SND_MPC52xx_DMA - tristate # ASoC platform support for the Freescale MPC8610 SOC. This compiles drivers # for the SSI and the Elo DMA controller. You will still need to select @@ -25,34 +22,7 @@ config SND_SOC_MPC8610_HPCD config SND_SOC_MPC5200_I2S tristate "Freescale MPC5200 PSC in I2S mode driver" depends on PPC_MPC52xx && PPC_BESTCOMM - select SND_MPC52xx_DMA + select SND_SOC_OF_SIMPLE select PPC_BESTCOMM_GEN_BD help Say Y here to support the MPC5200 PSCs in I2S mode. - -config SND_SOC_MPC5200_AC97 - tristate "Freescale MPC5200 PSC in AC97 mode driver" - depends on PPC_MPC52xx && PPC_BESTCOMM - select AC97_BUS - select SND_MPC52xx_DMA - select PPC_BESTCOMM_GEN_BD - help - Say Y here to support the MPC5200 PSCs in AC97 mode. - -config SND_MPC52xx_SOC_PCM030 - tristate "SoC AC97 Audio support for Phytec pcm030 and WM9712" - depends on PPC_MPC5200_SIMPLE && BROKEN - select SND_SOC_MPC5200_AC97 - select SND_SOC_WM9712 - help - Say Y if you want to add support for sound on the Phytec pcm030 - baseboard. - -config SND_MPC52xx_SOC_EFIKA - tristate "SoC AC97 Audio support for bbplan Efika and STAC9766" - depends on PPC_EFIKA && BROKEN - select SND_SOC_MPC5200_AC97 - select SND_SOC_STAC9766 - help - Say Y if you want to add support for sound on the Efika. - diff --git a/trunk/sound/soc/fsl/Makefile b/trunk/sound/soc/fsl/Makefile index a83a73967ec6..f85134c86387 100644 --- a/trunk/sound/soc/fsl/Makefile +++ b/trunk/sound/soc/fsl/Makefile @@ -10,12 +10,5 @@ snd-soc-fsl-ssi-objs := fsl_ssi.o snd-soc-fsl-dma-objs := fsl_dma.o obj-$(CONFIG_SND_SOC_MPC8610) += snd-soc-fsl-ssi.o snd-soc-fsl-dma.o -# MPC5200 Platform Support -obj-$(CONFIG_SND_MPC52xx_DMA) += mpc5200_dma.o obj-$(CONFIG_SND_SOC_MPC5200_I2S) += mpc5200_psc_i2s.o -obj-$(CONFIG_SND_SOC_MPC5200_AC97) += mpc5200_psc_ac97.o - -# MPC5200 Machine Support -obj-$(CONFIG_SND_MPC52xx_SOC_PCM030) += pcm030-audio-fabric.o -obj-$(CONFIG_SND_MPC52xx_SOC_EFIKA) += efika-audio-fabric.o diff --git a/trunk/sound/soc/fsl/efika-audio-fabric.c b/trunk/sound/soc/fsl/efika-audio-fabric.c deleted file mode 100644 index 85b0e7569504..000000000000 --- a/trunk/sound/soc/fsl/efika-audio-fabric.c +++ /dev/null @@ -1,90 +0,0 @@ -/* - * Efika driver for the PSC of the Freescale MPC52xx - * configured as AC97 interface - * - * Copyright 2008 Jon Smirl, Digispeaker - * Author: Jon Smirl - * - * This file is licensed under the terms of the GNU General Public License - * version 2. This program is licensed "as is" without any warranty of any - * kind, whether express or implied. - */ - -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include - -#include "mpc5200_dma.h" -#include "mpc5200_psc_ac97.h" -#include "../codecs/stac9766.h" - -static struct snd_soc_device device; -static struct snd_soc_card card; - -static struct snd_soc_dai_link efika_fabric_dai[] = { -{ - .name = "AC97", - .stream_name = "AC97 Analog", - .codec_dai = &stac9766_dai[STAC9766_DAI_AC97_ANALOG], - .cpu_dai = &psc_ac97_dai[MPC5200_AC97_NORMAL], -}, -{ - .name = "AC97", - .stream_name = "AC97 IEC958", - .codec_dai = &stac9766_dai[STAC9766_DAI_AC97_DIGITAL], - .cpu_dai = &psc_ac97_dai[MPC5200_AC97_SPDIF], -}, -}; - -static __init int efika_fabric_init(void) -{ - struct platform_device *pdev; - int rc; - - if (!machine_is_compatible("bplan,efika")) - return -ENODEV; - - card.platform = &mpc5200_audio_dma_platform; - card.name = "Efika"; - card.dai_link = efika_fabric_dai; - card.num_links = ARRAY_SIZE(efika_fabric_dai); - - device.card = &card; - device.codec_dev = &soc_codec_dev_stac9766; - - pdev = platform_device_alloc("soc-audio", 1); - if (!pdev) { - pr_err("efika_fabric_init: platform_device_alloc() failed\n"); - return -ENODEV; - } - - platform_set_drvdata(pdev, &device); - device.dev = &pdev->dev; - - rc = platform_device_add(pdev); - if (rc) { - pr_err("efika_fabric_init: platform_device_add() failed\n"); - return -ENODEV; - } - return 0; -} - -module_init(efika_fabric_init); - - -MODULE_AUTHOR("Jon Smirl "); -MODULE_DESCRIPTION(DRV_NAME ": mpc5200 Efika fabric driver"); -MODULE_LICENSE("GPL"); - diff --git a/trunk/sound/soc/fsl/fsl_ssi.c b/trunk/sound/soc/fsl/fsl_ssi.c index 93f0f38a32c9..3711d8454d96 100644 --- a/trunk/sound/soc/fsl/fsl_ssi.c +++ b/trunk/sound/soc/fsl/fsl_ssi.c @@ -375,14 +375,18 @@ static int fsl_ssi_startup(struct snd_pcm_substream *substream, struct snd_pcm_runtime *first_runtime = ssi_private->first_stream->runtime; - if (!first_runtime->sample_bits) { + if (!first_runtime->rate || !first_runtime->sample_bits) { dev_err(substream->pcm->card->dev, - "set sample size in %s stream first\n", + "set sample rate and size in %s stream first\n", substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? "capture" : "playback"); return -EAGAIN; } + snd_pcm_hw_constraint_minmax(substream->runtime, + SNDRV_PCM_HW_PARAM_RATE, + first_runtime->rate, first_runtime->rate); + /* If we're in synchronous mode, then we need to constrain * the sample size as well. We don't support independent sample * rates in asynchronous mode. @@ -670,7 +674,7 @@ struct snd_soc_dai *fsl_ssi_create_dai(struct fsl_ssi_info *ssi_info) ssi_private->dev = ssi_info->dev; ssi_private->asynchronous = ssi_info->asynchronous; - dev_set_drvdata(ssi_private->dev, fsl_ssi_dai); + ssi_private->dev->driver_data = fsl_ssi_dai; /* Initialize the the device_attribute structure */ dev_attr->attr.name = "ssi-stats"; @@ -689,7 +693,6 @@ struct snd_soc_dai *fsl_ssi_create_dai(struct fsl_ssi_info *ssi_info) fsl_ssi_dai->name = ssi_private->name; fsl_ssi_dai->id = ssi_info->id; fsl_ssi_dai->dev = ssi_info->dev; - fsl_ssi_dai->symmetric_rates = 1; ret = snd_soc_register_dai(fsl_ssi_dai); if (ret != 0) { diff --git a/trunk/sound/soc/fsl/mpc5200_dma.c b/trunk/sound/soc/fsl/mpc5200_dma.c deleted file mode 100644 index efec33a1c5bd..000000000000 --- a/trunk/sound/soc/fsl/mpc5200_dma.c +++ /dev/null @@ -1,564 +0,0 @@ -/* - * Freescale MPC5200 PSC DMA - * ALSA SoC Platform driver - * - * Copyright (C) 2008 Secret Lab Technologies Ltd. - * Copyright (C) 2009 Jon Smirl, Digispeaker - */ - -#include -#include - -#include - -#include -#include -#include - -#include "mpc5200_dma.h" - -/* - * Interrupt handlers - */ -static irqreturn_t psc_dma_status_irq(int irq, void *_psc_dma) -{ - struct psc_dma *psc_dma = _psc_dma; - struct mpc52xx_psc __iomem *regs = psc_dma->psc_regs; - u16 isr; - - isr = in_be16(®s->mpc52xx_psc_isr); - - /* Playback underrun error */ - if (psc_dma->playback.active && (isr & MPC52xx_PSC_IMR_TXEMP)) - psc_dma->stats.underrun_count++; - - /* Capture overrun error */ - if (psc_dma->capture.active && (isr & MPC52xx_PSC_IMR_ORERR)) - psc_dma->stats.overrun_count++; - - out_8(®s->command, MPC52xx_PSC_RST_ERR_STAT); - - return IRQ_HANDLED; -} - -/** - * psc_dma_bcom_enqueue_next_buffer - Enqueue another audio buffer - * @s: pointer to stream private data structure - * - * Enqueues another audio period buffer into the bestcomm queue. - * - * Note: The routine must only be called when there is space available in - * the queue. Otherwise the enqueue will fail and the audio ring buffer - * will get out of sync - */ -static void psc_dma_bcom_enqueue_next_buffer(struct psc_dma_stream *s) -{ - struct bcom_bd *bd; - - /* Prepare and enqueue the next buffer descriptor */ - bd = bcom_prepare_next_buffer(s->bcom_task); - bd->status = s->period_bytes; - bd->data[0] = s->period_next_pt; - bcom_submit_next_buffer(s->bcom_task, NULL); - - /* Update for next period */ - s->period_next_pt += s->period_bytes; - if (s->period_next_pt >= s->period_end) - s->period_next_pt = s->period_start; -} - -static void psc_dma_bcom_enqueue_tx(struct psc_dma_stream *s) -{ - while (s->appl_ptr < s->runtime->control->appl_ptr) { - - if (bcom_queue_full(s->bcom_task)) - return; - - s->appl_ptr += s->period_size; - - psc_dma_bcom_enqueue_next_buffer(s); - } -} - -/* Bestcomm DMA irq handler */ -static irqreturn_t psc_dma_bcom_irq_tx(int irq, void *_psc_dma_stream) -{ - struct psc_dma_stream *s = _psc_dma_stream; - - spin_lock(&s->psc_dma->lock); - /* For each finished period, dequeue the completed period buffer - * and enqueue a new one in it's place. */ - while (bcom_buffer_done(s->bcom_task)) { - bcom_retrieve_buffer(s->bcom_task, NULL, NULL); - - s->period_current_pt += s->period_bytes; - if (s->period_current_pt >= s->period_end) - s->period_current_pt = s->period_start; - } - psc_dma_bcom_enqueue_tx(s); - spin_unlock(&s->psc_dma->lock); - - /* If the stream is active, then also inform the PCM middle layer - * of the period finished event. */ - if (s->active) - snd_pcm_period_elapsed(s->stream); - - return IRQ_HANDLED; -} - -static irqreturn_t psc_dma_bcom_irq_rx(int irq, void *_psc_dma_stream) -{ - struct psc_dma_stream *s = _psc_dma_stream; - - spin_lock(&s->psc_dma->lock); - /* For each finished period, dequeue the completed period buffer - * and enqueue a new one in it's place. */ - while (bcom_buffer_done(s->bcom_task)) { - bcom_retrieve_buffer(s->bcom_task, NULL, NULL); - - s->period_current_pt += s->period_bytes; - if (s->period_current_pt >= s->period_end) - s->period_current_pt = s->period_start; - - psc_dma_bcom_enqueue_next_buffer(s); - } - spin_unlock(&s->psc_dma->lock); - - /* If the stream is active, then also inform the PCM middle layer - * of the period finished event. */ - if (s->active) - snd_pcm_period_elapsed(s->stream); - - return IRQ_HANDLED; -} - -static int psc_dma_hw_free(struct snd_pcm_substream *substream) -{ - snd_pcm_set_runtime_buffer(substream, NULL); - return 0; -} - -/** - * psc_dma_trigger: start and stop the DMA transfer. - * - * This function is called by ALSA to start, stop, pause, and resume the DMA - * transfer of data. - */ -static int psc_dma_trigger(struct snd_pcm_substream *substream, int cmd) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct psc_dma *psc_dma = rtd->dai->cpu_dai->private_data; - struct snd_pcm_runtime *runtime = substream->runtime; - struct psc_dma_stream *s; - struct mpc52xx_psc __iomem *regs = psc_dma->psc_regs; - u16 imr; - unsigned long flags; - int i; - - if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) - s = &psc_dma->capture; - else - s = &psc_dma->playback; - - dev_dbg(psc_dma->dev, "psc_dma_trigger(substream=%p, cmd=%i)" - " stream_id=%i\n", - substream, cmd, substream->pstr->stream); - - switch (cmd) { - case SNDRV_PCM_TRIGGER_START: - s->period_bytes = frames_to_bytes(runtime, - runtime->period_size); - s->period_start = virt_to_phys(runtime->dma_area); - s->period_end = s->period_start + - (s->period_bytes * runtime->periods); - s->period_next_pt = s->period_start; - s->period_current_pt = s->period_start; - s->period_size = runtime->period_size; - s->active = 1; - - /* track appl_ptr so that we have a better chance of detecting - * end of stream and not over running it. - */ - s->runtime = runtime; - s->appl_ptr = s->runtime->control->appl_ptr - - (runtime->period_size * runtime->periods); - - /* Fill up the bestcomm bd queue and enable DMA. - * This will begin filling the PSC's fifo. - */ - spin_lock_irqsave(&psc_dma->lock, flags); - - if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) { - bcom_gen_bd_rx_reset(s->bcom_task); - for (i = 0; i < runtime->periods; i++) - if (!bcom_queue_full(s->bcom_task)) - psc_dma_bcom_enqueue_next_buffer(s); - } else { - bcom_gen_bd_tx_reset(s->bcom_task); - psc_dma_bcom_enqueue_tx(s); - } - - bcom_enable(s->bcom_task); - spin_unlock_irqrestore(&psc_dma->lock, flags); - - out_8(®s->command, MPC52xx_PSC_RST_ERR_STAT); - - break; - - case SNDRV_PCM_TRIGGER_STOP: - s->active = 0; - - spin_lock_irqsave(&psc_dma->lock, flags); - bcom_disable(s->bcom_task); - if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) - bcom_gen_bd_rx_reset(s->bcom_task); - else - bcom_gen_bd_tx_reset(s->bcom_task); - spin_unlock_irqrestore(&psc_dma->lock, flags); - - break; - - default: - dev_dbg(psc_dma->dev, "invalid command\n"); - return -EINVAL; - } - - /* Update interrupt enable settings */ - imr = 0; - if (psc_dma->playback.active) - imr |= MPC52xx_PSC_IMR_TXEMP; - if (psc_dma->capture.active) - imr |= MPC52xx_PSC_IMR_ORERR; - out_be16(®s->isr_imr.imr, psc_dma->imr | imr); - - return 0; -} - - -/* --------------------------------------------------------------------- - * The PSC DMA 'ASoC platform' driver - * - * Can be referenced by an 'ASoC machine' driver - * This driver only deals with the audio bus; it doesn't have any - * interaction with the attached codec - */ - -static const struct snd_pcm_hardware psc_dma_hardware = { - .info = SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_MMAP_VALID | - SNDRV_PCM_INFO_INTERLEAVED | SNDRV_PCM_INFO_BLOCK_TRANSFER | - SNDRV_PCM_INFO_BATCH, - .formats = SNDRV_PCM_FMTBIT_S8 | SNDRV_PCM_FMTBIT_S16_BE | - SNDRV_PCM_FMTBIT_S24_BE | SNDRV_PCM_FMTBIT_S32_BE, - .rate_min = 8000, - .rate_max = 48000, - .channels_min = 1, - .channels_max = 2, - .period_bytes_max = 1024 * 1024, - .period_bytes_min = 32, - .periods_min = 2, - .periods_max = 256, - .buffer_bytes_max = 2 * 1024 * 1024, - .fifo_size = 512, -}; - -static int psc_dma_open(struct snd_pcm_substream *substream) -{ - struct snd_pcm_runtime *runtime = substream->runtime; - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct psc_dma *psc_dma = rtd->dai->cpu_dai->private_data; - struct psc_dma_stream *s; - int rc; - - dev_dbg(psc_dma->dev, "psc_dma_open(substream=%p)\n", substream); - - if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) - s = &psc_dma->capture; - else - s = &psc_dma->playback; - - snd_soc_set_runtime_hwparams(substream, &psc_dma_hardware); - - rc = snd_pcm_hw_constraint_integer(runtime, - SNDRV_PCM_HW_PARAM_PERIODS); - if (rc < 0) { - dev_err(substream->pcm->card->dev, "invalid buffer size\n"); - return rc; - } - - s->stream = substream; - return 0; -} - -static int psc_dma_close(struct snd_pcm_substream *substream) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct psc_dma *psc_dma = rtd->dai->cpu_dai->private_data; - struct psc_dma_stream *s; - - dev_dbg(psc_dma->dev, "psc_dma_close(substream=%p)\n", substream); - - if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) - s = &psc_dma->capture; - else - s = &psc_dma->playback; - - if (!psc_dma->playback.active && - !psc_dma->capture.active) { - - /* Disable all interrupts and reset the PSC */ - out_be16(&psc_dma->psc_regs->isr_imr.imr, psc_dma->imr); - out_8(&psc_dma->psc_regs->command, 4 << 4); /* reset error */ - } - s->stream = NULL; - return 0; -} - -static snd_pcm_uframes_t -psc_dma_pointer(struct snd_pcm_substream *substream) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct psc_dma *psc_dma = rtd->dai->cpu_dai->private_data; - struct psc_dma_stream *s; - dma_addr_t count; - - if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) - s = &psc_dma->capture; - else - s = &psc_dma->playback; - - count = s->period_current_pt - s->period_start; - - return bytes_to_frames(substream->runtime, count); -} - -static int -psc_dma_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params) -{ - snd_pcm_set_runtime_buffer(substream, &substream->dma_buffer); - - return 0; -} - -static struct snd_pcm_ops psc_dma_ops = { - .open = psc_dma_open, - .close = psc_dma_close, - .hw_free = psc_dma_hw_free, - .ioctl = snd_pcm_lib_ioctl, - .pointer = psc_dma_pointer, - .trigger = psc_dma_trigger, - .hw_params = psc_dma_hw_params, -}; - -static u64 psc_dma_dmamask = 0xffffffff; -static int psc_dma_new(struct snd_card *card, struct snd_soc_dai *dai, - struct snd_pcm *pcm) -{ - struct snd_soc_pcm_runtime *rtd = pcm->private_data; - struct psc_dma *psc_dma = rtd->dai->cpu_dai->private_data; - size_t size = psc_dma_hardware.buffer_bytes_max; - int rc = 0; - - dev_dbg(rtd->socdev->dev, "psc_dma_new(card=%p, dai=%p, pcm=%p)\n", - card, dai, pcm); - - if (!card->dev->dma_mask) - card->dev->dma_mask = &psc_dma_dmamask; - if (!card->dev->coherent_dma_mask) - card->dev->coherent_dma_mask = 0xffffffff; - - if (pcm->streams[0].substream) { - rc = snd_dma_alloc_pages(SNDRV_DMA_TYPE_DEV, pcm->card->dev, - size, &pcm->streams[0].substream->dma_buffer); - if (rc) - goto playback_alloc_err; - } - - if (pcm->streams[1].substream) { - rc = snd_dma_alloc_pages(SNDRV_DMA_TYPE_DEV, pcm->card->dev, - size, &pcm->streams[1].substream->dma_buffer); - if (rc) - goto capture_alloc_err; - } - - if (rtd->socdev->card->codec->ac97) - rtd->socdev->card->codec->ac97->private_data = psc_dma; - - return 0; - - capture_alloc_err: - if (pcm->streams[0].substream) - snd_dma_free_pages(&pcm->streams[0].substream->dma_buffer); - - playback_alloc_err: - dev_err(card->dev, "Cannot allocate buffer(s)\n"); - - return -ENOMEM; -} - -static void psc_dma_free(struct snd_pcm *pcm) -{ - struct snd_soc_pcm_runtime *rtd = pcm->private_data; - struct snd_pcm_substream *substream; - int stream; - - dev_dbg(rtd->socdev->dev, "psc_dma_free(pcm=%p)\n", pcm); - - for (stream = 0; stream < 2; stream++) { - substream = pcm->streams[stream].substream; - if (substream) { - snd_dma_free_pages(&substream->dma_buffer); - substream->dma_buffer.area = NULL; - substream->dma_buffer.addr = 0; - } - } -} - -struct snd_soc_platform mpc5200_audio_dma_platform = { - .name = "mpc5200-psc-audio", - .pcm_ops = &psc_dma_ops, - .pcm_new = &psc_dma_new, - .pcm_free = &psc_dma_free, -}; -EXPORT_SYMBOL_GPL(mpc5200_audio_dma_platform); - -int mpc5200_audio_dma_create(struct of_device *op) -{ - phys_addr_t fifo; - struct psc_dma *psc_dma; - struct resource res; - int size, irq, rc; - const __be32 *prop; - void __iomem *regs; - - /* Fetch the registers and IRQ of the PSC */ - irq = irq_of_parse_and_map(op->node, 0); - if (of_address_to_resource(op->node, 0, &res)) { - dev_err(&op->dev, "Missing reg property\n"); - return -ENODEV; - } - regs = ioremap(res.start, 1 + res.end - res.start); - if (!regs) { - dev_err(&op->dev, "Could not map registers\n"); - return -ENODEV; - } - - /* Allocate and initialize the driver private data */ - psc_dma = kzalloc(sizeof *psc_dma, GFP_KERNEL); - if (!psc_dma) { - iounmap(regs); - return -ENOMEM; - } - - /* Get the PSC ID */ - prop = of_get_property(op->node, "cell-index", &size); - if (!prop || size < sizeof *prop) - return -ENODEV; - - spin_lock_init(&psc_dma->lock); - psc_dma->id = be32_to_cpu(*prop); - psc_dma->irq = irq; - psc_dma->psc_regs = regs; - psc_dma->fifo_regs = regs + sizeof *psc_dma->psc_regs; - psc_dma->dev = &op->dev; - psc_dma->playback.psc_dma = psc_dma; - psc_dma->capture.psc_dma = psc_dma; - snprintf(psc_dma->name, sizeof psc_dma->name, "PSC%u", psc_dma->id); - - /* Find the address of the fifo data registers and setup the - * DMA tasks */ - fifo = res.start + offsetof(struct mpc52xx_psc, buffer.buffer_32); - psc_dma->capture.bcom_task = - bcom_psc_gen_bd_rx_init(psc_dma->id, 10, fifo, 512); - psc_dma->playback.bcom_task = - bcom_psc_gen_bd_tx_init(psc_dma->id, 10, fifo); - if (!psc_dma->capture.bcom_task || - !psc_dma->playback.bcom_task) { - dev_err(&op->dev, "Could not allocate bestcomm tasks\n"); - iounmap(regs); - kfree(psc_dma); - return -ENODEV; - } - - /* Disable all interrupts and reset the PSC */ - out_be16(&psc_dma->psc_regs->isr_imr.imr, psc_dma->imr); - /* reset receiver */ - out_8(&psc_dma->psc_regs->command, MPC52xx_PSC_RST_RX); - /* reset transmitter */ - out_8(&psc_dma->psc_regs->command, MPC52xx_PSC_RST_TX); - /* reset error */ - out_8(&psc_dma->psc_regs->command, MPC52xx_PSC_RST_ERR_STAT); - /* reset mode */ - out_8(&psc_dma->psc_regs->command, MPC52xx_PSC_SEL_MODE_REG_1); - - /* Set up mode register; - * First write: RxRdy (FIFO Alarm) generates rx FIFO irq - * Second write: register Normal mode for non loopback - */ - out_8(&psc_dma->psc_regs->mode, 0); - out_8(&psc_dma->psc_regs->mode, 0); - - /* Set the TX and RX fifo alarm thresholds */ - out_be16(&psc_dma->fifo_regs->rfalarm, 0x100); - out_8(&psc_dma->fifo_regs->rfcntl, 0x4); - out_be16(&psc_dma->fifo_regs->tfalarm, 0x100); - out_8(&psc_dma->fifo_regs->tfcntl, 0x7); - - /* Lookup the IRQ numbers */ - psc_dma->playback.irq = - bcom_get_task_irq(psc_dma->playback.bcom_task); - psc_dma->capture.irq = - bcom_get_task_irq(psc_dma->capture.bcom_task); - - rc = request_irq(psc_dma->irq, &psc_dma_status_irq, IRQF_SHARED, - "psc-dma-status", psc_dma); - rc |= request_irq(psc_dma->capture.irq, - &psc_dma_bcom_irq_rx, IRQF_SHARED, - "psc-dma-capture", &psc_dma->capture); - rc |= request_irq(psc_dma->playback.irq, - &psc_dma_bcom_irq_tx, IRQF_SHARED, - "psc-dma-playback", &psc_dma->playback); - if (rc) { - free_irq(psc_dma->irq, psc_dma); - free_irq(psc_dma->capture.irq, - &psc_dma->capture); - free_irq(psc_dma->playback.irq, - &psc_dma->playback); - return -ENODEV; - } - - /* Save what we've done so it can be found again later */ - dev_set_drvdata(&op->dev, psc_dma); - - /* Tell the ASoC OF helpers about it */ - return snd_soc_register_platform(&mpc5200_audio_dma_platform); -} -EXPORT_SYMBOL_GPL(mpc5200_audio_dma_create); - -int mpc5200_audio_dma_destroy(struct of_device *op) -{ - struct psc_dma *psc_dma = dev_get_drvdata(&op->dev); - - dev_dbg(&op->dev, "mpc5200_audio_dma_destroy()\n"); - - snd_soc_unregister_platform(&mpc5200_audio_dma_platform); - - bcom_gen_bd_rx_release(psc_dma->capture.bcom_task); - bcom_gen_bd_tx_release(psc_dma->playback.bcom_task); - - /* Release irqs */ - free_irq(psc_dma->irq, psc_dma); - free_irq(psc_dma->capture.irq, &psc_dma->capture); - free_irq(psc_dma->playback.irq, &psc_dma->playback); - - iounmap(psc_dma->psc_regs); - kfree(psc_dma); - dev_set_drvdata(&op->dev, NULL); - - return 0; -} -EXPORT_SYMBOL_GPL(mpc5200_audio_dma_destroy); - -MODULE_AUTHOR("Grant Likely "); -MODULE_DESCRIPTION("Freescale MPC5200 PSC in DMA mode ASoC Driver"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/fsl/mpc5200_dma.h b/trunk/sound/soc/fsl/mpc5200_dma.h deleted file mode 100644 index 2000803f06a7..000000000000 --- a/trunk/sound/soc/fsl/mpc5200_dma.h +++ /dev/null @@ -1,80 +0,0 @@ -/* - * Freescale MPC5200 Audio DMA driver - */ - -#ifndef __SOUND_SOC_FSL_MPC5200_DMA_H__ -#define __SOUND_SOC_FSL_MPC5200_DMA_H__ - -#define PSC_STREAM_NAME_LEN 32 - -/** - * psc_ac97_stream - Data specific to a single stream (playback or capture) - * @active: flag indicating if the stream is active - * @psc_dma: pointer back to parent psc_dma data structure - * @bcom_task: bestcomm task structure - * @irq: irq number for bestcomm task - * @period_start: physical address of start of DMA region - * @period_end: physical address of end of DMA region - * @period_next_pt: physical address of next DMA buffer to enqueue - * @period_bytes: size of DMA period in bytes - */ -struct psc_dma_stream { - struct snd_pcm_runtime *runtime; - snd_pcm_uframes_t appl_ptr; - - int active; - struct psc_dma *psc_dma; - struct bcom_task *bcom_task; - int irq; - struct snd_pcm_substream *stream; - dma_addr_t period_start; - dma_addr_t period_end; - dma_addr_t period_next_pt; - dma_addr_t period_current_pt; - int period_bytes; - int period_size; -}; - -/** - * psc_dma - Private driver data - * @name: short name for this device ("PSC0", "PSC1", etc) - * @psc_regs: pointer to the PSC's registers - * @fifo_regs: pointer to the PSC's FIFO registers - * @irq: IRQ of this PSC - * @dev: struct device pointer - * @dai: the CPU DAI for this device - * @sicr: Base value used in serial interface control register; mode is ORed - * with this value. - * @playback: Playback stream context data - * @capture: Capture stream context data - */ -struct psc_dma { - char name[32]; - struct mpc52xx_psc __iomem *psc_regs; - struct mpc52xx_psc_fifo __iomem *fifo_regs; - unsigned int irq; - struct device *dev; - spinlock_t lock; - u32 sicr; - uint sysclk; - int imr; - int id; - unsigned int slots; - - /* per-stream data */ - struct psc_dma_stream playback; - struct psc_dma_stream capture; - - /* Statistics */ - struct { - unsigned long overrun_count; - unsigned long underrun_count; - } stats; -}; - -int mpc5200_audio_dma_create(struct of_device *op); -int mpc5200_audio_dma_destroy(struct of_device *op); - -extern struct snd_soc_platform mpc5200_audio_dma_platform; - -#endif /* __SOUND_SOC_FSL_MPC5200_DMA_H__ */ diff --git a/trunk/sound/soc/fsl/mpc5200_psc_ac97.c b/trunk/sound/soc/fsl/mpc5200_psc_ac97.c deleted file mode 100644 index 794a247b3eb5..000000000000 --- a/trunk/sound/soc/fsl/mpc5200_psc_ac97.c +++ /dev/null @@ -1,329 +0,0 @@ -/* - * linux/sound/mpc5200-ac97.c -- AC97 support for the Freescale MPC52xx chip. - * - * Copyright (C) 2009 Jon Smirl, Digispeaker - * Author: Jon Smirl - * - * 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. - */ - -#include -#include -#include - -#include -#include -#include - -#include -#include -#include - -#include "mpc5200_dma.h" -#include "mpc5200_psc_ac97.h" - -#define DRV_NAME "mpc5200-psc-ac97" - -/* ALSA only supports a single AC97 device so static is recommend here */ -static struct psc_dma *psc_dma; - -static unsigned short psc_ac97_read(struct snd_ac97 *ac97, unsigned short reg) -{ - int status; - unsigned int val; - - /* Wait for command send status zero = ready */ - status = spin_event_timeout(!(in_be16(&psc_dma->psc_regs->sr_csr.status) & - MPC52xx_PSC_SR_CMDSEND), 100, 0); - if (status == 0) { - pr_err("timeout on ac97 bus (rdy)\n"); - return -ENODEV; - } - /* Send the read */ - out_be32(&psc_dma->psc_regs->ac97_cmd, (1<<31) | ((reg & 0x7f) << 24)); - - /* Wait for the answer */ - status = spin_event_timeout((in_be16(&psc_dma->psc_regs->sr_csr.status) & - MPC52xx_PSC_SR_DATA_VAL), 100, 0); - if (status == 0) { - pr_err("timeout on ac97 read (val) %x\n", - in_be16(&psc_dma->psc_regs->sr_csr.status)); - return -ENODEV; - } - /* Get the data */ - val = in_be32(&psc_dma->psc_regs->ac97_data); - if (((val >> 24) & 0x7f) != reg) { - pr_err("reg echo error on ac97 read\n"); - return -ENODEV; - } - val = (val >> 8) & 0xffff; - - return (unsigned short) val; -} - -static void psc_ac97_write(struct snd_ac97 *ac97, - unsigned short reg, unsigned short val) -{ - int status; - - /* Wait for command status zero = ready */ - status = spin_event_timeout(!(in_be16(&psc_dma->psc_regs->sr_csr.status) & - MPC52xx_PSC_SR_CMDSEND), 100, 0); - if (status == 0) { - pr_err("timeout on ac97 bus (write)\n"); - return; - } - /* Write data */ - out_be32(&psc_dma->psc_regs->ac97_cmd, - ((reg & 0x7f) << 24) | (val << 8)); -} - -static void psc_ac97_warm_reset(struct snd_ac97 *ac97) -{ - struct mpc52xx_psc __iomem *regs = psc_dma->psc_regs; - - out_be32(®s->sicr, psc_dma->sicr | MPC52xx_PSC_SICR_AWR); - udelay(3); - out_be32(®s->sicr, psc_dma->sicr); -} - -static void psc_ac97_cold_reset(struct snd_ac97 *ac97) -{ - struct mpc52xx_psc __iomem *regs = psc_dma->psc_regs; - - /* Do a cold reset */ - out_8(®s->op1, MPC52xx_PSC_OP_RES); - udelay(10); - out_8(®s->op0, MPC52xx_PSC_OP_RES); - udelay(50); - psc_ac97_warm_reset(ac97); -} - -struct snd_ac97_bus_ops soc_ac97_ops = { - .read = psc_ac97_read, - .write = psc_ac97_write, - .reset = psc_ac97_cold_reset, - .warm_reset = psc_ac97_warm_reset, -}; -EXPORT_SYMBOL_GPL(soc_ac97_ops); - -static int psc_ac97_hw_analog_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params, - struct snd_soc_dai *cpu_dai) -{ - struct psc_dma *psc_dma = cpu_dai->private_data; - - dev_dbg(psc_dma->dev, "%s(substream=%p) p_size=%i p_bytes=%i" - " periods=%i buffer_size=%i buffer_bytes=%i channels=%i" - " rate=%i format=%i\n", - __func__, substream, params_period_size(params), - params_period_bytes(params), params_periods(params), - params_buffer_size(params), params_buffer_bytes(params), - params_channels(params), params_rate(params), - params_format(params)); - - - if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) { - if (params_channels(params) == 1) - psc_dma->slots |= 0x00000100; - else - psc_dma->slots |= 0x00000300; - } else { - if (params_channels(params) == 1) - psc_dma->slots |= 0x01000000; - else - psc_dma->slots |= 0x03000000; - } - out_be32(&psc_dma->psc_regs->ac97_slots, psc_dma->slots); - - return 0; -} - -static int psc_ac97_hw_digital_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params, - struct snd_soc_dai *cpu_dai) -{ - struct psc_dma *psc_dma = cpu_dai->private_data; - - if (params_channels(params) == 1) - out_be32(&psc_dma->psc_regs->ac97_slots, 0x01000000); - else - out_be32(&psc_dma->psc_regs->ac97_slots, 0x03000000); - - return 0; -} - -static int psc_ac97_trigger(struct snd_pcm_substream *substream, int cmd, - struct snd_soc_dai *dai) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct psc_dma *psc_dma = rtd->dai->cpu_dai->private_data; - - switch (cmd) { - case SNDRV_PCM_TRIGGER_STOP: - if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) - psc_dma->slots &= 0xFFFF0000; - else - psc_dma->slots &= 0x0000FFFF; - - out_be32(&psc_dma->psc_regs->ac97_slots, psc_dma->slots); - break; - } - return 0; -} - -static int psc_ac97_probe(struct platform_device *pdev, - struct snd_soc_dai *cpu_dai) -{ - struct psc_dma *psc_dma = cpu_dai->private_data; - struct mpc52xx_psc __iomem *regs = psc_dma->psc_regs; - - /* Go */ - out_8(®s->command, MPC52xx_PSC_TX_ENABLE | MPC52xx_PSC_RX_ENABLE); - return 0; -} - -/* --------------------------------------------------------------------- - * ALSA SoC Bindings - * - * - Digital Audio Interface (DAI) template - * - create/destroy dai hooks - */ - -/** - * psc_ac97_dai_template: template CPU Digital Audio Interface - */ -static struct snd_soc_dai_ops psc_ac97_analog_ops = { - .hw_params = psc_ac97_hw_analog_params, - .trigger = psc_ac97_trigger, -}; - -static struct snd_soc_dai_ops psc_ac97_digital_ops = { - .hw_params = psc_ac97_hw_digital_params, -}; - -struct snd_soc_dai psc_ac97_dai[] = { -{ - .name = "AC97", - .ac97_control = 1, - .probe = psc_ac97_probe, - .playback = { - .channels_min = 1, - .channels_max = 6, - .rates = SNDRV_PCM_RATE_8000_48000, - .formats = SNDRV_PCM_FMTBIT_S32_BE, - }, - .capture = { - .channels_min = 1, - .channels_max = 2, - .rates = SNDRV_PCM_RATE_8000_48000, - .formats = SNDRV_PCM_FMTBIT_S32_BE, - }, - .ops = &psc_ac97_analog_ops, -}, -{ - .name = "SPDIF", - .ac97_control = 1, - .playback = { - .channels_min = 1, - .channels_max = 2, - .rates = SNDRV_PCM_RATE_32000 | \ - SNDRV_PCM_RATE_44100 | SNDRV_PCM_RATE_48000, - .formats = SNDRV_PCM_FMTBIT_IEC958_SUBFRAME_BE, - }, - .ops = &psc_ac97_digital_ops, -} }; -EXPORT_SYMBOL_GPL(psc_ac97_dai); - - - -/* --------------------------------------------------------------------- - * OF platform bus binding code: - * - Probe/remove operations - * - OF device match table - */ -static int __devinit psc_ac97_of_probe(struct of_device *op, - const struct of_device_id *match) -{ - int rc, i; - struct snd_ac97 ac97; - struct mpc52xx_psc __iomem *regs; - - rc = mpc5200_audio_dma_create(op); - if (rc != 0) - return rc; - - for (i = 0; i < ARRAY_SIZE(psc_ac97_dai); i++) - psc_ac97_dai[i].dev = &op->dev; - - rc = snd_soc_register_dais(psc_ac97_dai, ARRAY_SIZE(psc_ac97_dai)); - if (rc != 0) { - dev_err(&op->dev, "Failed to register DAI\n"); - return rc; - } - - psc_dma = dev_get_drvdata(&op->dev); - regs = psc_dma->psc_regs; - ac97.private_data = psc_dma; - - for (i = 0; i < ARRAY_SIZE(psc_ac97_dai); i++) - psc_ac97_dai[i].private_data = psc_dma; - - psc_dma->imr = 0; - out_be16(&psc_dma->psc_regs->isr_imr.imr, psc_dma->imr); - - /* Configure the serial interface mode to AC97 */ - psc_dma->sicr = MPC52xx_PSC_SICR_SIM_AC97 | MPC52xx_PSC_SICR_ENAC97; - out_be32(®s->sicr, psc_dma->sicr); - - /* No slots active */ - out_be32(®s->ac97_slots, 0x00000000); - - return 0; -} - -static int __devexit psc_ac97_of_remove(struct of_device *op) -{ - return mpc5200_audio_dma_destroy(op); -} - -/* Match table for of_platform binding */ -static struct of_device_id psc_ac97_match[] __devinitdata = { - { .compatible = "fsl,mpc5200-psc-ac97", }, - { .compatible = "fsl,mpc5200b-psc-ac97", }, - {} -}; -MODULE_DEVICE_TABLE(of, psc_ac97_match); - -static struct of_platform_driver psc_ac97_driver = { - .match_table = psc_ac97_match, - .probe = psc_ac97_of_probe, - .remove = __devexit_p(psc_ac97_of_remove), - .driver = { - .name = "mpc5200-psc-ac97", - .owner = THIS_MODULE, - }, -}; - -/* --------------------------------------------------------------------- - * Module setup and teardown; simply register the of_platform driver - * for the PSC in AC97 mode. - */ -static int __init psc_ac97_init(void) -{ - return of_register_platform_driver(&psc_ac97_driver); -} -module_init(psc_ac97_init); - -static void __exit psc_ac97_exit(void) -{ - of_unregister_platform_driver(&psc_ac97_driver); -} -module_exit(psc_ac97_exit); - -MODULE_AUTHOR("Jon Smirl "); -MODULE_DESCRIPTION("mpc5200 AC97 module"); -MODULE_LICENSE("GPL"); - diff --git a/trunk/sound/soc/fsl/mpc5200_psc_ac97.h b/trunk/sound/soc/fsl/mpc5200_psc_ac97.h deleted file mode 100644 index 4bc18c35c369..000000000000 --- a/trunk/sound/soc/fsl/mpc5200_psc_ac97.h +++ /dev/null @@ -1,15 +0,0 @@ -/* - * Freescale MPC5200 PSC in AC97 mode - * ALSA SoC Digital Audio Interface (DAI) driver - * - */ - -#ifndef __SOUND_SOC_FSL_MPC52xx_PSC_AC97_H__ -#define __SOUND_SOC_FSL_MPC52xx_PSC_AC97_H__ - -extern struct snd_soc_dai psc_ac97_dai[]; - -#define MPC5200_AC97_NORMAL 0 -#define MPC5200_AC97_SPDIF 1 - -#endif /* __SOUND_SOC_FSL_MPC52xx_PSC_AC97_H__ */ diff --git a/trunk/sound/soc/fsl/mpc5200_psc_i2s.c b/trunk/sound/soc/fsl/mpc5200_psc_i2s.c index ce8de90fb94a..1111c710118a 100644 --- a/trunk/sound/soc/fsl/mpc5200_psc_i2s.c +++ b/trunk/sound/soc/fsl/mpc5200_psc_i2s.c @@ -3,21 +3,31 @@ * ALSA SoC Digital Audio Interface (DAI) driver * * Copyright (C) 2008 Secret Lab Technologies Ltd. - * Copyright (C) 2009 Jon Smirl, Digispeaker */ +#include #include +#include +#include +#include #include #include +#include +#include #include #include +#include #include +#include +#include +#include #include -#include "mpc5200_psc_i2s.h" -#include "mpc5200_dma.h" +MODULE_AUTHOR("Grant Likely "); +MODULE_DESCRIPTION("Freescale MPC5200 PSC in I2S mode ASoC Driver"); +MODULE_LICENSE("GPL"); /** * PSC_I2S_RATES: sample rates supported by the I2S @@ -34,17 +44,191 @@ * PSC_I2S_FORMATS: audio formats supported by the PSC I2S mode */ #define PSC_I2S_FORMATS (SNDRV_PCM_FMTBIT_S8 | SNDRV_PCM_FMTBIT_S16_BE | \ - SNDRV_PCM_FMTBIT_S24_BE | SNDRV_PCM_FMTBIT_S32_BE) + SNDRV_PCM_FMTBIT_S24_BE | SNDRV_PCM_FMTBIT_S24_BE | \ + SNDRV_PCM_FMTBIT_S32_BE) + +/** + * psc_i2s_stream - Data specific to a single stream (playback or capture) + * @active: flag indicating if the stream is active + * @psc_i2s: pointer back to parent psc_i2s data structure + * @bcom_task: bestcomm task structure + * @irq: irq number for bestcomm task + * @period_start: physical address of start of DMA region + * @period_end: physical address of end of DMA region + * @period_next_pt: physical address of next DMA buffer to enqueue + * @period_bytes: size of DMA period in bytes + */ +struct psc_i2s_stream { + int active; + struct psc_i2s *psc_i2s; + struct bcom_task *bcom_task; + int irq; + struct snd_pcm_substream *stream; + dma_addr_t period_start; + dma_addr_t period_end; + dma_addr_t period_next_pt; + dma_addr_t period_current_pt; + int period_bytes; +}; + +/** + * psc_i2s - Private driver data + * @name: short name for this device ("PSC0", "PSC1", etc) + * @psc_regs: pointer to the PSC's registers + * @fifo_regs: pointer to the PSC's FIFO registers + * @irq: IRQ of this PSC + * @dev: struct device pointer + * @dai: the CPU DAI for this device + * @sicr: Base value used in serial interface control register; mode is ORed + * with this value. + * @playback: Playback stream context data + * @capture: Capture stream context data + */ +struct psc_i2s { + char name[32]; + struct mpc52xx_psc __iomem *psc_regs; + struct mpc52xx_psc_fifo __iomem *fifo_regs; + unsigned int irq; + struct device *dev; + struct snd_soc_dai dai; + spinlock_t lock; + u32 sicr; + + /* per-stream data */ + struct psc_i2s_stream playback; + struct psc_i2s_stream capture; + + /* Statistics */ + struct { + int overrun_count; + int underrun_count; + } stats; +}; + +/* + * Interrupt handlers + */ +static irqreturn_t psc_i2s_status_irq(int irq, void *_psc_i2s) +{ + struct psc_i2s *psc_i2s = _psc_i2s; + struct mpc52xx_psc __iomem *regs = psc_i2s->psc_regs; + u16 isr; + + isr = in_be16(®s->mpc52xx_psc_isr); + + /* Playback underrun error */ + if (psc_i2s->playback.active && (isr & MPC52xx_PSC_IMR_TXEMP)) + psc_i2s->stats.underrun_count++; + + /* Capture overrun error */ + if (psc_i2s->capture.active && (isr & MPC52xx_PSC_IMR_ORERR)) + psc_i2s->stats.overrun_count++; + + out_8(®s->command, 4 << 4); /* reset the error status */ + + return IRQ_HANDLED; +} + +/** + * psc_i2s_bcom_enqueue_next_buffer - Enqueue another audio buffer + * @s: pointer to stream private data structure + * + * Enqueues another audio period buffer into the bestcomm queue. + * + * Note: The routine must only be called when there is space available in + * the queue. Otherwise the enqueue will fail and the audio ring buffer + * will get out of sync + */ +static void psc_i2s_bcom_enqueue_next_buffer(struct psc_i2s_stream *s) +{ + struct bcom_bd *bd; + + /* Prepare and enqueue the next buffer descriptor */ + bd = bcom_prepare_next_buffer(s->bcom_task); + bd->status = s->period_bytes; + bd->data[0] = s->period_next_pt; + bcom_submit_next_buffer(s->bcom_task, NULL); + + /* Update for next period */ + s->period_next_pt += s->period_bytes; + if (s->period_next_pt >= s->period_end) + s->period_next_pt = s->period_start; +} + +/* Bestcomm DMA irq handler */ +static irqreturn_t psc_i2s_bcom_irq(int irq, void *_psc_i2s_stream) +{ + struct psc_i2s_stream *s = _psc_i2s_stream; + + /* For each finished period, dequeue the completed period buffer + * and enqueue a new one in it's place. */ + while (bcom_buffer_done(s->bcom_task)) { + bcom_retrieve_buffer(s->bcom_task, NULL, NULL); + s->period_current_pt += s->period_bytes; + if (s->period_current_pt >= s->period_end) + s->period_current_pt = s->period_start; + psc_i2s_bcom_enqueue_next_buffer(s); + bcom_enable(s->bcom_task); + } + + /* If the stream is active, then also inform the PCM middle layer + * of the period finished event. */ + if (s->active) + snd_pcm_period_elapsed(s->stream); + + return IRQ_HANDLED; +} + +/** + * psc_i2s_startup: create a new substream + * + * This is the first function called when a stream is opened. + * + * If this is the first stream open, then grab the IRQ and program most of + * the PSC registers. + */ +static int psc_i2s_startup(struct snd_pcm_substream *substream, + struct snd_soc_dai *dai) +{ + struct snd_soc_pcm_runtime *rtd = substream->private_data; + struct psc_i2s *psc_i2s = rtd->dai->cpu_dai->private_data; + int rc; + + dev_dbg(psc_i2s->dev, "psc_i2s_startup(substream=%p)\n", substream); + + if (!psc_i2s->playback.active && + !psc_i2s->capture.active) { + /* Setup the IRQs */ + rc = request_irq(psc_i2s->irq, &psc_i2s_status_irq, IRQF_SHARED, + "psc-i2s-status", psc_i2s); + rc |= request_irq(psc_i2s->capture.irq, + &psc_i2s_bcom_irq, IRQF_SHARED, + "psc-i2s-capture", &psc_i2s->capture); + rc |= request_irq(psc_i2s->playback.irq, + &psc_i2s_bcom_irq, IRQF_SHARED, + "psc-i2s-playback", &psc_i2s->playback); + if (rc) { + free_irq(psc_i2s->irq, psc_i2s); + free_irq(psc_i2s->capture.irq, + &psc_i2s->capture); + free_irq(psc_i2s->playback.irq, + &psc_i2s->playback); + return -ENODEV; + } + } + + return 0; +} static int psc_i2s_hw_params(struct snd_pcm_substream *substream, struct snd_pcm_hw_params *params, struct snd_soc_dai *dai) { struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct psc_dma *psc_dma = rtd->dai->cpu_dai->private_data; + struct psc_i2s *psc_i2s = rtd->dai->cpu_dai->private_data; u32 mode; - dev_dbg(psc_dma->dev, "%s(substream=%p) p_size=%i p_bytes=%i" + dev_dbg(psc_i2s->dev, "%s(substream=%p) p_size=%i p_bytes=%i" " periods=%i buffer_size=%i buffer_bytes=%i\n", __func__, substream, params_period_size(params), params_period_bytes(params), params_periods(params), @@ -64,14 +248,174 @@ static int psc_i2s_hw_params(struct snd_pcm_substream *substream, mode = MPC52xx_PSC_SICR_SIM_CODEC_32; break; default: - dev_dbg(psc_dma->dev, "invalid format\n"); + dev_dbg(psc_i2s->dev, "invalid format\n"); + return -EINVAL; + } + out_be32(&psc_i2s->psc_regs->sicr, psc_i2s->sicr | mode); + + snd_pcm_set_runtime_buffer(substream, &substream->dma_buffer); + + return 0; +} + +static int psc_i2s_hw_free(struct snd_pcm_substream *substream, + struct snd_soc_dai *dai) +{ + snd_pcm_set_runtime_buffer(substream, NULL); + return 0; +} + +/** + * psc_i2s_trigger: start and stop the DMA transfer. + * + * This function is called by ALSA to start, stop, pause, and resume the DMA + * transfer of data. + */ +static int psc_i2s_trigger(struct snd_pcm_substream *substream, int cmd, + struct snd_soc_dai *dai) +{ + struct snd_soc_pcm_runtime *rtd = substream->private_data; + struct psc_i2s *psc_i2s = rtd->dai->cpu_dai->private_data; + struct snd_pcm_runtime *runtime = substream->runtime; + struct psc_i2s_stream *s; + struct mpc52xx_psc __iomem *regs = psc_i2s->psc_regs; + u16 imr; + u8 psc_cmd; + unsigned long flags; + + if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) + s = &psc_i2s->capture; + else + s = &psc_i2s->playback; + + dev_dbg(psc_i2s->dev, "psc_i2s_trigger(substream=%p, cmd=%i)" + " stream_id=%i\n", + substream, cmd, substream->pstr->stream); + + switch (cmd) { + case SNDRV_PCM_TRIGGER_START: + s->period_bytes = frames_to_bytes(runtime, + runtime->period_size); + s->period_start = virt_to_phys(runtime->dma_area); + s->period_end = s->period_start + + (s->period_bytes * runtime->periods); + s->period_next_pt = s->period_start; + s->period_current_pt = s->period_start; + s->active = 1; + + /* First; reset everything */ + if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) { + out_8(®s->command, MPC52xx_PSC_RST_RX); + out_8(®s->command, MPC52xx_PSC_RST_ERR_STAT); + } else { + out_8(®s->command, MPC52xx_PSC_RST_TX); + out_8(®s->command, MPC52xx_PSC_RST_ERR_STAT); + } + + /* Next, fill up the bestcomm bd queue and enable DMA. + * This will begin filling the PSC's fifo. */ + if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) + bcom_gen_bd_rx_reset(s->bcom_task); + else + bcom_gen_bd_tx_reset(s->bcom_task); + while (!bcom_queue_full(s->bcom_task)) + psc_i2s_bcom_enqueue_next_buffer(s); + bcom_enable(s->bcom_task); + + /* Due to errata in the i2s mode; need to line up enabling + * the transmitter with a transition on the frame sync + * line */ + + spin_lock_irqsave(&psc_i2s->lock, flags); + /* first make sure it is low */ + while ((in_8(®s->ipcr_acr.ipcr) & 0x80) != 0) + ; + /* then wait for the transition to high */ + while ((in_8(®s->ipcr_acr.ipcr) & 0x80) == 0) + ; + /* Finally, enable the PSC. + * Receiver must always be enabled; even when we only want + * transmit. (see 15.3.2.3 of MPC5200B User's Guide) */ + psc_cmd = MPC52xx_PSC_RX_ENABLE; + if (substream->pstr->stream == SNDRV_PCM_STREAM_PLAYBACK) + psc_cmd |= MPC52xx_PSC_TX_ENABLE; + out_8(®s->command, psc_cmd); + spin_unlock_irqrestore(&psc_i2s->lock, flags); + + break; + + case SNDRV_PCM_TRIGGER_STOP: + /* Turn off the PSC */ + s->active = 0; + if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) { + if (!psc_i2s->playback.active) { + out_8(®s->command, 2 << 4); /* reset rx */ + out_8(®s->command, 3 << 4); /* reset tx */ + out_8(®s->command, 4 << 4); /* reset err */ + } + } else { + out_8(®s->command, 3 << 4); /* reset tx */ + out_8(®s->command, 4 << 4); /* reset err */ + if (!psc_i2s->capture.active) + out_8(®s->command, 2 << 4); /* reset rx */ + } + + bcom_disable(s->bcom_task); + while (!bcom_queue_empty(s->bcom_task)) + bcom_retrieve_buffer(s->bcom_task, NULL, NULL); + + break; + + default: + dev_dbg(psc_i2s->dev, "invalid command\n"); return -EINVAL; } - out_be32(&psc_dma->psc_regs->sicr, psc_dma->sicr | mode); + + /* Update interrupt enable settings */ + imr = 0; + if (psc_i2s->playback.active) + imr |= MPC52xx_PSC_IMR_TXEMP; + if (psc_i2s->capture.active) + imr |= MPC52xx_PSC_IMR_ORERR; + out_be16(®s->isr_imr.imr, imr); return 0; } +/** + * psc_i2s_shutdown: shutdown the data transfer on a stream + * + * Shutdown the PSC if there are no other substreams open. + */ +static void psc_i2s_shutdown(struct snd_pcm_substream *substream, + struct snd_soc_dai *dai) +{ + struct snd_soc_pcm_runtime *rtd = substream->private_data; + struct psc_i2s *psc_i2s = rtd->dai->cpu_dai->private_data; + + dev_dbg(psc_i2s->dev, "psc_i2s_shutdown(substream=%p)\n", substream); + + /* + * If this is the last active substream, disable the PSC and release + * the IRQ. + */ + if (!psc_i2s->playback.active && + !psc_i2s->capture.active) { + + /* Disable all interrupts and reset the PSC */ + out_be16(&psc_i2s->psc_regs->isr_imr.imr, 0); + out_8(&psc_i2s->psc_regs->command, 3 << 4); /* reset tx */ + out_8(&psc_i2s->psc_regs->command, 2 << 4); /* reset rx */ + out_8(&psc_i2s->psc_regs->command, 1 << 4); /* reset mode */ + out_8(&psc_i2s->psc_regs->command, 4 << 4); /* reset error */ + + /* Release irqs */ + free_irq(psc_i2s->irq, psc_i2s); + free_irq(psc_i2s->capture.irq, &psc_i2s->capture); + free_irq(psc_i2s->playback.irq, &psc_i2s->playback); + } +} + /** * psc_i2s_set_sysclk: set the clock frequency and direction * @@ -89,8 +433,8 @@ static int psc_i2s_hw_params(struct snd_pcm_substream *substream, static int psc_i2s_set_sysclk(struct snd_soc_dai *cpu_dai, int clk_id, unsigned int freq, int dir) { - struct psc_dma *psc_dma = cpu_dai->private_data; - dev_dbg(psc_dma->dev, "psc_i2s_set_sysclk(cpu_dai=%p, dir=%i)\n", + struct psc_i2s *psc_i2s = cpu_dai->private_data; + dev_dbg(psc_i2s->dev, "psc_i2s_set_sysclk(cpu_dai=%p, dir=%i)\n", cpu_dai, dir); return (dir == SND_SOC_CLOCK_IN) ? 0 : -EINVAL; } @@ -108,8 +452,8 @@ static int psc_i2s_set_sysclk(struct snd_soc_dai *cpu_dai, */ static int psc_i2s_set_fmt(struct snd_soc_dai *cpu_dai, unsigned int format) { - struct psc_dma *psc_dma = cpu_dai->private_data; - dev_dbg(psc_dma->dev, "psc_i2s_set_fmt(cpu_dai=%p, format=%i)\n", + struct psc_i2s *psc_i2s = cpu_dai->private_data; + dev_dbg(psc_i2s->dev, "psc_i2s_set_fmt(cpu_dai=%p, format=%i)\n", cpu_dai, format); return (format == SND_SOC_DAIFMT_I2S) ? 0 : -EINVAL; } @@ -125,13 +469,16 @@ static int psc_i2s_set_fmt(struct snd_soc_dai *cpu_dai, unsigned int format) * psc_i2s_dai_template: template CPU Digital Audio Interface */ static struct snd_soc_dai_ops psc_i2s_dai_ops = { + .startup = psc_i2s_startup, .hw_params = psc_i2s_hw_params, + .hw_free = psc_i2s_hw_free, + .shutdown = psc_i2s_shutdown, + .trigger = psc_i2s_trigger, .set_sysclk = psc_i2s_set_sysclk, .set_fmt = psc_i2s_set_fmt, }; -struct snd_soc_dai psc_i2s_dai[] = {{ - .name = "I2S", +static struct snd_soc_dai psc_i2s_dai_template = { .playback = { .channels_min = 2, .channels_max = 2, @@ -145,8 +492,223 @@ struct snd_soc_dai psc_i2s_dai[] = {{ .formats = PSC_I2S_FORMATS, }, .ops = &psc_i2s_dai_ops, -} }; -EXPORT_SYMBOL_GPL(psc_i2s_dai); +}; + +/* --------------------------------------------------------------------- + * The PSC I2S 'ASoC platform' driver + * + * Can be referenced by an 'ASoC machine' driver + * This driver only deals with the audio bus; it doesn't have any + * interaction with the attached codec + */ + +static const struct snd_pcm_hardware psc_i2s_pcm_hardware = { + .info = SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_MMAP_VALID | + SNDRV_PCM_INFO_INTERLEAVED | SNDRV_PCM_INFO_BLOCK_TRANSFER | + SNDRV_PCM_INFO_BATCH, + .formats = SNDRV_PCM_FMTBIT_S8 | SNDRV_PCM_FMTBIT_S16_BE | + SNDRV_PCM_FMTBIT_S24_BE | SNDRV_PCM_FMTBIT_S32_BE, + .rate_min = 8000, + .rate_max = 48000, + .channels_min = 2, + .channels_max = 2, + .period_bytes_max = 1024 * 1024, + .period_bytes_min = 32, + .periods_min = 2, + .periods_max = 256, + .buffer_bytes_max = 2 * 1024 * 1024, + .fifo_size = 0, +}; + +static int psc_i2s_pcm_open(struct snd_pcm_substream *substream) +{ + struct snd_soc_pcm_runtime *rtd = substream->private_data; + struct psc_i2s *psc_i2s = rtd->dai->cpu_dai->private_data; + struct psc_i2s_stream *s; + + dev_dbg(psc_i2s->dev, "psc_i2s_pcm_open(substream=%p)\n", substream); + + if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) + s = &psc_i2s->capture; + else + s = &psc_i2s->playback; + + snd_soc_set_runtime_hwparams(substream, &psc_i2s_pcm_hardware); + + s->stream = substream; + return 0; +} + +static int psc_i2s_pcm_close(struct snd_pcm_substream *substream) +{ + struct snd_soc_pcm_runtime *rtd = substream->private_data; + struct psc_i2s *psc_i2s = rtd->dai->cpu_dai->private_data; + struct psc_i2s_stream *s; + + dev_dbg(psc_i2s->dev, "psc_i2s_pcm_close(substream=%p)\n", substream); + + if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) + s = &psc_i2s->capture; + else + s = &psc_i2s->playback; + + s->stream = NULL; + return 0; +} + +static snd_pcm_uframes_t +psc_i2s_pcm_pointer(struct snd_pcm_substream *substream) +{ + struct snd_soc_pcm_runtime *rtd = substream->private_data; + struct psc_i2s *psc_i2s = rtd->dai->cpu_dai->private_data; + struct psc_i2s_stream *s; + dma_addr_t count; + + if (substream->pstr->stream == SNDRV_PCM_STREAM_CAPTURE) + s = &psc_i2s->capture; + else + s = &psc_i2s->playback; + + count = s->period_current_pt - s->period_start; + + return bytes_to_frames(substream->runtime, count); +} + +static struct snd_pcm_ops psc_i2s_pcm_ops = { + .open = psc_i2s_pcm_open, + .close = psc_i2s_pcm_close, + .ioctl = snd_pcm_lib_ioctl, + .pointer = psc_i2s_pcm_pointer, +}; + +static u64 psc_i2s_pcm_dmamask = 0xffffffff; +static int psc_i2s_pcm_new(struct snd_card *card, struct snd_soc_dai *dai, + struct snd_pcm *pcm) +{ + struct snd_soc_pcm_runtime *rtd = pcm->private_data; + size_t size = psc_i2s_pcm_hardware.buffer_bytes_max; + int rc = 0; + + dev_dbg(rtd->socdev->dev, "psc_i2s_pcm_new(card=%p, dai=%p, pcm=%p)\n", + card, dai, pcm); + + if (!card->dev->dma_mask) + card->dev->dma_mask = &psc_i2s_pcm_dmamask; + if (!card->dev->coherent_dma_mask) + card->dev->coherent_dma_mask = 0xffffffff; + + if (pcm->streams[0].substream) { + rc = snd_dma_alloc_pages(SNDRV_DMA_TYPE_DEV, pcm->dev, size, + &pcm->streams[0].substream->dma_buffer); + if (rc) + goto playback_alloc_err; + } + + if (pcm->streams[1].substream) { + rc = snd_dma_alloc_pages(SNDRV_DMA_TYPE_DEV, pcm->dev, size, + &pcm->streams[1].substream->dma_buffer); + if (rc) + goto capture_alloc_err; + } + + return 0; + + capture_alloc_err: + if (pcm->streams[0].substream) + snd_dma_free_pages(&pcm->streams[0].substream->dma_buffer); + playback_alloc_err: + dev_err(card->dev, "Cannot allocate buffer(s)\n"); + return -ENOMEM; +} + +static void psc_i2s_pcm_free(struct snd_pcm *pcm) +{ + struct snd_soc_pcm_runtime *rtd = pcm->private_data; + struct snd_pcm_substream *substream; + int stream; + + dev_dbg(rtd->socdev->dev, "psc_i2s_pcm_free(pcm=%p)\n", pcm); + + for (stream = 0; stream < 2; stream++) { + substream = pcm->streams[stream].substream; + if (substream) { + snd_dma_free_pages(&substream->dma_buffer); + substream->dma_buffer.area = NULL; + substream->dma_buffer.addr = 0; + } + } +} + +struct snd_soc_platform psc_i2s_pcm_soc_platform = { + .name = "mpc5200-psc-audio", + .pcm_ops = &psc_i2s_pcm_ops, + .pcm_new = &psc_i2s_pcm_new, + .pcm_free = &psc_i2s_pcm_free, +}; + +/* --------------------------------------------------------------------- + * Sysfs attributes for debugging + */ + +static ssize_t psc_i2s_status_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct psc_i2s *psc_i2s = dev_get_drvdata(dev); + + return sprintf(buf, "status=%.4x sicr=%.8x rfnum=%i rfstat=0x%.4x " + "tfnum=%i tfstat=0x%.4x\n", + in_be16(&psc_i2s->psc_regs->sr_csr.status), + in_be32(&psc_i2s->psc_regs->sicr), + in_be16(&psc_i2s->fifo_regs->rfnum) & 0x1ff, + in_be16(&psc_i2s->fifo_regs->rfstat), + in_be16(&psc_i2s->fifo_regs->tfnum) & 0x1ff, + in_be16(&psc_i2s->fifo_regs->tfstat)); +} + +static int *psc_i2s_get_stat_attr(struct psc_i2s *psc_i2s, const char *name) +{ + if (strcmp(name, "playback_underrun") == 0) + return &psc_i2s->stats.underrun_count; + if (strcmp(name, "capture_overrun") == 0) + return &psc_i2s->stats.overrun_count; + + return NULL; +} + +static ssize_t psc_i2s_stat_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct psc_i2s *psc_i2s = dev_get_drvdata(dev); + int *attrib; + + attrib = psc_i2s_get_stat_attr(psc_i2s, attr->attr.name); + if (!attrib) + return 0; + + return sprintf(buf, "%i\n", *attrib); +} + +static ssize_t psc_i2s_stat_store(struct device *dev, + struct device_attribute *attr, + const char *buf, + size_t count) +{ + struct psc_i2s *psc_i2s = dev_get_drvdata(dev); + int *attrib; + + attrib = psc_i2s_get_stat_attr(psc_i2s, attr->attr.name); + if (!attrib) + return 0; + + *attrib = simple_strtoul(buf, NULL, 0); + return count; +} + +static DEVICE_ATTR(status, 0644, psc_i2s_status_show, NULL); +static DEVICE_ATTR(playback_underrun, 0644, psc_i2s_stat_show, + psc_i2s_stat_store); +static DEVICE_ATTR(capture_overrun, 0644, psc_i2s_stat_show, + psc_i2s_stat_store); /* --------------------------------------------------------------------- * OF platform bus binding code: @@ -156,65 +718,150 @@ EXPORT_SYMBOL_GPL(psc_i2s_dai); static int __devinit psc_i2s_of_probe(struct of_device *op, const struct of_device_id *match) { - int rc; - struct psc_dma *psc_dma; - struct mpc52xx_psc __iomem *regs; - - rc = mpc5200_audio_dma_create(op); - if (rc != 0) - return rc; + phys_addr_t fifo; + struct psc_i2s *psc_i2s; + struct resource res; + int size, psc_id, irq, rc; + const __be32 *prop; + void __iomem *regs; + + dev_dbg(&op->dev, "probing psc i2s device\n"); + + /* Get the PSC ID */ + prop = of_get_property(op->node, "cell-index", &size); + if (!prop || size < sizeof *prop) + return -ENODEV; + psc_id = be32_to_cpu(*prop); + + /* Fetch the registers and IRQ of the PSC */ + irq = irq_of_parse_and_map(op->node, 0); + if (of_address_to_resource(op->node, 0, &res)) { + dev_err(&op->dev, "Missing reg property\n"); + return -ENODEV; + } + regs = ioremap(res.start, 1 + res.end - res.start); + if (!regs) { + dev_err(&op->dev, "Could not map registers\n"); + return -ENODEV; + } - rc = snd_soc_register_dais(psc_i2s_dai, ARRAY_SIZE(psc_i2s_dai)); - if (rc != 0) { - pr_err("Failed to register DAI\n"); - return 0; + /* Allocate and initialize the driver private data */ + psc_i2s = kzalloc(sizeof *psc_i2s, GFP_KERNEL); + if (!psc_i2s) { + iounmap(regs); + return -ENOMEM; + } + spin_lock_init(&psc_i2s->lock); + psc_i2s->irq = irq; + psc_i2s->psc_regs = regs; + psc_i2s->fifo_regs = regs + sizeof *psc_i2s->psc_regs; + psc_i2s->dev = &op->dev; + psc_i2s->playback.psc_i2s = psc_i2s; + psc_i2s->capture.psc_i2s = psc_i2s; + snprintf(psc_i2s->name, sizeof psc_i2s->name, "PSC%u", psc_id+1); + + /* Fill out the CPU DAI structure */ + memcpy(&psc_i2s->dai, &psc_i2s_dai_template, sizeof psc_i2s->dai); + psc_i2s->dai.private_data = psc_i2s; + psc_i2s->dai.name = psc_i2s->name; + psc_i2s->dai.id = psc_id; + + /* Find the address of the fifo data registers and setup the + * DMA tasks */ + fifo = res.start + offsetof(struct mpc52xx_psc, buffer.buffer_32); + psc_i2s->capture.bcom_task = + bcom_psc_gen_bd_rx_init(psc_id, 10, fifo, 512); + psc_i2s->playback.bcom_task = + bcom_psc_gen_bd_tx_init(psc_id, 10, fifo); + if (!psc_i2s->capture.bcom_task || + !psc_i2s->playback.bcom_task) { + dev_err(&op->dev, "Could not allocate bestcomm tasks\n"); + iounmap(regs); + kfree(psc_i2s); + return -ENODEV; } - psc_dma = dev_get_drvdata(&op->dev); - regs = psc_dma->psc_regs; + /* Disable all interrupts and reset the PSC */ + out_be16(&psc_i2s->psc_regs->isr_imr.imr, 0); + out_8(&psc_i2s->psc_regs->command, 3 << 4); /* reset transmitter */ + out_8(&psc_i2s->psc_regs->command, 2 << 4); /* reset receiver */ + out_8(&psc_i2s->psc_regs->command, 1 << 4); /* reset mode */ + out_8(&psc_i2s->psc_regs->command, 4 << 4); /* reset error */ /* Configure the serial interface mode; defaulting to CODEC8 mode */ - psc_dma->sicr = MPC52xx_PSC_SICR_DTS1 | MPC52xx_PSC_SICR_I2S | + psc_i2s->sicr = MPC52xx_PSC_SICR_DTS1 | MPC52xx_PSC_SICR_I2S | MPC52xx_PSC_SICR_CLKPOL; - out_be32(&psc_dma->psc_regs->sicr, - psc_dma->sicr | MPC52xx_PSC_SICR_SIM_CODEC_8); + if (of_get_property(op->node, "fsl,cellslave", NULL)) + psc_i2s->sicr |= MPC52xx_PSC_SICR_CELLSLAVE | + MPC52xx_PSC_SICR_GENCLK; + out_be32(&psc_i2s->psc_regs->sicr, + psc_i2s->sicr | MPC52xx_PSC_SICR_SIM_CODEC_8); /* Check for the codec handle. If it is not present then we * are done */ if (!of_get_property(op->node, "codec-handle", NULL)) return 0; - /* Due to errata in the dma mode; need to line up enabling - * the transmitter with a transition on the frame sync - * line */ - - /* first make sure it is low */ - while ((in_8(®s->ipcr_acr.ipcr) & 0x80) != 0) - ; - /* then wait for the transition to high */ - while ((in_8(®s->ipcr_acr.ipcr) & 0x80) == 0) - ; - /* Finally, enable the PSC. - * Receiver must always be enabled; even when we only want - * transmit. (see 15.3.2.3 of MPC5200B User's Guide) */ - - /* Go */ - out_8(&psc_dma->psc_regs->command, - MPC52xx_PSC_TX_ENABLE | MPC52xx_PSC_RX_ENABLE); + /* Set up mode register; + * First write: RxRdy (FIFO Alarm) generates rx FIFO irq + * Second write: register Normal mode for non loopback + */ + out_8(&psc_i2s->psc_regs->mode, 0); + out_8(&psc_i2s->psc_regs->mode, 0); + + /* Set the TX and RX fifo alarm thresholds */ + out_be16(&psc_i2s->fifo_regs->rfalarm, 0x100); + out_8(&psc_i2s->fifo_regs->rfcntl, 0x4); + out_be16(&psc_i2s->fifo_regs->tfalarm, 0x100); + out_8(&psc_i2s->fifo_regs->tfcntl, 0x7); + + /* Lookup the IRQ numbers */ + psc_i2s->playback.irq = + bcom_get_task_irq(psc_i2s->playback.bcom_task); + psc_i2s->capture.irq = + bcom_get_task_irq(psc_i2s->capture.bcom_task); + + /* Save what we've done so it can be found again later */ + dev_set_drvdata(&op->dev, psc_i2s); + + /* Register the SYSFS files */ + rc = device_create_file(psc_i2s->dev, &dev_attr_status); + rc |= device_create_file(psc_i2s->dev, &dev_attr_capture_overrun); + rc |= device_create_file(psc_i2s->dev, &dev_attr_playback_underrun); + if (rc) + dev_info(psc_i2s->dev, "error creating sysfs files\n"); + + snd_soc_register_platform(&psc_i2s_pcm_soc_platform); + + /* Tell the ASoC OF helpers about it */ + of_snd_soc_register_platform(&psc_i2s_pcm_soc_platform, op->node, + &psc_i2s->dai); return 0; - } static int __devexit psc_i2s_of_remove(struct of_device *op) { - return mpc5200_audio_dma_destroy(op); + struct psc_i2s *psc_i2s = dev_get_drvdata(&op->dev); + + dev_dbg(&op->dev, "psc_i2s_remove()\n"); + + snd_soc_unregister_platform(&psc_i2s_pcm_soc_platform); + + bcom_gen_bd_rx_release(psc_i2s->capture.bcom_task); + bcom_gen_bd_tx_release(psc_i2s->playback.bcom_task); + + iounmap(psc_i2s->psc_regs); + iounmap(psc_i2s->fifo_regs); + kfree(psc_i2s); + dev_set_drvdata(&op->dev, NULL); + + return 0; } /* Match table for of_platform binding */ static struct of_device_id psc_i2s_match[] __devinitdata = { { .compatible = "fsl,mpc5200-psc-i2s", }, - { .compatible = "fsl,mpc5200b-psc-i2s", }, {} }; MODULE_DEVICE_TABLE(of, psc_i2s_match); @@ -245,7 +892,4 @@ static void __exit psc_i2s_exit(void) } module_exit(psc_i2s_exit); -MODULE_AUTHOR("Grant Likely "); -MODULE_DESCRIPTION("Freescale MPC5200 PSC in I2S mode ASoC Driver"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/fsl/mpc5200_psc_i2s.h b/trunk/sound/soc/fsl/mpc5200_psc_i2s.h deleted file mode 100644 index ce55e070fdf3..000000000000 --- a/trunk/sound/soc/fsl/mpc5200_psc_i2s.h +++ /dev/null @@ -1,12 +0,0 @@ -/* - * Freescale MPC5200 PSC in I2S mode - * ALSA SoC Digital Audio Interface (DAI) driver - * - */ - -#ifndef __SOUND_SOC_FSL_MPC52xx_PSC_I2S_H__ -#define __SOUND_SOC_FSL_MPC52xx_PSC_I2S_H__ - -extern struct snd_soc_dai psc_i2s_dai[]; - -#endif /* __SOUND_SOC_FSL_MPC52xx_PSC_I2S_H__ */ diff --git a/trunk/sound/soc/fsl/pcm030-audio-fabric.c b/trunk/sound/soc/fsl/pcm030-audio-fabric.c deleted file mode 100644 index 8766f7a3893d..000000000000 --- a/trunk/sound/soc/fsl/pcm030-audio-fabric.c +++ /dev/null @@ -1,90 +0,0 @@ -/* - * Phytec pcm030 driver for the PSC of the Freescale MPC52xx - * configured as AC97 interface - * - * Copyright 2008 Jon Smirl, Digispeaker - * Author: Jon Smirl - * - * This file is licensed under the terms of the GNU General Public License - * version 2. This program is licensed "as is" without any warranty of any - * kind, whether express or implied. - */ - -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include - -#include "mpc5200_dma.h" -#include "mpc5200_psc_ac97.h" -#include "../codecs/wm9712.h" - -static struct snd_soc_device device; -static struct snd_soc_card card; - -static struct snd_soc_dai_link pcm030_fabric_dai[] = { -{ - .name = "AC97", - .stream_name = "AC97 Analog", - .codec_dai = &wm9712_dai[WM9712_DAI_AC97_HIFI], - .cpu_dai = &psc_ac97_dai[MPC5200_AC97_NORMAL], -}, -{ - .name = "AC97", - .stream_name = "AC97 IEC958", - .codec_dai = &wm9712_dai[WM9712_DAI_AC97_AUX], - .cpu_dai = &psc_ac97_dai[MPC5200_AC97_SPDIF], -}, -}; - -static __init int pcm030_fabric_init(void) -{ - struct platform_device *pdev; - int rc; - - if (!machine_is_compatible("phytec,pcm030")) - return -ENODEV; - - card.platform = &mpc5200_audio_dma_platform; - card.name = "pcm030"; - card.dai_link = pcm030_fabric_dai; - card.num_links = ARRAY_SIZE(pcm030_fabric_dai); - - device.card = &card; - device.codec_dev = &soc_codec_dev_wm9712; - - pdev = platform_device_alloc("soc-audio", 1); - if (!pdev) { - pr_err("pcm030_fabric_init: platform_device_alloc() failed\n"); - return -ENODEV; - } - - platform_set_drvdata(pdev, &device); - device.dev = &pdev->dev; - - rc = platform_device_add(pdev); - if (rc) { - pr_err("pcm030_fabric_init: platform_device_add() failed\n"); - return -ENODEV; - } - return 0; -} - -module_init(pcm030_fabric_init); - - -MODULE_AUTHOR("Jon Smirl "); -MODULE_DESCRIPTION(DRV_NAME ": mpc5200 pcm030 fabric driver"); -MODULE_LICENSE("GPL"); - diff --git a/trunk/sound/soc/omap/Kconfig b/trunk/sound/soc/omap/Kconfig index b771238662b6..675732e724d5 100644 --- a/trunk/sound/soc/omap/Kconfig +++ b/trunk/sound/soc/omap/Kconfig @@ -39,14 +39,6 @@ config SND_OMAP_SOC_OMAP2EVM help Say Y if you want to add support for SoC audio on the omap2evm board. -config SND_OMAP_SOC_OMAP3EVM - tristate "SoC Audio support for OMAP3EVM board" - depends on TWL4030_CORE && SND_OMAP_SOC && MACH_OMAP3EVM - select SND_OMAP_SOC_MCBSP - select SND_SOC_TWL4030 - help - Say Y if you want to add support for SoC audio on the omap3evm board. - config SND_OMAP_SOC_SDP3430 tristate "SoC Audio support for Texas Instruments SDP3430" depends on TWL4030_CORE && SND_OMAP_SOC && MACH_OMAP_3430SDP diff --git a/trunk/sound/soc/omap/Makefile b/trunk/sound/soc/omap/Makefile index a37f49862389..0c9e4ac37660 100644 --- a/trunk/sound/soc/omap/Makefile +++ b/trunk/sound/soc/omap/Makefile @@ -10,7 +10,6 @@ snd-soc-n810-objs := n810.o snd-soc-osk5912-objs := osk5912.o snd-soc-overo-objs := overo.o snd-soc-omap2evm-objs := omap2evm.o -snd-soc-omap3evm-objs := omap3evm.o snd-soc-sdp3430-objs := sdp3430.o snd-soc-omap3pandora-objs := omap3pandora.o snd-soc-omap3beagle-objs := omap3beagle.o @@ -19,7 +18,6 @@ obj-$(CONFIG_SND_OMAP_SOC_N810) += snd-soc-n810.o obj-$(CONFIG_SND_OMAP_SOC_OSK5912) += snd-soc-osk5912.o obj-$(CONFIG_SND_OMAP_SOC_OVERO) += snd-soc-overo.o obj-$(CONFIG_MACH_OMAP2EVM) += snd-soc-omap2evm.o -obj-$(CONFIG_MACH_OMAP3EVM) += snd-soc-omap3evm.o obj-$(CONFIG_SND_OMAP_SOC_SDP3430) += snd-soc-sdp3430.o obj-$(CONFIG_SND_OMAP_SOC_OMAP3_PANDORA) += snd-soc-omap3pandora.o obj-$(CONFIG_SND_OMAP_SOC_OMAP3_BEAGLE) += snd-soc-omap3beagle.o diff --git a/trunk/sound/soc/omap/n810.c b/trunk/sound/soc/omap/n810.c index b60b1dfbc435..91ef17992de5 100644 --- a/trunk/sound/soc/omap/n810.c +++ b/trunk/sound/soc/omap/n810.c @@ -383,9 +383,10 @@ static int __init n810_soc_init(void) clk_set_parent(sys_clkout2_src, func96m_clk); clk_set_rate(sys_clkout2, 12000000); - BUG_ON((gpio_request(N810_HEADSET_AMP_GPIO, "hs_amp") < 0) || - (gpio_request(N810_SPEAKER_AMP_GPIO, "spk_amp") < 0)); - + if (gpio_request(N810_HEADSET_AMP_GPIO, "hs_amp") < 0) + BUG(); + if (gpio_request(N810_SPEAKER_AMP_GPIO, "spk_amp") < 0) + BUG(); gpio_direction_output(N810_HEADSET_AMP_GPIO, 0); gpio_direction_output(N810_SPEAKER_AMP_GPIO, 0); diff --git a/trunk/sound/soc/omap/omap-mcbsp.c b/trunk/sound/soc/omap/omap-mcbsp.c index a5d46a7b196a..912614283848 100644 --- a/trunk/sound/soc/omap/omap-mcbsp.c +++ b/trunk/sound/soc/omap/omap-mcbsp.c @@ -215,9 +215,8 @@ static int omap_mcbsp_dai_hw_params(struct snd_pcm_substream *substream, struct omap_mcbsp_data *mcbsp_data = to_mcbsp(cpu_dai->private_data); struct omap_mcbsp_reg_cfg *regs = &mcbsp_data->regs; int dma, bus_id = mcbsp_data->bus_id, id = cpu_dai->id; - int wlen, channels, wpf; + int wlen, channels; unsigned long port; - unsigned int format; if (cpu_class_is_omap1()) { dma = omap1_dma_reqs[bus_id][substream->stream]; @@ -245,24 +244,18 @@ static int omap_mcbsp_dai_hw_params(struct snd_pcm_substream *substream, return 0; } - format = mcbsp_data->fmt & SND_SOC_DAIFMT_FORMAT_MASK; - wpf = channels = params_channels(params); + channels = params_channels(params); switch (channels) { case 2: - if (format == SND_SOC_DAIFMT_I2S) { - /* Use dual-phase frames */ - regs->rcr2 |= RPHASE; - regs->xcr2 |= XPHASE; - /* Set 1 word per (McBSP) frame for phase1 and phase2 */ - wpf--; - regs->rcr2 |= RFRLEN2(wpf - 1); - regs->xcr2 |= XFRLEN2(wpf - 1); - } + /* Use dual-phase frames */ + regs->rcr2 |= RPHASE; + regs->xcr2 |= XPHASE; case 1: - case 4: - /* Set word per (McBSP) frame for phase1 */ - regs->rcr1 |= RFRLEN1(wpf - 1); - regs->xcr1 |= XFRLEN1(wpf - 1); + /* Set 1 word per (McBSP) frame */ + regs->rcr2 |= RFRLEN2(1 - 1); + regs->rcr1 |= RFRLEN1(1 - 1); + regs->xcr2 |= XFRLEN2(1 - 1); + regs->xcr1 |= XFRLEN1(1 - 1); break; default: /* Unsupported number of channels */ @@ -284,12 +277,11 @@ static int omap_mcbsp_dai_hw_params(struct snd_pcm_substream *substream, } /* Set FS period and length in terms of bit clock periods */ - switch (format) { + switch (mcbsp_data->fmt & SND_SOC_DAIFMT_FORMAT_MASK) { case SND_SOC_DAIFMT_I2S: - regs->srgr2 |= FPER(wlen * channels - 1); + regs->srgr2 |= FPER(wlen * 2 - 1); regs->srgr1 |= FWID(wlen - 1); break; - case SND_SOC_DAIFMT_DSP_A: case SND_SOC_DAIFMT_DSP_B: regs->srgr2 |= FPER(wlen * channels - 1); regs->srgr1 |= FWID(0); @@ -334,13 +326,6 @@ static int omap_mcbsp_dai_set_dai_fmt(struct snd_soc_dai *cpu_dai, regs->rcr2 |= RDATDLY(1); regs->xcr2 |= XDATDLY(1); break; - case SND_SOC_DAIFMT_DSP_A: - /* 1-bit data delay */ - regs->rcr2 |= RDATDLY(1); - regs->xcr2 |= XDATDLY(1); - /* Invert FS polarity configuration */ - temp_fmt ^= SND_SOC_DAIFMT_NB_IF; - break; case SND_SOC_DAIFMT_DSP_B: /* 0-bit data delay */ regs->rcr2 |= RDATDLY(0); @@ -507,13 +492,13 @@ static struct snd_soc_dai_ops omap_mcbsp_dai_ops = { .id = (link_id), \ .playback = { \ .channels_min = 1, \ - .channels_max = 4, \ + .channels_max = 2, \ .rates = OMAP_MCBSP_RATES, \ .formats = SNDRV_PCM_FMTBIT_S16_LE, \ }, \ .capture = { \ .channels_min = 1, \ - .channels_max = 4, \ + .channels_max = 2, \ .rates = OMAP_MCBSP_RATES, \ .formats = SNDRV_PCM_FMTBIT_S16_LE, \ }, \ diff --git a/trunk/sound/soc/omap/omap-pcm.c b/trunk/sound/soc/omap/omap-pcm.c index 6454e15f7d28..07cf7f46b584 100644 --- a/trunk/sound/soc/omap/omap-pcm.c +++ b/trunk/sound/soc/omap/omap-pcm.c @@ -87,10 +87,8 @@ static int omap_pcm_hw_params(struct snd_pcm_substream *substream, struct omap_pcm_dma_data *dma_data = rtd->dai->cpu_dai->dma_data; int err = 0; - /* return if this is a bufferless transfer e.g. - * codec <--> BT codec or GSM modem -- lg FIXME */ if (!dma_data) - return 0; + return -ENODEV; snd_pcm_set_runtime_buffer(substream, &substream->dma_buffer); runtime->dma_bytes = params_buffer_bytes(params); @@ -136,11 +134,6 @@ static int omap_pcm_prepare(struct snd_pcm_substream *substream) struct omap_pcm_dma_data *dma_data = prtd->dma_data; struct omap_dma_channel_params dma_params; - /* return if this is a bufferless transfer e.g. - * codec <--> BT codec or GSM modem -- lg FIXME */ - if (!prtd->dma_data) - return 0; - memset(&dma_params, 0, sizeof(dma_params)); /* * Note: Regardless of interface data formats supported by OMAP McBSP diff --git a/trunk/sound/soc/omap/omap2evm.c b/trunk/sound/soc/omap/omap2evm.c index 027e1a40f8a1..0c2322dcf02a 100644 --- a/trunk/sound/soc/omap/omap2evm.c +++ b/trunk/sound/soc/omap/omap2evm.c @@ -86,7 +86,7 @@ static struct snd_soc_dai_link omap2evm_dai = { .name = "TWL4030", .stream_name = "TWL4030", .cpu_dai = &omap_mcbsp_dai[0], - .codec_dai = &twl4030_dai[TWL4030_DAI_HIFI], + .codec_dai = &twl4030_dai, .ops = &omap2evm_ops, }; diff --git a/trunk/sound/soc/omap/omap3beagle.c b/trunk/sound/soc/omap/omap3beagle.c index b0cff9f33b7e..fd24a4acd2f5 100644 --- a/trunk/sound/soc/omap/omap3beagle.c +++ b/trunk/sound/soc/omap/omap3beagle.c @@ -41,33 +41,23 @@ static int omap3beagle_hw_params(struct snd_pcm_substream *substream, struct snd_soc_pcm_runtime *rtd = substream->private_data; struct snd_soc_dai *codec_dai = rtd->dai->codec_dai; struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai; - unsigned int fmt; int ret; - switch (params_channels(params)) { - case 2: /* Stereo I2S mode */ - fmt = SND_SOC_DAIFMT_I2S | - SND_SOC_DAIFMT_NB_NF | - SND_SOC_DAIFMT_CBM_CFM; - break; - case 4: /* Four channel TDM mode */ - fmt = SND_SOC_DAIFMT_DSP_A | - SND_SOC_DAIFMT_IB_NF | - SND_SOC_DAIFMT_CBM_CFM; - break; - default: - return -EINVAL; - } - /* Set codec DAI configuration */ - ret = snd_soc_dai_set_fmt(codec_dai, fmt); + ret = snd_soc_dai_set_fmt(codec_dai, + SND_SOC_DAIFMT_I2S | + SND_SOC_DAIFMT_NB_NF | + SND_SOC_DAIFMT_CBM_CFM); if (ret < 0) { printk(KERN_ERR "can't set codec DAI configuration\n"); return ret; } /* Set cpu DAI configuration */ - ret = snd_soc_dai_set_fmt(cpu_dai, fmt); + ret = snd_soc_dai_set_fmt(cpu_dai, + SND_SOC_DAIFMT_I2S | + SND_SOC_DAIFMT_NB_NF | + SND_SOC_DAIFMT_CBM_CFM); if (ret < 0) { printk(KERN_ERR "can't set cpu DAI configuration\n"); return ret; @@ -93,7 +83,7 @@ static struct snd_soc_dai_link omap3beagle_dai = { .name = "TWL4030", .stream_name = "TWL4030", .cpu_dai = &omap_mcbsp_dai[0], - .codec_dai = &twl4030_dai[TWL4030_DAI_HIFI], + .codec_dai = &twl4030_dai, .ops = &omap3beagle_ops, }; diff --git a/trunk/sound/soc/omap/omap3evm.c b/trunk/sound/soc/omap/omap3evm.c deleted file mode 100644 index 9114c263077b..000000000000 --- a/trunk/sound/soc/omap/omap3evm.c +++ /dev/null @@ -1,147 +0,0 @@ -/* - * omap3evm.c -- ALSA SoC support for OMAP3 EVM - * - * Author: Anuj Aggarwal - * - * Based on sound/soc/omap/beagle.c by Steve Sakoman - * - * Copyright (C) 2008 Texas Instruments, Incorporated - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation version 2. - * - * This program is distributed "as is" WITHOUT ANY WARRANTY of any kind, - * whether express or implied; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - */ - -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include - -#include "omap-mcbsp.h" -#include "omap-pcm.h" -#include "../codecs/twl4030.h" - -static int omap3evm_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_dai *codec_dai = rtd->dai->codec_dai; - struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai; - int ret; - - /* Set codec DAI configuration */ - ret = snd_soc_dai_set_fmt(codec_dai, - SND_SOC_DAIFMT_I2S | - SND_SOC_DAIFMT_NB_NF | - SND_SOC_DAIFMT_CBM_CFM); - if (ret < 0) { - printk(KERN_ERR "Can't set codec DAI configuration\n"); - return ret; - } - - /* Set cpu DAI configuration */ - ret = snd_soc_dai_set_fmt(cpu_dai, - SND_SOC_DAIFMT_I2S | - SND_SOC_DAIFMT_NB_NF | - SND_SOC_DAIFMT_CBM_CFM); - if (ret < 0) { - printk(KERN_ERR "Can't set cpu DAI configuration\n"); - return ret; - } - - /* Set the codec system clock for DAC and ADC */ - ret = snd_soc_dai_set_sysclk(codec_dai, 0, 26000000, - SND_SOC_CLOCK_IN); - if (ret < 0) { - printk(KERN_ERR "Can't set codec system clock\n"); - return ret; - } - - return 0; -} - -static struct snd_soc_ops omap3evm_ops = { - .hw_params = omap3evm_hw_params, -}; - -/* Digital audio interface glue - connects codec <--> CPU */ -static struct snd_soc_dai_link omap3evm_dai = { - .name = "TWL4030", - .stream_name = "TWL4030", - .cpu_dai = &omap_mcbsp_dai[0], - .codec_dai = &twl4030_dai[TWL4030_DAI_HIFI], - .ops = &omap3evm_ops, -}; - -/* Audio machine driver */ -static struct snd_soc_card snd_soc_omap3evm = { - .name = "omap3evm", - .platform = &omap_soc_platform, - .dai_link = &omap3evm_dai, - .num_links = 1, -}; - -/* Audio subsystem */ -static struct snd_soc_device omap3evm_snd_devdata = { - .card = &snd_soc_omap3evm, - .codec_dev = &soc_codec_dev_twl4030, -}; - -static struct platform_device *omap3evm_snd_device; - -static int __init omap3evm_soc_init(void) -{ - int ret; - - if (!machine_is_omap3evm()) { - pr_err("Not OMAP3 EVM!\n"); - return -ENODEV; - } - pr_info("OMAP3 EVM SoC init\n"); - - omap3evm_snd_device = platform_device_alloc("soc-audio", -1); - if (!omap3evm_snd_device) { - printk(KERN_ERR "Platform device allocation failed\n"); - return -ENOMEM; - } - - platform_set_drvdata(omap3evm_snd_device, &omap3evm_snd_devdata); - omap3evm_snd_devdata.dev = &omap3evm_snd_device->dev; - *(unsigned int *)omap3evm_dai.cpu_dai->private_data = 1; - - ret = platform_device_add(omap3evm_snd_device); - if (ret) - goto err1; - - return 0; - -err1: - printk(KERN_ERR "Unable to add platform device\n"); - platform_device_put(omap3evm_snd_device); - - return ret; -} - -static void __exit omap3evm_soc_exit(void) -{ - platform_device_unregister(omap3evm_snd_device); -} - -module_init(omap3evm_soc_init); -module_exit(omap3evm_soc_exit); - -MODULE_AUTHOR("Anuj Aggarwal "); -MODULE_DESCRIPTION("ALSA SoC OMAP3 EVM"); -MODULE_LICENSE("GPLv2"); diff --git a/trunk/sound/soc/omap/omap3pandora.c b/trunk/sound/soc/omap/omap3pandora.c index ad219aaf7cb8..fe282d4ef422 100644 --- a/trunk/sound/soc/omap/omap3pandora.c +++ b/trunk/sound/soc/omap/omap3pandora.c @@ -228,14 +228,14 @@ static struct snd_soc_dai_link omap3pandora_dai[] = { .name = "PCM1773", .stream_name = "HiFi Out", .cpu_dai = &omap_mcbsp_dai[0], - .codec_dai = &twl4030_dai[TWL4030_DAI_HIFI], + .codec_dai = &twl4030_dai, .ops = &omap3pandora_out_ops, .init = omap3pandora_out_init, }, { .name = "TWL4030", .stream_name = "Line/Mic In", .cpu_dai = &omap_mcbsp_dai[1], - .codec_dai = &twl4030_dai[TWL4030_DAI_HIFI], + .codec_dai = &twl4030_dai, .ops = &omap3pandora_in_ops, .init = omap3pandora_in_init, } diff --git a/trunk/sound/soc/omap/overo.c b/trunk/sound/soc/omap/overo.c index ec4f8fd8b3a2..a72dc4e159e5 100644 --- a/trunk/sound/soc/omap/overo.c +++ b/trunk/sound/soc/omap/overo.c @@ -83,7 +83,7 @@ static struct snd_soc_dai_link overo_dai = { .name = "TWL4030", .stream_name = "TWL4030", .cpu_dai = &omap_mcbsp_dai[0], - .codec_dai = &twl4030_dai[TWL4030_DAI_HIFI], + .codec_dai = &twl4030_dai, .ops = &overo_ops, }; diff --git a/trunk/sound/soc/omap/sdp3430.c b/trunk/sound/soc/omap/sdp3430.c index b719e5db4f57..10f1c867f11d 100644 --- a/trunk/sound/soc/omap/sdp3430.c +++ b/trunk/sound/soc/omap/sdp3430.c @@ -84,49 +84,6 @@ static struct snd_soc_ops sdp3430_ops = { .hw_params = sdp3430_hw_params, }; -static int sdp3430_hw_voice_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_dai *codec_dai = rtd->dai->codec_dai; - struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai; - int ret; - - /* Set codec DAI configuration */ - ret = snd_soc_dai_set_fmt(codec_dai, - SND_SOC_DAIFMT_DSP_A | - SND_SOC_DAIFMT_IB_NF | - SND_SOC_DAIFMT_CBS_CFM); - if (ret) { - printk(KERN_ERR "can't set codec DAI configuration\n"); - return ret; - } - - /* Set cpu DAI configuration */ - ret = snd_soc_dai_set_fmt(cpu_dai, - SND_SOC_DAIFMT_DSP_A | - SND_SOC_DAIFMT_IB_NF | - SND_SOC_DAIFMT_CBM_CFM); - if (ret < 0) { - printk(KERN_ERR "can't set cpu DAI configuration\n"); - return ret; - } - - /* Set the codec system clock for DAC and ADC */ - ret = snd_soc_dai_set_sysclk(codec_dai, 0, 26000000, - SND_SOC_CLOCK_IN); - if (ret < 0) { - printk(KERN_ERR "can't set codec system clock\n"); - return ret; - } - - return 0; -} - -static struct snd_soc_ops sdp3430_voice_ops = { - .hw_params = sdp3430_hw_voice_params, -}; - /* Headset jack */ static struct snd_soc_jack hs_jack; @@ -235,58 +192,28 @@ static int sdp3430_twl4030_init(struct snd_soc_codec *codec) return ret; } -static int sdp3430_twl4030_voice_init(struct snd_soc_codec *codec) -{ - unsigned short reg; - - /* Enable voice interface */ - reg = codec->read(codec, TWL4030_REG_VOICE_IF); - reg |= TWL4030_VIF_DIN_EN | TWL4030_VIF_DOUT_EN | TWL4030_VIF_EN; - codec->write(codec, TWL4030_REG_VOICE_IF, reg); - - return 0; -} - - /* Digital audio interface glue - connects codec <--> CPU */ -static struct snd_soc_dai_link sdp3430_dai[] = { - { - .name = "TWL4030 I2S", - .stream_name = "TWL4030 Audio", - .cpu_dai = &omap_mcbsp_dai[0], - .codec_dai = &twl4030_dai[TWL4030_DAI_HIFI], - .init = sdp3430_twl4030_init, - .ops = &sdp3430_ops, - }, - { - .name = "TWL4030 PCM", - .stream_name = "TWL4030 Voice", - .cpu_dai = &omap_mcbsp_dai[1], - .codec_dai = &twl4030_dai[TWL4030_DAI_VOICE], - .init = sdp3430_twl4030_voice_init, - .ops = &sdp3430_voice_ops, - }, +static struct snd_soc_dai_link sdp3430_dai = { + .name = "TWL4030", + .stream_name = "TWL4030", + .cpu_dai = &omap_mcbsp_dai[0], + .codec_dai = &twl4030_dai, + .init = sdp3430_twl4030_init, + .ops = &sdp3430_ops, }; /* Audio machine driver */ static struct snd_soc_card snd_soc_sdp3430 = { .name = "SDP3430", .platform = &omap_soc_platform, - .dai_link = sdp3430_dai, - .num_links = ARRAY_SIZE(sdp3430_dai), -}; - -/* twl4030 setup */ -static struct twl4030_setup_data twl4030_setup = { - .ramp_delay_value = 3, - .sysclk = 26000, + .dai_link = &sdp3430_dai, + .num_links = 1, }; /* Audio subsystem */ static struct snd_soc_device sdp3430_snd_devdata = { .card = &snd_soc_sdp3430, .codec_dev = &soc_codec_dev_twl4030, - .codec_data = &twl4030_setup, }; static struct platform_device *sdp3430_snd_device; @@ -309,8 +236,7 @@ static int __init sdp3430_soc_init(void) platform_set_drvdata(sdp3430_snd_device, &sdp3430_snd_devdata); sdp3430_snd_devdata.dev = &sdp3430_snd_device->dev; - *(unsigned int *)sdp3430_dai[0].cpu_dai->private_data = 1; /* McBSP2 */ - *(unsigned int *)sdp3430_dai[1].cpu_dai->private_data = 2; /* McBSP3 */ + *(unsigned int *)sdp3430_dai.cpu_dai->private_data = 1; /* McBSP2 */ ret = platform_device_add(sdp3430_snd_device); if (ret) diff --git a/trunk/sound/soc/pxa/Kconfig b/trunk/sound/soc/pxa/Kconfig index dcd163a4ee9a..ad8a10fe6298 100644 --- a/trunk/sound/soc/pxa/Kconfig +++ b/trunk/sound/soc/pxa/Kconfig @@ -89,13 +89,13 @@ config SND_PXA2XX_SOC_E800 Toshiba e800 PDA config SND_PXA2XX_SOC_EM_X270 - tristate "SoC Audio support for CompuLab EM-x270, eXeda and CM-X300" + tristate "SoC Audio support for CompuLab EM-x270" depends on SND_PXA2XX_SOC && MACH_EM_X270 select SND_PXA2XX_SOC_AC97 select SND_SOC_WM9712 help Say Y if you want to add support for SoC audio on - CompuLab EM-x270, eXeda and CM-X300 machines. + CompuLab EM-x270. config SND_PXA2XX_SOC_PALM27X bool "SoC Audio support for Palm T|X, T5 and LifeDrive" @@ -134,12 +134,3 @@ config SND_PXA2XX_SOC_MIOA701 help Say Y if you want to add support for SoC audio on the MIO A701. - -config SND_PXA2XX_SOC_IMOTE2 - tristate "SoC Audio support for IMote 2" - depends on SND_PXA2XX_SOC && MACH_INTELMOTE2 - select SND_PXA2XX_SOC_I2S - select SND_SOC_WM8940 - help - Say Y if you want to add support for SoC audio on the - IMote 2. diff --git a/trunk/sound/soc/pxa/Makefile b/trunk/sound/soc/pxa/Makefile index 6e096b480335..4b90c3ccae45 100644 --- a/trunk/sound/soc/pxa/Makefile +++ b/trunk/sound/soc/pxa/Makefile @@ -22,7 +22,6 @@ snd-soc-palm27x-objs := palm27x.o snd-soc-zylonite-objs := zylonite.o snd-soc-magician-objs := magician.o snd-soc-mioa701-objs := mioa701_wm9713.o -snd-soc-imote2-objs := imote2.o obj-$(CONFIG_SND_PXA2XX_SOC_CORGI) += snd-soc-corgi.o obj-$(CONFIG_SND_PXA2XX_SOC_POODLE) += snd-soc-poodle.o @@ -36,4 +35,3 @@ obj-$(CONFIG_SND_PXA2XX_SOC_PALM27X) += snd-soc-palm27x.o obj-$(CONFIG_SND_PXA2XX_SOC_MAGICIAN) += snd-soc-magician.o obj-$(CONFIG_SND_PXA2XX_SOC_MIOA701) += snd-soc-mioa701.o obj-$(CONFIG_SND_SOC_ZYLONITE) += snd-soc-zylonite.o -obj-$(CONFIG_SND_PXA2XX_SOC_IMOTE2) += snd-soc-imote2.o diff --git a/trunk/sound/soc/pxa/em-x270.c b/trunk/sound/soc/pxa/em-x270.c index f4756e4025fd..949be9c2a01b 100644 --- a/trunk/sound/soc/pxa/em-x270.c +++ b/trunk/sound/soc/pxa/em-x270.c @@ -1,7 +1,7 @@ /* - * SoC audio driver for EM-X270, eXeda and CM-X300 + * em-x270.c -- SoC audio for EM-X270 * - * Copyright 2007, 2009 CompuLab, Ltd. + * Copyright 2007 CompuLab, Ltd. * * Author: Mike Rapoport * @@ -68,8 +68,7 @@ static int __init em_x270_init(void) { int ret; - if (!(machine_is_em_x270() || machine_is_exeda() - || machine_is_cm_x300())) + if (!machine_is_em_x270()) return -ENODEV; em_x270_snd_device = platform_device_alloc("soc-audio", -1); @@ -96,5 +95,5 @@ module_exit(em_x270_exit); /* Module information */ MODULE_AUTHOR("Mike Rapoport"); -MODULE_DESCRIPTION("ALSA SoC EM-X270, eXeda and CM-X300"); +MODULE_DESCRIPTION("ALSA SoC EM-X270"); MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/pxa/imote2.c b/trunk/sound/soc/pxa/imote2.c deleted file mode 100644 index 405587a01160..000000000000 --- a/trunk/sound/soc/pxa/imote2.c +++ /dev/null @@ -1,114 +0,0 @@ - -#include -#include - -#include - -#include "../codecs/wm8940.h" -#include "pxa2xx-i2s.h" -#include "pxa2xx-pcm.h" - -static int imote2_asoc_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_dai *codec_dai = rtd->dai->codec_dai; - struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai; - unsigned int clk = 0; - int ret; - - switch (params_rate(params)) { - case 8000: - case 16000: - case 48000: - case 96000: - clk = 12288000; - break; - case 11025: - case 22050: - case 44100: - clk = 11289600; - break; - } - - /* set codec DAI configuration */ - ret = snd_soc_dai_set_fmt(codec_dai, SND_SOC_DAIFMT_I2S - | SND_SOC_DAIFMT_NB_NF - | SND_SOC_DAIFMT_CBS_CFS); - if (ret < 0) - return ret; - - /* CPU should be clock master */ - ret = snd_soc_dai_set_fmt(cpu_dai, SND_SOC_DAIFMT_I2S - | SND_SOC_DAIFMT_NB_NF - | SND_SOC_DAIFMT_CBS_CFS); - if (ret < 0) - return ret; - - ret = snd_soc_dai_set_sysclk(codec_dai, 0, clk, - SND_SOC_CLOCK_IN); - if (ret < 0) - return ret; - - /* set the I2S system clock as input (unused) */ - ret = snd_soc_dai_set_sysclk(cpu_dai, PXA2XX_I2S_SYSCLK, clk, - SND_SOC_CLOCK_OUT); - - return ret; -} - -static struct snd_soc_ops imote2_asoc_ops = { - .hw_params = imote2_asoc_hw_params, -}; - -static struct snd_soc_dai_link imote2_dai = { - .name = "WM8940", - .stream_name = "WM8940", - .cpu_dai = &pxa_i2s_dai, - .codec_dai = &wm8940_dai, - .ops = &imote2_asoc_ops, -}; - -static struct snd_soc_card snd_soc_imote2 = { - .name = "Imote2", - .platform = &pxa2xx_soc_platform, - .dai_link = &imote2_dai, - .num_links = 1, -}; - -static struct snd_soc_device imote2_snd_devdata = { - .card = &snd_soc_imote2, - .codec_dev = &soc_codec_dev_wm8940, -}; - -static struct platform_device *imote2_snd_device; - -static int __init imote2_asoc_init(void) -{ - int ret; - - if (!machine_is_intelmote2()) - return -ENODEV; - imote2_snd_device = platform_device_alloc("soc-audio", -1); - if (!imote2_snd_device) - return -ENOMEM; - - platform_set_drvdata(imote2_snd_device, &imote2_snd_devdata); - imote2_snd_devdata.dev = &imote2_snd_device->dev; - ret = platform_device_add(imote2_snd_device); - if (ret) - platform_device_put(imote2_snd_device); - - return ret; -} -module_init(imote2_asoc_init); - -static void __exit imote2_asoc_exit(void) -{ - platform_device_unregister(imote2_snd_device); -} -module_exit(imote2_asoc_exit); - -MODULE_AUTHOR("Jonathan Cameron"); -MODULE_DESCRIPTION("ALSA SoC Imote 2"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/pxa/magician.c b/trunk/sound/soc/pxa/magician.c index c89a3cdf31e4..0625c342a1c9 100644 --- a/trunk/sound/soc/pxa/magician.c +++ b/trunk/sound/soc/pxa/magician.c @@ -106,7 +106,7 @@ static int magician_playback_hw_params(struct snd_pcm_substream *substream, /* 513156 Hz ~= _2_ * 8000 Hz * 32 (+0.23%) */ acds = PXA_SSP_CLK_AUDIO_DIV_16; break; - default: /* 32 */ + case 32: /* 1026312 Hz ~= _2_ * 8000 Hz * 64 (+0.23%) */ acds = PXA_SSP_CLK_AUDIO_DIV_8; } @@ -118,7 +118,7 @@ static int magician_playback_hw_params(struct snd_pcm_substream *substream, /* 351375 Hz ~= 11025 Hz * 32 (-0.41%) */ acds = PXA_SSP_CLK_AUDIO_DIV_4; break; - default: /* 32 */ + case 32: /* 702750 Hz ~= 11025 Hz * 64 (-0.41%) */ acds = PXA_SSP_CLK_AUDIO_DIV_2; } @@ -130,7 +130,7 @@ static int magician_playback_hw_params(struct snd_pcm_substream *substream, /* 702750 Hz ~= 22050 Hz * 32 (-0.41%) */ acds = PXA_SSP_CLK_AUDIO_DIV_2; break; - default: /* 32 */ + case 32: /* 1405500 Hz ~= 22050 Hz * 64 (-0.41%) */ acds = PXA_SSP_CLK_AUDIO_DIV_1; } @@ -142,7 +142,7 @@ static int magician_playback_hw_params(struct snd_pcm_substream *substream, /* 1405500 Hz ~= 44100 Hz * 32 (-0.41%) */ acds = PXA_SSP_CLK_AUDIO_DIV_2; break; - default: /* 32 */ + case 32: /* 2811000 Hz ~= 44100 Hz * 64 (-0.41%) */ acds = PXA_SSP_CLK_AUDIO_DIV_1; } @@ -154,20 +154,19 @@ static int magician_playback_hw_params(struct snd_pcm_substream *substream, /* 1529375 Hz ~= 48000 Hz * 32 (-0.44%) */ acds = PXA_SSP_CLK_AUDIO_DIV_2; break; - default: /* 32 */ + case 32: /* 3058750 Hz ~= 48000 Hz * 64 (-0.44%) */ acds = PXA_SSP_CLK_AUDIO_DIV_1; } break; case 96000: - default: acps = 12235000; switch (width) { case 16: /* 3058750 Hz ~= 96000 Hz * 32 (-0.44%) */ acds = PXA_SSP_CLK_AUDIO_DIV_1; break; - default: /* 32 */ + case 32: /* 6117500 Hz ~= 96000 Hz * 64 (-0.44%) */ acds = PXA_SSP_CLK_AUDIO_DIV_2; div4 = PXA_SSP_CLK_SCDB_1; diff --git a/trunk/sound/soc/pxa/pxa-ssp.c b/trunk/sound/soc/pxa/pxa-ssp.c index 19c45409d94c..286be31545df 100644 --- a/trunk/sound/soc/pxa/pxa-ssp.c +++ b/trunk/sound/soc/pxa/pxa-ssp.c @@ -50,6 +50,139 @@ struct ssp_priv { #endif }; +#define PXA2xx_SSP1_BASE 0x41000000 +#define PXA27x_SSP2_BASE 0x41700000 +#define PXA27x_SSP3_BASE 0x41900000 +#define PXA3xx_SSP4_BASE 0x41a00000 + +static struct pxa2xx_pcm_dma_params pxa_ssp1_pcm_mono_out = { + .name = "SSP1 PCM Mono out", + .dev_addr = PXA2xx_SSP1_BASE + SSDR, + .drcmr = &DRCMR(14), + .dcmd = DCMD_INCSRCADDR | DCMD_FLOWTRG | + DCMD_BURST16 | DCMD_WIDTH2, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp1_pcm_mono_in = { + .name = "SSP1 PCM Mono in", + .dev_addr = PXA2xx_SSP1_BASE + SSDR, + .drcmr = &DRCMR(13), + .dcmd = DCMD_INCTRGADDR | DCMD_FLOWSRC | + DCMD_BURST16 | DCMD_WIDTH2, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp1_pcm_stereo_out = { + .name = "SSP1 PCM Stereo out", + .dev_addr = PXA2xx_SSP1_BASE + SSDR, + .drcmr = &DRCMR(14), + .dcmd = DCMD_INCSRCADDR | DCMD_FLOWTRG | + DCMD_BURST16 | DCMD_WIDTH4, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp1_pcm_stereo_in = { + .name = "SSP1 PCM Stereo in", + .dev_addr = PXA2xx_SSP1_BASE + SSDR, + .drcmr = &DRCMR(13), + .dcmd = DCMD_INCTRGADDR | DCMD_FLOWSRC | + DCMD_BURST16 | DCMD_WIDTH4, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp2_pcm_mono_out = { + .name = "SSP2 PCM Mono out", + .dev_addr = PXA27x_SSP2_BASE + SSDR, + .drcmr = &DRCMR(16), + .dcmd = DCMD_INCSRCADDR | DCMD_FLOWTRG | + DCMD_BURST16 | DCMD_WIDTH2, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp2_pcm_mono_in = { + .name = "SSP2 PCM Mono in", + .dev_addr = PXA27x_SSP2_BASE + SSDR, + .drcmr = &DRCMR(15), + .dcmd = DCMD_INCTRGADDR | DCMD_FLOWSRC | + DCMD_BURST16 | DCMD_WIDTH2, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp2_pcm_stereo_out = { + .name = "SSP2 PCM Stereo out", + .dev_addr = PXA27x_SSP2_BASE + SSDR, + .drcmr = &DRCMR(16), + .dcmd = DCMD_INCSRCADDR | DCMD_FLOWTRG | + DCMD_BURST16 | DCMD_WIDTH4, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp2_pcm_stereo_in = { + .name = "SSP2 PCM Stereo in", + .dev_addr = PXA27x_SSP2_BASE + SSDR, + .drcmr = &DRCMR(15), + .dcmd = DCMD_INCTRGADDR | DCMD_FLOWSRC | + DCMD_BURST16 | DCMD_WIDTH4, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp3_pcm_mono_out = { + .name = "SSP3 PCM Mono out", + .dev_addr = PXA27x_SSP3_BASE + SSDR, + .drcmr = &DRCMR(67), + .dcmd = DCMD_INCSRCADDR | DCMD_FLOWTRG | + DCMD_BURST16 | DCMD_WIDTH2, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp3_pcm_mono_in = { + .name = "SSP3 PCM Mono in", + .dev_addr = PXA27x_SSP3_BASE + SSDR, + .drcmr = &DRCMR(66), + .dcmd = DCMD_INCTRGADDR | DCMD_FLOWSRC | + DCMD_BURST16 | DCMD_WIDTH2, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp3_pcm_stereo_out = { + .name = "SSP3 PCM Stereo out", + .dev_addr = PXA27x_SSP3_BASE + SSDR, + .drcmr = &DRCMR(67), + .dcmd = DCMD_INCSRCADDR | DCMD_FLOWTRG | + DCMD_BURST16 | DCMD_WIDTH4, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp3_pcm_stereo_in = { + .name = "SSP3 PCM Stereo in", + .dev_addr = PXA27x_SSP3_BASE + SSDR, + .drcmr = &DRCMR(66), + .dcmd = DCMD_INCTRGADDR | DCMD_FLOWSRC | + DCMD_BURST16 | DCMD_WIDTH4, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp4_pcm_mono_out = { + .name = "SSP4 PCM Mono out", + .dev_addr = PXA3xx_SSP4_BASE + SSDR, + .drcmr = &DRCMR(67), + .dcmd = DCMD_INCSRCADDR | DCMD_FLOWTRG | + DCMD_BURST16 | DCMD_WIDTH2, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp4_pcm_mono_in = { + .name = "SSP4 PCM Mono in", + .dev_addr = PXA3xx_SSP4_BASE + SSDR, + .drcmr = &DRCMR(66), + .dcmd = DCMD_INCTRGADDR | DCMD_FLOWSRC | + DCMD_BURST16 | DCMD_WIDTH2, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp4_pcm_stereo_out = { + .name = "SSP4 PCM Stereo out", + .dev_addr = PXA3xx_SSP4_BASE + SSDR, + .drcmr = &DRCMR(67), + .dcmd = DCMD_INCSRCADDR | DCMD_FLOWTRG | + DCMD_BURST16 | DCMD_WIDTH4, +}; + +static struct pxa2xx_pcm_dma_params pxa_ssp4_pcm_stereo_in = { + .name = "SSP4 PCM Stereo in", + .dev_addr = PXA3xx_SSP4_BASE + SSDR, + .drcmr = &DRCMR(66), + .dcmd = DCMD_INCTRGADDR | DCMD_FLOWSRC | + DCMD_BURST16 | DCMD_WIDTH4, +}; + static void dump_registers(struct ssp_device *ssp) { dev_dbg(&ssp->pdev->dev, "SSCR0 0x%08x SSCR1 0x%08x SSTO 0x%08x\n", @@ -61,33 +194,25 @@ static void dump_registers(struct ssp_device *ssp) ssp_read_reg(ssp, SSACD)); } -struct pxa2xx_pcm_dma_data { - struct pxa2xx_pcm_dma_params params; - char name[20]; +static struct pxa2xx_pcm_dma_params *ssp_dma_params[4][4] = { + { + &pxa_ssp1_pcm_mono_out, &pxa_ssp1_pcm_mono_in, + &pxa_ssp1_pcm_stereo_out, &pxa_ssp1_pcm_stereo_in, + }, + { + &pxa_ssp2_pcm_mono_out, &pxa_ssp2_pcm_mono_in, + &pxa_ssp2_pcm_stereo_out, &pxa_ssp2_pcm_stereo_in, + }, + { + &pxa_ssp3_pcm_mono_out, &pxa_ssp3_pcm_mono_in, + &pxa_ssp3_pcm_stereo_out, &pxa_ssp3_pcm_stereo_in, + }, + { + &pxa_ssp4_pcm_mono_out, &pxa_ssp4_pcm_mono_in, + &pxa_ssp4_pcm_stereo_out, &pxa_ssp4_pcm_stereo_in, + }, }; -static struct pxa2xx_pcm_dma_params * -ssp_get_dma_params(struct ssp_device *ssp, int width4, int out) -{ - struct pxa2xx_pcm_dma_data *dma; - - dma = kzalloc(sizeof(struct pxa2xx_pcm_dma_data), GFP_KERNEL); - if (dma == NULL) - return NULL; - - snprintf(dma->name, 20, "SSP%d PCM %s %s", ssp->port_id, - width4 ? "32-bit" : "16-bit", out ? "out" : "in"); - - dma->params.name = dma->name; - dma->params.drcmr = &DRCMR(out ? ssp->drcmr_tx : ssp->drcmr_rx); - dma->params.dcmd = (out ? (DCMD_INCSRCADDR | DCMD_FLOWTRG) : - (DCMD_INCTRGADDR | DCMD_FLOWSRC)) | - (width4 ? DCMD_WIDTH4 : DCMD_WIDTH2) | DCMD_BURST16; - dma->params.dev_addr = ssp->phys_base + SSDR; - - return &dma->params; -} - static int pxa_ssp_startup(struct snd_pcm_substream *substream, struct snd_soc_dai *dai) { @@ -102,11 +227,6 @@ static int pxa_ssp_startup(struct snd_pcm_substream *substream, clk_enable(priv->dev.ssp->clk); ssp_disable(&priv->dev); } - - if (cpu_dai->dma_data) { - kfree(cpu_dai->dma_data); - cpu_dai->dma_data = NULL; - } return ret; } @@ -121,11 +241,6 @@ static void pxa_ssp_shutdown(struct snd_pcm_substream *substream, ssp_disable(&priv->dev); clk_disable(priv->dev.ssp->clk); } - - if (cpu_dai->dma_data) { - kfree(cpu_dai->dma_data); - cpu_dai->dma_data = NULL; - } } #ifdef CONFIG_PM @@ -208,7 +323,7 @@ static int pxa_ssp_set_dai_sysclk(struct snd_soc_dai *cpu_dai, ~(SSCR0_ECS | SSCR0_NCS | SSCR0_MOD | SSCR0_ACS); dev_dbg(&ssp->pdev->dev, - "pxa_ssp_set_dai_sysclk id: %d, clk_id %d, freq %u\n", + "pxa_ssp_set_dai_sysclk id: %d, clk_id %d, freq %d\n", cpu_dai->id, clk_id, freq); switch (clk_id) { @@ -357,7 +472,7 @@ static int pxa_ssp_set_dai_pll(struct snd_soc_dai *cpu_dai, ssacd |= (0x6 << 4); dev_dbg(&ssp->pdev->dev, - "Using SSACDD %x to supply %uHz\n", + "Using SSACDD %x to supply %dHz\n", val, freq_out); break; } @@ -474,10 +589,7 @@ static int pxa_ssp_set_dai_fmt(struct snd_soc_dai *cpu_dai, case SND_SOC_DAIFMT_NB_IF: break; case SND_SOC_DAIFMT_IB_IF: - sspsp |= SSPSP_SCMODE(2); - break; - case SND_SOC_DAIFMT_IB_NF: - sspsp |= SSPSP_SCMODE(2) | SSPSP_SFRMP; + sspsp |= SSPSP_SCMODE(3); break; default: return -EINVAL; @@ -494,13 +606,7 @@ static int pxa_ssp_set_dai_fmt(struct snd_soc_dai *cpu_dai, case SND_SOC_DAIFMT_NB_NF: sspsp |= SSPSP_SFRMP; break; - case SND_SOC_DAIFMT_NB_IF: - break; case SND_SOC_DAIFMT_IB_IF: - sspsp |= SSPSP_SCMODE(2); - break; - case SND_SOC_DAIFMT_IB_NF: - sspsp |= SSPSP_SCMODE(2) | SSPSP_SFRMP; break; default: return -EINVAL; @@ -538,23 +644,25 @@ static int pxa_ssp_hw_params(struct snd_pcm_substream *substream, struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai; struct ssp_priv *priv = cpu_dai->private_data; struct ssp_device *ssp = priv->dev.ssp; - int chn = params_channels(params); + int dma = 0, chn = params_channels(params); u32 sscr0; u32 sspsp; int width = snd_pcm_format_physical_width(params_format(params)); int ttsa = ssp_read_reg(ssp, SSTSA) & 0xf; - /* generate correct DMA params */ - if (cpu_dai->dma_data) - kfree(cpu_dai->dma_data); - + /* select correct DMA params */ + if (substream->stream != SNDRV_PCM_STREAM_PLAYBACK) + dma = 1; /* capture DMA offset is 1,3 */ /* Network mode with one active slot (ttsa == 1) can be used * to force 16-bit frame width on the wire (for S16_LE), even * with two channels. Use 16-bit DMA transfers for this case. */ - cpu_dai->dma_data = ssp_get_dma_params(ssp, - ((chn == 2) && (ttsa != 1)) || (width == 32), - substream->stream == SNDRV_PCM_STREAM_PLAYBACK); + if (((chn == 2) && (ttsa != 1)) || (width == 32)) + dma += 2; /* 32-bit DMA offset is 2, 16-bit is 0 */ + + cpu_dai->dma_data = ssp_dma_params[cpu_dai->id][dma]; + + dev_dbg(&ssp->pdev->dev, "pxa_ssp_hw_params: dma %d\n", dma); /* we can only change the settings if the port is not in use */ if (ssp_read_reg(ssp, SSCR0) & SSCR0_SSE) diff --git a/trunk/sound/soc/pxa/pxa2xx-i2s.c b/trunk/sound/soc/pxa/pxa2xx-i2s.c index 4743e262895d..2f4b6e489b78 100644 --- a/trunk/sound/soc/pxa/pxa2xx-i2s.c +++ b/trunk/sound/soc/pxa/pxa2xx-i2s.c @@ -106,8 +106,10 @@ static int pxa2xx_i2s_startup(struct snd_pcm_substream *substream, if (IS_ERR(clk_i2s)) return PTR_ERR(clk_i2s); - if (!cpu_dai->active) + if (!cpu_dai->active) { + SACR0 |= SACR0_RST; SACR0 = 0; + } return 0; } @@ -176,7 +178,9 @@ static int pxa2xx_i2s_hw_params(struct snd_pcm_substream *substream, /* is port used by another stream */ if (!(SACR0 & SACR0_ENB)) { + SACR0 = 0; + SACR1 = 0; if (pxa_i2s.master) SACR0 |= SACR0_BCKD; @@ -222,10 +226,6 @@ static int pxa2xx_i2s_trigger(struct snd_pcm_substream *substream, int cmd, switch (cmd) { case SNDRV_PCM_TRIGGER_START: - if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) - SACR1 &= ~SACR1_DRPL; - else - SACR1 &= ~SACR1_DREC; SACR0 |= SACR0_ENB; break; case SNDRV_PCM_TRIGGER_RESUME: @@ -252,16 +252,21 @@ static void pxa2xx_i2s_shutdown(struct snd_pcm_substream *substream, SAIMR &= ~SAIMR_RFS; } - if ((SACR1 & (SACR1_DREC | SACR1_DRPL)) == (SACR1_DREC | SACR1_DRPL)) { + if (SACR1 & (SACR1_DREC | SACR1_DRPL)) { SACR0 &= ~SACR0_ENB; pxa_i2s_wait(); clk_disable(clk_i2s); } + + clk_put(clk_i2s); } #ifdef CONFIG_PM static int pxa2xx_i2s_suspend(struct snd_soc_dai *dai) { + if (!dai->active) + return 0; + /* store registers */ pxa_i2s.sacr0 = SACR0; pxa_i2s.sacr1 = SACR1; @@ -276,14 +281,16 @@ static int pxa2xx_i2s_suspend(struct snd_soc_dai *dai) static int pxa2xx_i2s_resume(struct snd_soc_dai *dai) { + if (!dai->active) + return 0; + pxa_i2s_wait(); - SACR0 = pxa_i2s.sacr0 & ~SACR0_ENB; + SACR0 = pxa_i2s.sacr0 &= ~SACR0_ENB; SACR1 = pxa_i2s.sacr1; SAIMR = pxa_i2s.saimr; SADIV = pxa_i2s.sadiv; - - SACR0 = pxa_i2s.sacr0; + SACR0 |= SACR0_ENB; return 0; } @@ -322,7 +329,6 @@ struct snd_soc_dai pxa_i2s_dai = { .rates = PXA2XX_I2S_RATES, .formats = SNDRV_PCM_FMTBIT_S16_LE,}, .ops = &pxa_i2s_dai_ops, - .symmetric_rates = 1, }; EXPORT_SYMBOL_GPL(pxa_i2s_dai); @@ -340,19 +346,6 @@ static int pxa2xx_i2s_probe(struct platform_device *dev) if (ret != 0) clk_put(clk_i2s); - /* - * PXA Developer's Manual: - * If SACR0[ENB] is toggled in the middle of a normal operation, - * the SACR0[RST] bit must also be set and cleared to reset all - * I2S controller registers. - */ - SACR0 = SACR0_RST; - SACR0 = 0; - /* Make sure RPL and REC are disabled */ - SACR1 = SACR1_DRPL | SACR1_DREC; - /* Along with FIFO servicing */ - SAIMR &= ~(SAIMR_RFS | SAIMR_TFS); - return ret; } diff --git a/trunk/sound/soc/s3c24xx/s3c-i2s-v2.c b/trunk/sound/soc/s3c24xx/s3c-i2s-v2.c index 1a283170ca92..ab680aac3fcb 100644 --- a/trunk/sound/soc/s3c24xx/s3c-i2s-v2.c +++ b/trunk/sound/soc/s3c24xx/s3c-i2s-v2.c @@ -37,20 +37,6 @@ #include "s3c-i2s-v2.h" -#undef S3C_IIS_V2_SUPPORTED - -#if defined(CONFIG_CPU_S3C2412) || defined(CONFIG_CPU_S3C2413) -#define S3C_IIS_V2_SUPPORTED -#endif - -#ifdef CONFIG_PLAT_S3C64XX -#define S3C_IIS_V2_SUPPORTED -#endif - -#ifndef S3C_IIS_V2_SUPPORTED -#error Unsupported CPU model -#endif - #define S3C2412_I2S_DEBUG_CON 0 static inline struct s3c_i2sv2_info *to_info(struct snd_soc_dai *cpu_dai) @@ -89,7 +75,7 @@ static inline void dbg_showcon(const char *fn, u32 con) /* Turn on or off the transmission path. */ -static void s3c2412_snd_txctrl(struct s3c_i2sv2_info *i2s, int on) +void s3c2412_snd_txctrl(struct s3c_i2sv2_info *i2s, int on) { void __iomem *regs = i2s->regs; u32 fic, con, mod; @@ -119,9 +105,7 @@ static void s3c2412_snd_txctrl(struct s3c_i2sv2_info *i2s, int on) break; default: - dev_err(i2s->dev, "TXEN: Invalid MODE %x in IISMOD\n", - mod & S3C2412_IISMOD_MODE_MASK); - break; + dev_err(i2s->dev, "TXEN: Invalid MODE in IISMOD\n"); } writel(con, regs + S3C2412_IISCON); @@ -148,9 +132,7 @@ static void s3c2412_snd_txctrl(struct s3c_i2sv2_info *i2s, int on) break; default: - dev_err(i2s->dev, "TXDIS: Invalid MODE %x in IISMOD\n", - mod & S3C2412_IISMOD_MODE_MASK); - break; + dev_err(i2s->dev, "TXDIS: Invalid MODE in IISMOD\n"); } writel(mod, regs + S3C2412_IISMOD); @@ -161,8 +143,9 @@ static void s3c2412_snd_txctrl(struct s3c_i2sv2_info *i2s, int on) dbg_showcon(__func__, con); pr_debug("%s: IIS: CON=%x MOD=%x FIC=%x\n", __func__, con, mod, fic); } +EXPORT_SYMBOL_GPL(s3c2412_snd_txctrl); -static void s3c2412_snd_rxctrl(struct s3c_i2sv2_info *i2s, int on) +void s3c2412_snd_rxctrl(struct s3c_i2sv2_info *i2s, int on) { void __iomem *regs = i2s->regs; u32 fic, con, mod; @@ -192,8 +175,7 @@ static void s3c2412_snd_rxctrl(struct s3c_i2sv2_info *i2s, int on) break; default: - dev_err(i2s->dev, "RXEN: Invalid MODE %x in IISMOD\n", - mod & S3C2412_IISMOD_MODE_MASK); + dev_err(i2s->dev, "RXEN: Invalid MODE in IISMOD\n"); } writel(mod, regs + S3C2412_IISMOD); @@ -217,8 +199,7 @@ static void s3c2412_snd_rxctrl(struct s3c_i2sv2_info *i2s, int on) break; default: - dev_err(i2s->dev, "RXDIS: Invalid MODE %x in IISMOD\n", - mod & S3C2412_IISMOD_MODE_MASK); + dev_err(i2s->dev, "RXEN: Invalid MODE in IISMOD\n"); } writel(con, regs + S3C2412_IISCON); @@ -228,6 +209,7 @@ static void s3c2412_snd_rxctrl(struct s3c_i2sv2_info *i2s, int on) fic = readl(regs + S3C2412_IISFIC); pr_debug("%s: IIS: CON=%x MOD=%x FIC=%x\n", __func__, con, mod, fic); } +EXPORT_SYMBOL_GPL(s3c2412_snd_rxctrl); /* * Wait for the LR signal to allow synchronisation to the L/R clock @@ -284,7 +266,7 @@ static int s3c2412_i2s_set_fmt(struct snd_soc_dai *cpu_dai, */ #define IISMOD_MASTER_MASK (1 << 11) #define IISMOD_SLAVE (1 << 11) -#define IISMOD_MASTER (0 << 11) +#define IISMOD_MASTER (0x0) #endif switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { @@ -299,7 +281,7 @@ static int s3c2412_i2s_set_fmt(struct snd_soc_dai *cpu_dai, iismod |= IISMOD_MASTER; break; default: - pr_err("unknwon master/slave format\n"); + pr_debug("unknwon master/slave format\n"); return -EINVAL; } @@ -316,7 +298,7 @@ static int s3c2412_i2s_set_fmt(struct snd_soc_dai *cpu_dai, iismod |= S3C2412_IISMOD_SDF_IIS; break; default: - pr_err("Unknown data format\n"); + pr_debug("Unknown data format\n"); return -EINVAL; } @@ -345,7 +327,6 @@ static int s3c2412_i2s_hw_params(struct snd_pcm_substream *substream, iismod = readl(i2s->regs + S3C2412_IISMOD); pr_debug("%s: r: IISMOD: %x\n", __func__, iismod); -#if defined(CONFIG_CPU_S3C2412) || defined(CONFIG_CPU_S3C2413) switch (params_format(params)) { case SNDRV_PCM_FORMAT_S8: iismod |= S3C2412_IISMOD_8BIT; @@ -354,25 +335,6 @@ static int s3c2412_i2s_hw_params(struct snd_pcm_substream *substream, iismod &= ~S3C2412_IISMOD_8BIT; break; } -#endif - -#ifdef CONFIG_PLAT_S3C64XX - iismod &= ~0x606; - /* Sample size */ - switch (params_format(params)) { - case SNDRV_PCM_FORMAT_S8: - /* 8 bit sample, 16fs BCLK */ - iismod |= 0x2004; - break; - case SNDRV_PCM_FORMAT_S16_LE: - /* 16 bit sample, 32fs BCLK */ - break; - case SNDRV_PCM_FORMAT_S24_LE: - /* 24 bit sample, 48fs BCLK */ - iismod |= 0x4002; - break; - } -#endif writel(iismod, i2s->regs + S3C2412_IISMOD); pr_debug("%s: w: IISMOD: %x\n", __func__, iismod); @@ -527,8 +489,6 @@ int s3c_i2sv2_iis_calc_rate(struct s3c_i2sv2_rate_calc *info, unsigned int best_rate = 0; unsigned int best_deviation = INT_MAX; - pr_debug("Input clock rate %ldHz\n", clkrate); - if (fstab == NULL) fstab = iis_fs_tab; @@ -547,7 +507,7 @@ int s3c_i2sv2_iis_calc_rate(struct s3c_i2sv2_rate_calc *info, actual = clkrate / (fsdiv * div); deviation = actual - rate; - printk(KERN_DEBUG "%ufs: div %u => result %u, deviation %d\n", + printk(KERN_DEBUG "%dfs: div %d => result %d, deviation %d\n", fsdiv, div, actual, deviation); deviation = abs(deviation); @@ -563,7 +523,7 @@ int s3c_i2sv2_iis_calc_rate(struct s3c_i2sv2_rate_calc *info, break; } - printk(KERN_DEBUG "best: fs=%u, div=%u, rate=%u\n", + printk(KERN_DEBUG "best: fs=%d, div=%d, rate=%d\n", best_fs, best_div, best_rate); info->fs_div = best_fs; @@ -579,31 +539,12 @@ int s3c_i2sv2_probe(struct platform_device *pdev, unsigned long base) { struct device *dev = &pdev->dev; - unsigned int iismod; i2s->dev = dev; /* record our i2s structure for later use in the callbacks */ dai->private_data = i2s; - if (!base) { - struct resource *res = platform_get_resource(pdev, - IORESOURCE_MEM, - 0); - if (!res) { - dev_err(dev, "Unable to get register resource\n"); - return -ENXIO; - } - - if (!request_mem_region(res->start, resource_size(res), - "s3c64xx-i2s-v4")) { - dev_err(dev, "Unable to request register region\n"); - return -EBUSY; - } - - base = res->start; - } - i2s->regs = ioremap(base, 0x100); if (i2s->regs == NULL) { dev_err(dev, "cannot ioremap registers\n"); @@ -619,16 +560,12 @@ int s3c_i2sv2_probe(struct platform_device *pdev, clk_enable(i2s->iis_pclk); - /* Mark ourselves as in TXRX mode so we can run through our cleanup - * process without warnings. */ - iismod = readl(i2s->regs + S3C2412_IISMOD); - iismod |= S3C2412_IISMOD_MODE_TXRX; - writel(iismod, i2s->regs + S3C2412_IISMOD); s3c2412_snd_txctrl(i2s, 0); s3c2412_snd_rxctrl(i2s, 0); return 0; } + EXPORT_SYMBOL_GPL(s3c_i2sv2_probe); #ifdef CONFIG_PM diff --git a/trunk/sound/soc/s3c24xx/s3c2412-i2s.c b/trunk/sound/soc/s3c24xx/s3c2412-i2s.c index 168a088ba761..b7e0b3f0bfc8 100644 --- a/trunk/sound/soc/s3c24xx/s3c2412-i2s.c +++ b/trunk/sound/soc/s3c24xx/s3c2412-i2s.c @@ -120,7 +120,7 @@ static int s3c2412_i2s_probe(struct platform_device *pdev, s3c2412_i2s.iis_cclk = clk_get(&pdev->dev, "i2sclk"); if (s3c2412_i2s.iis_cclk == NULL) { - pr_err("failed to get i2sclk clock\n"); + pr_debug("failed to get i2sclk clock\n"); iounmap(s3c2412_i2s.regs); return -ENODEV; } diff --git a/trunk/sound/soc/s3c24xx/s3c64xx-i2s.c b/trunk/sound/soc/s3c24xx/s3c64xx-i2s.c index 3c06c401d0fb..33c5de7e255f 100644 --- a/trunk/sound/soc/s3c24xx/s3c64xx-i2s.c +++ b/trunk/sound/soc/s3c24xx/s3c64xx-i2s.c @@ -108,19 +108,48 @@ static int s3c64xx_i2s_set_sysclk(struct snd_soc_dai *cpu_dai, return 0; } -struct clk *s3c64xx_i2s_get_clock(struct snd_soc_dai *dai) + +unsigned long s3c64xx_i2s_get_clockrate(struct snd_soc_dai *dai) { struct s3c_i2sv2_info *i2s = to_info(dai); - return i2s->iis_cclk; + return clk_get_rate(i2s->iis_cclk); } -EXPORT_SYMBOL_GPL(s3c64xx_i2s_get_clock); +EXPORT_SYMBOL_GPL(s3c64xx_i2s_get_clockrate); static int s3c64xx_i2s_probe(struct platform_device *pdev, struct snd_soc_dai *dai) { + struct device *dev = &pdev->dev; + struct s3c_i2sv2_info *i2s; + int ret; + + dev_dbg(dev, "%s: probing dai %d\n", __func__, pdev->id); + + if (pdev->id < 0 || pdev->id > ARRAY_SIZE(s3c64xx_i2s)) { + dev_err(dev, "id %d out of range\n", pdev->id); + return -EINVAL; + } + + i2s = &s3c64xx_i2s[pdev->id]; + + ret = s3c_i2sv2_probe(pdev, dai, i2s, + pdev->id ? S3C64XX_PA_IIS1 : S3C64XX_PA_IIS0); + if (ret) + return ret; + + i2s->dma_capture = &s3c64xx_i2s_pcm_stereo_in[pdev->id]; + i2s->dma_playback = &s3c64xx_i2s_pcm_stereo_out[pdev->id]; + + i2s->iis_cclk = clk_get(dev, "audio-bus"); + if (IS_ERR(i2s->iis_cclk)) { + dev_err(dev, "failed to get audio-bus"); + iounmap(i2s->regs); + return -ENODEV; + } + /* configure GPIO for i2s port */ - switch (dai->id) { + switch (pdev->id) { case 0: s3c_gpio_cfgpin(S3C64XX_GPD(0), S3C64XX_GPD0_I2S0_CLK); s3c_gpio_cfgpin(S3C64XX_GPD(1), S3C64XX_GPD1_I2S0_CDCLK); @@ -146,122 +175,41 @@ static int s3c64xx_i2s_probe(struct platform_device *pdev, SNDRV_PCM_RATE_48000 | SNDRV_PCM_RATE_88200 | SNDRV_PCM_RATE_96000) #define S3C64XX_I2S_FMTS \ - (SNDRV_PCM_FMTBIT_S8 | SNDRV_PCM_FMTBIT_S16_LE |\ - SNDRV_PCM_FMTBIT_S24_LE) + (SNDRV_PCM_FMTBIT_S8 | SNDRV_PCM_FMTBIT_S16_LE) static struct snd_soc_dai_ops s3c64xx_i2s_dai_ops = { .set_sysclk = s3c64xx_i2s_set_sysclk, }; -struct snd_soc_dai s3c64xx_i2s_dai[] = { - { - .name = "s3c64xx-i2s", - .id = 0, - .probe = s3c64xx_i2s_probe, - .playback = { - .channels_min = 2, - .channels_max = 2, - .rates = S3C64XX_I2S_RATES, - .formats = S3C64XX_I2S_FMTS, - }, - .capture = { - .channels_min = 2, - .channels_max = 2, - .rates = S3C64XX_I2S_RATES, - .formats = S3C64XX_I2S_FMTS, - }, - .ops = &s3c64xx_i2s_dai_ops, - .symmetric_rates = 1, +struct snd_soc_dai s3c64xx_i2s_dai = { + .name = "s3c64xx-i2s", + .id = 0, + .probe = s3c64xx_i2s_probe, + .playback = { + .channels_min = 2, + .channels_max = 2, + .rates = S3C64XX_I2S_RATES, + .formats = S3C64XX_I2S_FMTS, }, - { - .name = "s3c64xx-i2s", - .id = 1, - .probe = s3c64xx_i2s_probe, - .playback = { - .channels_min = 2, - .channels_max = 2, - .rates = S3C64XX_I2S_RATES, - .formats = S3C64XX_I2S_FMTS, - }, - .capture = { - .channels_min = 2, - .channels_max = 2, - .rates = S3C64XX_I2S_RATES, - .formats = S3C64XX_I2S_FMTS, - }, - .ops = &s3c64xx_i2s_dai_ops, - .symmetric_rates = 1, + .capture = { + .channels_min = 2, + .channels_max = 2, + .rates = S3C64XX_I2S_RATES, + .formats = S3C64XX_I2S_FMTS, }, + .ops = &s3c64xx_i2s_dai_ops, }; EXPORT_SYMBOL_GPL(s3c64xx_i2s_dai); -static __devinit int s3c64xx_iis_dev_probe(struct platform_device *pdev) -{ - struct s3c_i2sv2_info *i2s; - struct snd_soc_dai *dai; - int ret; - - if (pdev->id >= ARRAY_SIZE(s3c64xx_i2s)) { - dev_err(&pdev->dev, "id %d out of range\n", pdev->id); - return -EINVAL; - } - - i2s = &s3c64xx_i2s[pdev->id]; - dai = &s3c64xx_i2s_dai[pdev->id]; - dai->dev = &pdev->dev; - - i2s->dma_capture = &s3c64xx_i2s_pcm_stereo_in[pdev->id]; - i2s->dma_playback = &s3c64xx_i2s_pcm_stereo_out[pdev->id]; - - i2s->iis_cclk = clk_get(&pdev->dev, "audio-bus"); - if (IS_ERR(i2s->iis_cclk)) { - dev_err(&pdev->dev, "failed to get audio-bus\n"); - ret = PTR_ERR(i2s->iis_cclk); - goto err; - } - - ret = s3c_i2sv2_probe(pdev, dai, i2s, 0); - if (ret) - goto err_clk; - - ret = s3c_i2sv2_register_dai(dai); - if (ret != 0) - goto err_i2sv2; - - return 0; - -err_i2sv2: - /* Not implemented for I2Sv2 core yet */ -err_clk: - clk_put(i2s->iis_cclk); -err: - return ret; -} - -static __devexit int s3c64xx_iis_dev_remove(struct platform_device *pdev) -{ - dev_err(&pdev->dev, "Device removal not yet supported\n"); - return 0; -} - -static struct platform_driver s3c64xx_iis_driver = { - .probe = s3c64xx_iis_dev_probe, - .remove = s3c64xx_iis_dev_remove, - .driver = { - .name = "s3c64xx-iis", - .owner = THIS_MODULE, - }, -}; - static int __init s3c64xx_i2s_init(void) { - return platform_driver_register(&s3c64xx_iis_driver); + return s3c_i2sv2_register_dai(&s3c64xx_i2s_dai); } module_init(s3c64xx_i2s_init); static void __exit s3c64xx_i2s_exit(void) { - platform_driver_unregister(&s3c64xx_iis_driver); + snd_soc_unregister_dai(&s3c64xx_i2s_dai); } module_exit(s3c64xx_i2s_exit); @@ -269,3 +217,6 @@ module_exit(s3c64xx_i2s_exit); MODULE_AUTHOR("Ben Dooks, "); MODULE_DESCRIPTION("S3C64XX I2S SoC Interface"); MODULE_LICENSE("GPL"); + + + diff --git a/trunk/sound/soc/s3c24xx/s3c64xx-i2s.h b/trunk/sound/soc/s3c24xx/s3c64xx-i2s.h index 02148cee2613..b7ffe3c38b66 100644 --- a/trunk/sound/soc/s3c24xx/s3c64xx-i2s.h +++ b/trunk/sound/soc/s3c24xx/s3c64xx-i2s.h @@ -15,8 +15,6 @@ #ifndef __SND_SOC_S3C24XX_S3C64XX_I2S_H #define __SND_SOC_S3C24XX_S3C64XX_I2S_H __FILE__ -struct clk; - #include "s3c-i2s-v2.h" #define S3C64XX_DIV_BCLK S3C_I2SV2_DIV_BCLK @@ -26,8 +24,8 @@ struct clk; #define S3C64XX_CLKSRC_PCLK (0) #define S3C64XX_CLKSRC_MUX (1) -extern struct snd_soc_dai s3c64xx_i2s_dai[]; +extern struct snd_soc_dai s3c64xx_i2s_dai; -extern struct clk *s3c64xx_i2s_get_clock(struct snd_soc_dai *dai); +extern unsigned long s3c64xx_i2s_get_clockrate(struct snd_soc_dai *cpu_dai); #endif /* __SND_SOC_S3C24XX_S3C64XX_I2S_H */ diff --git a/trunk/sound/soc/s6000/Kconfig b/trunk/sound/soc/s6000/Kconfig deleted file mode 100644 index c74eb3d4a47c..000000000000 --- a/trunk/sound/soc/s6000/Kconfig +++ /dev/null @@ -1,19 +0,0 @@ -config SND_S6000_SOC - tristate "SoC Audio for the Stretch s6000 family" - depends on XTENSA_VARIANT_S6000 - help - Say Y or M if you want to add support for codecs attached to - s6000 family chips. You will also need to select the platform - to support below. - -config SND_S6000_SOC_I2S - tristate - -config SND_S6000_SOC_S6IPCAM - tristate "SoC Audio support for Stretch 6105 IP Camera" - depends on SND_S6000_SOC && XTENSA_PLATFORM_S6105 - select SND_S6000_SOC_I2S - select SND_SOC_TLV320AIC3X - help - Say Y if you want to add support for SoC audio on the - Stretch s6105 IP Camera Reference Design. diff --git a/trunk/sound/soc/s6000/Makefile b/trunk/sound/soc/s6000/Makefile deleted file mode 100644 index 7a613612e010..000000000000 --- a/trunk/sound/soc/s6000/Makefile +++ /dev/null @@ -1,11 +0,0 @@ -# s6000 Platform Support -snd-soc-s6000-objs := s6000-pcm.o -snd-soc-s6000-i2s-objs := s6000-i2s.o - -obj-$(CONFIG_SND_S6000_SOC) += snd-soc-s6000.o -obj-$(CONFIG_SND_S6000_SOC_I2S) += snd-soc-s6000-i2s.o - -# s6105 Machine Support -snd-soc-s6ipcam-objs := s6105-ipcam.o - -obj-$(CONFIG_SND_S6000_SOC_S6IPCAM) += snd-soc-s6ipcam.o diff --git a/trunk/sound/soc/s6000/s6000-i2s.c b/trunk/sound/soc/s6000/s6000-i2s.c deleted file mode 100644 index c5cda187ecab..000000000000 --- a/trunk/sound/soc/s6000/s6000-i2s.c +++ /dev/null @@ -1,629 +0,0 @@ -/* - * ALSA SoC I2S Audio Layer for the Stretch S6000 family - * - * Author: Daniel Gloeckner, - * Copyright: (C) 2009 emlix GmbH - * - * 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. - */ - -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include - -#include "s6000-i2s.h" -#include "s6000-pcm.h" - -struct s6000_i2s_dev { - dma_addr_t sifbase; - u8 __iomem *scbbase; - unsigned int wide; - unsigned int channel_in; - unsigned int channel_out; - unsigned int lines_in; - unsigned int lines_out; - struct s6000_pcm_dma_params dma_params; -}; - -#define S6_I2S_INTERRUPT_STATUS 0x00 -#define S6_I2S_INT_OVERRUN 1 -#define S6_I2S_INT_UNDERRUN 2 -#define S6_I2S_INT_ALIGNMENT 4 -#define S6_I2S_INTERRUPT_ENABLE 0x04 -#define S6_I2S_INTERRUPT_RAW 0x08 -#define S6_I2S_INTERRUPT_CLEAR 0x0C -#define S6_I2S_INTERRUPT_SET 0x10 -#define S6_I2S_MODE 0x20 -#define S6_I2S_DUAL 0 -#define S6_I2S_WIDE 1 -#define S6_I2S_TX_DEFAULT 0x24 -#define S6_I2S_DATA_CFG(c) (0x40 + 0x10 * (c)) -#define S6_I2S_IN 0 -#define S6_I2S_OUT 1 -#define S6_I2S_UNUSED 2 -#define S6_I2S_INTERFACE_CFG(c) (0x44 + 0x10 * (c)) -#define S6_I2S_DIV_MASK 0x001fff -#define S6_I2S_16BIT 0x000000 -#define S6_I2S_20BIT 0x002000 -#define S6_I2S_24BIT 0x004000 -#define S6_I2S_32BIT 0x006000 -#define S6_I2S_BITS_MASK 0x006000 -#define S6_I2S_MEM_16BIT 0x000000 -#define S6_I2S_MEM_32BIT 0x008000 -#define S6_I2S_MEM_MASK 0x008000 -#define S6_I2S_CHANNELS_SHIFT 16 -#define S6_I2S_CHANNELS_MASK 0x030000 -#define S6_I2S_SCK_IN 0x000000 -#define S6_I2S_SCK_OUT 0x040000 -#define S6_I2S_SCK_DIR 0x040000 -#define S6_I2S_WS_IN 0x000000 -#define S6_I2S_WS_OUT 0x080000 -#define S6_I2S_WS_DIR 0x080000 -#define S6_I2S_LEFT_FIRST 0x000000 -#define S6_I2S_RIGHT_FIRST 0x100000 -#define S6_I2S_FIRST 0x100000 -#define S6_I2S_CUR_SCK 0x200000 -#define S6_I2S_CUR_WS 0x400000 -#define S6_I2S_ENABLE(c) (0x48 + 0x10 * (c)) -#define S6_I2S_DISABLE_IF 0x02 -#define S6_I2S_ENABLE_IF 0x03 -#define S6_I2S_IS_BUSY 0x04 -#define S6_I2S_DMA_ACTIVE 0x08 -#define S6_I2S_IS_ENABLED 0x10 - -#define S6_I2S_NUM_LINES 4 - -#define S6_I2S_SIF_PORT0 0x0000000 -#define S6_I2S_SIF_PORT1 0x0000080 /* docs say 0x0000010 */ - -static inline void s6_i2s_write_reg(struct s6000_i2s_dev *dev, int reg, u32 val) -{ - writel(val, dev->scbbase + reg); -} - -static inline u32 s6_i2s_read_reg(struct s6000_i2s_dev *dev, int reg) -{ - return readl(dev->scbbase + reg); -} - -static inline void s6_i2s_mod_reg(struct s6000_i2s_dev *dev, int reg, - u32 mask, u32 val) -{ - val ^= s6_i2s_read_reg(dev, reg) & ~mask; - s6_i2s_write_reg(dev, reg, val); -} - -static void s6000_i2s_start_channel(struct s6000_i2s_dev *dev, int channel) -{ - int i, j, cur, prev; - - /* - * Wait for WCLK to toggle 5 times before enabling the channel - * s6000 Family Datasheet 3.6.4: - * "At least two cycles of WS must occur between commands - * to disable or enable the interface" - */ - j = 0; - prev = ~S6_I2S_CUR_WS; - for (i = 1000000; --i && j < 6; ) { - cur = s6_i2s_read_reg(dev, S6_I2S_INTERFACE_CFG(channel)) - & S6_I2S_CUR_WS; - if (prev != cur) { - prev = cur; - j++; - } - } - if (j < 6) - printk(KERN_WARNING "s6000-i2s: timeout waiting for WCLK\n"); - - s6_i2s_write_reg(dev, S6_I2S_ENABLE(channel), S6_I2S_ENABLE_IF); -} - -static void s6000_i2s_stop_channel(struct s6000_i2s_dev *dev, int channel) -{ - s6_i2s_write_reg(dev, S6_I2S_ENABLE(channel), S6_I2S_DISABLE_IF); -} - -static void s6000_i2s_start(struct snd_pcm_substream *substream) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct s6000_i2s_dev *dev = rtd->dai->cpu_dai->private_data; - int channel; - - channel = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) ? - dev->channel_out : dev->channel_in; - - s6000_i2s_start_channel(dev, channel); -} - -static void s6000_i2s_stop(struct snd_pcm_substream *substream) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct s6000_i2s_dev *dev = rtd->dai->cpu_dai->private_data; - int channel; - - channel = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) ? - dev->channel_out : dev->channel_in; - - s6000_i2s_stop_channel(dev, channel); -} - -static int s6000_i2s_trigger(struct snd_pcm_substream *substream, int cmd, - int after) -{ - switch (cmd) { - case SNDRV_PCM_TRIGGER_START: - case SNDRV_PCM_TRIGGER_RESUME: - case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: - if ((substream->stream == SNDRV_PCM_STREAM_CAPTURE) ^ !after) - s6000_i2s_start(substream); - break; - case SNDRV_PCM_TRIGGER_STOP: - case SNDRV_PCM_TRIGGER_SUSPEND: - case SNDRV_PCM_TRIGGER_PAUSE_PUSH: - if (!after) - s6000_i2s_stop(substream); - } - return 0; -} - -static unsigned int s6000_i2s_int_sources(struct s6000_i2s_dev *dev) -{ - unsigned int pending; - pending = s6_i2s_read_reg(dev, S6_I2S_INTERRUPT_RAW); - pending &= S6_I2S_INT_ALIGNMENT | - S6_I2S_INT_UNDERRUN | - S6_I2S_INT_OVERRUN; - s6_i2s_write_reg(dev, S6_I2S_INTERRUPT_CLEAR, pending); - - return pending; -} - -static unsigned int s6000_i2s_check_xrun(struct snd_soc_dai *cpu_dai) -{ - struct s6000_i2s_dev *dev = cpu_dai->private_data; - unsigned int errors; - unsigned int ret; - - errors = s6000_i2s_int_sources(dev); - if (likely(!errors)) - return 0; - - ret = 0; - if (errors & S6_I2S_INT_ALIGNMENT) - printk(KERN_ERR "s6000-i2s: WCLK misaligned\n"); - if (errors & S6_I2S_INT_UNDERRUN) - ret |= 1 << SNDRV_PCM_STREAM_PLAYBACK; - if (errors & S6_I2S_INT_OVERRUN) - ret |= 1 << SNDRV_PCM_STREAM_CAPTURE; - return ret; -} - -static void s6000_i2s_wait_disabled(struct s6000_i2s_dev *dev) -{ - int channel; - int n = 50; - for (channel = 0; channel < 2; channel++) { - while (--n >= 0) { - int v = s6_i2s_read_reg(dev, S6_I2S_ENABLE(channel)); - if ((v & S6_I2S_IS_ENABLED) - || !(v & (S6_I2S_DMA_ACTIVE | S6_I2S_IS_BUSY))) - break; - udelay(20); - } - } - if (n < 0) - printk(KERN_WARNING "s6000-i2s: timeout disabling interfaces"); -} - -static int s6000_i2s_set_dai_fmt(struct snd_soc_dai *cpu_dai, - unsigned int fmt) -{ - struct s6000_i2s_dev *dev = cpu_dai->private_data; - u32 w; - - switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { - case SND_SOC_DAIFMT_CBM_CFM: - w = S6_I2S_SCK_IN | S6_I2S_WS_IN; - break; - case SND_SOC_DAIFMT_CBS_CFM: - w = S6_I2S_SCK_OUT | S6_I2S_WS_IN; - break; - case SND_SOC_DAIFMT_CBM_CFS: - w = S6_I2S_SCK_IN | S6_I2S_WS_OUT; - break; - case SND_SOC_DAIFMT_CBS_CFS: - w = S6_I2S_SCK_OUT | S6_I2S_WS_OUT; - break; - default: - return -EINVAL; - } - - switch (fmt & SND_SOC_DAIFMT_INV_MASK) { - case SND_SOC_DAIFMT_NB_NF: - w |= S6_I2S_LEFT_FIRST; - break; - case SND_SOC_DAIFMT_NB_IF: - w |= S6_I2S_RIGHT_FIRST; - break; - default: - return -EINVAL; - } - - s6_i2s_mod_reg(dev, S6_I2S_INTERFACE_CFG(0), - S6_I2S_FIRST | S6_I2S_WS_DIR | S6_I2S_SCK_DIR, w); - s6_i2s_mod_reg(dev, S6_I2S_INTERFACE_CFG(1), - S6_I2S_FIRST | S6_I2S_WS_DIR | S6_I2S_SCK_DIR, w); - - return 0; -} - -static int s6000_i2s_set_clkdiv(struct snd_soc_dai *dai, int div_id, int div) -{ - struct s6000_i2s_dev *dev = dai->private_data; - - if (!div || (div & 1) || div > (S6_I2S_DIV_MASK + 1) * 2) - return -EINVAL; - - s6_i2s_mod_reg(dev, S6_I2S_INTERFACE_CFG(div_id), - S6_I2S_DIV_MASK, div / 2 - 1); - return 0; -} - -static int s6000_i2s_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params, - struct snd_soc_dai *dai) -{ - struct s6000_i2s_dev *dev = dai->private_data; - int interf; - u32 w = 0; - - if (dev->wide) - interf = 0; - else { - w |= (((params_channels(params) - 2) / 2) - << S6_I2S_CHANNELS_SHIFT) & S6_I2S_CHANNELS_MASK; - interf = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) - ? dev->channel_out : dev->channel_in; - } - - switch (params_format(params)) { - case SNDRV_PCM_FORMAT_S16_LE: - w |= S6_I2S_16BIT | S6_I2S_MEM_16BIT; - break; - case SNDRV_PCM_FORMAT_S32_LE: - w |= S6_I2S_32BIT | S6_I2S_MEM_32BIT; - break; - default: - printk(KERN_WARNING "s6000-i2s: unsupported PCM format %x\n", - params_format(params)); - return -EINVAL; - } - - if (s6_i2s_read_reg(dev, S6_I2S_INTERFACE_CFG(interf)) - & S6_I2S_IS_ENABLED) { - printk(KERN_ERR "s6000-i2s: interface already enabled\n"); - return -EBUSY; - } - - s6_i2s_mod_reg(dev, S6_I2S_INTERFACE_CFG(interf), - S6_I2S_CHANNELS_MASK|S6_I2S_MEM_MASK|S6_I2S_BITS_MASK, - w); - - return 0; -} - -static int s6000_i2s_dai_probe(struct platform_device *pdev, - struct snd_soc_dai *dai) -{ - struct s6000_i2s_dev *dev = dai->private_data; - struct s6000_snd_platform_data *pdata = pdev->dev.platform_data; - - if (!pdata) - return -EINVAL; - - dev->wide = pdata->wide; - dev->channel_in = pdata->channel_in; - dev->channel_out = pdata->channel_out; - dev->lines_in = pdata->lines_in; - dev->lines_out = pdata->lines_out; - - s6_i2s_write_reg(dev, S6_I2S_MODE, - dev->wide ? S6_I2S_WIDE : S6_I2S_DUAL); - - if (dev->wide) { - int i; - - if (dev->lines_in + dev->lines_out > S6_I2S_NUM_LINES) - return -EINVAL; - - dev->channel_in = 0; - dev->channel_out = 1; - dai->capture.channels_min = 2 * dev->lines_in; - dai->capture.channels_max = dai->capture.channels_min; - dai->playback.channels_min = 2 * dev->lines_out; - dai->playback.channels_max = dai->playback.channels_min; - - for (i = 0; i < dev->lines_out; i++) - s6_i2s_write_reg(dev, S6_I2S_DATA_CFG(i), S6_I2S_OUT); - - for (; i < S6_I2S_NUM_LINES - dev->lines_in; i++) - s6_i2s_write_reg(dev, S6_I2S_DATA_CFG(i), - S6_I2S_UNUSED); - - for (; i < S6_I2S_NUM_LINES; i++) - s6_i2s_write_reg(dev, S6_I2S_DATA_CFG(i), S6_I2S_IN); - } else { - unsigned int cfg[2] = {S6_I2S_UNUSED, S6_I2S_UNUSED}; - - if (dev->lines_in > 1 || dev->lines_out > 1) - return -EINVAL; - - dai->capture.channels_min = 2 * dev->lines_in; - dai->capture.channels_max = 8 * dev->lines_in; - dai->playback.channels_min = 2 * dev->lines_out; - dai->playback.channels_max = 8 * dev->lines_out; - - if (dev->lines_in) - cfg[dev->channel_in] = S6_I2S_IN; - if (dev->lines_out) - cfg[dev->channel_out] = S6_I2S_OUT; - - s6_i2s_write_reg(dev, S6_I2S_DATA_CFG(0), cfg[0]); - s6_i2s_write_reg(dev, S6_I2S_DATA_CFG(1), cfg[1]); - } - - if (dev->lines_out) { - if (dev->lines_in) { - if (!dev->dma_params.dma_out) - return -ENODEV; - } else { - dev->dma_params.dma_out = dev->dma_params.dma_in; - dev->dma_params.dma_in = 0; - } - } - dev->dma_params.sif_in = dev->sifbase + (dev->channel_in ? - S6_I2S_SIF_PORT1 : S6_I2S_SIF_PORT0); - dev->dma_params.sif_out = dev->sifbase + (dev->channel_out ? - S6_I2S_SIF_PORT1 : S6_I2S_SIF_PORT0); - dev->dma_params.same_rate = pdata->same_rate | pdata->wide; - return 0; -} - -#define S6000_I2S_RATES (SNDRV_PCM_RATE_CONTINUOUS | SNDRV_PCM_RATE_5512 | \ - SNDRV_PCM_RATE_8000_192000) -#define S6000_I2S_FORMATS (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S32_LE) - -static struct snd_soc_dai_ops s6000_i2s_dai_ops = { - .set_fmt = s6000_i2s_set_dai_fmt, - .set_clkdiv = s6000_i2s_set_clkdiv, - .hw_params = s6000_i2s_hw_params, -}; - -struct snd_soc_dai s6000_i2s_dai = { - .name = "s6000-i2s", - .id = 0, - .probe = s6000_i2s_dai_probe, - .playback = { - .channels_min = 2, - .channels_max = 8, - .formats = S6000_I2S_FORMATS, - .rates = S6000_I2S_RATES, - .rate_min = 0, - .rate_max = 1562500, - }, - .capture = { - .channels_min = 2, - .channels_max = 8, - .formats = S6000_I2S_FORMATS, - .rates = S6000_I2S_RATES, - .rate_min = 0, - .rate_max = 1562500, - }, - .ops = &s6000_i2s_dai_ops, -} -EXPORT_SYMBOL_GPL(s6000_i2s_dai); - -static int __devinit s6000_i2s_probe(struct platform_device *pdev) -{ - struct s6000_i2s_dev *dev; - struct resource *scbmem, *sifmem, *region, *dma1, *dma2; - u8 __iomem *mmio; - int ret; - - scbmem = platform_get_resource(pdev, IORESOURCE_MEM, 0); - if (!scbmem) { - dev_err(&pdev->dev, "no mem resource?\n"); - ret = -ENODEV; - goto err_release_none; - } - - region = request_mem_region(scbmem->start, - scbmem->end - scbmem->start + 1, - pdev->name); - if (!region) { - dev_err(&pdev->dev, "I2S SCB region already claimed\n"); - ret = -EBUSY; - goto err_release_none; - } - - mmio = ioremap(scbmem->start, scbmem->end - scbmem->start + 1); - if (!mmio) { - dev_err(&pdev->dev, "can't ioremap SCB region\n"); - ret = -ENOMEM; - goto err_release_scb; - } - - sifmem = platform_get_resource(pdev, IORESOURCE_MEM, 1); - if (!sifmem) { - dev_err(&pdev->dev, "no second mem resource?\n"); - ret = -ENODEV; - goto err_release_map; - } - - region = request_mem_region(sifmem->start, - sifmem->end - sifmem->start + 1, - pdev->name); - if (!region) { - dev_err(&pdev->dev, "I2S SIF region already claimed\n"); - ret = -EBUSY; - goto err_release_map; - } - - dma1 = platform_get_resource(pdev, IORESOURCE_DMA, 0); - if (!dma1) { - dev_err(&pdev->dev, "no dma resource?\n"); - ret = -ENODEV; - goto err_release_sif; - } - - region = request_mem_region(dma1->start, dma1->end - dma1->start + 1, - pdev->name); - if (!region) { - dev_err(&pdev->dev, "I2S DMA region already claimed\n"); - ret = -EBUSY; - goto err_release_sif; - } - - dma2 = platform_get_resource(pdev, IORESOURCE_DMA, 1); - if (dma2) { - region = request_mem_region(dma2->start, - dma2->end - dma2->start + 1, - pdev->name); - if (!region) { - dev_err(&pdev->dev, - "I2S DMA region already claimed\n"); - ret = -EBUSY; - goto err_release_dma1; - } - } - - dev = kzalloc(sizeof(struct s6000_i2s_dev), GFP_KERNEL); - if (!dev) { - ret = -ENOMEM; - goto err_release_dma2; - } - - s6000_i2s_dai.dev = &pdev->dev; - s6000_i2s_dai.private_data = dev; - s6000_i2s_dai.dma_data = &dev->dma_params; - - dev->sifbase = sifmem->start; - dev->scbbase = mmio; - - s6_i2s_write_reg(dev, S6_I2S_INTERRUPT_ENABLE, 0); - s6_i2s_write_reg(dev, S6_I2S_INTERRUPT_CLEAR, - S6_I2S_INT_ALIGNMENT | - S6_I2S_INT_UNDERRUN | - S6_I2S_INT_OVERRUN); - - s6000_i2s_stop_channel(dev, 0); - s6000_i2s_stop_channel(dev, 1); - s6000_i2s_wait_disabled(dev); - - dev->dma_params.check_xrun = s6000_i2s_check_xrun; - dev->dma_params.trigger = s6000_i2s_trigger; - dev->dma_params.dma_in = dma1->start; - dev->dma_params.dma_out = dma2 ? dma2->start : 0; - dev->dma_params.irq = platform_get_irq(pdev, 0); - if (dev->dma_params.irq < 0) { - dev_err(&pdev->dev, "no irq resource?\n"); - ret = -ENODEV; - goto err_release_dev; - } - - s6_i2s_write_reg(dev, S6_I2S_INTERRUPT_ENABLE, - S6_I2S_INT_ALIGNMENT | - S6_I2S_INT_UNDERRUN | - S6_I2S_INT_OVERRUN); - - ret = snd_soc_register_dai(&s6000_i2s_dai); - if (ret) - goto err_release_dev; - - return 0; - -err_release_dev: - kfree(dev); -err_release_dma2: - if (dma2) - release_mem_region(dma2->start, dma2->end - dma2->start + 1); -err_release_dma1: - release_mem_region(dma1->start, dma1->end - dma1->start + 1); -err_release_sif: - release_mem_region(sifmem->start, (sifmem->end - sifmem->start) + 1); -err_release_map: - iounmap(mmio); -err_release_scb: - release_mem_region(scbmem->start, (scbmem->end - scbmem->start) + 1); -err_release_none: - return ret; -} - -static void __devexit s6000_i2s_remove(struct platform_device *pdev) -{ - struct s6000_i2s_dev *dev = s6000_i2s_dai.private_data; - struct resource *region; - void __iomem *mmio = dev->scbbase; - - snd_soc_unregister_dai(&s6000_i2s_dai); - - s6000_i2s_stop_channel(dev, 0); - s6000_i2s_stop_channel(dev, 1); - - s6_i2s_write_reg(dev, S6_I2S_INTERRUPT_ENABLE, 0); - s6000_i2s_dai.private_data = 0; - kfree(dev); - - region = platform_get_resource(pdev, IORESOURCE_DMA, 0); - release_mem_region(region->start, region->end - region->start + 1); - - region = platform_get_resource(pdev, IORESOURCE_DMA, 1); - if (region) - release_mem_region(region->start, - region->end - region->start + 1); - - region = platform_get_resource(pdev, IORESOURCE_MEM, 0); - release_mem_region(region->start, (region->end - region->start) + 1); - - iounmap(mmio); - region = platform_get_resource(pdev, IORESOURCE_IO, 0); - release_mem_region(region->start, (region->end - region->start) + 1); -} - -static struct platform_driver s6000_i2s_driver = { - .probe = s6000_i2s_probe, - .remove = __devexit_p(s6000_i2s_remove), - .driver = { - .name = "s6000-i2s", - .owner = THIS_MODULE, - }, -}; - -static int __init s6000_i2s_init(void) -{ - return platform_driver_register(&s6000_i2s_driver); -} -module_init(s6000_i2s_init); - -static void __exit s6000_i2s_exit(void) -{ - platform_driver_unregister(&s6000_i2s_driver); -} -module_exit(s6000_i2s_exit); - -MODULE_AUTHOR("Daniel Gloeckner"); -MODULE_DESCRIPTION("Stretch s6000 family I2S SoC Interface"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/s6000/s6000-i2s.h b/trunk/sound/soc/s6000/s6000-i2s.h deleted file mode 100644 index 2375fdfe6dba..000000000000 --- a/trunk/sound/soc/s6000/s6000-i2s.h +++ /dev/null @@ -1,25 +0,0 @@ -/* - * ALSA SoC I2S Audio Layer for the Stretch s6000 family - * - * Author: Daniel Gloeckner, - * Copyright: (C) 2009 emlix GmbH - * - * 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 _S6000_I2S_H -#define _S6000_I2S_H - -extern struct snd_soc_dai s6000_i2s_dai; - -struct s6000_snd_platform_data { - int lines_in; - int lines_out; - int channel_in; - int channel_out; - int wide; - int same_rate; -}; -#endif diff --git a/trunk/sound/soc/s6000/s6000-pcm.c b/trunk/sound/soc/s6000/s6000-pcm.c deleted file mode 100644 index 83b8028e209d..000000000000 --- a/trunk/sound/soc/s6000/s6000-pcm.c +++ /dev/null @@ -1,497 +0,0 @@ -/* - * ALSA PCM interface for the Stetch s6000 family - * - * Author: Daniel Gloeckner, - * Copyright: (C) 2009 emlix GmbH - * - * 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. - */ - -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include - -#include -#include - -#include "s6000-pcm.h" - -#define S6_PCM_PREALLOCATE_SIZE (96 * 1024) -#define S6_PCM_PREALLOCATE_MAX (2048 * 1024) - -static struct snd_pcm_hardware s6000_pcm_hardware = { - .info = (SNDRV_PCM_INFO_INTERLEAVED | SNDRV_PCM_INFO_BLOCK_TRANSFER | - SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_MMAP_VALID | - SNDRV_PCM_INFO_PAUSE | SNDRV_PCM_INFO_JOINT_DUPLEX), - .formats = (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S32_LE), - .rates = (SNDRV_PCM_RATE_CONTINUOUS | SNDRV_PCM_RATE_5512 | \ - SNDRV_PCM_RATE_8000_192000), - .rate_min = 0, - .rate_max = 1562500, - .channels_min = 2, - .channels_max = 8, - .buffer_bytes_max = 0x7ffffff0, - .period_bytes_min = 16, - .period_bytes_max = 0xfffff0, - .periods_min = 2, - .periods_max = 1024, /* no limit */ - .fifo_size = 0, -}; - -struct s6000_runtime_data { - spinlock_t lock; - int period; /* current DMA period */ -}; - -static void s6000_pcm_enqueue_dma(struct snd_pcm_substream *substream) -{ - struct snd_pcm_runtime *runtime = substream->runtime; - struct s6000_runtime_data *prtd = runtime->private_data; - struct snd_soc_pcm_runtime *soc_runtime = substream->private_data; - struct s6000_pcm_dma_params *par = soc_runtime->dai->cpu_dai->dma_data; - int channel; - unsigned int period_size; - unsigned int dma_offset; - dma_addr_t dma_pos; - dma_addr_t src, dst; - - period_size = snd_pcm_lib_period_bytes(substream); - dma_offset = prtd->period * period_size; - dma_pos = runtime->dma_addr + dma_offset; - - if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) { - src = dma_pos; - dst = par->sif_out; - channel = par->dma_out; - } else { - src = par->sif_in; - dst = dma_pos; - channel = par->dma_in; - } - - if (!s6dmac_channel_enabled(DMA_MASK_DMAC(channel), - DMA_INDEX_CHNL(channel))) - return; - - if (s6dmac_fifo_full(DMA_MASK_DMAC(channel), DMA_INDEX_CHNL(channel))) { - printk(KERN_ERR "s6000-pcm: fifo full\n"); - return; - } - - BUG_ON(period_size & 15); - s6dmac_put_fifo(DMA_MASK_DMAC(channel), DMA_INDEX_CHNL(channel), - src, dst, period_size); - - prtd->period++; - if (unlikely(prtd->period >= runtime->periods)) - prtd->period = 0; -} - -static irqreturn_t s6000_pcm_irq(int irq, void *data) -{ - struct snd_pcm *pcm = data; - struct snd_soc_pcm_runtime *runtime = pcm->private_data; - struct s6000_pcm_dma_params *params = runtime->dai->cpu_dai->dma_data; - struct s6000_runtime_data *prtd; - unsigned int has_xrun; - int i, ret = IRQ_NONE; - u32 channel[2] = { - [SNDRV_PCM_STREAM_PLAYBACK] = params->dma_out, - [SNDRV_PCM_STREAM_CAPTURE] = params->dma_in - }; - - has_xrun = params->check_xrun(runtime->dai->cpu_dai); - - for (i = 0; i < ARRAY_SIZE(channel); ++i) { - struct snd_pcm_substream *substream = pcm->streams[i].substream; - unsigned int pending; - - if (!channel[i]) - continue; - - if (unlikely(has_xrun & (1 << i)) && - substream->runtime && - snd_pcm_running(substream)) { - dev_dbg(pcm->dev, "xrun\n"); - snd_pcm_stop(substream, SNDRV_PCM_STATE_XRUN); - ret = IRQ_HANDLED; - } - - pending = s6dmac_int_sources(DMA_MASK_DMAC(channel[i]), - DMA_INDEX_CHNL(channel[i])); - - if (pending & 1) { - ret = IRQ_HANDLED; - if (likely(substream->runtime && - snd_pcm_running(substream))) { - snd_pcm_period_elapsed(substream); - dev_dbg(pcm->dev, "period elapsed %x %x\n", - s6dmac_cur_src(DMA_MASK_DMAC(channel[i]), - DMA_INDEX_CHNL(channel[i])), - s6dmac_cur_dst(DMA_MASK_DMAC(channel[i]), - DMA_INDEX_CHNL(channel[i]))); - prtd = substream->runtime->private_data; - spin_lock(&prtd->lock); - s6000_pcm_enqueue_dma(substream); - spin_unlock(&prtd->lock); - } - } - - if (unlikely(pending & ~7)) { - if (pending & (1 << 3)) - printk(KERN_WARNING - "s6000-pcm: DMA %x Underflow\n", - channel[i]); - if (pending & (1 << 4)) - printk(KERN_WARNING - "s6000-pcm: DMA %x Overflow\n", - channel[i]); - if (pending & 0x1e0) - printk(KERN_WARNING - "s6000-pcm: DMA %x Master Error " - "(mask %x)\n", - channel[i], pending >> 5); - - } - } - - return ret; -} - -static int s6000_pcm_start(struct snd_pcm_substream *substream) -{ - struct s6000_runtime_data *prtd = substream->runtime->private_data; - struct snd_soc_pcm_runtime *soc_runtime = substream->private_data; - struct s6000_pcm_dma_params *par = soc_runtime->dai->cpu_dai->dma_data; - unsigned long flags; - int srcinc; - u32 dma; - - spin_lock_irqsave(&prtd->lock, flags); - - if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) { - srcinc = 1; - dma = par->dma_out; - } else { - srcinc = 0; - dma = par->dma_in; - } - s6dmac_enable_chan(DMA_MASK_DMAC(dma), DMA_INDEX_CHNL(dma), - 1 /* priority 1 (0 is max) */, - 0 /* peripheral requests w/o xfer length mode */, - srcinc /* source address increment */, - srcinc^1 /* destination address increment */, - 0 /* chunksize 0 (skip impossible on this dma) */, - 0 /* source skip after chunk (impossible) */, - 0 /* destination skip after chunk (impossible) */, - 4 /* 16 byte burst size */, - -1 /* don't conserve bandwidth */, - 0 /* low watermark irq descriptor theshold */, - 0 /* disable hardware timestamps */, - 1 /* enable channel */); - - s6000_pcm_enqueue_dma(substream); - s6000_pcm_enqueue_dma(substream); - - spin_unlock_irqrestore(&prtd->lock, flags); - - return 0; -} - -static int s6000_pcm_stop(struct snd_pcm_substream *substream) -{ - struct s6000_runtime_data *prtd = substream->runtime->private_data; - struct snd_soc_pcm_runtime *soc_runtime = substream->private_data; - struct s6000_pcm_dma_params *par = soc_runtime->dai->cpu_dai->dma_data; - unsigned long flags; - u32 channel; - - if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) - channel = par->dma_out; - else - channel = par->dma_in; - - s6dmac_set_terminal_count(DMA_MASK_DMAC(channel), - DMA_INDEX_CHNL(channel), 0); - - spin_lock_irqsave(&prtd->lock, flags); - - s6dmac_disable_chan(DMA_MASK_DMAC(channel), DMA_INDEX_CHNL(channel)); - - spin_unlock_irqrestore(&prtd->lock, flags); - - return 0; -} - -static int s6000_pcm_trigger(struct snd_pcm_substream *substream, int cmd) -{ - struct snd_soc_pcm_runtime *soc_runtime = substream->private_data; - struct s6000_pcm_dma_params *par = soc_runtime->dai->cpu_dai->dma_data; - int ret; - - ret = par->trigger(substream, cmd, 0); - if (ret < 0) - return ret; - - switch (cmd) { - case SNDRV_PCM_TRIGGER_START: - case SNDRV_PCM_TRIGGER_RESUME: - case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: - ret = s6000_pcm_start(substream); - break; - case SNDRV_PCM_TRIGGER_STOP: - case SNDRV_PCM_TRIGGER_SUSPEND: - case SNDRV_PCM_TRIGGER_PAUSE_PUSH: - ret = s6000_pcm_stop(substream); - break; - default: - ret = -EINVAL; - } - if (ret < 0) - return ret; - - return par->trigger(substream, cmd, 1); -} - -static int s6000_pcm_prepare(struct snd_pcm_substream *substream) -{ - struct s6000_runtime_data *prtd = substream->runtime->private_data; - - prtd->period = 0; - - return 0; -} - -static snd_pcm_uframes_t s6000_pcm_pointer(struct snd_pcm_substream *substream) -{ - struct snd_soc_pcm_runtime *soc_runtime = substream->private_data; - struct s6000_pcm_dma_params *par = soc_runtime->dai->cpu_dai->dma_data; - struct snd_pcm_runtime *runtime = substream->runtime; - struct s6000_runtime_data *prtd = runtime->private_data; - unsigned long flags; - unsigned int offset; - dma_addr_t count; - - spin_lock_irqsave(&prtd->lock, flags); - - if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) - count = s6dmac_cur_src(DMA_MASK_DMAC(par->dma_out), - DMA_INDEX_CHNL(par->dma_out)); - else - count = s6dmac_cur_dst(DMA_MASK_DMAC(par->dma_in), - DMA_INDEX_CHNL(par->dma_in)); - - count -= runtime->dma_addr; - - spin_unlock_irqrestore(&prtd->lock, flags); - - offset = bytes_to_frames(runtime, count); - if (unlikely(offset >= runtime->buffer_size)) - offset = 0; - - return offset; -} - -static int s6000_pcm_open(struct snd_pcm_substream *substream) -{ - struct snd_soc_pcm_runtime *soc_runtime = substream->private_data; - struct s6000_pcm_dma_params *par = soc_runtime->dai->cpu_dai->dma_data; - struct snd_pcm_runtime *runtime = substream->runtime; - struct s6000_runtime_data *prtd; - int ret; - - snd_soc_set_runtime_hwparams(substream, &s6000_pcm_hardware); - - ret = snd_pcm_hw_constraint_step(runtime, 0, - SNDRV_PCM_HW_PARAM_PERIOD_BYTES, 16); - if (ret < 0) - return ret; - ret = snd_pcm_hw_constraint_step(runtime, 0, - SNDRV_PCM_HW_PARAM_BUFFER_BYTES, 16); - if (ret < 0) - return ret; - ret = snd_pcm_hw_constraint_integer(runtime, - SNDRV_PCM_HW_PARAM_PERIODS); - if (ret < 0) - return ret; - - if (par->same_rate) { - int rate; - spin_lock(&par->lock); /* needed? */ - rate = par->rate; - spin_unlock(&par->lock); - if (rate != -1) { - ret = snd_pcm_hw_constraint_minmax(runtime, - SNDRV_PCM_HW_PARAM_RATE, - rate, rate); - if (ret < 0) - return ret; - } - } - - prtd = kzalloc(sizeof(struct s6000_runtime_data), GFP_KERNEL); - if (prtd == NULL) - return -ENOMEM; - - spin_lock_init(&prtd->lock); - - runtime->private_data = prtd; - - return 0; -} - -static int s6000_pcm_close(struct snd_pcm_substream *substream) -{ - struct snd_pcm_runtime *runtime = substream->runtime; - struct s6000_runtime_data *prtd = runtime->private_data; - - kfree(prtd); - - return 0; -} - -static int s6000_pcm_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *hw_params) -{ - struct snd_soc_pcm_runtime *soc_runtime = substream->private_data; - struct s6000_pcm_dma_params *par = soc_runtime->dai->cpu_dai->dma_data; - int ret; - ret = snd_pcm_lib_malloc_pages(substream, - params_buffer_bytes(hw_params)); - if (ret < 0) { - printk(KERN_WARNING "s6000-pcm: allocation of memory failed\n"); - return ret; - } - - if (par->same_rate) { - spin_lock(&par->lock); - if (par->rate == -1 || - !(par->in_use & ~(1 << substream->stream))) { - par->rate = params_rate(hw_params); - par->in_use |= 1 << substream->stream; - } else if (params_rate(hw_params) != par->rate) { - snd_pcm_lib_free_pages(substream); - par->in_use &= ~(1 << substream->stream); - ret = -EBUSY; - } - spin_unlock(&par->lock); - } - return ret; -} - -static int s6000_pcm_hw_free(struct snd_pcm_substream *substream) -{ - struct snd_soc_pcm_runtime *soc_runtime = substream->private_data; - struct s6000_pcm_dma_params *par = soc_runtime->dai->cpu_dai->dma_data; - - spin_lock(&par->lock); - par->in_use &= ~(1 << substream->stream); - if (!par->in_use) - par->rate = -1; - spin_unlock(&par->lock); - - return snd_pcm_lib_free_pages(substream); -} - -static struct snd_pcm_ops s6000_pcm_ops = { - .open = s6000_pcm_open, - .close = s6000_pcm_close, - .ioctl = snd_pcm_lib_ioctl, - .hw_params = s6000_pcm_hw_params, - .hw_free = s6000_pcm_hw_free, - .trigger = s6000_pcm_trigger, - .prepare = s6000_pcm_prepare, - .pointer = s6000_pcm_pointer, -}; - -static void s6000_pcm_free(struct snd_pcm *pcm) -{ - struct snd_soc_pcm_runtime *runtime = pcm->private_data; - struct s6000_pcm_dma_params *params = runtime->dai->cpu_dai->dma_data; - - free_irq(params->irq, pcm); - snd_pcm_lib_preallocate_free_for_all(pcm); -} - -static u64 s6000_pcm_dmamask = DMA_32BIT_MASK; - -static int s6000_pcm_new(struct snd_card *card, - struct snd_soc_dai *dai, struct snd_pcm *pcm) -{ - struct snd_soc_pcm_runtime *runtime = pcm->private_data; - struct s6000_pcm_dma_params *params = runtime->dai->cpu_dai->dma_data; - int res; - - if (!card->dev->dma_mask) - card->dev->dma_mask = &s6000_pcm_dmamask; - if (!card->dev->coherent_dma_mask) - card->dev->coherent_dma_mask = DMA_32BIT_MASK; - - if (params->dma_in) { - s6dmac_disable_chan(DMA_MASK_DMAC(params->dma_in), - DMA_INDEX_CHNL(params->dma_in)); - s6dmac_int_sources(DMA_MASK_DMAC(params->dma_in), - DMA_INDEX_CHNL(params->dma_in)); - } - - if (params->dma_out) { - s6dmac_disable_chan(DMA_MASK_DMAC(params->dma_out), - DMA_INDEX_CHNL(params->dma_out)); - s6dmac_int_sources(DMA_MASK_DMAC(params->dma_out), - DMA_INDEX_CHNL(params->dma_out)); - } - - res = request_irq(params->irq, s6000_pcm_irq, IRQF_SHARED, - s6000_soc_platform.name, pcm); - if (res) { - printk(KERN_ERR "s6000-pcm couldn't get IRQ\n"); - return res; - } - - res = snd_pcm_lib_preallocate_pages_for_all(pcm, - SNDRV_DMA_TYPE_DEV, - card->dev, - S6_PCM_PREALLOCATE_SIZE, - S6_PCM_PREALLOCATE_MAX); - if (res) - printk(KERN_WARNING "s6000-pcm: preallocation failed\n"); - - spin_lock_init(¶ms->lock); - params->in_use = 0; - params->rate = -1; - return 0; -} - -struct snd_soc_platform s6000_soc_platform = { - .name = "s6000-audio", - .pcm_ops = &s6000_pcm_ops, - .pcm_new = s6000_pcm_new, - .pcm_free = s6000_pcm_free, -}; -EXPORT_SYMBOL_GPL(s6000_soc_platform); - -static int __init s6000_pcm_init(void) -{ - return snd_soc_register_platform(&s6000_soc_platform); -} -module_init(s6000_pcm_init); - -static void __exit s6000_pcm_exit(void) -{ - snd_soc_unregister_platform(&s6000_soc_platform); -} -module_exit(s6000_pcm_exit); - -MODULE_AUTHOR("Daniel Gloeckner"); -MODULE_DESCRIPTION("Stretch s6000 family PCM DMA module"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/s6000/s6000-pcm.h b/trunk/sound/soc/s6000/s6000-pcm.h deleted file mode 100644 index 96f23f6f52bf..000000000000 --- a/trunk/sound/soc/s6000/s6000-pcm.h +++ /dev/null @@ -1,35 +0,0 @@ -/* - * ALSA PCM interface for the Stretch s6000 family - * - * Author: Daniel Gloeckner, - * Copyright: (C) 2009 emlix GmbH - * - * 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 _S6000_PCM_H -#define _S6000_PCM_H - -struct snd_soc_dai; -struct snd_pcm_substream; - -struct s6000_pcm_dma_params { - unsigned int (*check_xrun)(struct snd_soc_dai *cpu_dai); - int (*trigger)(struct snd_pcm_substream *substream, int cmd, int after); - dma_addr_t sif_in; - dma_addr_t sif_out; - u32 dma_in; - u32 dma_out; - int irq; - int same_rate; - - spinlock_t lock; - int in_use; - int rate; -}; - -extern struct snd_soc_platform s6000_soc_platform; - -#endif diff --git a/trunk/sound/soc/s6000/s6105-ipcam.c b/trunk/sound/soc/s6000/s6105-ipcam.c deleted file mode 100644 index b5f95f9781c1..000000000000 --- a/trunk/sound/soc/s6000/s6105-ipcam.c +++ /dev/null @@ -1,244 +0,0 @@ -/* - * ASoC driver for Stretch s6105 IP camera platform - * - * Author: Daniel Gloeckner, - * Copyright: (C) 2009 emlix GmbH - * - * 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. - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include - -#include "../codecs/tlv320aic3x.h" -#include "s6000-pcm.h" -#include "s6000-i2s.h" - -#define S6105_CAM_CODEC_CLOCK 12288000 - -static int s6105_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_dai *codec_dai = rtd->dai->codec_dai; - struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai; - int ret = 0; - - /* set codec DAI configuration */ - ret = snd_soc_dai_set_fmt(codec_dai, SND_SOC_DAIFMT_I2S | - SND_SOC_DAIFMT_CBM_CFM); - if (ret < 0) - return ret; - - /* set cpu DAI configuration */ - ret = snd_soc_dai_set_fmt(cpu_dai, SND_SOC_DAIFMT_CBM_CFM | - SND_SOC_DAIFMT_NB_NF); - if (ret < 0) - return ret; - - /* set the codec system clock */ - ret = snd_soc_dai_set_sysclk(codec_dai, 0, S6105_CAM_CODEC_CLOCK, - SND_SOC_CLOCK_OUT); - if (ret < 0) - return ret; - - return 0; -} - -static struct snd_soc_ops s6105_ops = { - .hw_params = s6105_hw_params, -}; - -/* s6105 machine dapm widgets */ -static const struct snd_soc_dapm_widget aic3x_dapm_widgets[] = { - SND_SOC_DAPM_LINE("Audio Out Differential", NULL), - SND_SOC_DAPM_LINE("Audio Out Stereo", NULL), - SND_SOC_DAPM_LINE("Audio In", NULL), -}; - -/* s6105 machine audio_mapnections to the codec pins */ -static const struct snd_soc_dapm_route audio_map[] = { - /* Audio Out connected to HPLOUT, HPLCOM, HPROUT */ - {"Audio Out Differential", NULL, "HPLOUT"}, - {"Audio Out Differential", NULL, "HPLCOM"}, - {"Audio Out Stereo", NULL, "HPLOUT"}, - {"Audio Out Stereo", NULL, "HPROUT"}, - - /* Audio In connected to LINE1L, LINE1R */ - {"LINE1L", NULL, "Audio In"}, - {"LINE1R", NULL, "Audio In"}, -}; - -static int output_type_info(struct snd_kcontrol *kcontrol, - struct snd_ctl_elem_info *uinfo) -{ - uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED; - uinfo->count = 1; - uinfo->value.enumerated.items = 2; - if (uinfo->value.enumerated.item) { - uinfo->value.enumerated.item = 1; - strcpy(uinfo->value.enumerated.name, "HPLOUT/HPROUT"); - } else { - strcpy(uinfo->value.enumerated.name, "HPLOUT/HPLCOM"); - } - return 0; -} - -static int output_type_get(struct snd_kcontrol *kcontrol, - struct snd_ctl_elem_value *ucontrol) -{ - ucontrol->value.enumerated.item[0] = kcontrol->private_value; - return 0; -} - -static int output_type_put(struct snd_kcontrol *kcontrol, - struct snd_ctl_elem_value *ucontrol) -{ - struct snd_soc_codec *codec = kcontrol->private_data; - unsigned int val = (ucontrol->value.enumerated.item[0] != 0); - char *differential = "Audio Out Differential"; - char *stereo = "Audio Out Stereo"; - - if (kcontrol->private_value == val) - return 0; - kcontrol->private_value = val; - snd_soc_dapm_disable_pin(codec, val ? differential : stereo); - snd_soc_dapm_sync(codec); - snd_soc_dapm_enable_pin(codec, val ? stereo : differential); - snd_soc_dapm_sync(codec); - - return 1; -} - -static const struct snd_kcontrol_new audio_out_mux = { - .iface = SNDRV_CTL_ELEM_IFACE_MIXER, - .name = "Master Output Mux", - .index = 0, - .access = SNDRV_CTL_ELEM_ACCESS_READWRITE, - .info = output_type_info, - .get = output_type_get, - .put = output_type_put, - .private_value = 1 /* default to stereo */ -}; - -/* Logic for a aic3x as connected on the s6105 ip camera ref design */ -static int s6105_aic3x_init(struct snd_soc_codec *codec) -{ - /* Add s6105 specific widgets */ - snd_soc_dapm_new_controls(codec, aic3x_dapm_widgets, - ARRAY_SIZE(aic3x_dapm_widgets)); - - /* Set up s6105 specific audio path audio_map */ - snd_soc_dapm_add_routes(codec, audio_map, ARRAY_SIZE(audio_map)); - - /* not present */ - snd_soc_dapm_nc_pin(codec, "MONO_LOUT"); - snd_soc_dapm_nc_pin(codec, "LINE2L"); - snd_soc_dapm_nc_pin(codec, "LINE2R"); - - /* not connected */ - snd_soc_dapm_nc_pin(codec, "MIC3L"); /* LINE2L on this chip */ - snd_soc_dapm_nc_pin(codec, "MIC3R"); /* LINE2R on this chip */ - snd_soc_dapm_nc_pin(codec, "LLOUT"); - snd_soc_dapm_nc_pin(codec, "RLOUT"); - snd_soc_dapm_nc_pin(codec, "HPRCOM"); - - /* always connected */ - snd_soc_dapm_enable_pin(codec, "Audio In"); - - /* must correspond to audio_out_mux.private_value initializer */ - snd_soc_dapm_disable_pin(codec, "Audio Out Differential"); - snd_soc_dapm_sync(codec); - snd_soc_dapm_enable_pin(codec, "Audio Out Stereo"); - - snd_soc_dapm_sync(codec); - - snd_ctl_add(codec->card, snd_ctl_new1(&audio_out_mux, codec)); - - return 0; -} - -/* s6105 digital audio interface glue - connects codec <--> CPU */ -static struct snd_soc_dai_link s6105_dai = { - .name = "TLV320AIC31", - .stream_name = "AIC31", - .cpu_dai = &s6000_i2s_dai, - .codec_dai = &aic3x_dai, - .init = s6105_aic3x_init, - .ops = &s6105_ops, -}; - -/* s6105 audio machine driver */ -static struct snd_soc_card snd_soc_card_s6105 = { - .name = "Stretch IP Camera", - .platform = &s6000_soc_platform, - .dai_link = &s6105_dai, - .num_links = 1, -}; - -/* s6105 audio private data */ -static struct aic3x_setup_data s6105_aic3x_setup = { - .i2c_bus = 0, - .i2c_address = 0x18, -}; - -/* s6105 audio subsystem */ -static struct snd_soc_device s6105_snd_devdata = { - .card = &snd_soc_card_s6105, - .codec_dev = &soc_codec_dev_aic3x, - .codec_data = &s6105_aic3x_setup, -}; - -static struct s6000_snd_platform_data __initdata s6105_snd_data = { - .wide = 0, - .channel_in = 0, - .channel_out = 1, - .lines_in = 1, - .lines_out = 1, - .same_rate = 1, -}; - -static struct platform_device *s6105_snd_device; - -static int __init s6105_init(void) -{ - int ret; - - s6105_snd_device = platform_device_alloc("soc-audio", -1); - if (!s6105_snd_device) - return -ENOMEM; - - platform_set_drvdata(s6105_snd_device, &s6105_snd_devdata); - s6105_snd_devdata.dev = &s6105_snd_device->dev; - platform_device_add_data(s6105_snd_device, &s6105_snd_data, - sizeof(s6105_snd_data)); - - ret = platform_device_add(s6105_snd_device); - if (ret) - platform_device_put(s6105_snd_device); - - return ret; -} - -static void __exit s6105_exit(void) -{ - platform_device_unregister(s6105_snd_device); -} - -module_init(s6105_init); -module_exit(s6105_exit); - -MODULE_AUTHOR("Daniel Gloeckner"); -MODULE_DESCRIPTION("Stretch s6105 IP camera ASoC driver"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/sh/ssi.c b/trunk/sound/soc/sh/ssi.c index b378096cadb1..56fa0872abbb 100644 --- a/trunk/sound/soc/sh/ssi.c +++ b/trunk/sound/soc/sh/ssi.c @@ -145,7 +145,7 @@ static int ssi_hw_params(struct snd_pcm_substream *substream, recv = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) ? 0 : 1; pr_debug("ssi_hw_params() enter\nssicr was %08lx\n", ssicr); - pr_debug("bits: %u channels: %u\n", bits, channels); + pr_debug("bits: %d channels: %d\n", bits, channels); ssicr &= ~(CR_TRMD | CR_CHNL_MASK | CR_DWL_MASK | CR_PDTA | CR_SWL_MASK); diff --git a/trunk/sound/soc/soc-core.c b/trunk/sound/soc/soc-core.c index 3f44150d8e30..1cd149b9ce69 100644 --- a/trunk/sound/soc/soc-core.c +++ b/trunk/sound/soc/soc-core.c @@ -113,35 +113,6 @@ static int soc_ac97_dev_register(struct snd_soc_codec *codec) } #endif -static int soc_pcm_apply_symmetry(struct snd_pcm_substream *substream) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct snd_soc_device *socdev = rtd->socdev; - struct snd_soc_card *card = socdev->card; - struct snd_soc_dai_link *machine = rtd->dai; - struct snd_soc_dai *cpu_dai = machine->cpu_dai; - struct snd_soc_dai *codec_dai = machine->codec_dai; - int ret; - - if (codec_dai->symmetric_rates || cpu_dai->symmetric_rates || - machine->symmetric_rates) { - dev_dbg(card->dev, "Symmetry forces %dHz rate\n", - machine->rate); - - ret = snd_pcm_hw_constraint_minmax(substream->runtime, - SNDRV_PCM_HW_PARAM_RATE, - machine->rate, - machine->rate); - if (ret < 0) { - dev_err(card->dev, - "Unable to apply rate symmetry constraint: %d\n", ret); - return ret; - } - } - - return 0; -} - /* * Called by ALSA when a PCM substream is opened, the runtime->hw record is * then initialized and any private data can be allocated. This also calls @@ -250,13 +221,6 @@ static int soc_pcm_open(struct snd_pcm_substream *substream) goto machine_err; } - /* Symmetry only applies if we've already got an active stream. */ - if (cpu_dai->active || codec_dai->active) { - ret = soc_pcm_apply_symmetry(substream); - if (ret != 0) - goto machine_err; - } - pr_debug("asoc: %s <-> %s info:\n", codec_dai->name, cpu_dai->name); pr_debug("asoc: rate mask 0x%x\n", runtime->hw.rates); pr_debug("asoc: min ch %d max ch %d\n", runtime->hw.channels_min, @@ -299,6 +263,7 @@ static void close_delayed_work(struct work_struct *work) { struct snd_soc_card *card = container_of(work, struct snd_soc_card, delayed_work.work); + struct snd_soc_device *socdev = card->socdev; struct snd_soc_codec *codec = card->codec; struct snd_soc_dai *codec_dai; int i; @@ -314,10 +279,27 @@ static void close_delayed_work(struct work_struct *work) /* are we waiting on this codec DAI stream */ if (codec_dai->pop_wait == 1) { + + /* Reduce power if no longer active */ + if (codec->active == 0) { + pr_debug("pop wq D1 %s %s\n", codec->name, + codec_dai->playback.stream_name); + snd_soc_dapm_set_bias_level(socdev, + SND_SOC_BIAS_PREPARE); + } + codec_dai->pop_wait = 0; snd_soc_dapm_stream_event(codec, codec_dai->playback.stream_name, SND_SOC_DAPM_STREAM_STOP); + + /* Fall into standby if no longer active */ + if (codec->active == 0) { + pr_debug("pop wq D3 %s %s\n", codec->name, + codec_dai->playback.stream_name); + snd_soc_dapm_set_bias_level(socdev, + SND_SOC_BIAS_STANDBY); + } } } mutex_unlock(&pcm_mutex); @@ -381,6 +363,10 @@ static int soc_codec_close(struct snd_pcm_substream *substream) snd_soc_dapm_stream_event(codec, codec_dai->capture.stream_name, SND_SOC_DAPM_STREAM_STOP); + + if (codec->active == 0 && codec_dai->pop_wait == 0) + snd_soc_dapm_set_bias_level(socdev, + SND_SOC_BIAS_STANDBY); } mutex_unlock(&pcm_mutex); @@ -445,16 +431,36 @@ static int soc_pcm_prepare(struct snd_pcm_substream *substream) cancel_delayed_work(&card->delayed_work); } - if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) - snd_soc_dapm_stream_event(codec, - codec_dai->playback.stream_name, - SND_SOC_DAPM_STREAM_START); - else - snd_soc_dapm_stream_event(codec, - codec_dai->capture.stream_name, - SND_SOC_DAPM_STREAM_START); + /* do we need to power up codec */ + if (codec->bias_level != SND_SOC_BIAS_ON) { + snd_soc_dapm_set_bias_level(socdev, + SND_SOC_BIAS_PREPARE); + + if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) + snd_soc_dapm_stream_event(codec, + codec_dai->playback.stream_name, + SND_SOC_DAPM_STREAM_START); + else + snd_soc_dapm_stream_event(codec, + codec_dai->capture.stream_name, + SND_SOC_DAPM_STREAM_START); - snd_soc_dai_digital_mute(codec_dai, 0); + snd_soc_dapm_set_bias_level(socdev, SND_SOC_BIAS_ON); + snd_soc_dai_digital_mute(codec_dai, 0); + + } else { + /* codec already powered - power on widgets */ + if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) + snd_soc_dapm_stream_event(codec, + codec_dai->playback.stream_name, + SND_SOC_DAPM_STREAM_START); + else + snd_soc_dapm_stream_event(codec, + codec_dai->capture.stream_name, + SND_SOC_DAPM_STREAM_START); + + snd_soc_dai_digital_mute(codec_dai, 0); + } out: mutex_unlock(&pcm_mutex); @@ -515,8 +521,6 @@ static int soc_pcm_hw_params(struct snd_pcm_substream *substream, } } - machine->rate = params_rate(params); - out: mutex_unlock(&pcm_mutex); return ret; @@ -628,12 +632,6 @@ static int soc_suspend(struct platform_device *pdev, pm_message_t state) struct snd_soc_codec *codec = card->codec; int i; - /* If the initialization of this soc device failed, there is no codec - * associated with it. Just bail out in this case. - */ - if (!codec) - return 0; - /* Due to the resume being scheduled into a workqueue we could * suspend before that's finished - wait for it to complete. */ @@ -1336,7 +1334,6 @@ int snd_soc_new_pcms(struct snd_soc_device *socdev, int idx, const char *xid) return ret; } - codec->socdev = socdev; codec->card->dev = socdev->dev; codec->card->private_data = codec; strncpy(codec->card->driver, codec->name, sizeof(codec->card->driver)); @@ -1747,7 +1744,7 @@ int snd_soc_info_volsw_ext(struct snd_kcontrol *kcontrol, { int max = kcontrol->private_value; - if (max == 1 && !strstr(kcontrol->id.name, " Volume")) + if (max == 1) uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN; else uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER; @@ -1777,7 +1774,7 @@ int snd_soc_info_volsw(struct snd_kcontrol *kcontrol, unsigned int shift = mc->shift; unsigned int rshift = mc->rshift; - if (max == 1 && !strstr(kcontrol->id.name, " Volume")) + if (max == 1) uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN; else uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER; @@ -1884,7 +1881,7 @@ int snd_soc_info_volsw_2r(struct snd_kcontrol *kcontrol, (struct soc_mixer_control *)kcontrol->private_value; int max = mc->max; - if (max == 1 && !strstr(kcontrol->id.name, " Volume")) + if (max == 1) uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN; else uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER; @@ -2068,7 +2065,7 @@ EXPORT_SYMBOL_GPL(snd_soc_put_volsw_s8); int snd_soc_dai_set_sysclk(struct snd_soc_dai *dai, int clk_id, unsigned int freq, int dir) { - if (dai->ops && dai->ops->set_sysclk) + if (dai->ops->set_sysclk) return dai->ops->set_sysclk(dai, clk_id, freq, dir); else return -EINVAL; @@ -2088,7 +2085,7 @@ EXPORT_SYMBOL_GPL(snd_soc_dai_set_sysclk); int snd_soc_dai_set_clkdiv(struct snd_soc_dai *dai, int div_id, int div) { - if (dai->ops && dai->ops->set_clkdiv) + if (dai->ops->set_clkdiv) return dai->ops->set_clkdiv(dai, div_id, div); else return -EINVAL; @@ -2107,7 +2104,7 @@ EXPORT_SYMBOL_GPL(snd_soc_dai_set_clkdiv); int snd_soc_dai_set_pll(struct snd_soc_dai *dai, int pll_id, unsigned int freq_in, unsigned int freq_out) { - if (dai->ops && dai->ops->set_pll) + if (dai->ops->set_pll) return dai->ops->set_pll(dai, pll_id, freq_in, freq_out); else return -EINVAL; @@ -2123,7 +2120,7 @@ EXPORT_SYMBOL_GPL(snd_soc_dai_set_pll); */ int snd_soc_dai_set_fmt(struct snd_soc_dai *dai, unsigned int fmt) { - if (dai->ops && dai->ops->set_fmt) + if (dai->ops->set_fmt) return dai->ops->set_fmt(dai, fmt); else return -EINVAL; @@ -2142,7 +2139,7 @@ EXPORT_SYMBOL_GPL(snd_soc_dai_set_fmt); int snd_soc_dai_set_tdm_slot(struct snd_soc_dai *dai, unsigned int mask, int slots) { - if (dai->ops && dai->ops->set_tdm_slot) + if (dai->ops->set_sysclk) return dai->ops->set_tdm_slot(dai, mask, slots); else return -EINVAL; @@ -2158,7 +2155,7 @@ EXPORT_SYMBOL_GPL(snd_soc_dai_set_tdm_slot); */ int snd_soc_dai_set_tristate(struct snd_soc_dai *dai, int tristate) { - if (dai->ops && dai->ops->set_tristate) + if (dai->ops->set_sysclk) return dai->ops->set_tristate(dai, tristate); else return -EINVAL; @@ -2174,7 +2171,7 @@ EXPORT_SYMBOL_GPL(snd_soc_dai_set_tristate); */ int snd_soc_dai_digital_mute(struct snd_soc_dai *dai, int mute) { - if (dai->ops && dai->ops->digital_mute) + if (dai->ops->digital_mute) return dai->ops->digital_mute(dai, mute); else return -EINVAL; @@ -2355,39 +2352,6 @@ void snd_soc_unregister_platform(struct snd_soc_platform *platform) } EXPORT_SYMBOL_GPL(snd_soc_unregister_platform); -static u64 codec_format_map[] = { - SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S16_BE, - SNDRV_PCM_FMTBIT_U16_LE | SNDRV_PCM_FMTBIT_U16_BE, - SNDRV_PCM_FMTBIT_S24_LE | SNDRV_PCM_FMTBIT_S24_BE, - SNDRV_PCM_FMTBIT_U24_LE | SNDRV_PCM_FMTBIT_U24_BE, - SNDRV_PCM_FMTBIT_S32_LE | SNDRV_PCM_FMTBIT_S32_BE, - SNDRV_PCM_FMTBIT_U32_LE | SNDRV_PCM_FMTBIT_U32_BE, - SNDRV_PCM_FMTBIT_S24_3LE | SNDRV_PCM_FMTBIT_U24_3BE, - SNDRV_PCM_FMTBIT_U24_3LE | SNDRV_PCM_FMTBIT_U24_3BE, - SNDRV_PCM_FMTBIT_S20_3LE | SNDRV_PCM_FMTBIT_S20_3BE, - SNDRV_PCM_FMTBIT_U20_3LE | SNDRV_PCM_FMTBIT_U20_3BE, - SNDRV_PCM_FMTBIT_S18_3LE | SNDRV_PCM_FMTBIT_S18_3BE, - SNDRV_PCM_FMTBIT_U18_3LE | SNDRV_PCM_FMTBIT_U18_3BE, - SNDRV_PCM_FMTBIT_FLOAT_LE | SNDRV_PCM_FMTBIT_FLOAT_BE, - SNDRV_PCM_FMTBIT_FLOAT64_LE | SNDRV_PCM_FMTBIT_FLOAT64_BE, - SNDRV_PCM_FMTBIT_IEC958_SUBFRAME_LE - | SNDRV_PCM_FMTBIT_IEC958_SUBFRAME_BE, -}; - -/* Fix up the DAI formats for endianness: codecs don't actually see - * the endianness of the data but we're using the CPU format - * definitions which do need to include endianness so we ensure that - * codec DAIs always have both big and little endian variants set. - */ -static void fixup_codec_formats(struct snd_soc_pcm_stream *stream) -{ - int i; - - for (i = 0; i < ARRAY_SIZE(codec_format_map); i++) - if (stream->formats & codec_format_map[i]) - stream->formats |= codec_format_map[i]; -} - /** * snd_soc_register_codec - Register a codec with the ASoC core * @@ -2395,8 +2359,6 @@ static void fixup_codec_formats(struct snd_soc_pcm_stream *stream) */ int snd_soc_register_codec(struct snd_soc_codec *codec) { - int i; - if (!codec->name) return -EINVAL; @@ -2406,11 +2368,6 @@ int snd_soc_register_codec(struct snd_soc_codec *codec) INIT_LIST_HEAD(&codec->list); - for (i = 0; i < codec->num_dai; i++) { - fixup_codec_formats(&codec->dai[i].playback); - fixup_codec_formats(&codec->dai[i].capture); - } - mutex_lock(&client_mutex); list_add(&codec->list, &codec_list); snd_soc_instantiate_cards(); diff --git a/trunk/sound/soc/soc-dapm.c b/trunk/sound/soc/soc-dapm.c index 21c69074aa17..735903a74675 100644 --- a/trunk/sound/soc/soc-dapm.c +++ b/trunk/sound/soc/soc-dapm.c @@ -12,7 +12,7 @@ * Features: * o Changes power status of internal codec blocks depending on the * dynamic configuration of codec internal audio paths and active - * DACs/ADCs. + * DAC's/ADC's. * o Platform power domain - can support external components i.e. amps and * mic/meadphone insertion events. * o Automatic Mic Bias support @@ -52,21 +52,23 @@ /* dapm power sequences - make this per codec in the future */ static int dapm_up_seq[] = { - snd_soc_dapm_pre, snd_soc_dapm_supply, snd_soc_dapm_micbias, - snd_soc_dapm_mic, snd_soc_dapm_mux, snd_soc_dapm_value_mux, - snd_soc_dapm_dac, snd_soc_dapm_mixer, snd_soc_dapm_mixer_named_ctl, - snd_soc_dapm_pga, snd_soc_dapm_adc, snd_soc_dapm_hp, snd_soc_dapm_spk, - snd_soc_dapm_post + snd_soc_dapm_pre, snd_soc_dapm_micbias, snd_soc_dapm_mic, + snd_soc_dapm_mux, snd_soc_dapm_value_mux, snd_soc_dapm_dac, + snd_soc_dapm_mixer, snd_soc_dapm_mixer_named_ctl, snd_soc_dapm_pga, + snd_soc_dapm_adc, snd_soc_dapm_hp, snd_soc_dapm_spk, snd_soc_dapm_post }; static int dapm_down_seq[] = { snd_soc_dapm_pre, snd_soc_dapm_adc, snd_soc_dapm_hp, snd_soc_dapm_spk, snd_soc_dapm_pga, snd_soc_dapm_mixer_named_ctl, snd_soc_dapm_mixer, snd_soc_dapm_dac, snd_soc_dapm_mic, snd_soc_dapm_micbias, - snd_soc_dapm_mux, snd_soc_dapm_value_mux, snd_soc_dapm_supply, - snd_soc_dapm_post + snd_soc_dapm_mux, snd_soc_dapm_value_mux, snd_soc_dapm_post }; +static int dapm_status = 1; +module_param(dapm_status, int, 0); +MODULE_PARM_DESC(dapm_status, "enable DPM sysfs entries"); + static void pop_wait(u32 pop_time) { if (pop_time) @@ -94,48 +96,6 @@ static inline struct snd_soc_dapm_widget *dapm_cnew_widget( return kmemdup(_widget, sizeof(*_widget), GFP_KERNEL); } -/** - * snd_soc_dapm_set_bias_level - set the bias level for the system - * @socdev: audio device - * @level: level to configure - * - * Configure the bias (power) levels for the SoC audio device. - * - * Returns 0 for success else error. - */ -static int snd_soc_dapm_set_bias_level(struct snd_soc_device *socdev, - enum snd_soc_bias_level level) -{ - struct snd_soc_card *card = socdev->card; - struct snd_soc_codec *codec = socdev->card->codec; - int ret = 0; - - switch (level) { - case SND_SOC_BIAS_ON: - dev_dbg(socdev->dev, "Setting full bias\n"); - break; - case SND_SOC_BIAS_PREPARE: - dev_dbg(socdev->dev, "Setting bias prepare\n"); - break; - case SND_SOC_BIAS_STANDBY: - dev_dbg(socdev->dev, "Setting standby bias\n"); - break; - case SND_SOC_BIAS_OFF: - dev_dbg(socdev->dev, "Setting bias off\n"); - break; - default: - dev_err(socdev->dev, "Setting invalid bias %d\n", level); - return -EINVAL; - } - - if (card->set_bias_level) - ret = card->set_bias_level(card, level); - if (ret == 0 && codec->set_bias_level) - ret = codec->set_bias_level(codec, level); - - return ret; -} - /* set up initial codec paths */ static void dapm_set_path_status(struct snd_soc_dapm_widget *w, struct snd_soc_dapm_path *p, int i) @@ -205,7 +165,6 @@ static void dapm_set_path_status(struct snd_soc_dapm_widget *w, case snd_soc_dapm_dac: case snd_soc_dapm_micbias: case snd_soc_dapm_vmid: - case snd_soc_dapm_supply: p->connect = 1; break; /* does effect routing - dynamically connected */ @@ -220,7 +179,7 @@ static void dapm_set_path_status(struct snd_soc_dapm_widget *w, } } -/* connect mux widget to its interconnecting audio paths */ +/* connect mux widget to it's interconnecting audio paths */ static int dapm_connect_mux(struct snd_soc_codec *codec, struct snd_soc_dapm_widget *src, struct snd_soc_dapm_widget *dest, struct snd_soc_dapm_path *path, const char *control_name, @@ -243,7 +202,7 @@ static int dapm_connect_mux(struct snd_soc_codec *codec, return -ENODEV; } -/* connect mixer widget to its interconnecting audio paths */ +/* connect mixer widget to it's interconnecting audio paths */ static int dapm_connect_mixer(struct snd_soc_codec *codec, struct snd_soc_dapm_widget *src, struct snd_soc_dapm_widget *dest, struct snd_soc_dapm_path *path, const char *control_name) @@ -398,9 +357,8 @@ static int dapm_new_mixer(struct snd_soc_codec *codec, path->long_name); ret = snd_ctl_add(codec->card, path->kcontrol); if (ret < 0) { - printk(KERN_ERR "asoc: failed to add dapm kcontrol %s: %d\n", - path->long_name, - ret); + printk(KERN_ERR "asoc: failed to add dapm kcontrol %s\n", + path->long_name); kfree(path->long_name); path->long_name = NULL; return ret; @@ -476,9 +434,6 @@ static int is_connected_output_ep(struct snd_soc_dapm_widget *widget) struct snd_soc_dapm_path *path; int con = 0; - if (widget->id == snd_soc_dapm_supply) - return 0; - if (widget->id == snd_soc_dapm_adc && widget->active) return 1; @@ -515,9 +470,6 @@ static int is_connected_input_ep(struct snd_soc_dapm_widget *widget) struct snd_soc_dapm_path *path; int con = 0; - if (widget->id == snd_soc_dapm_supply) - return 0; - /* active stream ? */ if (widget->id == snd_soc_dapm_dac && widget->active) return 1; @@ -569,12 +521,84 @@ int dapm_reg_event(struct snd_soc_dapm_widget *w, } EXPORT_SYMBOL_GPL(dapm_reg_event); -/* Standard power change method, used to apply power changes to most - * widgets. +/* + * Scan a single DAPM widget for a complete audio path and update the + * power status appropriately. */ -static int dapm_generic_apply_power(struct snd_soc_dapm_widget *w) +static int dapm_power_widget(struct snd_soc_codec *codec, int event, + struct snd_soc_dapm_widget *w) { - int ret; + int in, out, power_change, power, ret; + + /* vmid - no action */ + if (w->id == snd_soc_dapm_vmid) + return 0; + + /* active ADC */ + if (w->id == snd_soc_dapm_adc && w->active) { + in = is_connected_input_ep(w); + dapm_clear_walk(w->codec); + w->power = (in != 0) ? 1 : 0; + dapm_update_bits(w); + return 0; + } + + /* active DAC */ + if (w->id == snd_soc_dapm_dac && w->active) { + out = is_connected_output_ep(w); + dapm_clear_walk(w->codec); + w->power = (out != 0) ? 1 : 0; + dapm_update_bits(w); + return 0; + } + + /* pre and post event widgets */ + if (w->id == snd_soc_dapm_pre) { + if (!w->event) + return 0; + + if (event == SND_SOC_DAPM_STREAM_START) { + ret = w->event(w, + NULL, SND_SOC_DAPM_PRE_PMU); + if (ret < 0) + return ret; + } else if (event == SND_SOC_DAPM_STREAM_STOP) { + ret = w->event(w, + NULL, SND_SOC_DAPM_PRE_PMD); + if (ret < 0) + return ret; + } + return 0; + } + if (w->id == snd_soc_dapm_post) { + if (!w->event) + return 0; + + if (event == SND_SOC_DAPM_STREAM_START) { + ret = w->event(w, + NULL, SND_SOC_DAPM_POST_PMU); + if (ret < 0) + return ret; + } else if (event == SND_SOC_DAPM_STREAM_STOP) { + ret = w->event(w, + NULL, SND_SOC_DAPM_POST_PMD); + if (ret < 0) + return ret; + } + return 0; + } + + /* all other widgets */ + in = is_connected_input_ep(w); + dapm_clear_walk(w->codec); + out = is_connected_output_ep(w); + dapm_clear_walk(w->codec); + power = (out != 0 && in != 0) ? 1 : 0; + power_change = (w->power == power) ? 0 : 1; + w->power = power; + + if (!power_change) + return 0; /* call any power change event handlers */ if (w->event) @@ -583,7 +607,7 @@ static int dapm_generic_apply_power(struct snd_soc_dapm_widget *w) w->name, w->event_flags); /* power up pre event */ - if (w->power && w->event && + if (power && w->event && (w->event_flags & SND_SOC_DAPM_PRE_PMU)) { ret = w->event(w, NULL, SND_SOC_DAPM_PRE_PMU); if (ret < 0) @@ -591,7 +615,7 @@ static int dapm_generic_apply_power(struct snd_soc_dapm_widget *w) } /* power down pre event */ - if (!w->power && w->event && + if (!power && w->event && (w->event_flags & SND_SOC_DAPM_PRE_PMD)) { ret = w->event(w, NULL, SND_SOC_DAPM_PRE_PMD); if (ret < 0) @@ -599,17 +623,17 @@ static int dapm_generic_apply_power(struct snd_soc_dapm_widget *w) } /* Lower PGA volume to reduce pops */ - if (w->id == snd_soc_dapm_pga && !w->power) - dapm_set_pga(w, w->power); + if (w->id == snd_soc_dapm_pga && !power) + dapm_set_pga(w, power); dapm_update_bits(w); /* Raise PGA volume to reduce pops */ - if (w->id == snd_soc_dapm_pga && w->power) - dapm_set_pga(w, w->power); + if (w->id == snd_soc_dapm_pga && power) + dapm_set_pga(w, power); /* power up post event */ - if (w->power && w->event && + if (power && w->event && (w->event_flags & SND_SOC_DAPM_POST_PMU)) { ret = w->event(w, NULL, SND_SOC_DAPM_POST_PMU); @@ -618,7 +642,7 @@ static int dapm_generic_apply_power(struct snd_soc_dapm_widget *w) } /* power down post event */ - if (!w->power && w->event && + if (!power && w->event && (w->event_flags & SND_SOC_DAPM_POST_PMD)) { ret = w->event(w, NULL, SND_SOC_DAPM_POST_PMD); if (ret < 0) @@ -628,116 +652,6 @@ static int dapm_generic_apply_power(struct snd_soc_dapm_widget *w) return 0; } -/* Generic check to see if a widget should be powered. - */ -static int dapm_generic_check_power(struct snd_soc_dapm_widget *w) -{ - int in, out; - - in = is_connected_input_ep(w); - dapm_clear_walk(w->codec); - out = is_connected_output_ep(w); - dapm_clear_walk(w->codec); - return out != 0 && in != 0; -} - -/* Check to see if an ADC has power */ -static int dapm_adc_check_power(struct snd_soc_dapm_widget *w) -{ - int in; - - if (w->active) { - in = is_connected_input_ep(w); - dapm_clear_walk(w->codec); - return in != 0; - } else { - return dapm_generic_check_power(w); - } -} - -/* Check to see if a DAC has power */ -static int dapm_dac_check_power(struct snd_soc_dapm_widget *w) -{ - int out; - - if (w->active) { - out = is_connected_output_ep(w); - dapm_clear_walk(w->codec); - return out != 0; - } else { - return dapm_generic_check_power(w); - } -} - -/* Check to see if a power supply is needed */ -static int dapm_supply_check_power(struct snd_soc_dapm_widget *w) -{ - struct snd_soc_dapm_path *path; - int power = 0; - - /* Check if one of our outputs is connected */ - list_for_each_entry(path, &w->sinks, list_source) { - if (path->sink && path->sink->power_check && - path->sink->power_check(path->sink)) { - power = 1; - break; - } - } - - dapm_clear_walk(w->codec); - - return power; -} - -/* - * Scan a single DAPM widget for a complete audio path and update the - * power status appropriately. - */ -static int dapm_power_widget(struct snd_soc_codec *codec, int event, - struct snd_soc_dapm_widget *w) -{ - int ret; - - switch (w->id) { - case snd_soc_dapm_pre: - if (!w->event) - return 0; - - if (event == SND_SOC_DAPM_STREAM_START) { - ret = w->event(w, - NULL, SND_SOC_DAPM_PRE_PMU); - if (ret < 0) - return ret; - } else if (event == SND_SOC_DAPM_STREAM_STOP) { - ret = w->event(w, - NULL, SND_SOC_DAPM_PRE_PMD); - if (ret < 0) - return ret; - } - return 0; - - case snd_soc_dapm_post: - if (!w->event) - return 0; - - if (event == SND_SOC_DAPM_STREAM_START) { - ret = w->event(w, - NULL, SND_SOC_DAPM_POST_PMU); - if (ret < 0) - return ret; - } else if (event == SND_SOC_DAPM_STREAM_STOP) { - ret = w->event(w, - NULL, SND_SOC_DAPM_POST_PMD); - if (ret < 0) - return ret; - } - return 0; - - default: - return dapm_generic_apply_power(w); - } -} - /* * Scan each dapm widget for complete audio path. * A complete path is a route that has valid endpoints i.e.:- @@ -749,102 +663,31 @@ static int dapm_power_widget(struct snd_soc_codec *codec, int event, */ static int dapm_power_widgets(struct snd_soc_codec *codec, int event) { - struct snd_soc_device *socdev = codec->socdev; struct snd_soc_dapm_widget *w; - int ret = 0; - int i, power; - int sys_power = 0; - - INIT_LIST_HEAD(&codec->up_list); - INIT_LIST_HEAD(&codec->down_list); - - /* Check which widgets we need to power and store them in - * lists indicating if they should be powered up or down. - */ - list_for_each_entry(w, &codec->dapm_widgets, list) { - switch (w->id) { - case snd_soc_dapm_pre: - list_add_tail(&codec->down_list, &w->power_list); - break; - case snd_soc_dapm_post: - list_add_tail(&codec->up_list, &w->power_list); - break; - - default: - if (!w->power_check) - continue; - - power = w->power_check(w); - if (power) - sys_power = 1; - - if (w->power == power) - continue; - - if (power) - list_add_tail(&w->power_list, &codec->up_list); - else - list_add_tail(&w->power_list, - &codec->down_list); - - w->power = power; - break; - } + int i, c = 1, *seq = NULL, ret = 0; + + /* do we have a sequenced stream event */ + if (event == SND_SOC_DAPM_STREAM_START) { + c = ARRAY_SIZE(dapm_up_seq); + seq = dapm_up_seq; + } else if (event == SND_SOC_DAPM_STREAM_STOP) { + c = ARRAY_SIZE(dapm_down_seq); + seq = dapm_down_seq; } - /* If we're changing to all on or all off then prepare */ - if ((sys_power && codec->bias_level == SND_SOC_BIAS_STANDBY) || - (!sys_power && codec->bias_level == SND_SOC_BIAS_ON)) { - ret = snd_soc_dapm_set_bias_level(socdev, - SND_SOC_BIAS_PREPARE); - if (ret != 0) - pr_err("Failed to prepare bias: %d\n", ret); - } + for (i = 0; i < c; i++) { + list_for_each_entry(w, &codec->dapm_widgets, list) { - /* Power down widgets first; try to avoid amplifying pops. */ - for (i = 0; i < ARRAY_SIZE(dapm_down_seq); i++) { - list_for_each_entry(w, &codec->down_list, power_list) { /* is widget in stream order */ - if (w->id != dapm_down_seq[i]) + if (seq && seq[i] && w->id != seq[i]) continue; ret = dapm_power_widget(codec, event, w); if (ret != 0) - pr_err("Failed to power down %s: %d\n", - w->name, ret); - } - } - - /* Now power up. */ - for (i = 0; i < ARRAY_SIZE(dapm_up_seq); i++) { - list_for_each_entry(w, &codec->up_list, power_list) { - /* is widget in stream order */ - if (w->id != dapm_up_seq[i]) - continue; - - ret = dapm_power_widget(codec, event, w); - if (ret != 0) - pr_err("Failed to power up %s: %d\n", - w->name, ret); + return ret; } } - /* If we just powered the last thing off drop to standby bias */ - if (codec->bias_level == SND_SOC_BIAS_PREPARE && !sys_power) { - ret = snd_soc_dapm_set_bias_level(socdev, - SND_SOC_BIAS_STANDBY); - if (ret != 0) - pr_err("Failed to apply standby bias: %d\n", ret); - } - - /* If we just powered up then move to active bias */ - if (codec->bias_level == SND_SOC_BIAS_PREPARE && sys_power) { - ret = snd_soc_dapm_set_bias_level(socdev, - SND_SOC_BIAS_ON); - if (ret != 0) - pr_err("Failed to apply active bias: %d\n", ret); - } - return 0; } @@ -880,7 +723,6 @@ static void dbg_dump_dapm(struct snd_soc_codec* codec, const char *action) case snd_soc_dapm_pga: case snd_soc_dapm_mixer: case snd_soc_dapm_mixer_named_ctl: - case snd_soc_dapm_supply: if (w->name) { in = is_connected_input_ep(w); dapm_clear_walk(w->codec); @@ -1009,7 +851,6 @@ static ssize_t dapm_widget_show(struct device *dev, case snd_soc_dapm_pga: case snd_soc_dapm_mixer: case snd_soc_dapm_mixer_named_ctl: - case snd_soc_dapm_supply: if (w->name) count += sprintf(buf + count, "%s: %s\n", w->name, w->power ? "On":"Off"); @@ -1042,12 +883,16 @@ static DEVICE_ATTR(dapm_widget, 0444, dapm_widget_show, NULL); int snd_soc_dapm_sys_add(struct device *dev) { + if (!dapm_status) + return 0; return device_create_file(dev, &dev_attr_dapm_widget); } static void snd_soc_dapm_sys_remove(struct device *dev) { - device_remove_file(dev, &dev_attr_dapm_widget); + if (dapm_status) { + device_remove_file(dev, &dev_attr_dapm_widget); + } } /* free all dapm widgets and resources */ @@ -1170,7 +1015,6 @@ static int snd_soc_dapm_add_route(struct snd_soc_codec *codec, case snd_soc_dapm_vmid: case snd_soc_dapm_pre: case snd_soc_dapm_post: - case snd_soc_dapm_supply: list_add(&path->list, &codec->dapm_paths); list_add(&path->list_sink, &wsink->sources); list_add(&path->list_source, &wsource->sinks); @@ -1264,22 +1108,15 @@ int snd_soc_dapm_new_widgets(struct snd_soc_codec *codec) case snd_soc_dapm_switch: case snd_soc_dapm_mixer: case snd_soc_dapm_mixer_named_ctl: - w->power_check = dapm_generic_check_power; dapm_new_mixer(codec, w); break; case snd_soc_dapm_mux: case snd_soc_dapm_value_mux: - w->power_check = dapm_generic_check_power; dapm_new_mux(codec, w); break; case snd_soc_dapm_adc: - w->power_check = dapm_adc_check_power; - break; case snd_soc_dapm_dac: - w->power_check = dapm_dac_check_power; - break; case snd_soc_dapm_pga: - w->power_check = dapm_generic_check_power; dapm_new_pga(codec, w); break; case snd_soc_dapm_input: @@ -1289,10 +1126,6 @@ int snd_soc_dapm_new_widgets(struct snd_soc_codec *codec) case snd_soc_dapm_hp: case snd_soc_dapm_mic: case snd_soc_dapm_line: - w->power_check = dapm_generic_check_power; - break; - case snd_soc_dapm_supply: - w->power_check = dapm_supply_check_power; case snd_soc_dapm_vmid: case snd_soc_dapm_pre: case snd_soc_dapm_post: @@ -1792,12 +1625,36 @@ int snd_soc_dapm_stream_event(struct snd_soc_codec *codec, } EXPORT_SYMBOL_GPL(snd_soc_dapm_stream_event); +/** + * snd_soc_dapm_set_bias_level - set the bias level for the system + * @socdev: audio device + * @level: level to configure + * + * Configure the bias (power) levels for the SoC audio device. + * + * Returns 0 for success else error. + */ +int snd_soc_dapm_set_bias_level(struct snd_soc_device *socdev, + enum snd_soc_bias_level level) +{ + struct snd_soc_card *card = socdev->card; + struct snd_soc_codec *codec = socdev->card->codec; + int ret = 0; + + if (card->set_bias_level) + ret = card->set_bias_level(card, level); + if (ret == 0 && codec->set_bias_level) + ret = codec->set_bias_level(codec, level); + + return ret; +} + /** * snd_soc_dapm_enable_pin - enable pin. * @codec: SoC codec * @pin: pin name * - * Enables input/output pin and its parents or children widgets iff there is + * Enables input/output pin and it's parents or children widgets iff there is * a valid audio route and active audio stream. * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to * do any widget power switching. @@ -1813,7 +1670,7 @@ EXPORT_SYMBOL_GPL(snd_soc_dapm_enable_pin); * @codec: SoC codec * @pin: pin name * - * Disables input/output pin and its parents or children widgets. + * Disables input/output pin and it's parents or children widgets. * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to * do any widget power switching. */ diff --git a/trunk/sound/soc/txx9/Kconfig b/trunk/sound/soc/txx9/Kconfig deleted file mode 100644 index ebc9327eae71..000000000000 --- a/trunk/sound/soc/txx9/Kconfig +++ /dev/null @@ -1,29 +0,0 @@ -## -## TXx9 ACLC -## -config SND_SOC_TXX9ACLC - tristate "SoC Audio for TXx9" - depends on HAS_TXX9_ACLC && TXX9_DMAC - help - This option enables support for the AC Link Controllers in TXx9 SoC. - -config HAS_TXX9_ACLC - bool - -config SND_SOC_TXX9ACLC_AC97 - tristate - select AC97_BUS - select SND_AC97_CODEC - select SND_SOC_AC97_BUS - - -## -## Boards -## -config SND_SOC_TXX9ACLC_GENERIC - tristate "Generic TXx9 ACLC sound machine" - depends on SND_SOC_TXX9ACLC - select SND_SOC_TXX9ACLC_AC97 - select SND_SOC_AC97_CODEC - help - This is a generic AC97 sound machine for use in TXx9 based systems. diff --git a/trunk/sound/soc/txx9/Makefile b/trunk/sound/soc/txx9/Makefile deleted file mode 100644 index 551f16c0c4f9..000000000000 --- a/trunk/sound/soc/txx9/Makefile +++ /dev/null @@ -1,11 +0,0 @@ -# Platform -snd-soc-txx9aclc-objs := txx9aclc.o -snd-soc-txx9aclc-ac97-objs := txx9aclc-ac97.o - -obj-$(CONFIG_SND_SOC_TXX9ACLC) += snd-soc-txx9aclc.o -obj-$(CONFIG_SND_SOC_TXX9ACLC_AC97) += snd-soc-txx9aclc-ac97.o - -# Machine -snd-soc-txx9aclc-generic-objs := txx9aclc-generic.o - -obj-$(CONFIG_SND_SOC_TXX9ACLC_GENERIC) += snd-soc-txx9aclc-generic.o diff --git a/trunk/sound/soc/txx9/txx9aclc-ac97.c b/trunk/sound/soc/txx9/txx9aclc-ac97.c deleted file mode 100644 index 0f83bdb9b16f..000000000000 --- a/trunk/sound/soc/txx9/txx9aclc-ac97.c +++ /dev/null @@ -1,255 +0,0 @@ -/* - * TXx9 ACLC AC97 driver - * - * Copyright (C) 2009 Atsushi Nemoto - * - * Based on RBTX49xx patch from CELF patch archive. - * (C) Copyright TOSHIBA CORPORATION 2004-2006 - * - * 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. - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include "txx9aclc.h" - -#define AC97_DIR \ - (SND_SOC_DAIDIR_PLAYBACK | SND_SOC_DAIDIR_CAPTURE) - -#define AC97_RATES \ - SNDRV_PCM_RATE_8000_48000 - -#ifdef __BIG_ENDIAN -#define AC97_FMTS SNDRV_PCM_FMTBIT_S16_BE -#else -#define AC97_FMTS SNDRV_PCM_FMTBIT_S16_LE -#endif - -static DECLARE_WAIT_QUEUE_HEAD(ac97_waitq); - -/* REVISIT: How to find txx9aclc_soc_device from snd_ac97? */ -static struct txx9aclc_soc_device *txx9aclc_soc_dev; - -static int txx9aclc_regready(struct txx9aclc_soc_device *dev) -{ - struct txx9aclc_plat_drvdata *drvdata = txx9aclc_get_plat_drvdata(dev); - - return __raw_readl(drvdata->base + ACINTSTS) & ACINT_REGACCRDY; -} - -/* AC97 controller reads codec register */ -static unsigned short txx9aclc_ac97_read(struct snd_ac97 *ac97, - unsigned short reg) -{ - struct txx9aclc_soc_device *dev = txx9aclc_soc_dev; - struct txx9aclc_plat_drvdata *drvdata = txx9aclc_get_plat_drvdata(dev); - void __iomem *base = drvdata->base; - u32 dat; - - if (!(__raw_readl(base + ACINTSTS) & ACINT_CODECRDY(ac97->num))) - return 0xffff; - reg |= ac97->num << 7; - dat = (reg << ACREGACC_REG_SHIFT) | ACREGACC_READ; - __raw_writel(dat, base + ACREGACC); - __raw_writel(ACINT_REGACCRDY, base + ACINTEN); - if (!wait_event_timeout(ac97_waitq, txx9aclc_regready(dev), HZ)) { - __raw_writel(ACINT_REGACCRDY, base + ACINTDIS); - dev_err(dev->soc_dev.dev, "ac97 read timeout (reg %#x)\n", reg); - dat = 0xffff; - goto done; - } - dat = __raw_readl(base + ACREGACC); - if (((dat >> ACREGACC_REG_SHIFT) & 0xff) != reg) { - dev_err(dev->soc_dev.dev, "reg mismatch %x with %x\n", - dat, reg); - dat = 0xffff; - goto done; - } - dat = (dat >> ACREGACC_DAT_SHIFT) & 0xffff; -done: - __raw_writel(ACINT_REGACCRDY, base + ACINTDIS); - return dat; -} - -/* AC97 controller writes to codec register */ -static void txx9aclc_ac97_write(struct snd_ac97 *ac97, unsigned short reg, - unsigned short val) -{ - struct txx9aclc_soc_device *dev = txx9aclc_soc_dev; - struct txx9aclc_plat_drvdata *drvdata = txx9aclc_get_plat_drvdata(dev); - void __iomem *base = drvdata->base; - - __raw_writel(((reg | (ac97->num << 7)) << ACREGACC_REG_SHIFT) | - (val << ACREGACC_DAT_SHIFT), - base + ACREGACC); - __raw_writel(ACINT_REGACCRDY, base + ACINTEN); - if (!wait_event_timeout(ac97_waitq, txx9aclc_regready(dev), HZ)) { - dev_err(dev->soc_dev.dev, - "ac97 write timeout (reg %#x)\n", reg); - } - __raw_writel(ACINT_REGACCRDY, base + ACINTDIS); -} - -static void txx9aclc_ac97_cold_reset(struct snd_ac97 *ac97) -{ - struct txx9aclc_soc_device *dev = txx9aclc_soc_dev; - struct txx9aclc_plat_drvdata *drvdata = txx9aclc_get_plat_drvdata(dev); - void __iomem *base = drvdata->base; - u32 ready = ACINT_CODECRDY(ac97->num) | ACINT_REGACCRDY; - - __raw_writel(ACCTL_ENLINK, base + ACCTLDIS); - mmiowb(); - udelay(1); - __raw_writel(ACCTL_ENLINK, base + ACCTLEN); - /* wait for primary codec ready status */ - __raw_writel(ready, base + ACINTEN); - if (!wait_event_timeout(ac97_waitq, - (__raw_readl(base + ACINTSTS) & ready) == ready, - HZ)) { - dev_err(&ac97->dev, "primary codec is not ready " - "(status %#x)\n", - __raw_readl(base + ACINTSTS)); - } - __raw_writel(ACINT_REGACCRDY, base + ACINTSTS); - __raw_writel(ready, base + ACINTDIS); -} - -/* AC97 controller operations */ -struct snd_ac97_bus_ops soc_ac97_ops = { - .read = txx9aclc_ac97_read, - .write = txx9aclc_ac97_write, - .reset = txx9aclc_ac97_cold_reset, -}; -EXPORT_SYMBOL_GPL(soc_ac97_ops); - -static irqreturn_t txx9aclc_ac97_irq(int irq, void *dev_id) -{ - struct txx9aclc_plat_drvdata *drvdata = dev_id; - void __iomem *base = drvdata->base; - - __raw_writel(__raw_readl(base + ACINTMSTS), base + ACINTDIS); - wake_up(&ac97_waitq); - return IRQ_HANDLED; -} - -static int txx9aclc_ac97_probe(struct platform_device *pdev, - struct snd_soc_dai *dai) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct txx9aclc_soc_device *dev = - container_of(socdev, struct txx9aclc_soc_device, soc_dev); - - dev->aclc_pdev = to_platform_device(dai->dev); - txx9aclc_soc_dev = dev; - return 0; -} - -static void txx9aclc_ac97_remove(struct platform_device *pdev, - struct snd_soc_dai *dai) -{ - struct platform_device *aclc_pdev = to_platform_device(dai->dev); - struct txx9aclc_plat_drvdata *drvdata = platform_get_drvdata(aclc_pdev); - - /* disable AC-link */ - __raw_writel(ACCTL_ENLINK, drvdata->base + ACCTLDIS); - txx9aclc_soc_dev = NULL; -} - -struct snd_soc_dai txx9aclc_ac97_dai = { - .name = "txx9aclc_ac97", - .ac97_control = 1, - .probe = txx9aclc_ac97_probe, - .remove = txx9aclc_ac97_remove, - .playback = { - .rates = AC97_RATES, - .formats = AC97_FMTS, - .channels_min = 2, - .channels_max = 2, - }, - .capture = { - .rates = AC97_RATES, - .formats = AC97_FMTS, - .channels_min = 2, - .channels_max = 2, - }, -}; -EXPORT_SYMBOL_GPL(txx9aclc_ac97_dai); - -static int __devinit txx9aclc_ac97_dev_probe(struct platform_device *pdev) -{ - struct txx9aclc_plat_drvdata *drvdata; - struct resource *r; - int err; - int irq; - - irq = platform_get_irq(pdev, 0); - if (irq < 0) - return irq; - r = platform_get_resource(pdev, IORESOURCE_MEM, 0); - if (!r) - return -EBUSY; - - if (!devm_request_mem_region(&pdev->dev, r->start, resource_size(r), - dev_name(&pdev->dev))) - return -EBUSY; - - drvdata = devm_kzalloc(&pdev->dev, sizeof(*drvdata), GFP_KERNEL); - if (!drvdata) - return -ENOMEM; - platform_set_drvdata(pdev, drvdata); - drvdata->physbase = r->start; - if (sizeof(drvdata->physbase) > sizeof(r->start) && - r->start >= TXX9_DIRECTMAP_BASE && - r->start < TXX9_DIRECTMAP_BASE + 0x400000) - drvdata->physbase |= 0xf00000000ull; - drvdata->base = devm_ioremap(&pdev->dev, r->start, resource_size(r)); - if (!drvdata->base) - return -EBUSY; - err = devm_request_irq(&pdev->dev, irq, txx9aclc_ac97_irq, - IRQF_DISABLED, dev_name(&pdev->dev), drvdata); - if (err < 0) - return err; - - txx9aclc_ac97_dai.dev = &pdev->dev; - return snd_soc_register_dai(&txx9aclc_ac97_dai); -} - -static int __devexit txx9aclc_ac97_dev_remove(struct platform_device *pdev) -{ - snd_soc_unregister_dai(&txx9aclc_ac97_dai); - return 0; -} - -static struct platform_driver txx9aclc_ac97_driver = { - .probe = txx9aclc_ac97_dev_probe, - .remove = __devexit_p(txx9aclc_ac97_dev_remove), - .driver = { - .name = "txx9aclc-ac97", - .owner = THIS_MODULE, - }, -}; - -static int __init txx9aclc_ac97_init(void) -{ - return platform_driver_register(&txx9aclc_ac97_driver); -} - -static void __exit txx9aclc_ac97_exit(void) -{ - platform_driver_unregister(&txx9aclc_ac97_driver); -} - -module_init(txx9aclc_ac97_init); -module_exit(txx9aclc_ac97_exit); - -MODULE_AUTHOR("Atsushi Nemoto "); -MODULE_DESCRIPTION("TXx9 ACLC AC97 driver"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/txx9/txx9aclc-generic.c b/trunk/sound/soc/txx9/txx9aclc-generic.c deleted file mode 100644 index 3175de9a92cb..000000000000 --- a/trunk/sound/soc/txx9/txx9aclc-generic.c +++ /dev/null @@ -1,98 +0,0 @@ -/* - * Generic TXx9 ACLC machine driver - * - * Copyright (C) 2009 Atsushi Nemoto - * - * Based on RBTX49xx patch from CELF patch archive. - * (C) Copyright TOSHIBA CORPORATION 2004-2006 - * - * 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. - * - * This is a very generic AC97 sound machine driver for boards which - * have (AC97) audio at ACLC (e.g. RBTX49XX boards). - */ - -#include -#include -#include -#include -#include -#include "../codecs/ac97.h" -#include "txx9aclc.h" - -static struct snd_soc_dai_link txx9aclc_generic_dai = { - .name = "AC97", - .stream_name = "AC97 HiFi", - .cpu_dai = &txx9aclc_ac97_dai, - .codec_dai = &ac97_dai, -}; - -static struct snd_soc_card txx9aclc_generic_card = { - .name = "Generic TXx9 ACLC Audio", - .platform = &txx9aclc_soc_platform, - .dai_link = &txx9aclc_generic_dai, - .num_links = 1, -}; - -static struct txx9aclc_soc_device txx9aclc_generic_soc_device = { - .soc_dev = { - .card = &txx9aclc_generic_card, - .codec_dev = &soc_codec_dev_ac97, - }, -}; - -static int __init txx9aclc_generic_probe(struct platform_device *pdev) -{ - struct txx9aclc_soc_device *dev = &txx9aclc_generic_soc_device; - struct platform_device *soc_pdev; - int ret; - - soc_pdev = platform_device_alloc("soc-audio", -1); - if (!soc_pdev) - return -ENOMEM; - platform_set_drvdata(soc_pdev, &dev->soc_dev); - dev->soc_dev.dev = &soc_pdev->dev; - ret = platform_device_add(soc_pdev); - if (ret) { - platform_device_put(soc_pdev); - return ret; - } - platform_set_drvdata(pdev, soc_pdev); - return 0; -} - -static int __exit txx9aclc_generic_remove(struct platform_device *pdev) -{ - struct platform_device *soc_pdev = platform_get_drvdata(pdev); - - platform_device_unregister(soc_pdev); - return 0; -} - -static struct platform_driver txx9aclc_generic_driver = { - .remove = txx9aclc_generic_remove, - .driver = { - .name = "txx9aclc-generic", - .owner = THIS_MODULE, - }, -}; - -static int __init txx9aclc_generic_init(void) -{ - return platform_driver_probe(&txx9aclc_generic_driver, - txx9aclc_generic_probe); -} - -static void __exit txx9aclc_generic_exit(void) -{ - platform_driver_unregister(&txx9aclc_generic_driver); -} - -module_init(txx9aclc_generic_init); -module_exit(txx9aclc_generic_exit); - -MODULE_AUTHOR("Atsushi Nemoto "); -MODULE_DESCRIPTION("Generic TXx9 ACLC ALSA SoC audio driver"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/txx9/txx9aclc.c b/trunk/sound/soc/txx9/txx9aclc.c deleted file mode 100644 index fa336616152e..000000000000 --- a/trunk/sound/soc/txx9/txx9aclc.c +++ /dev/null @@ -1,430 +0,0 @@ -/* - * Generic TXx9 ACLC platform driver - * - * Copyright (C) 2009 Atsushi Nemoto - * - * Based on RBTX49xx patch from CELF patch archive. - * (C) Copyright TOSHIBA CORPORATION 2004-2006 - * - * 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. - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include "txx9aclc.h" - -static const struct snd_pcm_hardware txx9aclc_pcm_hardware = { - /* - * REVISIT: SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_MMAP_VALID - * needs more works for noncoherent MIPS. - */ - .info = SNDRV_PCM_INFO_INTERLEAVED | - SNDRV_PCM_INFO_BATCH | - SNDRV_PCM_INFO_PAUSE, -#ifdef __BIG_ENDIAN - .formats = SNDRV_PCM_FMTBIT_S16_BE, -#else - .formats = SNDRV_PCM_FMTBIT_S16_LE, -#endif - .period_bytes_min = 1024, - .period_bytes_max = 8 * 1024, - .periods_min = 2, - .periods_max = 4096, - .buffer_bytes_max = 32 * 1024, -}; - -static int txx9aclc_pcm_hw_params(struct snd_pcm_substream *substream, - struct snd_pcm_hw_params *params) -{ - struct snd_soc_pcm_runtime *rtd = snd_pcm_substream_chip(substream); - struct snd_soc_device *socdev = rtd->socdev; - struct snd_pcm_runtime *runtime = substream->runtime; - struct txx9aclc_dmadata *dmadata = runtime->private_data; - int ret; - - ret = snd_pcm_lib_malloc_pages(substream, params_buffer_bytes(params)); - if (ret < 0) - return ret; - - dev_dbg(socdev->dev, - "runtime->dma_area = %#lx dma_addr = %#lx dma_bytes = %zd " - "runtime->min_align %ld\n", - (unsigned long)runtime->dma_area, - (unsigned long)runtime->dma_addr, runtime->dma_bytes, - runtime->min_align); - dev_dbg(socdev->dev, - "periods %d period_bytes %d stream %d\n", - params_periods(params), params_period_bytes(params), - substream->stream); - - dmadata->substream = substream; - dmadata->pos = 0; - return 0; -} - -static int txx9aclc_pcm_hw_free(struct snd_pcm_substream *substream) -{ - return snd_pcm_lib_free_pages(substream); -} - -static int txx9aclc_pcm_prepare(struct snd_pcm_substream *substream) -{ - struct snd_pcm_runtime *runtime = substream->runtime; - struct txx9aclc_dmadata *dmadata = runtime->private_data; - - dmadata->dma_addr = runtime->dma_addr; - dmadata->buffer_bytes = snd_pcm_lib_buffer_bytes(substream); - dmadata->period_bytes = snd_pcm_lib_period_bytes(substream); - - if (dmadata->buffer_bytes == dmadata->period_bytes) { - dmadata->frag_bytes = dmadata->period_bytes >> 1; - dmadata->frags = 2; - } else { - dmadata->frag_bytes = dmadata->period_bytes; - dmadata->frags = dmadata->buffer_bytes / dmadata->period_bytes; - } - dmadata->frag_count = 0; - dmadata->pos = 0; - return 0; -} - -static void txx9aclc_dma_complete(void *arg) -{ - struct txx9aclc_dmadata *dmadata = arg; - unsigned long flags; - - /* dma completion handler cannot submit new operations */ - spin_lock_irqsave(&dmadata->dma_lock, flags); - if (dmadata->frag_count >= 0) { - dmadata->dmacount--; - BUG_ON(dmadata->dmacount < 0); - tasklet_schedule(&dmadata->tasklet); - } - spin_unlock_irqrestore(&dmadata->dma_lock, flags); -} - -static struct dma_async_tx_descriptor * -txx9aclc_dma_submit(struct txx9aclc_dmadata *dmadata, dma_addr_t buf_dma_addr) -{ - struct dma_chan *chan = dmadata->dma_chan; - struct dma_async_tx_descriptor *desc; - struct scatterlist sg; - - sg_init_table(&sg, 1); - sg_set_page(&sg, pfn_to_page(PFN_DOWN(buf_dma_addr)), - dmadata->frag_bytes, buf_dma_addr & (PAGE_SIZE - 1)); - sg_dma_address(&sg) = buf_dma_addr; - desc = chan->device->device_prep_slave_sg(chan, &sg, 1, - dmadata->substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? - DMA_TO_DEVICE : DMA_FROM_DEVICE, - DMA_PREP_INTERRUPT | DMA_CTRL_ACK); - if (!desc) { - dev_err(&chan->dev->device, "cannot prepare slave dma\n"); - return NULL; - } - desc->callback = txx9aclc_dma_complete; - desc->callback_param = dmadata; - desc->tx_submit(desc); - return desc; -} - -#define NR_DMA_CHAIN 2 - -static void txx9aclc_dma_tasklet(unsigned long data) -{ - struct txx9aclc_dmadata *dmadata = (struct txx9aclc_dmadata *)data; - struct dma_chan *chan = dmadata->dma_chan; - struct dma_async_tx_descriptor *desc; - struct snd_pcm_substream *substream = dmadata->substream; - u32 ctlbit = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? - ACCTL_AUDODMA : ACCTL_AUDIDMA; - int i; - unsigned long flags; - - spin_lock_irqsave(&dmadata->dma_lock, flags); - if (dmadata->frag_count < 0) { - struct txx9aclc_soc_device *dev = - container_of(dmadata, struct txx9aclc_soc_device, - dmadata[substream->stream]); - struct txx9aclc_plat_drvdata *drvdata = - txx9aclc_get_plat_drvdata(dev); - void __iomem *base = drvdata->base; - - spin_unlock_irqrestore(&dmadata->dma_lock, flags); - chan->device->device_terminate_all(chan); - /* first time */ - for (i = 0; i < NR_DMA_CHAIN; i++) { - desc = txx9aclc_dma_submit(dmadata, - dmadata->dma_addr + i * dmadata->frag_bytes); - if (!desc) - return; - } - dmadata->dmacount = NR_DMA_CHAIN; - chan->device->device_issue_pending(chan); - spin_lock_irqsave(&dmadata->dma_lock, flags); - __raw_writel(ctlbit, base + ACCTLEN); - dmadata->frag_count = NR_DMA_CHAIN % dmadata->frags; - spin_unlock_irqrestore(&dmadata->dma_lock, flags); - return; - } - BUG_ON(dmadata->dmacount >= NR_DMA_CHAIN); - while (dmadata->dmacount < NR_DMA_CHAIN) { - dmadata->dmacount++; - spin_unlock_irqrestore(&dmadata->dma_lock, flags); - desc = txx9aclc_dma_submit(dmadata, - dmadata->dma_addr + - dmadata->frag_count * dmadata->frag_bytes); - if (!desc) - return; - chan->device->device_issue_pending(chan); - - spin_lock_irqsave(&dmadata->dma_lock, flags); - dmadata->frag_count++; - dmadata->frag_count %= dmadata->frags; - dmadata->pos += dmadata->frag_bytes; - dmadata->pos %= dmadata->buffer_bytes; - if ((dmadata->frag_count * dmadata->frag_bytes) % - dmadata->period_bytes == 0) - snd_pcm_period_elapsed(substream); - } - spin_unlock_irqrestore(&dmadata->dma_lock, flags); -} - -static int txx9aclc_pcm_trigger(struct snd_pcm_substream *substream, int cmd) -{ - struct txx9aclc_dmadata *dmadata = substream->runtime->private_data; - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct txx9aclc_soc_device *dev = - container_of(rtd->socdev, struct txx9aclc_soc_device, soc_dev); - struct txx9aclc_plat_drvdata *drvdata = txx9aclc_get_plat_drvdata(dev); - void __iomem *base = drvdata->base; - unsigned long flags; - int ret = 0; - u32 ctlbit = substream->stream == SNDRV_PCM_STREAM_PLAYBACK ? - ACCTL_AUDODMA : ACCTL_AUDIDMA; - - spin_lock_irqsave(&dmadata->dma_lock, flags); - switch (cmd) { - case SNDRV_PCM_TRIGGER_START: - dmadata->frag_count = -1; - tasklet_schedule(&dmadata->tasklet); - break; - case SNDRV_PCM_TRIGGER_STOP: - case SNDRV_PCM_TRIGGER_PAUSE_PUSH: - case SNDRV_PCM_TRIGGER_SUSPEND: - __raw_writel(ctlbit, base + ACCTLDIS); - break; - case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: - case SNDRV_PCM_TRIGGER_RESUME: - __raw_writel(ctlbit, base + ACCTLEN); - break; - default: - ret = -EINVAL; - } - spin_unlock_irqrestore(&dmadata->dma_lock, flags); - return ret; -} - -static snd_pcm_uframes_t -txx9aclc_pcm_pointer(struct snd_pcm_substream *substream) -{ - struct txx9aclc_dmadata *dmadata = substream->runtime->private_data; - - return bytes_to_frames(substream->runtime, dmadata->pos); -} - -static int txx9aclc_pcm_open(struct snd_pcm_substream *substream) -{ - struct snd_soc_pcm_runtime *rtd = substream->private_data; - struct txx9aclc_soc_device *dev = - container_of(rtd->socdev, struct txx9aclc_soc_device, soc_dev); - struct txx9aclc_dmadata *dmadata = &dev->dmadata[substream->stream]; - int ret; - - ret = snd_soc_set_runtime_hwparams(substream, &txx9aclc_pcm_hardware); - if (ret) - return ret; - /* ensure that buffer size is a multiple of period size */ - ret = snd_pcm_hw_constraint_integer(substream->runtime, - SNDRV_PCM_HW_PARAM_PERIODS); - if (ret < 0) - return ret; - substream->runtime->private_data = dmadata; - return 0; -} - -static int txx9aclc_pcm_close(struct snd_pcm_substream *substream) -{ - struct txx9aclc_dmadata *dmadata = substream->runtime->private_data; - struct dma_chan *chan = dmadata->dma_chan; - - dmadata->frag_count = -1; - chan->device->device_terminate_all(chan); - return 0; -} - -static struct snd_pcm_ops txx9aclc_pcm_ops = { - .open = txx9aclc_pcm_open, - .close = txx9aclc_pcm_close, - .ioctl = snd_pcm_lib_ioctl, - .hw_params = txx9aclc_pcm_hw_params, - .hw_free = txx9aclc_pcm_hw_free, - .prepare = txx9aclc_pcm_prepare, - .trigger = txx9aclc_pcm_trigger, - .pointer = txx9aclc_pcm_pointer, -}; - -static void txx9aclc_pcm_free_dma_buffers(struct snd_pcm *pcm) -{ - snd_pcm_lib_preallocate_free_for_all(pcm); -} - -static int txx9aclc_pcm_new(struct snd_card *card, struct snd_soc_dai *dai, - struct snd_pcm *pcm) -{ - return snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV, - card->dev, 64 * 1024, 4 * 1024 * 1024); -} - -static bool filter(struct dma_chan *chan, void *param) -{ - struct txx9aclc_dmadata *dmadata = param; - char devname[BUS_ID_SIZE + 2]; - - sprintf(devname, "%s.%d", dmadata->dma_res->name, - (int)dmadata->dma_res->start); - if (strcmp(dev_name(chan->device->dev), devname) == 0) { - chan->private = &dmadata->dma_slave; - return true; - } - return false; -} - -static int txx9aclc_dma_init(struct txx9aclc_soc_device *dev, - struct txx9aclc_dmadata *dmadata) -{ - struct txx9aclc_plat_drvdata *drvdata = txx9aclc_get_plat_drvdata(dev); - struct txx9dmac_slave *ds = &dmadata->dma_slave; - dma_cap_mask_t mask; - - spin_lock_init(&dmadata->dma_lock); - - ds->reg_width = sizeof(u32); - if (dmadata->stream == SNDRV_PCM_STREAM_PLAYBACK) { - ds->tx_reg = drvdata->physbase + ACAUDODAT; - ds->rx_reg = 0; - } else { - ds->tx_reg = 0; - ds->rx_reg = drvdata->physbase + ACAUDIDAT; - } - - /* Try to grab a DMA channel */ - dma_cap_zero(mask); - dma_cap_set(DMA_SLAVE, mask); - dmadata->dma_chan = dma_request_channel(mask, filter, dmadata); - if (!dmadata->dma_chan) { - dev_err(dev->soc_dev.dev, - "DMA channel for %s is not available\n", - dmadata->stream == SNDRV_PCM_STREAM_PLAYBACK ? - "playback" : "capture"); - return -EBUSY; - } - tasklet_init(&dmadata->tasklet, txx9aclc_dma_tasklet, - (unsigned long)dmadata); - return 0; -} - -static int txx9aclc_pcm_probe(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct txx9aclc_soc_device *dev = - container_of(socdev, struct txx9aclc_soc_device, soc_dev); - struct resource *r; - int i; - int ret; - - dev->dmadata[0].stream = SNDRV_PCM_STREAM_PLAYBACK; - dev->dmadata[1].stream = SNDRV_PCM_STREAM_CAPTURE; - for (i = 0; i < 2; i++) { - r = platform_get_resource(dev->aclc_pdev, IORESOURCE_DMA, i); - if (!r) { - ret = -EBUSY; - goto exit; - } - dev->dmadata[i].dma_res = r; - ret = txx9aclc_dma_init(dev, &dev->dmadata[i]); - if (ret) - goto exit; - } - return 0; - -exit: - for (i = 0; i < 2; i++) { - if (dev->dmadata[i].dma_chan) - dma_release_channel(dev->dmadata[i].dma_chan); - dev->dmadata[i].dma_chan = NULL; - } - return ret; -} - -static int txx9aclc_pcm_remove(struct platform_device *pdev) -{ - struct snd_soc_device *socdev = platform_get_drvdata(pdev); - struct txx9aclc_soc_device *dev = - container_of(socdev, struct txx9aclc_soc_device, soc_dev); - struct txx9aclc_plat_drvdata *drvdata = txx9aclc_get_plat_drvdata(dev); - void __iomem *base = drvdata->base; - int i; - - /* disable all FIFO DMAs */ - __raw_writel(ACCTL_AUDODMA | ACCTL_AUDIDMA, base + ACCTLDIS); - /* dummy R/W to clear pending DMAREQ if any */ - __raw_writel(__raw_readl(base + ACAUDIDAT), base + ACAUDODAT); - - for (i = 0; i < 2; i++) { - struct txx9aclc_dmadata *dmadata = &dev->dmadata[i]; - struct dma_chan *chan = dmadata->dma_chan; - if (chan) { - dmadata->frag_count = -1; - chan->device->device_terminate_all(chan); - dma_release_channel(chan); - } - dev->dmadata[i].dma_chan = NULL; - } - return 0; -} - -struct snd_soc_platform txx9aclc_soc_platform = { - .name = "txx9aclc-audio", - .probe = txx9aclc_pcm_probe, - .remove = txx9aclc_pcm_remove, - .pcm_ops = &txx9aclc_pcm_ops, - .pcm_new = txx9aclc_pcm_new, - .pcm_free = txx9aclc_pcm_free_dma_buffers, -}; -EXPORT_SYMBOL_GPL(txx9aclc_soc_platform); - -static int __init txx9aclc_soc_platform_init(void) -{ - return snd_soc_register_platform(&txx9aclc_soc_platform); -} - -static void __exit txx9aclc_soc_platform_exit(void) -{ - snd_soc_unregister_platform(&txx9aclc_soc_platform); -} - -module_init(txx9aclc_soc_platform_init); -module_exit(txx9aclc_soc_platform_exit); - -MODULE_AUTHOR("Atsushi Nemoto "); -MODULE_DESCRIPTION("TXx9 ACLC Audio DMA driver"); -MODULE_LICENSE("GPL"); diff --git a/trunk/sound/soc/txx9/txx9aclc.h b/trunk/sound/soc/txx9/txx9aclc.h deleted file mode 100644 index 6769aab41b33..000000000000 --- a/trunk/sound/soc/txx9/txx9aclc.h +++ /dev/null @@ -1,83 +0,0 @@ -/* - * TXx9 SoC AC Link Controller - * - * 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 __TXX9ACLC_H -#define __TXX9ACLC_H - -#include -#include - -#define ACCTLEN 0x00 /* control enable */ -#define ACCTLDIS 0x04 /* control disable */ -#define ACCTL_ENLINK 0x00000001 /* enable/disable AC-link */ -#define ACCTL_AUDODMA 0x00000100 /* AUDODMA enable/disable */ -#define ACCTL_AUDIDMA 0x00001000 /* AUDIDMA enable/disable */ -#define ACCTL_AUDOEHLT 0x00010000 /* AUDO error halt - enable/disable */ -#define ACCTL_AUDIEHLT 0x00100000 /* AUDI error halt - enable/disable */ -#define ACREGACC 0x08 /* codec register access */ -#define ACREGACC_DAT_SHIFT 0 /* data field */ -#define ACREGACC_REG_SHIFT 16 /* address field */ -#define ACREGACC_CODECID_SHIFT 24 /* CODEC ID field */ -#define ACREGACC_READ 0x80000000 /* CODEC read */ -#define ACREGACC_WRITE 0x00000000 /* CODEC write */ -#define ACINTSTS 0x10 /* interrupt status */ -#define ACINTMSTS 0x14 /* interrupt masked status */ -#define ACINTEN 0x18 /* interrupt enable */ -#define ACINTDIS 0x1c /* interrupt disable */ -#define ACINT_CODECRDY(n) (0x00000001 << (n)) /* CODECn ready */ -#define ACINT_REGACCRDY 0x00000010 /* ACREGACC ready */ -#define ACINT_AUDOERR 0x00000100 /* AUDO underrun error */ -#define ACINT_AUDIERR 0x00001000 /* AUDI overrun error */ -#define ACDMASTS 0x80 /* DMA request status */ -#define ACDMA_AUDO 0x00000001 /* AUDODMA pending */ -#define ACDMA_AUDI 0x00000010 /* AUDIDMA pending */ -#define ACAUDODAT 0xa0 /* audio out data */ -#define ACAUDIDAT 0xb0 /* audio in data */ -#define ACREVID 0xfc /* revision ID */ - -struct txx9aclc_dmadata { - struct resource *dma_res; - struct txx9dmac_slave dma_slave; - struct dma_chan *dma_chan; - struct tasklet_struct tasklet; - spinlock_t dma_lock; - int stream; /* SNDRV_PCM_STREAM_PLAYBACK or SNDRV_PCM_STREAM_CAPTURE */ - struct snd_pcm_substream *substream; - unsigned long pos; - dma_addr_t dma_addr; - unsigned long buffer_bytes; - unsigned long period_bytes; - unsigned long frag_bytes; - int frags; - int frag_count; - int dmacount; -}; - -struct txx9aclc_plat_drvdata { - void __iomem *base; - u64 physbase; -}; - -struct txx9aclc_soc_device { - struct snd_soc_device soc_dev; - struct platform_device *aclc_pdev; /* for ioresources, drvdata */ - struct txx9aclc_dmadata dmadata[2]; -}; - -static inline struct txx9aclc_plat_drvdata *txx9aclc_get_plat_drvdata( - struct txx9aclc_soc_device *sdev) -{ - return platform_get_drvdata(sdev->aclc_pdev); -} - -extern struct snd_soc_platform txx9aclc_soc_platform; -extern struct snd_soc_dai txx9aclc_ac97_dai; - -#endif /* __TXX9ACLC_H */ diff --git a/trunk/sound/usb/caiaq/audio.c b/trunk/sound/usb/caiaq/audio.c index b14451342166..b13ce767ac72 100644 --- a/trunk/sound/usb/caiaq/audio.c +++ b/trunk/sound/usb/caiaq/audio.c @@ -42,10 +42,10 @@ (stream << 1) | (~(i / (dev->n_streams * BYTES_PER_SAMPLE_USB)) & 1) static struct snd_pcm_hardware snd_usb_caiaq_pcm_hardware = { - .info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED | + .info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED | SNDRV_PCM_INFO_BLOCK_TRANSFER), .formats = SNDRV_PCM_FMTBIT_S24_3BE, - .rates = (SNDRV_PCM_RATE_44100 | SNDRV_PCM_RATE_48000 | + .rates = (SNDRV_PCM_RATE_44100 | SNDRV_PCM_RATE_48000 | SNDRV_PCM_RATE_96000), .rate_min = 44100, .rate_max = 0, /* will overwrite later */ @@ -68,7 +68,7 @@ activate_substream(struct snd_usb_caiaqdev *dev, dev->sub_capture[sub->number] = sub; } -static void +static void deactivate_substream(struct snd_usb_caiaqdev *dev, struct snd_pcm_substream *sub) { @@ -118,7 +118,7 @@ static int stream_start(struct snd_usb_caiaqdev *dev) return -EPIPE; } } - + return 0; } @@ -129,7 +129,7 @@ static void stream_stop(struct snd_usb_caiaqdev *dev) debug("%s(%p)\n", __func__, dev); if (!dev->streaming) return; - + dev->streaming = 0; for (i = 0; i < N_URBS; i++) { @@ -154,7 +154,7 @@ static int snd_usb_caiaq_substream_close(struct snd_pcm_substream *substream) debug("%s(%p)\n", __func__, substream); if (all_substreams_zero(dev->sub_playback) && all_substreams_zero(dev->sub_capture)) { - /* when the last client has stopped streaming, + /* when the last client has stopped streaming, * all sample rates are allowed again */ stream_stop(dev); dev->pcm_info.rates = dev->samplerates; @@ -194,7 +194,7 @@ static int snd_usb_caiaq_pcm_prepare(struct snd_pcm_substream *substream) struct snd_pcm_runtime *runtime = substream->runtime; debug("%s(%p)\n", __func__, substream); - + if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) { dev->period_out_count[index] = BYTES_PER_SAMPLE + 1; dev->audio_out_buf_pos[index] = BYTES_PER_SAMPLE + 1; @@ -205,19 +205,19 @@ static int snd_usb_caiaq_pcm_prepare(struct snd_pcm_substream *substream) if (dev->streaming) return 0; - + /* the first client that opens a stream defines the sample rate * setting for all subsequent calls, until the last client closed. */ for (i=0; i < ARRAY_SIZE(rates); i++) if (runtime->rate == rates[i]) dev->pcm_info.rates = 1 << i; - + snd_pcm_limit_hw_rates(runtime); bytes_per_sample = BYTES_PER_SAMPLE; if (dev->spec.data_alignment == 2) bytes_per_sample++; - + bpp = ((runtime->rate / 8000) + CLOCK_DRIFT_TOLERANCE) * bytes_per_sample * CHANNELS_PER_STREAM * dev->n_streams; @@ -232,7 +232,7 @@ static int snd_usb_caiaq_pcm_prepare(struct snd_pcm_substream *substream) ret = stream_start(dev); if (ret) return ret; - + dev->output_running = 0; wait_event_timeout(dev->prepare_wait_queue, dev->output_running, HZ); if (!dev->output_running) { @@ -273,7 +273,7 @@ snd_usb_caiaq_pcm_pointer(struct snd_pcm_substream *sub) return SNDRV_PCM_POS_XRUN; if (sub->stream == SNDRV_PCM_STREAM_PLAYBACK) - return bytes_to_frames(sub->runtime, + return bytes_to_frames(sub->runtime, dev->audio_out_buf_pos[index]); else return bytes_to_frames(sub->runtime, @@ -291,7 +291,7 @@ static struct snd_pcm_ops snd_usb_caiaq_ops = { .trigger = snd_usb_caiaq_pcm_trigger, .pointer = snd_usb_caiaq_pcm_pointer }; - + static void check_for_elapsed_periods(struct snd_usb_caiaqdev *dev, struct snd_pcm_substream **subs) { @@ -333,7 +333,7 @@ static void read_in_urb_mode0(struct snd_usb_caiaqdev *dev, struct snd_pcm_runtime *rt = sub->runtime; char *audio_buf = rt->dma_area; int sz = frames_to_bytes(rt, rt->buffer_size); - audio_buf[dev->audio_in_buf_pos[stream]++] + audio_buf[dev->audio_in_buf_pos[stream]++] = usb_buf[i]; dev->period_in_count[stream]++; if (dev->audio_in_buf_pos[stream] == sz) @@ -354,14 +354,14 @@ static void read_in_urb_mode2(struct snd_usb_caiaqdev *dev, for (i = 0; i < iso->actual_length;) { if (i % (dev->n_streams * BYTES_PER_SAMPLE_USB) == 0) { - for (stream = 0; - stream < dev->n_streams; + for (stream = 0; + stream < dev->n_streams; stream++, i++) { if (dev->first_packet) continue; check_byte = MAKE_CHECKBYTE(dev, stream, i); - + if ((usb_buf[i] & 0x3f) != check_byte) dev->input_panic = 1; @@ -410,21 +410,21 @@ static void read_in_urb(struct snd_usb_caiaqdev *dev, } if ((dev->input_panic || dev->output_panic) && !dev->warned) { - debug("streaming error detected %s %s\n", + debug("streaming error detected %s %s\n", dev->input_panic ? "(input)" : "", dev->output_panic ? "(output)" : ""); dev->warned = 1; } } -static void fill_out_urb(struct snd_usb_caiaqdev *dev, - struct urb *urb, +static void fill_out_urb(struct snd_usb_caiaqdev *dev, + struct urb *urb, const struct usb_iso_packet_descriptor *iso) { unsigned char *usb_buf = urb->transfer_buffer + iso->offset; struct snd_pcm_substream *sub; int stream, i; - + for (i = 0; i < iso->length;) { for (stream = 0; stream < dev->n_streams; stream++, i++) { sub = dev->sub_playback[stream]; @@ -444,7 +444,7 @@ static void fill_out_urb(struct snd_usb_caiaqdev *dev, /* fill in the check bytes */ if (dev->spec.data_alignment == 2 && - i % (dev->n_streams * BYTES_PER_SAMPLE_USB) == + i % (dev->n_streams * BYTES_PER_SAMPLE_USB) == (dev->n_streams * CHANNELS_PER_STREAM)) for (stream = 0; stream < dev->n_streams; stream++, i++) usb_buf[i] = MAKE_CHECKBYTE(dev, stream, i); @@ -453,7 +453,7 @@ static void fill_out_urb(struct snd_usb_caiaqdev *dev, static void read_completed(struct urb *urb) { - struct snd_usb_caiaq_cb_info *info = urb->context; + struct snd_usb_caiaq_cb_info *info = urb->context; struct snd_usb_caiaqdev *dev; struct urb *out; int frame, len, send_it = 0, outframe = 0; @@ -478,7 +478,7 @@ static void read_completed(struct urb *urb) out->iso_frame_desc[outframe].length = len; out->iso_frame_desc[outframe].actual_length = 0; out->iso_frame_desc[outframe].offset = BYTES_PER_FRAME * frame; - + if (len > 0) { spin_lock(&dev->spinlock); fill_out_urb(dev, out, &out->iso_frame_desc[outframe]); @@ -497,14 +497,14 @@ static void read_completed(struct urb *urb) out->transfer_flags = URB_ISO_ASAP; usb_submit_urb(out, GFP_ATOMIC); } - + /* re-submit inbound urb */ for (frame = 0; frame < FRAMES_PER_URB; frame++) { urb->iso_frame_desc[frame].offset = BYTES_PER_FRAME * frame; urb->iso_frame_desc[frame].length = BYTES_PER_FRAME; urb->iso_frame_desc[frame].actual_length = 0; } - + urb->number_of_packets = FRAMES_PER_URB; urb->transfer_flags = URB_ISO_ASAP; usb_submit_urb(urb, GFP_ATOMIC); @@ -528,7 +528,7 @@ static struct urb **alloc_urbs(struct snd_usb_caiaqdev *dev, int dir, int *ret) struct usb_device *usb_dev = dev->chip.dev; unsigned int pipe; - pipe = (dir == SNDRV_PCM_STREAM_PLAYBACK) ? + pipe = (dir == SNDRV_PCM_STREAM_PLAYBACK) ? usb_sndisocpipe(usb_dev, ENDPOINT_PLAYBACK) : usb_rcvisocpipe(usb_dev, ENDPOINT_CAPTURE); @@ -547,25 +547,25 @@ static struct urb **alloc_urbs(struct snd_usb_caiaqdev *dev, int dir, int *ret) return urbs; } - urbs[i]->transfer_buffer = + urbs[i]->transfer_buffer = kmalloc(FRAMES_PER_URB * BYTES_PER_FRAME, GFP_KERNEL); if (!urbs[i]->transfer_buffer) { log("unable to kmalloc() transfer buffer, OOM!?\n"); *ret = -ENOMEM; return urbs; } - + for (frame = 0; frame < FRAMES_PER_URB; frame++) { - struct usb_iso_packet_descriptor *iso = + struct usb_iso_packet_descriptor *iso = &urbs[i]->iso_frame_desc[frame]; - + iso->offset = BYTES_PER_FRAME * frame; iso->length = BYTES_PER_FRAME; } - + urbs[i]->dev = usb_dev; urbs[i]->pipe = pipe; - urbs[i]->transfer_buffer_length = FRAMES_PER_URB + urbs[i]->transfer_buffer_length = FRAMES_PER_URB * BYTES_PER_FRAME; urbs[i]->context = &dev->data_cb_info[i]; urbs[i]->interval = 1; @@ -589,7 +589,7 @@ static void free_urbs(struct urb **urbs) for (i = 0; i < N_URBS; i++) { if (!urbs[i]) continue; - + usb_kill_urb(urbs[i]); kfree(urbs[i]->transfer_buffer); usb_free_urb(urbs[i]); @@ -602,11 +602,11 @@ int snd_usb_caiaq_audio_init(struct snd_usb_caiaqdev *dev) { int i, ret; - dev->n_audio_in = max(dev->spec.num_analog_audio_in, - dev->spec.num_digital_audio_in) / + dev->n_audio_in = max(dev->spec.num_analog_audio_in, + dev->spec.num_digital_audio_in) / CHANNELS_PER_STREAM; dev->n_audio_out = max(dev->spec.num_analog_audio_out, - dev->spec.num_digital_audio_out) / + dev->spec.num_digital_audio_out) / CHANNELS_PER_STREAM; dev->n_streams = max(dev->n_audio_in, dev->n_audio_out); @@ -619,7 +619,7 @@ int snd_usb_caiaq_audio_init(struct snd_usb_caiaqdev *dev) return -EINVAL; } - ret = snd_pcm_new(dev->chip.card, dev->product_name, 0, + ret = snd_pcm_new(dev->chip.card, dev->product_name, 0, dev->n_audio_out, dev->n_audio_in, &dev->pcm); if (ret < 0) { @@ -632,7 +632,7 @@ int snd_usb_caiaq_audio_init(struct snd_usb_caiaqdev *dev) memset(dev->sub_playback, 0, sizeof(dev->sub_playback)); memset(dev->sub_capture, 0, sizeof(dev->sub_capture)); - + memcpy(&dev->pcm_info, &snd_usb_caiaq_pcm_hardware, sizeof(snd_usb_caiaq_pcm_hardware)); @@ -651,9 +651,9 @@ int snd_usb_caiaq_audio_init(struct snd_usb_caiaqdev *dev) break; } - snd_pcm_set_ops(dev->pcm, SNDRV_PCM_STREAM_PLAYBACK, + snd_pcm_set_ops(dev->pcm, SNDRV_PCM_STREAM_PLAYBACK, &snd_usb_caiaq_ops); - snd_pcm_set_ops(dev->pcm, SNDRV_PCM_STREAM_CAPTURE, + snd_pcm_set_ops(dev->pcm, SNDRV_PCM_STREAM_CAPTURE, &snd_usb_caiaq_ops); snd_pcm_lib_preallocate_pages_for_all(dev->pcm, @@ -662,7 +662,7 @@ int snd_usb_caiaq_audio_init(struct snd_usb_caiaqdev *dev) MAX_BUFFER_SIZE, MAX_BUFFER_SIZE); dev->data_cb_info = - kmalloc(sizeof(struct snd_usb_caiaq_cb_info) * N_URBS, + kmalloc(sizeof(struct snd_usb_caiaq_cb_info) * N_URBS, GFP_KERNEL); if (!dev->data_cb_info) @@ -672,14 +672,14 @@ int snd_usb_caiaq_audio_init(struct snd_usb_caiaqdev *dev) dev->data_cb_info[i].dev = dev; dev->data_cb_info[i].index = i; } - + dev->data_urbs_in = alloc_urbs(dev, SNDRV_PCM_STREAM_CAPTURE, &ret); if (ret < 0) { kfree(dev->data_cb_info); free_urbs(dev->data_urbs_in); return ret; } - + dev->data_urbs_out = alloc_urbs(dev, SNDRV_PCM_STREAM_PLAYBACK, &ret); if (ret < 0) { kfree(dev->data_cb_info); diff --git a/trunk/sound/usb/caiaq/device.c b/trunk/sound/usb/caiaq/device.c index b9a2b312b83e..515de1cd2a3e 100644 --- a/trunk/sound/usb/caiaq/device.c +++ b/trunk/sound/usb/caiaq/device.c @@ -35,7 +35,7 @@ #include "input.h" MODULE_AUTHOR("Daniel Mack "); -MODULE_DESCRIPTION("caiaq USB audio, version 1.3.15"); +MODULE_DESCRIPTION("caiaq USB audio, version 1.3.14"); MODULE_LICENSE("GPL"); MODULE_SUPPORTED_DEVICE("{{Native Instruments, RigKontrol2}," "{Native Instruments, RigKontrol3}," @@ -79,7 +79,7 @@ static struct usb_device_id snd_usb_id_table[] = { { .match_flags = USB_DEVICE_ID_MATCH_DEVICE, .idVendor = USB_VID_NATIVEINSTRUMENTS, - .idProduct = USB_PID_RIGKONTROL2 + .idProduct = USB_PID_RIGKONTROL2 }, { .match_flags = USB_DEVICE_ID_MATCH_DEVICE, @@ -197,7 +197,7 @@ int snd_usb_caiaq_send_command(struct snd_usb_caiaqdev *dev, if (buffer && len > 0) memcpy(dev->ep1_out_buf+1, buffer, len); - + dev->ep1_out_buf[0] = command; return usb_bulk_msg(usb_dev, usb_sndbulkpipe(usb_dev, 1), dev->ep1_out_buf, len+1, &actual_len, 200); @@ -208,7 +208,7 @@ int snd_usb_caiaq_set_audio_params (struct snd_usb_caiaqdev *dev, { int ret; char tmp[5]; - + switch (rate) { case 44100: tmp[0] = SAMPLERATE_44100; break; case 48000: tmp[0] = SAMPLERATE_48000; break; @@ -237,12 +237,12 @@ int snd_usb_caiaq_set_audio_params (struct snd_usb_caiaqdev *dev, if (ret) return ret; - - if (!wait_event_timeout(dev->ep1_wait_queue, + + if (!wait_event_timeout(dev->ep1_wait_queue, dev->audio_parm_answer >= 0, HZ)) return -EPIPE; - - if (dev->audio_parm_answer != 1) + + if (dev->audio_parm_answer != 1) debug("unable to set the device's audio params\n"); else dev->bpp = bpp; @@ -250,8 +250,8 @@ int snd_usb_caiaq_set_audio_params (struct snd_usb_caiaqdev *dev, return dev->audio_parm_answer == 1 ? 0 : -EINVAL; } -int snd_usb_caiaq_set_auto_msg(struct snd_usb_caiaqdev *dev, - int digital, int analog, int erp) +int snd_usb_caiaq_set_auto_msg (struct snd_usb_caiaqdev *dev, + int digital, int analog, int erp) { char tmp[3] = { digital, analog, erp }; return snd_usb_caiaq_send_command(dev, EP1_CMD_AUTO_MSG, @@ -262,7 +262,7 @@ static void __devinit setup_card(struct snd_usb_caiaqdev *dev) { int ret; char val[4]; - + /* device-specific startup specials */ switch (dev->chip.usb_id) { case USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_RIGKONTROL2): @@ -314,7 +314,7 @@ static void __devinit setup_card(struct snd_usb_caiaqdev *dev) dev->control_state, 1); break; } - + if (dev->spec.num_analog_audio_out + dev->spec.num_analog_audio_in + dev->spec.num_digital_audio_out + @@ -323,7 +323,7 @@ static void __devinit setup_card(struct snd_usb_caiaqdev *dev) if (ret < 0) log("Unable to set up audio system (ret=%d)\n", ret); } - + if (dev->spec.num_midi_in + dev->spec.num_midi_out > 0) { ret = snd_usb_caiaq_midi_init(dev); @@ -363,7 +363,7 @@ static int create_card(struct usb_device* usb_dev, struct snd_card **cardp) if (devnum >= SNDRV_CARDS) return -ENODEV; - err = snd_card_create(index[devnum], id[devnum], THIS_MODULE, + err = snd_card_create(index[devnum], id[devnum], THIS_MODULE, sizeof(struct snd_usb_caiaqdev), &card); if (err < 0) return err; @@ -382,11 +382,11 @@ static int create_card(struct usb_device* usb_dev, struct snd_card **cardp) static int __devinit init_card(struct snd_usb_caiaqdev *dev) { - char *c, usbpath[32]; + char *c; struct usb_device *usb_dev = dev->chip.dev; struct snd_card *card = dev->chip.card; int err, len; - + if (usb_set_interface(usb_dev, 0, 1) != 0) { log("can't set alt interface.\n"); return -EIO; @@ -395,19 +395,19 @@ static int __devinit init_card(struct snd_usb_caiaqdev *dev) usb_init_urb(&dev->ep1_in_urb); usb_init_urb(&dev->midi_out_urb); - usb_fill_bulk_urb(&dev->ep1_in_urb, usb_dev, + usb_fill_bulk_urb(&dev->ep1_in_urb, usb_dev, usb_rcvbulkpipe(usb_dev, 0x1), - dev->ep1_in_buf, EP1_BUFSIZE, + dev->ep1_in_buf, EP1_BUFSIZE, usb_ep1_command_reply_dispatch, dev); - usb_fill_bulk_urb(&dev->midi_out_urb, usb_dev, + usb_fill_bulk_urb(&dev->midi_out_urb, usb_dev, usb_sndbulkpipe(usb_dev, 0x1), - dev->midi_out_buf, EP1_BUFSIZE, + dev->midi_out_buf, EP1_BUFSIZE, snd_usb_caiaq_midi_output_done, dev); - + init_waitqueue_head(&dev->ep1_wait_queue); init_waitqueue_head(&dev->prepare_wait_queue); - + if (usb_submit_urb(&dev->ep1_in_urb, GFP_KERNEL) != 0) return -EIO; @@ -420,51 +420,47 @@ static int __devinit init_card(struct snd_usb_caiaqdev *dev) usb_string(usb_dev, usb_dev->descriptor.iManufacturer, dev->vendor_name, CAIAQ_USB_STR_LEN); - + usb_string(usb_dev, usb_dev->descriptor.iProduct, dev->product_name, CAIAQ_USB_STR_LEN); - - strlcpy(card->driver, MODNAME, sizeof(card->driver)); - strlcpy(card->shortname, dev->product_name, sizeof(card->shortname)); - - /* if the id was not passed as module option, fill it with a shortened - * version of the product string which does not contain any - * whitespaces */ - - if (*card->id == '\0') { - char id[sizeof(card->id)]; - - memset(id, 0, sizeof(id)); - - for (c = card->shortname, len = 0; - *c && len < sizeof(card->id); c++) - if (*c != ' ') - id[len++] = *c; - - snd_card_set_id(card, id); - } - - usb_make_path(usb_dev, usbpath, sizeof(usbpath)); - snprintf(card->longname, sizeof(card->longname), - "%s %s (%s)", - dev->vendor_name, dev->product_name, usbpath); - + + usb_string(usb_dev, usb_dev->descriptor.iSerialNumber, + dev->serial, CAIAQ_USB_STR_LEN); + + /* terminate serial string at first white space occurence */ + c = strchr(dev->serial, ' '); + if (c) + *c = '\0'; + + strcpy(card->driver, MODNAME); + strcpy(card->shortname, dev->product_name); + + len = snprintf(card->longname, sizeof(card->longname), + "%s %s (serial %s, ", + dev->vendor_name, dev->product_name, dev->serial); + + if (len < sizeof(card->longname) - 2) + len += usb_make_path(usb_dev, card->longname + len, + sizeof(card->longname) - len); + + card->longname[len++] = ')'; + card->longname[len] = '\0'; setup_card(dev); return 0; } -static int __devinit snd_probe(struct usb_interface *intf, +static int __devinit snd_probe(struct usb_interface *intf, const struct usb_device_id *id) { int ret; struct snd_card *card; struct usb_device *device = interface_to_usbdev(intf); - + ret = create_card(device, &card); - + if (ret < 0) return ret; - + usb_set_intfdata(intf, card); ret = init_card(caiaqdev(card)); if (ret < 0) { @@ -472,7 +468,7 @@ static int __devinit snd_probe(struct usb_interface *intf, snd_card_free(card); return ret; } - + return 0; } @@ -493,10 +489,10 @@ static void snd_disconnect(struct usb_interface *intf) snd_usb_caiaq_input_free(dev); #endif snd_usb_caiaq_audio_free(dev); - + usb_kill_urb(&dev->ep1_in_urb); usb_kill_urb(&dev->midi_out_urb); - + snd_card_free(card); usb_reset_device(interface_to_usbdev(intf)); } diff --git a/trunk/sound/usb/caiaq/device.h b/trunk/sound/usb/caiaq/device.h index ece73514854e..4cce1ad7493d 100644 --- a/trunk/sound/usb/caiaq/device.h +++ b/trunk/sound/usb/caiaq/device.h @@ -81,6 +81,7 @@ struct snd_usb_caiaqdev { char vendor_name[CAIAQ_USB_STR_LEN]; char product_name[CAIAQ_USB_STR_LEN]; + char serial[CAIAQ_USB_STR_LEN]; int n_streams, n_audio_in, n_audio_out; int streaming, first_packet, output_running; diff --git a/trunk/sound/usb/caiaq/midi.c b/trunk/sound/usb/caiaq/midi.c index 538e8c00d31a..8fa8cd88d763 100644 --- a/trunk/sound/usb/caiaq/midi.c +++ b/trunk/sound/usb/caiaq/midi.c @@ -40,7 +40,7 @@ static void snd_usb_caiaq_midi_input_trigger(struct snd_rawmidi_substream *subst if (!dev) return; - + dev->midi_receive_substream = up ? substream : NULL; } @@ -64,18 +64,18 @@ static void snd_usb_caiaq_midi_send(struct snd_usb_caiaqdev *dev, struct snd_rawmidi_substream *substream) { int len, ret; - + dev->midi_out_buf[0] = EP1_CMD_MIDI_WRITE; dev->midi_out_buf[1] = 0; /* port */ len = snd_rawmidi_transmit(substream, dev->midi_out_buf + 3, EP1_BUFSIZE - 3); - + if (len <= 0) return; - + dev->midi_out_buf[2] = len; dev->midi_out_urb.transfer_buffer_length = len+3; - + ret = usb_submit_urb(&dev->midi_out_urb, GFP_ATOMIC); if (ret < 0) log("snd_usb_caiaq_midi_send(%p): usb_submit_urb() failed," @@ -88,7 +88,7 @@ static void snd_usb_caiaq_midi_send(struct snd_usb_caiaqdev *dev, static void snd_usb_caiaq_midi_output_trigger(struct snd_rawmidi_substream *substream, int up) { struct snd_usb_caiaqdev *dev = substream->rmidi->private_data; - + if (up) { dev->midi_out_substream = substream; if (!dev->midi_out_active) @@ -113,12 +113,12 @@ static struct snd_rawmidi_ops snd_usb_caiaq_midi_input = .trigger = snd_usb_caiaq_midi_input_trigger, }; -void snd_usb_caiaq_midi_handle_input(struct snd_usb_caiaqdev *dev, +void snd_usb_caiaq_midi_handle_input(struct snd_usb_caiaqdev *dev, int port, const char *buf, int len) { if (!dev->midi_receive_substream) return; - + snd_rawmidi_receive(dev->midi_receive_substream, buf, len); } @@ -142,16 +142,16 @@ int snd_usb_caiaq_midi_init(struct snd_usb_caiaqdev *device) if (device->spec.num_midi_out > 0) { rmidi->info_flags |= SNDRV_RAWMIDI_INFO_OUTPUT; - snd_rawmidi_set_ops(rmidi, SNDRV_RAWMIDI_STREAM_OUTPUT, + snd_rawmidi_set_ops(rmidi, SNDRV_RAWMIDI_STREAM_OUTPUT, &snd_usb_caiaq_midi_output); } if (device->spec.num_midi_in > 0) { rmidi->info_flags |= SNDRV_RAWMIDI_INFO_INPUT; - snd_rawmidi_set_ops(rmidi, SNDRV_RAWMIDI_STREAM_INPUT, + snd_rawmidi_set_ops(rmidi, SNDRV_RAWMIDI_STREAM_INPUT, &snd_usb_caiaq_midi_input); } - + device->rmidi = rmidi; return 0; @@ -160,7 +160,7 @@ int snd_usb_caiaq_midi_init(struct snd_usb_caiaqdev *device) void snd_usb_caiaq_midi_output_done(struct urb* urb) { struct snd_usb_caiaqdev *dev = urb->context; - + dev->midi_out_active = 0; if (urb->status != 0) return; diff --git a/trunk/virt/kvm/kvm_main.c b/trunk/virt/kvm/kvm_main.c index 4d0dd390aa50..1ecbe2391c8b 100644 --- a/trunk/virt/kvm/kvm_main.c +++ b/trunk/virt/kvm/kvm_main.c @@ -2301,11 +2301,10 @@ int kvm_init(void *opaque, unsigned int vcpu_size, bad_pfn = page_to_pfn(bad_page); - if (!zalloc_cpumask_var(&cpus_hardware_enabled, GFP_KERNEL)) { + if (!alloc_cpumask_var(&cpus_hardware_enabled, GFP_KERNEL)) { r = -ENOMEM; goto out_free_0; } - cpumask_clear(cpus_hardware_enabled); r = kvm_arch_hardware_setup(); if (r < 0)