NetBSD Problem Report #39204

From www@NetBSD.org  Fri Jul 25 08:51:14 2008
Return-Path: <www@NetBSD.org>
Received: from mail.netbsd.org (mail.netbsd.org [204.152.190.11])
	by narn.NetBSD.org (Postfix) with ESMTP id 5937B63B89E
	for <gnats-bugs@gnats.netbsd.org>; Fri, 25 Jul 2008 08:51:14 +0000 (UTC)
Message-Id: <20080725085113.E435A63B880@narn.NetBSD.org>
Date: Fri, 25 Jul 2008 08:51:13 +0000 (UTC)
From: asau@inbox.ru
Reply-To: asau@inbox.ru
To: gnats-bugs@NetBSD.org
Subject: pad(4) device doesn't emit PCM data
X-Send-Pr-Version: www-1.0

>Number:         39204
>Category:       kern
>Synopsis:       pad(4) device doesn't emit PCM data, or emits broken data
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    nat
>State:          closed
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Fri Jul 25 08:55:00 +0000 2008
>Closed-Date:    Wed Apr 12 14:09:25 +0000 2017
>Last-Modified:  Wed Apr 12 14:09:25 +0000 2017
>Originator:     Aleksej Saushev
>Release:        NetBSD 4.99.67 i386
>Organization:
>Environment:
NetBSD 4.99.67 i386
>Description:
I'm trying to capture data sent to audio device.
After pad(4) reading /dev/pad0 should emit PCM data fed to /dev/sound0,
I run
	hexdump -C /dev/pad0 & mplayer some.mp3
and don't see any data. Starting in different order doesn't
affect the overall result.

dmesg reports following:

pad0: cv_timedwait_sig returned -3

>How-To-Repeat:
hexdump -C /dev/pad0 & mplayer -quiet some-audio-file
>Fix:

>Release-Note:

>Audit-Trail:
From: Jeff Rizzo <riz@netbsd.org>
To: gnats-bugs@netbsd.org
Cc: 
Subject: Re: kern/39204
Date: Mon, 28 Feb 2011 08:38:22 -0800

 This is a multi-part message in MIME format.
 --------------050402050908030604080308
 Content-Type: text/plain; charset=ISO-8859-1; format=flowed
 Content-Transfer-Encoding: 7bit

 >  I'm trying to capture data sent to audio device.
 >  After pad(4) reading /dev/pad0 should emit PCM data fed to /dev/sound0,
 >  I run
 >	hexdump -C /dev/pad0&  mplayer some.mp3
 >  and don't see any data. Starting in different order doesn't
 >  affect the overall result.


 Is this still a problem for you?  I notice that you're inputting the 
 audio to /dev/sound0, while pad0 usually corresponds to /dev/sound1.  
 Can you test again and close unless it's still a problem?

 +j


 --------------050402050908030604080308
 Content-Type: text/html; charset=ISO-8859-1
 Content-Transfer-Encoding: 7bit

 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
 <html>
   <head>

     <meta http-equiv="content-type" content="text/html; charset=ISO-8859-1">
   </head>
   <body text="#000000" bgcolor="#ffffff">
     <span class="Apple-style-span" style="border-collapse: separate;
       color: rgb(0, 0, 0); font-family: Times; font-style: normal;
       font-variant: normal; font-weight: normal; letter-spacing: normal;
       line-height: normal; orphans: 2; text-indent: 0px; text-transform:
       none; white-space: normal; widows: 2; word-spacing: 0px;
       font-size: medium;">
       <pre>&gt; I'm trying to capture data sent to audio device.
 &gt; After pad(4) reading /dev/pad0 should emit PCM data fed to /dev/sound0,
 &gt; I run
 &gt;	hexdump -C /dev/pad0 &amp; mplayer some.mp3
 &gt; and don't see any data. Starting in different order doesn't
 &gt; affect the overall result.
 </pre>
     </span><br>
     Is this still a problem for you?&nbsp; I notice that you're inputting the
     audio to /dev/sound0, while pad0 usually corresponds to
     /dev/sound1.&nbsp; Can you test again and close unless it's still a
     problem?<br>
     <br>
     +j<br>
     &nbsp;<br class="Apple-interchange-newline">
   </body>
 </html>

 --------------050402050908030604080308--

State-Changed-From-To: open->feedback
State-Changed-By: riz@NetBSD.org
State-Changed-When: Tue, 01 Mar 2011 21:13:22 +0000
State-Changed-Why:
I requested feedback from the user.


