Ticket #849: sound-autotune-queue-v2.patch
File sound-autotune-queue-v2.patch, 6.9 KB (added by , 6 years ago) |
---|
-
xpra/sound/sink.py
4 4 # Xpra is released under the terms of the GNU GPL v2, or, at your option, any 5 5 # later version. See the file COPYING for details. 6 6 7 import sys, os , time7 import sys, os 8 8 9 9 from xpra.sound.sound_pipeline import SoundPipeline, gobject, one_arg_signal 10 10 from xpra.sound.pulseaudio_util import has_pa … … 46 46 DEFAULT_SINK = SINKS[0] 47 47 QUEUE_SILENT = 0 48 48 QUEUE_TIME = get_queue_time(450) 49 QUEUE_MIN_TIME = get_queue_time(QUEUE_TIME//10//MS_TO_NS, "MIN")50 assert QUEUE_MIN_TIME<=QUEUE_TIME51 49 52 VARIABLE_MIN_QUEUE = os.environ.get("XPRA_VARIABLE_MIN_QUEUE", "1")=="1"53 54 55 50 GST_FORMAT_BUFFERS = 4 56 51 57 52 def sink_has_device_attribute(sink): … … 94 89 pipeline_els.append("volume name=volume volume=%s" % volume) 95 90 queue_el = ["queue", 96 91 "name=queue", 97 "min-threshold-time= %s" % QUEUE_MIN_TIME,92 "min-threshold-time=0", 98 93 "max-size-buffers=0", 99 94 "max-size-bytes=0", 100 95 "max-size-time=%s" % QUEUE_TIME, … … 131 126 def queue_pushing(self, *args): 132 127 ltime = self.queue.get_property("current-level-time")/MS_TO_NS 133 128 log("queue pushing: level=%i", ltime) 129 self.check_levels() 134 130 self.queue_state = "pushing" 135 self.emit_info()131 #self.emit_info() 136 132 return 0 137 133 138 134 def queue_running(self, *args): 139 135 ltime = self.queue.get_property("current-level-time")/MS_TO_NS 140 136 log("queue running: level=%s", ltime) 141 if self.queue_state=="underrun" and VARIABLE_MIN_QUEUE: 137 self.check_levels() 138 self.queue_state = "running" 139 return 0 140 141 def check_levels(self): 142 if True: 143 return 144 if self.queue_state=="underrun": 142 145 #lift min time restrictions: 143 146 self.queue.set_property("min-threshold-time", 0) 144 147 elif self.queue_state == "overrun": 145 148 clt = self.queue.get_property("current-level-time") 146 149 qpct = min(QUEUE_TIME, clt)*100//QUEUE_TIME 147 log ("resetting max-size-time back to %ims (level=%ims, %i%%)", QUEUE_TIME//MS_TO_NS, clt//MS_TO_NS, qpct)150 log.info("resetting max-size-time back to %ims (level=%ims, %i%%)", QUEUE_TIME//MS_TO_NS, clt//MS_TO_NS, qpct) 148 151 self.queue.set_property("max-size-time", QUEUE_TIME) 149 152 self.queue_state = "running" 150 153 self.emit_info() 151 return 0152 154 155 153 156 def queue_underrun(self, *args): 157 if self.queue_state=="underrun" or self.queue_state=="starting": 158 return 154 159 ltime = self.queue.get_property("current-level-time")/MS_TO_NS 155 log("queue underrun: level=%i", ltime) 156 if self.queue_state!="underrun" and VARIABLE_MIN_QUEUE: 157 #lift min time restrictions: 158 self.queue.set_property("min-threshold-time", QUEUE_MIN_TIME) 160 log.info("queue underrun: level=%i, previous state=%s", ltime, self.queue_state) 159 161 self.queue_state = "underrun" 160 self.emit_info() 162 MIN_QUEUE = QUEUE_TIME//2 163 mts = self.queue.get_property("min-threshold-time") 164 if mts==MIN_QUEUE: 165 return 0 166 #set min time restrictions to fill up queue: 167 log.info("increasing the min-threshold-time to %ims", MIN_QUEUE//MS_TO_NS) 168 self.queue.set_property("min-threshold-time", MIN_QUEUE) 169 def restore(): 170 if self.queue.get_property("min-threshold-time")==0: 171 log.info("min-threshold-time already restored!") 172 return False 173 ltime = self.queue.get_property("current-level-time")//MS_TO_NS 174 if ltime==0: 175 log.info("not restored! (still underrun: %ims)", ltime) 176 return True 177 log.info("resetting the min-threshold-time back to %ims", 0) 178 self.queue.set_property("min-threshold-time", 0) 179 self.queue_state = "running" 180 return False 181 import glib 182 glib.timeout_add(1000, restore) 183 #self.emit_info() 161 184 return 0 162 185 163 186 def queue_overrun(self, *args): 187 if self.queue_state=="overrun": 188 return 164 189 ltime = self.queue.get_property("current-level-time")//MS_TO_NS 165 pqs = self.queue_state190 log("queue overrun: level=%i, previous state=%s", ltime, self.queue_state) 166 191 self.queue_state = "overrun" 167 #no overruns for the first 2 seconds: 168 if ltime<QUEUE_TIME//MS_TO_NS//2*75//100: 169 elapsed = time.time()-self.start_time 170 log("queue overrun ignored: level=%i, elapsed time=%.1f", ltime, elapsed) 171 return 0 172 log("queue overrun: level=%i, previous state=%s", ltime//MS_TO_NS, pqs) 173 if pqs!="overrun": 174 log("halving the max-size-time to %ims", QUEUE_TIME//2//MS_TO_NS) 175 self.queue.set_property("max-size-time", QUEUE_TIME//2) 176 self.overruns += 1 177 self.emit("overrun", ltime) 178 self.emit_info() 192 REDUCED_QT = QUEUE_TIME//2 193 #empty the queue by reducing its max size: 194 log.info("queue overrun: halving the max-size-time to %ims", REDUCED_QT//MS_TO_NS) 195 self.queue.set_property("max-size-time", REDUCED_QT) 196 self.overruns += 1 197 self.emit("overrun", ltime) 198 def restore(): 199 if self.queue.get_property("max-size-time")==QUEUE_TIME: 200 log.info("max-size-time already restored!") 201 return False 202 ltime = self.queue.get_property("current-level-time")//MS_TO_NS 203 if ltime>=REDUCED_QT: 204 log.info("max-size-time not restored! (still overrun: %ims)", ltime) 205 return True 206 log.info("raising the max-size-time back to %ims", QUEUE_TIME//MS_TO_NS) 207 self.queue.set_property("max-size-time", QUEUE_TIME) 208 self.queue_state = "running" 209 return False 210 import glib 211 glib.timeout_add(1000, restore) 212 #self.emit_info() 179 213 return 0 180 214 181 215 def eos(self): … … 191 225 clt = self.queue.get_property("current-level-time") 192 226 updict(info, "queue", { 193 227 "time" : QUEUE_TIME//MS_TO_NS, 194 "min_time" : QUEUE_MIN_TIME//MS_TO_NS,195 228 "used_pct" : min(QUEUE_TIME, clt)*100//QUEUE_TIME, 196 229 "used" : clt//MS_TO_NS, 197 230 "overruns" : self.overruns, … … 202 235 if not self.src: 203 236 log("add_data(..) dropped") 204 237 return 238 if self.queue_state=="overrun": 239 log.info("add_data(..) queue in overrun, data dropped") 240 return 205 241 #having a timestamp causes problems with the queue and overruns: 206 242 if "timestamp" in metadata: 207 243 del metadata["timestamp"]