[PATCH 05/10] S3C I2S: lrsync function made to work with IRQs disabled.
jassi brar
jassisinghbrar at gmail.com
Tue Sep 15 21:03:41 EDT 2009
On Wed, Sep 16, 2009 at 9:14 AM, Ben Dooks <ben-linux at fluff.org> wrote:
> On Tue, Sep 15, 2009 at 07:02:37PM +0900, Jassi wrote:
>> s3c2412_snd_lrsync() maybe reached with IRQs disabled and if LRCLK
>> is dead due to improper initialization of CPU or CODEC, the system
>> gets stuck in the loop because jiffies may never get updated.
>> Implemented counter based wait mechanism for atleast the same
>> timeout period.
>>
>> Signed-Off-by: Jassi <jassi.brar at samsung.com>
>> ---
>> sound/soc/s3c24xx/s3c-i2s-v2.c | 16 ++++++++++------
>> 1 files changed, 10 insertions(+), 6 deletions(-)
>>
>> diff --git a/sound/soc/s3c24xx/s3c-i2s-v2.c b/sound/soc/s3c24xx/s3c-i2s-v2.c
>> index aa7af0b..8865bc7 100644
>> --- a/sound/soc/s3c24xx/s3c-i2s-v2.c
>> +++ b/sound/soc/s3c24xx/s3c-i2s-v2.c
>> @@ -230,6 +230,8 @@ static void s3c2412_snd_rxctrl(struct s3c_i2sv2_info *i2s, int on)
>> pr_debug("%s: IIS: CON=%x MOD=%x FIC=%x\n", __func__, con, mod, fic);
>> }
>>
>> +#define msecs_to_loops(t) (loops_per_jiffy / 1000 * HZ * t)
>> +
>> /*
>> * Wait for the LR signal to allow synchronisation to the L/R clock
>> * from the codec. May only be needed for slave mode.
>> @@ -237,19 +239,21 @@ static void s3c2412_snd_rxctrl(struct s3c_i2sv2_info *i2s, int on)
>> static int s3c2412_snd_lrsync(struct s3c_i2sv2_info *i2s)
>> {
>> u32 iiscon;
>> - unsigned long timeout = jiffies + msecs_to_jiffies(5);
>> + unsigned long loops = msecs_to_loops(5);
>>
>> pr_debug("Entered %s\n", __func__);
>>
>> - while (1) {
>> + while (--loops) {
>> iiscon = readl(i2s->regs + S3C2412_IISCON);
>> if (iiscon & S3C2412_IISCON_LRINDEX)
>> break;
>>
>> - if (timeout < jiffies) {
>> - printk(KERN_ERR "%s: timeout\n", __func__);
>> - return -ETIMEDOUT;
>> - }
>> + cpu_relax();
>
> I don't think cpu_relax() gives a defined 'timeout' length, thus this
> loop is of a very indeterminate length of timeout.
Ofcourse the total delay is non-deterministic. Besides, there is no
hard limit on the amount of time we want to wait on lrsync. And this
non-deterministic delay comes into picture only when the I2S is
broken. It is second best option to simply hanging.
Total wait period is _atleast_ what we want, as is mentioned in the changelog.
Besides, i think we can do without the cpu_relax(), no?
More information about the linux-arm-kernel
mailing list