Have dmabuf.c match the roll-back in soundcard.c. We should be making

better noises again.
Submitted by:	Sujal Patel <smpatel@wam.umd.edu>
This commit is contained in:
jkh 1995-03-05 08:10:28 +00:00
parent b71189ccd4
commit f652677290
3 changed files with 105 additions and 20 deletions

View File

@ -11,7 +11,7 @@ device snd3 at isa? port 0x388 irq 10 drq 6 vector pasintr # PAS
device snd2 at isa? port 0x220 irq 7 drq 1 vector sbintr # SB
device snd6 at isa? port 0x220 irq 7 drq 5 vector sbintr # SB16 ?
device snd7 at isa? port 0x300 # YM3812 ???
device snd1 at isa? port 0x388 # ADLIB
device snd1 at isa? port 0x388 # YM3812
device snd10 at isa? port 0x530 irq 10 drq 1 vector adintr # MSS
Then add some of these (no need for EXCLUDE_BLAH anymore):
@ -20,7 +20,6 @@ Then add some of these (no need for EXCLUDE_BLAH anymore):
options AUDIO_PAS
options AUDIO_SB
options AUDIO_ADLIB
options AUDIO_GUS
options AUDIO_MPU401
options AUDIO_UART6850

View File

@ -25,6 +25,7 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* $Id: dmabuf.c,v 1.11 1995/02/13 22:49:04 jkh Exp $
*/
#include "sound_config.h"
@ -32,16 +33,20 @@
#ifdef CONFIGURE_SOUNDCARD
#include "sound_calls.h"
#ifdef __FreeBSD__
#include <machine/soundcard.h>
extern struct selinfo selinfo[SND_NDEVS>>4];
#endif
#if !defined(EXCLUDE_AUDIO) || !defined(EXCLUDE_GUS)
DEFINE_WAIT_QUEUES (dev_sleeper[MAX_AUDIO_DEV], dev_sleep_flag[MAX_AUDIO_DEV]);
static struct dma_buffparms dmaps[MAX_AUDIO_DEV] =
{{0}}; /*
{0}; /*
* Primitive way to allocate
* such a large array.
* Needs dynamic run-time allocation.
* Needs dynamic run-time alloction.
*/
static void
@ -78,7 +83,7 @@ reorganize_buffers (int dev)
sz = sr * nc * sz;
/*
* Compute a buffer size for time not exceeding 1 second.
* Compute a buffer size for time not exeeding 1 second.
* Usually this algorithm gives a buffer size for 0.5 to 1.0 seconds
* of sound (using the current speed, sample size and #channels).
*/
@ -106,8 +111,8 @@ reorganize_buffers (int dev)
else
{
/*
* The process has specified the buffer size with SNDCTL_DSP_SETFRAGMENT or
* the buffer size computation has already been done.
* The process has specified the buffer sice with SNDCTL_DSP_SETFRAGMENT or
* the buffer sice computation has already been done.
*/
if (dmap->fragment_size > audio_devs[dev]->buffsize)
dmap->fragment_size = audio_devs[dev]->buffsize;
@ -294,11 +299,10 @@ DMAbuf_release (int dev, int mode)
return 0;
}
int
DMAbuf_getrdbuffer (int dev, char **buf, int *len)
static int
DMAbuf_start_input(int dev)
{
unsigned long flags;
int err = EIO;
struct dma_buffparms *dmap = audio_devs[dev]->dmap;
DISABLE_INTR (flags);
@ -320,7 +324,7 @@ DMAbuf_getrdbuffer (int dev, char **buf, int *len)
if (!(dmap->flags & DMA_ALLOC_DONE))
reorganize_buffers (dev);
if (!dmap->dma_mode)
if (dmap->dma_mode)
{
int err;
@ -341,14 +345,32 @@ DMAbuf_getrdbuffer (int dev, char **buf, int *len)
!(dmap->flags & DMA_STARTED));
dmap->flags |= DMA_ACTIVE | DMA_STARTED;
}
}
RESTORE_INTR (flags);
return 0;
}
int
DMAbuf_getrdbuffer (int dev, char **buf, int *len)
{
unsigned long flags;
int err = EIO;
struct dma_buffparms *dmap = audio_devs[dev]->dmap;
DISABLE_INTR (flags);
if (!dmap->qlen)
{
if(err = DMAbuf_start_input(dev))
return err;
/* Wait for the next block */
err = EIO;
DO_SLEEP (dev_sleeper[dev], dev_sleep_flag[dev], 2 * HZ);
if (TIMED_OUT (dev_sleeper[dev], dev_sleep_flag[dev]))
{
printk ("Sound: DMA timed out - IRQ/DRQ config error?\n");
err = EIO;
SET_ABORT_FLAG (dev_sleeper[dev], dev_sleep_flag[dev]);
}
else
@ -425,7 +447,7 @@ DMAbuf_ioctl (int dev, unsigned int cmd, unsigned int arg, int local)
}
if (dmap->subdivision != 0 ||
dmap->fragment_size)/* Too late to change */
dmap->fragment_size)/* Loo late to change */
return RET_ERROR (EINVAL);
if (fact > MAX_REALTIME_FACTOR)
@ -448,7 +470,7 @@ DMAbuf_ioctl (int dev, unsigned int cmd, unsigned int arg, int local)
return RET_ERROR (EIO);
if (dmap->subdivision != 0 ||
dmap->fragment_size)/* Too late to change */
dmap->fragment_size)/* Loo late to change */
return RET_ERROR (EINVAL);
bytes = fact & 0xffff;
@ -482,6 +504,7 @@ DMAbuf_ioctl (int dev, unsigned int cmd, unsigned int arg, int local)
return audio_devs[dev]->ioctl (dev, cmd, arg, local);
}
/* NOTREACHED */
return RET_ERROR (EIO);
}
@ -782,6 +805,10 @@ DMAbuf_outputintr (int dev, int event_type)
WAKE_UP (dev_sleeper[dev], dev_sleep_flag[dev]);
}
RESTORE_INTR (flags);
#ifdef __FreeBSD__
if(selinfo[dev].si_pid)
selwakeup(&selinfo[dev]);
#endif
}
void
@ -821,6 +848,10 @@ DMAbuf_inputintr (int dev)
WAKE_UP (dev_sleeper[dev], dev_sleep_flag[dev]);
}
RESTORE_INTR (flags);
#ifdef __FreeBSD__
if(selinfo[dev].si_pid)
selwakeup(&selinfo[dev]);
#endif
}
int
@ -859,6 +890,49 @@ DMAbuf_reset_dma (int chan)
{
}
/*
* Used by unix select system call to see if data is ready.
*/
int
DMAbuf_output_ready(int dev)
{
struct dma_buffparms *dmap = audio_devs[dev]->dmap;
if (!(dmap->flags & DMA_ALLOC_DONE))
reorganize_buffers (dev);
return space_in_queue (dev);
}
int
DMAbuf_input_ready(int dev)
{
int h,i,r;
struct dma_buffparms *dmap = audio_devs[dev]->dmap;
r = 0;
if(dmap->qlen)
{
if(dmap->fragment_size)
{
for(i=0; i<dmap->qlen; i++)
{
h = (dmap->qhead + i) % dmap->nbufs;
r += dmap->fragment_size - dmap->counts[h];
if(r >= dmap->fragment_size)
break;
}
if(r < dmap->fragment_size)
r = 0;
else
r = 1;
}
else
r = 1;
}
else
DMAbuf_start_input(dev);
return(r);
}
/*
* The sound_mem_init() is called by mem_init() immediately after mem_map is
* initialized and before free_page_list is created.
@ -884,6 +958,24 @@ DMAbuf_release (int dev, int mode)
return 0;
}
int
DMAbuf_start_input (int dev)
{
return RET_ERROR (EIO);
}
int
DMAbuf_input_ready (int dev)
{
return 0;
}
int
DMAbuf_output_ready (int dev)
{
return 0;
}
int
DMAbuf_getwrbuffer (int dev, char **buf, int *size)
{

View File

@ -37,9 +37,6 @@
#ifndef EXCLUDE_SB
#define EXCLUDE_SB
#endif
#ifndef EXCLUDE_ADLIB
#define EXCLUDE_ADLIB
#endif
#ifndef EXCLUDE_GUS
#define EXCLUDE_GUS
#endif
@ -77,9 +74,6 @@
#ifdef AUDIO_SB
#undef EXCLUDE_SB
#endif
#ifdef AUDIO_ADLIB
#undef EXCLUDE_ADLIB
#endif
#ifdef AUDIO_GUS
#undef EXCLUDE_GUS
#endif