Merge branch 'fixes' of master.kernel.org:/home/rmk/linux-2.6-arm
* 'fixes' of master.kernel.org:/home/rmk/linux-2.6-arm: ALSA: AACI: fix timeout duration ALSA: AACI: fix timeout condition checking ARM: 6636/1: ep93xx: default multiplexed gpio ports to gpio mode ARM: 6637/1: Make the argument to virt_to_phys() "const volatile" ARM: twd: ensure timer reload is reprogrammed on entry to periodic mode ARM: 6635/2: Configure reference clock for Versatile Express timers ARM: versatile: name configuration options after actual board names ARM: realview: name configuration options after actual board names ARM: realview,vexpress: fix section mismatch warning for pen_release ARM: 6632/3: mmci: stop using the blockend interrupts
This commit is contained in:
Коммит
6663050edd
|
@ -50,6 +50,12 @@
|
|||
#define SCPCELLID2 0xFF8
|
||||
#define SCPCELLID3 0xFFC
|
||||
|
||||
#define SCCTRL_TIMEREN0SEL_REFCLK (0 << 15)
|
||||
#define SCCTRL_TIMEREN0SEL_TIMCLK (1 << 15)
|
||||
|
||||
#define SCCTRL_TIMEREN1SEL_REFCLK (0 << 17)
|
||||
#define SCCTRL_TIMEREN1SEL_TIMCLK (1 << 17)
|
||||
|
||||
static inline void sysctl_soft_reset(void __iomem *base)
|
||||
{
|
||||
/* writing any value to SCSYSSTAT reg will reset system */
|
||||
|
|
|
@ -188,7 +188,7 @@
|
|||
* translation for translating DMA addresses. Use the driver
|
||||
* DMA support - see dma-mapping.h.
|
||||
*/
|
||||
static inline unsigned long virt_to_phys(void *x)
|
||||
static inline unsigned long virt_to_phys(const volatile void *x)
|
||||
{
|
||||
return __virt_to_phys((unsigned long)(x));
|
||||
}
|
||||
|
|
|
@ -36,6 +36,7 @@ static void twd_set_mode(enum clock_event_mode mode,
|
|||
/* timer load already set up */
|
||||
ctrl = TWD_TIMER_CONTROL_ENABLE | TWD_TIMER_CONTROL_IT_ENABLE
|
||||
| TWD_TIMER_CONTROL_PERIODIC;
|
||||
__raw_writel(twd_timer_rate / HZ, twd_base + TWD_TIMER_LOAD);
|
||||
break;
|
||||
case CLOCK_EVT_MODE_ONESHOT:
|
||||
/* period set, and timer enabled in 'next_event' hook */
|
||||
|
@ -81,7 +82,7 @@ int twd_timer_ack(void)
|
|||
|
||||
static void __cpuinit twd_calibrate_rate(void)
|
||||
{
|
||||
unsigned long load, count;
|
||||
unsigned long count;
|
||||
u64 waitjiffies;
|
||||
|
||||
/*
|
||||
|
@ -116,10 +117,6 @@ static void __cpuinit twd_calibrate_rate(void)
|
|||
printk("%lu.%02luMHz.\n", twd_timer_rate / 1000000,
|
||||
(twd_timer_rate / 1000000) % 100);
|
||||
}
|
||||
|
||||
load = twd_timer_rate / HZ;
|
||||
|
||||
__raw_writel(load, twd_base + TWD_TIMER_LOAD);
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
|
@ -427,6 +427,13 @@ void __init ep93xx_gpio_init(void)
|
|||
{
|
||||
int i;
|
||||
|
||||
/* Set Ports C, D, E, G, and H for GPIO use */
|
||||
ep93xx_devcfg_set_bits(EP93XX_SYSCON_DEVCFG_KEYS |
|
||||
EP93XX_SYSCON_DEVCFG_GONK |
|
||||
EP93XX_SYSCON_DEVCFG_EONIDE |
|
||||
EP93XX_SYSCON_DEVCFG_GONIDE |
|
||||
EP93XX_SYSCON_DEVCFG_HONIDE);
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(ep93xx_gpio_banks); i++)
|
||||
gpiochip_add(&ep93xx_gpio_banks[i].chip);
|
||||
}
|
||||
|
|
|
@ -2,52 +2,56 @@ menu "RealView platform type"
|
|||
depends on ARCH_REALVIEW
|
||||
|
||||
config MACH_REALVIEW_EB
|
||||
bool "Support RealView/EB platform"
|
||||
bool "Support RealView(R) Emulation Baseboard"
|
||||
select ARM_GIC
|
||||
help
|
||||
Include support for the ARM(R) RealView Emulation Baseboard platform.
|
||||
Include support for the ARM(R) RealView(R) Emulation Baseboard
|
||||
platform.
|
||||
|
||||
config REALVIEW_EB_A9MP
|
||||
bool "Support Multicore Cortex-A9"
|
||||
bool "Support Multicore Cortex-A9 Tile"
|
||||
depends on MACH_REALVIEW_EB
|
||||
select CPU_V7
|
||||
help
|
||||
Enable support for the Cortex-A9MPCore tile on the Realview platform.
|
||||
Enable support for the Cortex-A9MPCore tile fitted to the
|
||||
Realview(R) Emulation Baseboard platform.
|
||||
|
||||
config REALVIEW_EB_ARM11MP
|
||||
bool "Support ARM11MPCore tile"
|
||||
bool "Support ARM11MPCore Tile"
|
||||
depends on MACH_REALVIEW_EB
|
||||
select CPU_V6
|
||||
select ARCH_HAS_BARRIERS if SMP
|
||||
help
|
||||
Enable support for the ARM11MPCore tile on the Realview platform.
|
||||
Enable support for the ARM11MPCore tile fitted to the Realview(R)
|
||||
Emulation Baseboard platform.
|
||||
|
||||
config REALVIEW_EB_ARM11MP_REVB
|
||||
bool "Support ARM11MPCore RevB tile"
|
||||
bool "Support ARM11MPCore RevB Tile"
|
||||
depends on REALVIEW_EB_ARM11MP
|
||||
help
|
||||
Enable support for the ARM11MPCore RevB tile on the Realview
|
||||
platform. Since there are device address differences, a
|
||||
kernel built with this option enabled is not compatible with
|
||||
other revisions of the ARM11MPCore tile.
|
||||
Enable support for the ARM11MPCore Revision B tile on the
|
||||
Realview(R) Emulation Baseboard platform. Since there are device
|
||||
address differences, a kernel built with this option enabled is
|
||||
not compatible with other revisions of the ARM11MPCore tile.
|
||||
|
||||
config MACH_REALVIEW_PB11MP
|
||||
bool "Support RealView/PB11MPCore platform"
|
||||
bool "Support RealView(R) Platform Baseboard for ARM11MPCore"
|
||||
select CPU_V6
|
||||
select ARM_GIC
|
||||
select HAVE_PATA_PLATFORM
|
||||
select ARCH_HAS_BARRIERS if SMP
|
||||
help
|
||||
Include support for the ARM(R) RealView MPCore Platform Baseboard.
|
||||
PB11MPCore is a platform with an on-board ARM11MPCore and has
|
||||
Include support for the ARM(R) RealView(R) Platform Baseboard for
|
||||
the ARM11MPCore. This platform has an on-board ARM11MPCore and has
|
||||
support for PCI-E and Compact Flash.
|
||||
|
||||
config MACH_REALVIEW_PB1176
|
||||
bool "Support RealView/PB1176 platform"
|
||||
bool "Support RealView(R) Platform Baseboard for ARM1176JZF-S"
|
||||
select CPU_V6
|
||||
select ARM_GIC
|
||||
help
|
||||
Include support for the ARM(R) RealView ARM1176 Platform Baseboard.
|
||||
Include support for the ARM(R) RealView(R) Platform Baseboard for
|
||||
ARM1176JZF-S.
|
||||
|
||||
config REALVIEW_PB1176_SECURE_FLASH
|
||||
bool "Allow access to the secure flash memory block"
|
||||
|
@ -59,23 +63,24 @@ config REALVIEW_PB1176_SECURE_FLASH
|
|||
block (64MB @ 0x3c000000) is required.
|
||||
|
||||
config MACH_REALVIEW_PBA8
|
||||
bool "Support RealView/PB-A8 platform"
|
||||
bool "Support RealView(R) Platform Baseboard for Cortex(tm)-A8 platform"
|
||||
select CPU_V7
|
||||
select ARM_GIC
|
||||
select HAVE_PATA_PLATFORM
|
||||
help
|
||||
Include support for the ARM(R) RealView Cortex-A8 Platform Baseboard.
|
||||
PB-A8 is a platform with an on-board Cortex-A8 and has support for
|
||||
PCI-E and Compact Flash.
|
||||
Include support for the ARM(R) RealView Platform Baseboard for
|
||||
Cortex(tm)-A8. This platform has an on-board Cortex-A8 and has
|
||||
support for PCI-E and Compact Flash.
|
||||
|
||||
config MACH_REALVIEW_PBX
|
||||
bool "Support RealView/PBX platform"
|
||||
bool "Support RealView(R) Platform Baseboard Explore"
|
||||
select ARM_GIC
|
||||
select HAVE_PATA_PLATFORM
|
||||
select ARCH_SPARSEMEM_ENABLE if CPU_V7 && !REALVIEW_HIGH_PHYS_OFFSET
|
||||
select ZONE_DMA if SPARSEMEM
|
||||
help
|
||||
Include support for the ARM(R) RealView PBX platform.
|
||||
Include support for the ARM(R) RealView(R) Platform Baseboard
|
||||
Explore.
|
||||
|
||||
config REALVIEW_HIGH_PHYS_OFFSET
|
||||
bool "High physical base address for the RealView platform"
|
||||
|
|
|
@ -41,7 +41,7 @@ volatile int __cpuinitdata pen_release = -1;
|
|||
* observers, irrespective of whether they're taking part in coherency
|
||||
* or not. This is necessary for the hotplug code to work reliably.
|
||||
*/
|
||||
static void write_pen_release(int val)
|
||||
static void __cpuinit write_pen_release(int val)
|
||||
{
|
||||
pen_release = val;
|
||||
smp_wmb();
|
||||
|
|
|
@ -2,17 +2,19 @@ menu "Versatile platform type"
|
|||
depends on ARCH_VERSATILE
|
||||
|
||||
config ARCH_VERSATILE_PB
|
||||
bool "Support Versatile/PB platform"
|
||||
bool "Support Versatile Platform Baseboard for ARM926EJ-S"
|
||||
select CPU_ARM926T
|
||||
select MIGHT_HAVE_PCI
|
||||
default y
|
||||
help
|
||||
Include support for the ARM(R) Versatile/PB platform.
|
||||
Include support for the ARM(R) Versatile Platform Baseboard
|
||||
for the ARM926EJ-S.
|
||||
|
||||
config MACH_VERSATILE_AB
|
||||
bool "Support Versatile/AB platform"
|
||||
bool "Support Versatile Application Baseboard for ARM926EJ-S"
|
||||
select CPU_ARM926T
|
||||
help
|
||||
Include support for the ARM(R) Versatile/AP platform.
|
||||
Include support for the ARM(R) Versatile Application Baseboard
|
||||
for the ARM926EJ-S.
|
||||
|
||||
endmenu
|
||||
|
|
|
@ -39,7 +39,7 @@ volatile int __cpuinitdata pen_release = -1;
|
|||
* observers, irrespective of whether they're taking part in coherency
|
||||
* or not. This is necessary for the hotplug code to work reliably.
|
||||
*/
|
||||
static void write_pen_release(int val)
|
||||
static void __cpuinit write_pen_release(int val)
|
||||
{
|
||||
pen_release = val;
|
||||
smp_wmb();
|
||||
|
|
|
@ -19,6 +19,7 @@
|
|||
#include <asm/mach/time.h>
|
||||
#include <asm/hardware/arm_timer.h>
|
||||
#include <asm/hardware/timer-sp.h>
|
||||
#include <asm/hardware/sp810.h>
|
||||
|
||||
#include <mach/motherboard.h>
|
||||
|
||||
|
@ -50,8 +51,16 @@ void __init v2m_map_io(struct map_desc *tile, size_t num)
|
|||
|
||||
static void __init v2m_timer_init(void)
|
||||
{
|
||||
u32 scctrl;
|
||||
|
||||
versatile_sched_clock_init(MMIO_P2V(V2M_SYS_24MHZ), 24000000);
|
||||
|
||||
/* Select 1MHz TIMCLK as the reference clock for SP804 timers */
|
||||
scctrl = readl(MMIO_P2V(V2M_SYSCTL + SCCTRL));
|
||||
scctrl |= SCCTRL_TIMEREN0SEL_TIMCLK;
|
||||
scctrl |= SCCTRL_TIMEREN1SEL_TIMCLK;
|
||||
writel(scctrl, MMIO_P2V(V2M_SYSCTL + SCCTRL));
|
||||
|
||||
writel(0, MMIO_P2V(V2M_TIMER0) + TIMER_CTRL);
|
||||
writel(0, MMIO_P2V(V2M_TIMER1) + TIMER_CTRL);
|
||||
|
||||
|
|
|
@ -46,10 +46,6 @@ static unsigned int fmax = 515633;
|
|||
* is asserted (likewise for RX)
|
||||
* @fifohalfsize: number of bytes that can be written when MCI_TXFIFOHALFEMPTY
|
||||
* is asserted (likewise for RX)
|
||||
* @broken_blockend: the MCI_DATABLOCKEND is broken on the hardware
|
||||
* and will not work at all.
|
||||
* @broken_blockend_dma: the MCI_DATABLOCKEND is broken on the hardware when
|
||||
* using DMA.
|
||||
* @sdio: variant supports SDIO
|
||||
* @st_clkdiv: true if using a ST-specific clock divider algorithm
|
||||
*/
|
||||
|
@ -59,8 +55,6 @@ struct variant_data {
|
|||
unsigned int datalength_bits;
|
||||
unsigned int fifosize;
|
||||
unsigned int fifohalfsize;
|
||||
bool broken_blockend;
|
||||
bool broken_blockend_dma;
|
||||
bool sdio;
|
||||
bool st_clkdiv;
|
||||
};
|
||||
|
@ -76,7 +70,6 @@ static struct variant_data variant_u300 = {
|
|||
.fifohalfsize = 8 * 4,
|
||||
.clkreg_enable = 1 << 13, /* HWFCEN */
|
||||
.datalength_bits = 16,
|
||||
.broken_blockend_dma = true,
|
||||
.sdio = true,
|
||||
};
|
||||
|
||||
|
@ -86,7 +79,6 @@ static struct variant_data variant_ux500 = {
|
|||
.clkreg = MCI_CLK_ENABLE,
|
||||
.clkreg_enable = 1 << 14, /* HWFCEN */
|
||||
.datalength_bits = 24,
|
||||
.broken_blockend = true,
|
||||
.sdio = true,
|
||||
.st_clkdiv = true,
|
||||
};
|
||||
|
@ -210,8 +202,6 @@ static void mmci_start_data(struct mmci_host *host, struct mmc_data *data)
|
|||
host->data = data;
|
||||
host->size = data->blksz * data->blocks;
|
||||
host->data_xfered = 0;
|
||||
host->blockend = false;
|
||||
host->dataend = false;
|
||||
|
||||
mmci_init_sg(host, data);
|
||||
|
||||
|
@ -288,21 +278,26 @@ static void
|
|||
mmci_data_irq(struct mmci_host *host, struct mmc_data *data,
|
||||
unsigned int status)
|
||||
{
|
||||
struct variant_data *variant = host->variant;
|
||||
|
||||
/* First check for errors */
|
||||
if (status & (MCI_DATACRCFAIL|MCI_DATATIMEOUT|MCI_TXUNDERRUN|MCI_RXOVERRUN)) {
|
||||
dev_dbg(mmc_dev(host->mmc), "MCI ERROR IRQ (status %08x)\n", status);
|
||||
if (status & MCI_DATACRCFAIL)
|
||||
data->error = -EILSEQ;
|
||||
else if (status & MCI_DATATIMEOUT)
|
||||
data->error = -ETIMEDOUT;
|
||||
else if (status & (MCI_TXUNDERRUN|MCI_RXOVERRUN))
|
||||
data->error = -EIO;
|
||||
u32 remain, success;
|
||||
|
||||
/* Force-complete the transaction */
|
||||
host->blockend = true;
|
||||
host->dataend = true;
|
||||
/* Calculate how far we are into the transfer */
|
||||
remain = readl(host->base + MMCIDATACNT) << 2;
|
||||
success = data->blksz * data->blocks - remain;
|
||||
|
||||
dev_dbg(mmc_dev(host->mmc), "MCI ERROR IRQ (status %08x)\n", status);
|
||||
if (status & MCI_DATACRCFAIL) {
|
||||
/* Last block was not successful */
|
||||
host->data_xfered = ((success / data->blksz) - 1 * data->blksz);
|
||||
data->error = -EILSEQ;
|
||||
} else if (status & MCI_DATATIMEOUT) {
|
||||
host->data_xfered = success;
|
||||
data->error = -ETIMEDOUT;
|
||||
} else if (status & (MCI_TXUNDERRUN|MCI_RXOVERRUN)) {
|
||||
host->data_xfered = success;
|
||||
data->error = -EIO;
|
||||
}
|
||||
|
||||
/*
|
||||
* We hit an error condition. Ensure that any data
|
||||
|
@ -321,61 +316,14 @@ mmci_data_irq(struct mmci_host *host, struct mmc_data *data,
|
|||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* On ARM variants in PIO mode, MCI_DATABLOCKEND
|
||||
* is always sent first, and we increase the
|
||||
* transfered number of bytes for that IRQ. Then
|
||||
* MCI_DATAEND follows and we conclude the transaction.
|
||||
*
|
||||
* On the Ux500 single-IRQ variant MCI_DATABLOCKEND
|
||||
* doesn't seem to immediately clear from the status,
|
||||
* so we can't use it keep count when only one irq is
|
||||
* used because the irq will hit for other reasons, and
|
||||
* then the flag is still up. So we use the MCI_DATAEND
|
||||
* IRQ at the end of the entire transfer because
|
||||
* MCI_DATABLOCKEND is broken.
|
||||
*
|
||||
* In the U300, the IRQs can arrive out-of-order,
|
||||
* e.g. MCI_DATABLOCKEND sometimes arrives after MCI_DATAEND,
|
||||
* so for this case we use the flags "blockend" and
|
||||
* "dataend" to make sure both IRQs have arrived before
|
||||
* concluding the transaction. (This does not apply
|
||||
* to the Ux500 which doesn't fire MCI_DATABLOCKEND
|
||||
* at all.) In DMA mode it suffers from the same problem
|
||||
* as the Ux500.
|
||||
*/
|
||||
if (status & MCI_DATABLOCKEND) {
|
||||
/*
|
||||
* Just being a little over-cautious, we do not
|
||||
* use this progressive update if the hardware blockend
|
||||
* flag is unreliable: since it can stay high between
|
||||
* IRQs it will corrupt the transfer counter.
|
||||
*/
|
||||
if (!variant->broken_blockend)
|
||||
host->data_xfered += data->blksz;
|
||||
host->blockend = true;
|
||||
}
|
||||
if (status & MCI_DATABLOCKEND)
|
||||
dev_err(mmc_dev(host->mmc), "stray MCI_DATABLOCKEND interrupt\n");
|
||||
|
||||
if (status & MCI_DATAEND)
|
||||
host->dataend = true;
|
||||
|
||||
/*
|
||||
* On variants with broken blockend we shall only wait for dataend,
|
||||
* on others we must sync with the blockend signal since they can
|
||||
* appear out-of-order.
|
||||
*/
|
||||
if (host->dataend && (host->blockend || variant->broken_blockend)) {
|
||||
if (status & MCI_DATAEND) {
|
||||
mmci_stop_data(host);
|
||||
|
||||
/* Reset these flags */
|
||||
host->blockend = false;
|
||||
host->dataend = false;
|
||||
|
||||
/*
|
||||
* Variants with broken blockend flags need to handle the
|
||||
* end of the entire transfer here.
|
||||
*/
|
||||
if (variant->broken_blockend && !data->error)
|
||||
if (!data->error)
|
||||
/* The error clause is handled above, success! */
|
||||
host->data_xfered += data->blksz * data->blocks;
|
||||
|
||||
if (!data->stop) {
|
||||
|
@ -770,7 +718,6 @@ static int __devinit mmci_probe(struct amba_device *dev, struct amba_id *id)
|
|||
struct variant_data *variant = id->data;
|
||||
struct mmci_host *host;
|
||||
struct mmc_host *mmc;
|
||||
unsigned int mask;
|
||||
int ret;
|
||||
|
||||
/* must have platform data */
|
||||
|
@ -951,12 +898,7 @@ static int __devinit mmci_probe(struct amba_device *dev, struct amba_id *id)
|
|||
goto irq0_free;
|
||||
}
|
||||
|
||||
mask = MCI_IRQENABLE;
|
||||
/* Don't use the datablockend flag if it's broken */
|
||||
if (variant->broken_blockend)
|
||||
mask &= ~MCI_DATABLOCKEND;
|
||||
|
||||
writel(mask, host->base + MMCIMASK0);
|
||||
writel(MCI_IRQENABLE, host->base + MMCIMASK0);
|
||||
|
||||
amba_set_drvdata(dev, mmc);
|
||||
|
||||
|
|
|
@ -137,7 +137,7 @@
|
|||
#define MCI_IRQENABLE \
|
||||
(MCI_CMDCRCFAILMASK|MCI_DATACRCFAILMASK|MCI_CMDTIMEOUTMASK| \
|
||||
MCI_DATATIMEOUTMASK|MCI_TXUNDERRUNMASK|MCI_RXOVERRUNMASK| \
|
||||
MCI_CMDRESPENDMASK|MCI_CMDSENTMASK|MCI_DATABLOCKENDMASK)
|
||||
MCI_CMDRESPENDMASK|MCI_CMDSENTMASK)
|
||||
|
||||
/* These interrupts are directed to IRQ1 when two IRQ lines are available */
|
||||
#define MCI_IRQ1MASK \
|
||||
|
@ -177,9 +177,6 @@ struct mmci_host {
|
|||
struct timer_list timer;
|
||||
unsigned int oldstat;
|
||||
|
||||
bool blockend;
|
||||
bool dataend;
|
||||
|
||||
/* pio stuff */
|
||||
struct sg_mapping_iter sg_miter;
|
||||
unsigned int size;
|
||||
|
|
|
@ -30,6 +30,8 @@
|
|||
|
||||
#define DRIVER_NAME "aaci-pl041"
|
||||
|
||||
#define FRAME_PERIOD_US 21
|
||||
|
||||
/*
|
||||
* PM support is not complete. Turn it off.
|
||||
*/
|
||||
|
@ -64,8 +66,8 @@ static void aaci_ac97_write(struct snd_ac97 *ac97, unsigned short reg,
|
|||
unsigned short val)
|
||||
{
|
||||
struct aaci *aaci = ac97->private_data;
|
||||
int timeout;
|
||||
u32 v;
|
||||
int timeout = 5000;
|
||||
|
||||
if (ac97->num >= 4)
|
||||
return;
|
||||
|
@ -81,14 +83,17 @@ static void aaci_ac97_write(struct snd_ac97 *ac97, unsigned short reg,
|
|||
writel(val << 4, aaci->base + AACI_SL2TX);
|
||||
writel(reg << 12, aaci->base + AACI_SL1TX);
|
||||
|
||||
/*
|
||||
* Wait for the transmission of both slots to complete.
|
||||
*/
|
||||
/* Initially, wait one frame period */
|
||||
udelay(FRAME_PERIOD_US);
|
||||
|
||||
/* And then wait an additional eight frame periods for it to be sent */
|
||||
timeout = FRAME_PERIOD_US * 8;
|
||||
do {
|
||||
udelay(1);
|
||||
v = readl(aaci->base + AACI_SLFR);
|
||||
} while ((v & (SLFR_1TXB|SLFR_2TXB)) && --timeout);
|
||||
|
||||
if (!timeout)
|
||||
if (v & (SLFR_1TXB|SLFR_2TXB))
|
||||
dev_err(&aaci->dev->dev,
|
||||
"timeout waiting for write to complete\n");
|
||||
|
||||
|
@ -101,9 +106,8 @@ static void aaci_ac97_write(struct snd_ac97 *ac97, unsigned short reg,
|
|||
static unsigned short aaci_ac97_read(struct snd_ac97 *ac97, unsigned short reg)
|
||||
{
|
||||
struct aaci *aaci = ac97->private_data;
|
||||
int timeout, retries = 10;
|
||||
u32 v;
|
||||
int timeout = 5000;
|
||||
int retries = 10;
|
||||
|
||||
if (ac97->num >= 4)
|
||||
return ~0;
|
||||
|
@ -117,35 +121,34 @@ static unsigned short aaci_ac97_read(struct snd_ac97 *ac97, unsigned short reg)
|
|||
*/
|
||||
writel((reg << 12) | (1 << 19), aaci->base + AACI_SL1TX);
|
||||
|
||||
/*
|
||||
* Wait for the transmission to complete.
|
||||
*/
|
||||
/* Initially, wait one frame period */
|
||||
udelay(FRAME_PERIOD_US);
|
||||
|
||||
/* And then wait an additional eight frame periods for it to be sent */
|
||||
timeout = FRAME_PERIOD_US * 8;
|
||||
do {
|
||||
udelay(1);
|
||||
v = readl(aaci->base + AACI_SLFR);
|
||||
} while ((v & SLFR_1TXB) && --timeout);
|
||||
|
||||
if (!timeout) {
|
||||
if (v & SLFR_1TXB) {
|
||||
dev_err(&aaci->dev->dev, "timeout on slot 1 TX busy\n");
|
||||
v = ~0;
|
||||
goto out;
|
||||
}
|
||||
|
||||
/*
|
||||
* Give the AC'97 codec more than enough time
|
||||
* to respond. (42us = ~2 frames at 48kHz.)
|
||||
*/
|
||||
udelay(42);
|
||||
/* Now wait for the response frame */
|
||||
udelay(FRAME_PERIOD_US);
|
||||
|
||||
/*
|
||||
* Wait for slot 2 to indicate data.
|
||||
*/
|
||||
timeout = 5000;
|
||||
/* And then wait an additional eight frame periods for data */
|
||||
timeout = FRAME_PERIOD_US * 8;
|
||||
do {
|
||||
udelay(1);
|
||||
cond_resched();
|
||||
v = readl(aaci->base + AACI_SLFR) & (SLFR_1RXV|SLFR_2RXV);
|
||||
} while ((v != (SLFR_1RXV|SLFR_2RXV)) && --timeout);
|
||||
|
||||
if (!timeout) {
|
||||
if (v != (SLFR_1RXV|SLFR_2RXV)) {
|
||||
dev_err(&aaci->dev->dev, "timeout on RX valid\n");
|
||||
v = ~0;
|
||||
goto out;
|
||||
|
@ -179,6 +182,7 @@ aaci_chan_wait_ready(struct aaci_runtime *aacirun, unsigned long mask)
|
|||
int timeout = 5000;
|
||||
|
||||
do {
|
||||
udelay(1);
|
||||
val = readl(aacirun->base + AACI_SR);
|
||||
} while (val & mask && timeout--);
|
||||
}
|
||||
|
@ -874,7 +878,7 @@ static int __devinit aaci_probe_ac97(struct aaci *aaci)
|
|||
* Give the AC'97 codec more than enough time
|
||||
* to wake up. (42us = ~2 frames at 48kHz.)
|
||||
*/
|
||||
udelay(42);
|
||||
udelay(FRAME_PERIOD_US * 2);
|
||||
|
||||
ret = snd_ac97_bus(aaci->card, 0, &aaci_bus_ops, aaci, &ac97_bus);
|
||||
if (ret)
|
||||
|
|
Загрузка…
Ссылка в новой задаче