From: Aleksej Saushev <asau@inbox.ru>
To: gnats-bugs@NetBSD.org
Cc: kern-bug-people@netbsd.org, netbsd-bugs@netbsd.org, gnats-admin@netbsd.org, riz@NetBSD.org
Subject: Re: kern/39204 (pad(4) device doesn't emit PCM data)
Date: Wed, 02 Mar 2011 01:25:07 +0300

 It became worse. With the testcase as above, I observe panic.
 Backtrace is recorded manually:

 turnstile_block
 mutex_vector_enter
 cv_timedwait_sync
 ?
 cdev_read
 spec_read
 VOP_READ
 dofileread
 sys_read

 This is NetBSD 5.99.47 i386 GENERIC built today from fresh source.

 I couldn't get crash dump, but when I typed "sync" in ddb, I've got
 the second panic.

From: Jeff Rizzo <riz@NetBSD.org>
To: gnats-bugs@NetBSD.org
Cc: 
Subject: Re: kern/39204 (pad(4) device doesn't emit PCM data)
Date: Tue, 01 Mar 2011 16:32:54 -0800

 I think this may be two different issues, and think there may still be a
 misunderstanding.  Can you please provide a full dmesg from the system
 in question, as well as explicitly cut-and-paste the commandline that
 gives you trouble?


From: Nat Sloss <nathanialsloss@yahoo.com.au>
To: gnats-bugs@netbsd.org
Cc: 
Subject: Re: kern/39204
Date: Tue, 13 Mar 2012 18:39:04 +1100

 Hi.

 I can confirm this behavior of pad audio on 6.99.3 and 5.99.58.

 In one terminal run: cat /dev/pad0 > test.dat
 In another terminal run: mplayer -ao:oss /dev/audio1 your.mp3
 Then interrupt cat when mplayer has finished playing.

 Finally play back the audio with: audioplay -f -e slinear_le -P 16 -c 2 -s 
 44100 test.dat

 And you'll probably notice silence or broken up audio it is worse if run from 
 or saving to usb.

 I have as yet to find a solution.  But this problem makes pad unusable.

 Regards,

 Nat. 

From: David Holland <dholland-bugs@netbsd.org>
To: gnats-bugs@NetBSD.org
Cc: 
Subject: Re: kern/39204
Date: Sun, 18 Mar 2012 21:29:51 +0000

 On Tue, Mar 13, 2012 at 07:45:02AM +0000, Nat Sloss wrote:
  >  I can confirm this behavior of pad audio on 6.99.3 and 5.99.58.
  >  
  >  In one terminal run: cat /dev/pad0 > test.dat
  >  In another terminal run: mplayer -ao:oss /dev/audio1 your.mp3
  >  Then interrupt cat when mplayer has finished playing.
  >  
  >  Finally play back the audio with: audioplay -f -e slinear_le -P 16 -c 2 -s 
  >  44100 test.dat
  >  
  >  And you'll probably notice silence or broken up audio it is worse if run from 
  >  or saving to usb.
  >  
  >  I have as yet to find a solution.  But this problem makes pad unusable.

 This seems like a different problem from the original (no output) or
 second (panic) cases...

 -- 
 David A. Holland
 dholland@netbsd.org

From: Matthew Mondor <mm_lists@pulsar-zone.net>
To: gnats-bugs@netbsd.org
Cc: 
Subject: Re: kern/39204: pad(4) device doesn't emit PCM data
Date: Thu, 22 Mar 2012 05:29:31 -0400

 Please see related kern/46232 for the panic problem
 -- 
 Matt

From: Matthew Mondor <mm_lists@pulsar-zone.net>
To: gnats-bugs@NetBSD.org
Cc: 
Subject: Re: kern/39204: pad(4) device doesn't emit PCM data
Date: Mon, 16 Apr 2012 18:38:15 -0400

 On Thu, 22 Mar 2012 09:30:06 +0000 (UTC)
 Matthew Mondor <mm_lists@pulsar-zone.net> wrote:

 > The following reply was made to PR kern/39204; it has been noted by GNATS.
 > 
 > From: Matthew Mondor <mm_lists@pulsar-zone.net>
 > To: gnats-bugs@netbsd.org
 > Cc: 
 > Subject: Re: kern/39204: pad(4) device doesn't emit PCM data
 > Date: Thu, 22 Mar 2012 05:29:31 -0400
 > 
 >  Please see related kern/46232 for the panic problem

 The panic issue in kern/46232 should now be fixed.  As for the other
 issue I had with broken data, I think that this PR seems related.

 However, I just did a test now and interestingly I didn't get obviously
 broken data:

 I first started a dd command to dump pad0 to file, which as expected
 blocks waiting for data:

 dd if=/dev/pad0 of=pad.raw

 Then I started another process to generate some audio to the audio1
 device:

 mplayer -ao sun:/dev/audio1 foo.mp4

 Which I left running a bit, while it was possible to see the pad.raw
 file growing.  I then stopped this last process after a minute or so,
 and noticed that the pad.raw file was no longer growing, the dd process
 blocking for more data.  I then killed the dd process.

 I then tested the result by playing pad.raw:

 audioplay -f -e slinear_le -P 16 -c 2 -s 44100 pad.raw

 And this time there seemed to be problem whatsoever.  I then reiterated
 the process a second time, and the results still seemed fine.

 A third time, this time playing an ogg-vorbis file with mplayer, in
 which case the results were only slightly skipping.  A fourth time,
 playing an mp3, also with slight skipping approximately 3 times a
 second.

 A fith test, this time with an mp4 like for the first, but another
 one.  I also could hear small skipping.  It's possible that skipping
 did occur in the first two tests, but that I couldn't hear it because
 of the type of music.  In any case, it wasn't huge skipping anymore as
 I had described in kern/46232.

 The last test I did was playing a single-channel audio wav file to
 audio1.  In this case, the time required to play it was much longer
 than expected, at which point I stopped the process with a break.
 Interestingly, only about half a second of output have been recorded.
 I remember being able to play mono samples while recording from pad0,
 in which case the first channel seemed duplicated on the second, with
 the pad(4) output always stereo (see kern/44677).

 Where skipping occurs, the bytes are still set at 0x00.  By looking at
 the data, I could see two such skip of exactly 1024 bytes, but didn't
 check if all other gaps were this size.  According to dd, the default
 block size would be 512.  If I try using cat(1) rather than dd(1), I
 only get a huge file of 0x00 bytes created at the maximum speed the
 disk allows, whenever writing to audio1 occurs.
 -- 
 Matt

State-Changed-From-To: feedback->open
State-Changed-By: dholland@NetBSD.org
State-Changed-When: Tue, 17 Apr 2012 17:02:08 +0000
State-Changed-Why:
A problem definitely exists.
(I've updated the synopsis)


From: David Holland <dholland-bugs@netbsd.org>
To: gnats-bugs@netbsd.org
Cc: 
Subject: Re: kern/39204 (pad(4) device doesn't emit PCM data, or emits broken
 data)
Date: Tue, 17 Apr 2012 17:08:41 +0000

 On Tue, Apr 17, 2012 at 05:02:10PM +0000, dholland@NetBSD.org wrote:
  > State-Changed-From-To: feedback->open
  > State-Changed-By: dholland@NetBSD.org
  > State-Changed-When: Tue, 17 Apr 2012 17:02:08 +0000
  > State-Changed-Why:
  > A problem definitely exists.
  > (I've updated the synopsis)

 There is also, as described in the beginning part of kern/46232, a
 problem where the dd process reading from pad becomes unkillably
 wedged.

 I suspect this problem is related (IOW, one set of locking bugs with
 varying symptoms) but it might not be and shouldn't be lost track of.

 -- 
 David A. Holland
 dholland@netbsd.org

From: Matthew Mondor <mm_lists@pulsar-zone.net>
To: gnats-bugs@NetBSD.org
Cc: 
Subject: Re: kern/39204 (pad(4) device doesn't emit PCM data, or emits
 broken data)
Date: Tue, 17 Apr 2012 15:26:55 -0400

 On Tue, 17 Apr 2012 17:10:05 +0000 (UTC)
 David Holland <dholland-bugs@netbsd.org> wrote:

 >   > (I've updated the synopsis)

 Thanks for the update,

 >  
 >  There is also, as described in the beginning part of kern/46232, a
 >  problem where the dd process reading from pad becomes unkillably
 >  wedged.

 I've not yet observed this hang anymore since the kern/46232 locking
 fixes.
 -- 
 Matt

From: David Holland <dholland-bugs@netbsd.org>
To: gnats-bugs@NetBSD.org
Cc: 
Subject: Re: kern/39204 (pad(4) device doesn't emit PCM data, or emits broken
 data)
Date: Wed, 18 Apr 2012 03:44:53 +0000

 On Tue, Apr 17, 2012 at 07:30:05PM +0000, Matthew Mondor wrote:
  >  >  There is also, as described in the beginning part of kern/46232, a
  >  >  problem where the dd process reading from pad becomes unkillably
  >  >  wedged.
  >  
  >  I've not yet observed this hang anymore since the kern/46232 locking
  >  fixes.

 Good... if it doesn't show again we can call it fixed.

 -- 
 David A. Holland
 dholland@netbsd.org

From: Nat Sloss <nathanialsloss@yahoo.com.au>
To: gnats-bugs@netbsd.org
Cc: 
Subject: Re: kern/39204
Date: Thu, 26 Apr 2012 11:23:20 +1000

 Hi,

 I did notice in 6.99.5 that the audio process mplayer -ao sun:/audio1 your.mp3 
 failed to start and halts when skipping audio in mplayer and caused a system 
 reset on me.  Three distinct problems that are related.

 If you try mplayer -ao oss all is fine but with the sun driver -ao sun the 
 audio process dosen't start sometimes and the mplayer and cat /dev/pad 
 processes freeze and cant be killed.

 Also if you skip audio in the mplayer process if audio starts by pressing up 
 arrow or right arrow the output freezes and sometimes the process can be 
 killed.

 What I did was to apply the same patch as in kern/45776 which affected 
 start_output on btsco audio and it fixed the problem.

 I hope this helps.

 Regards,

 Nat.

From: Nat Sloss <nathanialsloss@yahoo.com.au>
To: gnats-bugs@netbsd.org
Cc: 
Subject: Re: kern/39204
Date: Fri, 11 May 2012 23:57:39 +1000

 Hi,

 I think I fixed the problem.  I had broken audio when booted from and saving 
 to harddrive, more so when booted from and saving to usb, and it was even 
 more broken in emulated in qemu. 

 What fixed it was adding a delay before the call to start output in pad_read.  
 The delay would work for one of the scenarios above but not for the others.

 More delay was needed for usb and qemu.  And then I discovered that the writer 
 was only scheduled at the end of audio pint.  So calling start output in 
 quick succession resulted in silence being copied.

 I also found that audio would skip on small reads less than PADBLKSIZE and 
 this was because of the second call to start output outside of the while loop 
 in pad_read as it was no longer necessary as there was a delay ensuring that 
 data was in the stream.

 So after attempting many different things I came up with this patch:

 --- pad.c.orig  2012-01-27 16:58:34.000000000 +1100
 +++ pad.c       2012-05-11 23:35:22.000000000 +1000
 @@ -54,6 +54,7 @@
  #define PADUNIT(x)     minor(x)

  extern struct cfdriver pad_cd;
 +extern struct cfdriver audio_cd;

  typedef struct pad_block {
         uint8_t         *pb_ptr;
 @@ -333,14 +334,21 @@
  {
         pad_softc_t *sc;
         pad_block_t pb;
 +       struct audio_softc *ac;
         void (*intr)(void *);
         void *intrarg;
 -       int err;
 +       int err, i, used;

         sc = device_lookup_private(&pad_cd, PADUNIT(dev));
         if (sc == NULL)
                 return ENXIO;

 +       for (i = 0; i < 256; i++) {
 +               ac = device_lookup_private(&audio_cd, i);
 +               if (ac->hw_hdl == sc)
 +                       break;
 +       }
 +
         err = 0;

         mutex_enter(&sc->sc_lock);
 @@ -356,6 +364,18 @@
                         continue;
                 }

 +               mutex_exit(&sc->sc_lock);
 +               i = 0;
 +               while ((used = audio_stream_get_used(ac->sc_pustream)) <
 +                   PAD_BLKSIZE * 2 && used < ac->sc_pr.usedlow) {
 +                       softint_schedule(ac->sc_sih_wr);
 +                       DELAY(250);
 +                       i++;
 +                       if (i > 8000)
 +                               break;
 +               }
 +               mutex_enter(&sc->sc_lock);
 +
                 if (intr) {
                         mutex_enter(&sc->sc_intr_lock);
                         (*intr)(intrarg);
 @@ -374,11 +394,6 @@
                 intrarg = sc->sc_intrarg;
         }

 -       if (intr) {
 -               mutex_enter(&sc->sc_intr_lock);
 -               (*intr)(intrarg);
 -               mutex_exit(&sc->sc_intr_lock);
 -       }
         mutex_exit(&sc->sc_lock);

         return err;


 This solves the problem for harddrive with 1 GHz cpu, usb and qemu situations.  
 If audio is not broken for you try using pad in an qemu emulation and you 
 will find with the un-patched version is gives broken audio, but with the 
 patch above it is fixed.

 Note:  This patch is my own work which I submit freely under the NetBSD 
 license.

 I hope this helps.

 Regards,

 Nat.

From: Matthew Mondor <mm_lists@pulsar-zone.net>
To: gnats-bugs@NetBSD.org
Cc: 
Subject: Re: kern/39204 (pad(4) device doesn't emit PCM data)
Date: Sat, 12 May 2012 18:06:14 -0400

 On Fri, 11 May 2012 14:00:08 +0000 (UTC)
 Nat Sloss <nathanialsloss@yahoo.com.au> wrote:

 >  This solves the problem for harddrive with 1 GHz cpu, usb and qemu situations.  
 >  If audio is not broken for you try using pad in an qemu emulation and you 
 >  will find with the un-patched version is gives broken audio, but with the 
 >  patch above it is fixed.

 Although I don't use qemu or uaudio, I thought I'd adapt the patch and
 try it on netbsd-6 to see if this also helps against the skipping I
 observed.  Unfortunately, netbsd-6 doesn't have
 uaudio_stream_get_used() however.  I could test the patch against
 -current instead then, although I'll have to do that later.

 It might make sense that the audio softint might need such a reschedule
 under other non-uaudio circumstances, perhaps...

 Thanks,
 -- 
 Matt

From: Nat Sloss <nathanialsloss@yahoo.com.au>
To: gnats-bugs@netbsd.org
Cc: 
Subject: Re: kern/39204
Date: Sun, 13 May 2012 18:36:28 +1000

 Hi,

 It wasn't uaudio but rather booting from and saving the resulting pad output 
 to a usb drive on real hardware or qemu emulation.  I think it has something 
 to do with the speed of the device its reading from and writing to.

 Sorry for the confusion.

 Regards,

 Nat.

 PS:  I thought it would be better if a conditional variable was added that 
 signalled when the audio writer is finished so pad_read could sleep on that 
 variable instead.  I don't know how practical it would be though and using 
 delay works just fine :)

From: matthew green <mrg@eterna.com.au>
To: gnats-bugs@NetBSD.org
Cc: kern-bug-people@netbsd.org, gnats-admin@netbsd.org,
    netbsd-bugs@netbsd.org, asau@inbox.ru
Subject: re: kern/39204
Date: Sun, 13 May 2012 18:53:26 +1000

 >  PS:  I thought it would be better if a conditional variable was added that 
 >  signalled when the audio writer is finished so pad_read could sleep on that 
 >  variable instead.  I don't know how practical it would be though and using 
 >  delay works just fine :)

 actually, the patch as-is is pretty gross.  :)

 - the hard coded "256" for unit is ugly.

 - the calls into audio.c directly are layer violations.  (ie, this and
   the above mean you shouldn't go looking for a struct audio_softc *.)

 - the loop of upto 8000 calls to DELAY(500) with softint_schedule()
   probably only works on SMP systems.  i'm not sure a UP system would
   leave this code section normally without completing the loop.

 - said loop is very CPU wasteful, due to the 8000 DELAY() calls.  the
   slower the backend is, the worse the CPU usage will be (kind of like
   PIO vs DMA for IDE controllers :-)


 do you think you could work on a patch that is more like the text i
 quoted above?  that would be great :)

From: Nat Sloss <nathanialsloss@yahoo.com.au>
To: gnats-bugs@netbsd.org
Cc: 
Subject: Re: kern/39204
Date: Mon, 14 May 2012 22:26:11 +1000

 Hi.

 Thank you for the guidelines.  I'm still learning.  I'm more of a hack than a 
 programmer though :)

 I hope this is better:

 ===================================================================
 RCS file: /cvsroot/src/sys/dev/pad/pad.c,v
 retrieving revision 1.19
 diff -u -r1.19 pad.c
 --- pad/pad.c   24 Nov 2011 01:54:08 -0000      1.19
 +++ pad/pad.c   14 May 2012 12:20:17 -0000
 @@ -374,11 +374,6 @@
                 intrarg = sc->sc_intrarg;
         }

 -       if (intr) {
 -               mutex_enter(&sc->sc_intr_lock);
 -               (*intr)(intrarg);
 -               mutex_exit(&sc->sc_intr_lock);
 -       }
         mutex_exit(&sc->sc_lock);

         return 
 err;===================================================================
 RCS file: /cvsroot/src/sys/dev/audio.c,v
 retrieving revision 1.261
 diff -u -r1.261 audio.c
 --- audio.c     30 Apr 2012 02:16:46 -0000      1.261
 +++ audio.c     14 May 2012 12:21:06 -0000
 @@ -401,6 +401,7 @@
         cv_init(&sc->sc_rchan, "audiord");
         cv_init(&sc->sc_wchan, "audiowr");
         cv_init(&sc->sc_lchan, "audiolk");
 +       cv_init(&sc->sc_dataready, "audiordy");

         if (hwp == 0 || hwp->get_locks == 0) {
                 printf(": missing method\n");
 @@ -760,6 +761,7 @@
         cv_destroy(&sc->sc_rchan);
         cv_destroy(&sc->sc_wchan);
         cv_destroy(&sc->sc_lchan);
 +       cv_destroy(&sc->sc_dataready);

         return 0;
  }
 @@ -2211,12 +2213,15 @@
                     sc, uio->uio_resid, 
 audio_stream_get_used(sc->sc_pustream),
                     sc->sc_pr.usedhigh));
         cb = &sc->sc_pr;
 -       if (cb->mmapped)
 -               return EINVAL;
 +       if (cb->mmapped) {
 +               error = EINVAL;
 +               goto audio_write_end;
 +       }

         if (uio->uio_resid == 0) {
                 sc->sc_eof++;
 -               return 0;
 +               error = 0;
 +               goto audio_write_end;
         }

  #ifdef AUDIO_PM_IDLE
 @@ -2232,7 +2237,8 @@
                 uio->uio_offset += uio->uio_resid;
                 uio->uio_resid = 0;
                 DPRINTF(("audio_write: half-dpx read busy\n"));
 -               return 0;
 +               error = 0;
 +               goto audio_write_end;
         }

         if (!(sc->sc_mode & AUMODE_PLAY_ALL) && sc->sc_playdrop > 0) {
 @@ -2241,8 +2247,10 @@
                 uio->uio_offset += n;
                 uio->uio_resid -= n;
                 sc->sc_playdrop -= n;
 -               if (uio->uio_resid == 0)
 -                       return 0;
 +               if (uio->uio_resid == 0) {
 +                       error = 0;
 +                       goto audio_write_end;
 +               }
         }

         /**
 @@ -2265,13 +2273,15 @@
                                      "hiwat=%d\n", used,
                                      cb->usedlow, cb->usedhigh));
                         mutex_exit(sc->sc_intr_lock);
 -                       if (ioflag & IO_NDELAY)
 -                               return EWOULDBLOCK;
 +                       if (ioflag & IO_NDELAY) {
 +                               error = EWOULDBLOCK;
 +                               goto audio_write_end;
 +                       }
                         error = audio_waitio(sc, &sc->sc_wchan);
                         if (sc->sc_dying)
                                 error = EIO;
                         if (error)
 -                               return error;
 +                               goto audio_write_end;
                         mutex_enter(sc->sc_intr_lock);
                 }
                 inp = cb->s.inp;
 @@ -2298,6 +2308,7 @@
                         cc = stream.end - stream.start;
                         error = fetcher->fetch_to(sc, fetcher, &stream, cc);
                 }
 +
                 mutex_enter(sc->sc_intr_lock);
                 if (sc->sc_npfilters > 0) {
                         cb->fstamp += ufetcher.last_used
 @@ -2343,6 +2354,8 @@
         }
         mutex_exit(sc->sc_intr_lock);

 +audio_write_end:
 +       cv_broadcast(&sc->sc_dataready);
         return error;
  }

 @@ -2791,7 +2804,8 @@
         if (!audio_can_playback(sc))
                 return EINVAL;

 -       if (!sc->sc_pr.mmapped && used < sc->sc_pr.blksize) {
 +       if (!sc->sc_pr.mmapped && used < sc->sc_pr.blksize &&
 +           sc->hw_if->trigger_output != NULL) {
                 cv_broadcast(&sc->sc_wchan);
                 DPRINTF(("%s: wakeup and return\n", __func__));
                 return 0;
 @@ -2928,6 +2942,7 @@
         int cc, used;
         int blksize;
         int error;
 +       int i, timeout;

         sc = v;

 @@ -3042,8 +3057,28 @@
                      sc->sc_mode, cb->pause,
                      audio_stream_get_used(sc->sc_pustream), cb->usedlow));
         if ((sc->sc_mode & AUMODE_PLAY) && !cb->pause) {
 -               if (audio_stream_get_used(sc->sc_pustream) <= cb->usedlow)
 +               if ((used = audio_stream_get_used(sc->sc_pustream)) <= 
 cb->usedlow)
                         softint_schedule(sc->sc_sih_wr);
 +
 +               if (used < blksize && device_is_a(sc->sc_dev, "pad")) {
 +                       i = 0;
 +                       timeout = mstohz(5);
 +                       if (timeout == 0)
 +                               timeout = 1;
 +
 +                       mutex_exit(sc->sc_intr_lock);
 +                       while ((used = audio_stream_get_used(sc->sc_pustream))
 +                           < blksize && cb->usedlow > blksize) {
 +                               softint_schedule(sc->sc_sih_wr);
 +                               error = cv_timedwait_sig(&sc->sc_dataready, 
 sc->sc_lock, timeout);
 +                               i++;
 +                               if (error != 0 && error != EWOULDBLOCK)
 +                                       break;
 +                               if (i > 200)
 +                                       break;
 +                       }
 +                       mutex_enter(sc->sc_intr_lock);
 +               }
         }

         /* Possible to return one or more "phantom blocks" now. */

 ===================================================================
 RCS file: /cvsroot/src/sys/dev/audiovar.h,v
 retrieving revision 1.46
 diff -u -r1.46 audiovar.h
 --- audiovar.h  23 Nov 2011 23:07:31 -0000      1.46
 +++ audiovar.h  14 May 2012 12:23:06 -0000
 @@ -147,6 +147,7 @@
         kcondvar_t      sc_rchan;
         kcondvar_t      sc_wchan;
         kcondvar_t      sc_lchan;
 +       kcondvar_t      sc_dataready;
         int             sc_dvlock;
         bool            sc_dying;

 I tested this with the scenarios mentioned before and it works even better 
 than my first attempt :)

 Note:  This patch is my own work which I submit under the NetBSD license.

 I hope this helps and thanks for the feedback.  May my future patches be even 
 better.

 Regards,

 Nat.

