shithub: riscv

Download patch

ref: 581e6909b026205ed77caae27bae68baeecc59a3
parent: 62513de3f29a39606c0c5fa876baf9efc3ae7be5
author: qwx <qwx@sciops.net>
date: Sun Feb 9 20:39:19 EST 2025

audio/mixfs: set and forward a more sensible audio delay amount

remove the hardcoded constant which does not honor what the underlying
driver sets or uses.  instead, set a default value ourselves, the same
as what the drivers already use, and update it on change.  this fixes
issues with the emulators where the delay being too small caused a
high amount of jitter in the time it took to write the audio buffer,
severely impacting performance.

--- a/sys/src/cmd/audio/mixfs/mixfs.c
+++ b/sys/src/cmd/audio/mixfs/mixfs.c
@@ -8,7 +8,7 @@
 
 enum {
 	NBUF = 8*1024,
-	NDELAY = 512,	/* ~11.6ms */
+	NDELAY = 1764,	/* 25.0ms */
 	NQUANTA = 64,	/* ~1.45ms */
 	NCHAN = 2,
 	ABUF = NBUF*NCHAN*2,
@@ -50,6 +50,7 @@
 Pcmdesc	fmt;
 Lock	fmtlock;
 int	fmtchanged;
+int delay;
 
 int
 s16(uchar *p)
@@ -184,6 +185,8 @@
 		name = smprint("%.*svolume%s", (int)(p - name), name, p+5);
 		volfd = open(name, ORDWR);
 		free(name);
+		if(volfd >= 0)
+			fprint(volfd, "delay %d\n", delay);
 		updfmt();
 	}
 	return 0;
@@ -268,6 +271,7 @@
 	bufconv = nil;
 	sweep = 0;
 	rate = fmt.rate;
+	delay = NDELAY;
 
 	for(;;){
 		m = NBUF;
@@ -280,7 +284,7 @@
 						s->run = 0;
 					else if(n < m)
 						m = n;
-					if(n < NDELAY)
+					if(n < delay)
 						rwakeup(s);
 				} else {
 					n = (long)(mixrp - s->rp);
@@ -486,6 +490,14 @@
 			vol64k[0] = 65.536 * (exp(volume[0] * 0.0690876) - 1.0);
 			vol64k[1] = 65.536 * (exp(volume[1] * 0.0690876) - 1.0);
 		}else if(volfd >= 0){
+			if(nf > 1 && strcmp(f[0], "delay") == 0){
+				n = atoi(f[1]);
+				if(n < NQUANTA || n > NBUF){
+					responderror(r);
+					return;
+				}
+				delay = n;
+			}
 			if(write(volfd, r->ifcall.data, r->ifcall.count) < 0){
 				responderror(r);
 				return;
@@ -536,7 +548,7 @@
 
 		n -= m;
 	}
-	if((long)(s->wp - mixrp) >= NDELAY && !s->flush){
+	if((long)(s->wp - mixrp) >= delay && !s->flush){
 		s->run = 1;
 		rsleep(s);
 	}
--