after every cycle, check if this was the last cycle in which case the

device may be closed and shouldn't be used
This commit is contained in:
Alexandre Ratchov 2014-03-17 18:38:57 +01:00
parent 0594488a66
commit 4b820e4de0
3 changed files with 53 additions and 62 deletions

View File

@ -55,11 +55,10 @@ void dev_mix_adjvol(struct dev *);
int rec_filt_resamp(struct slot *, void *, void *, int);
int rec_filt_enc(struct slot *, void *, void *, int);
void dev_sub_bcopy(struct dev *, struct slot *);
void dev_full_cycle(struct dev *);
void dev_onmove(struct dev *, int);
void dev_master(struct dev *, unsigned int);
void dev_cycle(struct dev *);
int dev_cycle(struct dev *);
int dev_getpos(struct dev *);
struct dev *dev_new(char *, struct aparams *, unsigned int, unsigned int,
unsigned int, unsigned int, unsigned int, unsigned int);
@ -74,7 +73,6 @@ struct dev *dev_bynum(int);
void dev_del(struct dev *);
unsigned int dev_roundof(struct dev *, unsigned int);
void dev_wakeup(struct dev *);
void dev_clear(struct dev *);
void dev_sync_attach(struct dev *);
void dev_mmcstart(struct dev *);
void dev_mmcstop(struct dev *);
@ -635,16 +633,6 @@ dev_mix_badd(struct dev *d, struct slot *s)
void
dev_empty_cycle(struct dev *d)
{
unsigned char *base;
int nsamp;
base = (unsigned char *)DEV_PBUF(d);
nsamp = d->round * d->pchan;
memset(base, 0, nsamp * sizeof(adata_t));
if (d->encbuf) {
enc_do(&d->enc, (unsigned char *)DEV_PBUF(d),
d->encbuf, d->round);
}
}
/*
@ -760,18 +748,58 @@ dev_sub_bcopy(struct dev *d, struct slot *s)
abuf_wcommit(&s->sub.buf, ocount * s->sub.bpf);
}
void
dev_full_cycle(struct dev *d)
/*
* run a one block cycle, return 0 if the device was stopped and/or
* closed.
*/
int
dev_cycle(struct dev *d)
{
struct slot *s, **ps;
unsigned char *base;
int nsamp;
/*
* check if the device is actually used. If it isn't,
* then close it
*/
if (d->slot_list == NULL && d->tstate != MMC_RUN) {
if (log_level >= 2) {
dev_log(d);
log_puts(": device stopped\n");
}
dev_sio_stop(d);
d->pstate = DEV_INIT;
if (d->refcnt == 0)
dev_close(d);
return 0;
}
if (d->prime > 0) {
#ifdef DEBUG
if (log_level >= 4) {
dev_log(d);
log_puts(": empty cycle, prime = ");
log_putu(d->prime);
log_puts("\n");
}
#endif
base = (unsigned char *)DEV_PBUF(d);
nsamp = d->round * d->pchan;
memset(base, 0, nsamp * sizeof(adata_t));
if (d->encbuf) {
enc_do(&d->enc, (unsigned char *)DEV_PBUF(d),
d->encbuf, d->round);
}
d->prime -= d->round;
return 1;
}
d->delta -= d->round;
#ifdef DEBUG
if (log_level >= 4) {
dev_log(d);
log_puts(": dev_full_cycle: clk=");
log_puts(": full cycle: delta = ");
log_puti(d->delta);
if (d->mode & MODE_PLAY) {
log_puts(", poffs = ");
@ -897,6 +925,7 @@ dev_full_cycle(struct dev *d)
enc_do(&d->enc, (unsigned char *)DEV_PBUF(d),
d->encbuf, d->round);
}
return 1;
}
/*
@ -939,38 +968,6 @@ dev_master(struct dev *d, unsigned int master)
dev_mix_adjvol(d);
}
void
dev_cycle(struct dev *d)
{
if (d->slot_list == NULL && d->tstate != MMC_RUN) {
if (log_level >= 2) {
dev_log(d);
log_puts(": device stopped\n");
}
dev_sio_stop(d);
d->pstate = DEV_INIT;
if (d->refcnt == 0)
dev_close(d);
else
dev_clear(d);
return;
}
#ifdef DEBUG
if (log_level >= 4) {
dev_log(d);
log_puts(": device cycle, prime = ");
log_putu(d->prime);
log_puts("\n");
}
#endif
if (d->prime > 0) {
d->prime -= d->round;
dev_empty_cycle(d);
} else {
dev_full_cycle(d);
}
}
/*
* return the latency that a stream would have if it's attached
*/
@ -1173,7 +1170,6 @@ dev_close(struct dev *d)
xfree(d->decbuf);
xfree(d->rbuf);
}
dev_clear(d);
}
int
@ -1303,8 +1299,12 @@ dev_wakeup(struct dev *d)
} else {
d->prime = 0;
}
d->poffs = 0;
/* empty cycles don't increment delta */
/*
* empty cycles don't increment delta, so it's ok to
* start at 0
**/
d->delta = 0;
d->pstate = DEV_RUN;
@ -1312,16 +1312,6 @@ dev_wakeup(struct dev *d)
}
}
/*
* Clear buffers of the play and record chains so that when the device
* is started, playback and record start in sync.
*/
void
dev_clear(struct dev *d)
{
d->poffs = 0;
}
/*
* check that all clients controlled by MMC are ready to start, if so,
* attach them all at the same position

View File

@ -206,7 +206,7 @@ unsigned int dev_roundof(struct dev *, unsigned int);
* interface to hardware device
*/
void dev_onmove(struct dev *, int);
void dev_cycle(struct dev *);
int dev_cycle(struct dev *);
/*
* midi & midi call-backs

View File

@ -348,7 +348,8 @@ dev_sio_run(void *arg)
panic();
}
#endif
dev_cycle(d);
if (!dev_cycle(d))
return;
if (d->mode & MODE_PLAY) {
d->sio.cstate = DEV_SIO_WRITE;
d->sio.todo = d->round * d->pchan * d->par.bps;