From: Nat Sloss <nathanialsloss@yahoo.com.au>
To: gnats-bugs@netbsd.org
Cc: 
Subject: Re: kern/39204
Date: Tue, 15 May 2012 23:22:02 +1000

 Hi.

 I have been working on a better patch so I came up with this:

 pad.c - same as version 2.
 audiovar.c - same as version 2.

 audio.c as follows:
 ===================================================================
 RCS file: /cvsroot/src/sys/dev/audio.c,v
 retrieving revision 1.261
 diff -u -r1.261 audio.c
 --- audio.c     30 Apr 2012 02:16:46 -0000      1.261
 +++ audio.c     15 May 2012 13:22:46 -0000
 @@ -401,6 +401,7 @@
         cv_init(&sc->sc_rchan, "audiord");
         cv_init(&sc->sc_wchan, "audiowr");
         cv_init(&sc->sc_lchan, "audiolk");
 +       cv_init(&sc->sc_dataready, "audiordy");

         if (hwp == 0 || hwp->get_locks == 0) {
                 printf(": missing method\n");
 @@ -760,6 +761,7 @@
         cv_destroy(&sc->sc_rchan);
         cv_destroy(&sc->sc_wchan);
         cv_destroy(&sc->sc_lchan);
 +       cv_destroy(&sc->sc_dataready);

         return 0;
  }
 @@ -1780,6 +1782,7 @@
         KASSERT(mutex_owned(sc->sc_lock));
         KASSERT(mutex_owned(sc->sc_intr_lock));

 +       cv_broadcast(&sc->sc_dataready);
         DPRINTF(("audio_drain: enter busy=%d\n", sc->sc_pbus));
         cb = &sc->sc_pr;
         if (cb->mmapped)
 @@ -1824,6 +1827,7 @@
                          audio_stream_get_used(&sc->sc_pr.s), cb->drops));
                 mutex_exit(sc->sc_intr_lock);
                 error = audio_waitio(sc, &sc->sc_wchan);
 +               cv_broadcast(&sc->sc_dataready);
                 mutex_enter(sc->sc_intr_lock);
                 if (sc->sc_dying)
                         error = EIO;
 @@ -2001,6 +2005,7 @@
         }
         if (sc->sc_pbus) {
                 cv_broadcast(&sc->sc_wchan);
 +               cv_broadcast(&sc->sc_dataready);
                 sc->hw_if->halt_output(sc->hw_hdl);
                 sc->sc_pbus = false;
                 sc->sc_pr.pause = false;
 @@ -2298,6 +2303,7 @@
                         cc = stream.end - stream.start;
                         error = fetcher->fetch_to(sc, fetcher, &stream, cc);
                 }
 +
                 mutex_enter(sc->sc_intr_lock);
                 if (sc->sc_npfilters > 0) {
                         cb->fstamp += ufetcher.last_used
 @@ -2343,6 +2349,7 @@
         }
         mutex_exit(sc->sc_intr_lock);

 +       cv_broadcast(&sc->sc_dataready);
         return error;
  }

 @@ -2783,7 +2790,7 @@
         KASSERT(mutex_owned(sc->sc_lock));
         KASSERT(mutex_owned(sc->sc_intr_lock));

 -       used = audio_stream_get_used(&sc->sc_pr.s);
 +       used = audio_stream_get_used(sc->sc_pustream);
         DPRINTF(("audiostartp: start=%p used=%d(hi=%d blk=%d) mmapped=%d\n",
                  sc->sc_pr.s.start, used, sc->sc_pr.usedhigh,
                  sc->sc_pr.blksize, sc->sc_pr.mmapped));
 @@ -3042,8 +3049,15 @@
                      sc->sc_mode, cb->pause,
                      audio_stream_get_used(sc->sc_pustream), cb->usedlow));
         if ((sc->sc_mode & AUMODE_PLAY) && !cb->pause) {
 -               if (audio_stream_get_used(sc->sc_pustream) <= cb->usedlow)
 +               if ((used = audio_stream_get_used(sc->sc_pustream)) <= 
 cb->usedlow) {
                         softint_schedule(sc->sc_sih_wr);
 +
 +                       if (used < blksize && device_is_a(sc->sc_dev, "pad")) 
 {
 +                               mutex_exit(sc->sc_intr_lock);
 +                               cv_wait_sig(&sc->sc_dataready, sc->sc_lock);
 +                               mutex_enter(sc->sc_intr_lock);
 +                       }
 +               }
         }

         /* Possible to return one or more "phantom blocks" now. */


 I hope this helps.

 Regards,

 Nat.

From: "Nathanial Sloss" <nat@netbsd.org>
To: gnats-bugs@gnats.NetBSD.org
Cc: 
Subject: PR/39204 CVS commit: src/sys/dev/pad
Date: Fri, 26 Feb 2016 13:17:04 +0000

 Module Name:	src
 Committed By:	nat
 Date:		Fri Feb 26 13:17:04 UTC 2016

 Modified Files:
 	src/sys/dev/pad: pad.c padvar.h

 Log Message:
 Allow reads from pad(4) less or greater than PAD_BLKSIZE.

 Ensure that audio data is ready before reading.
 Addresses PR 39204.

 OK jmcneil@.


 To generate a diff of this commit:
 cvs rdiff -u -r1.23 -r1.24 src/sys/dev/pad/pad.c
 cvs rdiff -u -r1.5 -r1.6 src/sys/dev/pad/padvar.h

 Please note that diffs are not public domain; they are subject to the
 copyright notices on the relevant files.

Responsible-Changed-From-To: kern-bug-people->nat
Responsible-Changed-By: nat@NetBSD.org
Responsible-Changed-When: Tue, 07 Feb 2017 02:08:33 +0000
Responsible-Changed-Why:
I'll handle this.


State-Changed-From-To: open->feedback
State-Changed-By: nat@NetBSD.org
State-Changed-When: Tue, 07 Feb 2017 02:08:33 +0000
State-Changed-Why:
A commit to address this was made some time ago.
Does it work now?


State-Changed-From-To: feedback->closed
State-Changed-By: nat@NetBSD.org
State-Changed-When: Wed, 12 Apr 2017 14:09:25 +0000
State-Changed-Why:
Submitter has not replied.  Assume this is fixed.


>Unformatted:

NetBSD Home
NetBSD PR Database Search

(Contact us) $NetBSD: query-full-pr,v 1.39 2013/11/01 18:47:49 spz Exp $
$NetBSD: gnats_config.sh,v 1.8 2006/05/07 09:23:38 tsutsui Exp $
Copyright © 1994-2014 The NetBSD Foundation, Inc. ALL RIGHTS RESERVED.