def run_sound(mode, error_cb, options, args): """ this function just parses command line arguments to feed into the sound subprocess class, which in turn just feeds them into the sound pipeline class (sink.py or src.py) """ from xpra.gtk_common.gobject_compat import want_gtk3 want_gtk3(True) gst = import_gst() if not gst: return 1 info = mode.replace("_sound_", "") #ie: "_sound_record" -> "record" from xpra.platform import program_context with program_context("Xpra-Audio-%s" % info, "Xpra Audio %s" % info): log("run_sound(%s, %s, %s, %s) gst=%s", mode, error_cb, options, args, gst) if mode=="_sound_record": subproc = sound_record elif mode=="_sound_play": subproc = sound_play elif mode=="_sound_query": plugins = get_all_plugin_names() sources = [x for x in get_source_plugins() if x in plugins] sinks = [x for x in get_sink_plugins() if x in plugins] from xpra.sound.gstreamer_util import gst_version, pygst_version import struct bits = struct.calcsize("P")*8 d = { "encoders" : can_encode(), "decoders" : can_decode(), "sources" : sources, "source.default" : get_default_source() or "", "sinks" : sinks, "sink.default" : get_default_sink() or "", "muxers" : get_muxers(), "demuxers" : get_demuxers(), "gst.version" : [int(x) for x in gst_version], "pygst.version" : pygst_version, "plugins" : plugins, "python.version" : sys.version_info[:3], "python.bits" : bits, } if BUNDLE_METADATA: d["bundle-metadata"] = True for k,v in d.items(): if type(v) in (list, tuple): v = ",".join(str(x) for x in v) print("%s=%s" % (k, v)) return 0 else: log.error("unknown mode: %s" % mode) return 1 assert len(args)>=6, "not enough arguments" #the plugin to use (ie: 'pulsesrc' for src.py or 'autoaudiosink' for sink.py) plugin = args[2] #plugin options (ie: "device=monitor_device,something=value") options = parse_simple_dict(args[3]) #codecs: codecs = [x.strip() for x in args[4].split(",")] #codec options: codec_options = parse_simple_dict(args[5]) #volume (optional): try: volume = int(args[6]) except: volume = 1.0 ss = None try: ss = subproc(plugin, options, codecs, codec_options, volume) ss.start() return 0 except InitExit as e: log.error("%s: %s", info, e) return e.status except InitException as e: log.error("%s: %s", info, e) return 1 except Exception: log.error("run_sound%s error", (mode, error_cb, options, args), exc_info=True) return 1 finally: if ss: ss.stop()
# This file is part of Xpra. # Copyright (C) 2010-2018 Antoine Martin <*****@*****.**> # Xpra is released under the terms of the GNU GPL v2, or, at your option, any # later version. See the file COPYING for details. from xpra.log import Logger log = Logger("sound") gstlog = Logger("gstreamer") #must be done before importing gobject! from xpra.sound.gstreamer_util import import_gst gst = import_gst() from xpra.util import envint from xpra.os_util import monotonic_time from xpra.gtk_common.gobject_compat import import_glib from xpra.gtk_common.gobject_util import one_arg_signal, gobject FAULT_RATE = envint("XPRA_SOUND_FAULT_INJECTION_RATE") _counter = 0 def inject_fault(): global FAULT_RATE if FAULT_RATE<=0: return False global _counter _counter += 1 return (_counter % FAULT_RATE)==0 class SoundPipeline(gobject.GObject):
def run_sound(mode, error_cb, options, args): """ this function just parses command line arguments to feed into the sound subprocess class, which in turn just feeds them into the sound pipeline class (sink.py or src.py) """ #we have to import gstreamer before init() on OSX, #because init will end up import gobject, #which means choosing between gi and gtk2 bindings from xpra.sound.gstreamer_util import import_gst, get_pygst_version gst = import_gst() from xpra.gtk_common.gobject_compat import want_gtk3 want_gtk3(get_pygst_version()[0]>0) from xpra.platform import program_context with program_context("Xpra"): log("run_sound(%s, %s, %s, %s) gst=%s", mode, error_cb, options, args, gst) if not gst: return 1 if mode=="_sound_record": subproc = sound_record info = "record" elif mode=="_sound_play": subproc = sound_play info = "play" elif mode=="_sound_query": plugins = get_all_plugin_names() sources = [x for x in get_source_plugins() if x in plugins] from xpra.sound.gstreamer_util import gst_version, pygst_version d = {"encoders" : can_encode(), "decoders" : can_decode(), "sources" : sources, "muxers" : get_muxers(), "demuxers" : get_demuxers(), "gst.version" : gst_version, "pygst.version" : pygst_version, "plugins" : plugins, "python.version" : sys.version_info[:3], } for k,v in d.items(): print("%s=%s" % (k, ",".join(str(x) for x in v))) return 0 else: log.error("unknown mode: %s" % mode) return 1 assert len(args)>=6, "not enough arguments" #the plugin to use (ie: 'pulsesrc' for src.py or 'autoaudiosink' for sink.py) plugin = args[2] #plugin options (ie: "device=monitor_device,something=value") options = parse_simple_dict(args[3]) #codecs: codecs = [x.strip() for x in args[4].split(",")] #codec options: codec_options = parse_simple_dict(args[5]) #volume (optional): try: volume = int(args[6]) except: volume = 1.0 ss = None try: ss = subproc(plugin, options, codecs, codec_options, volume) ss.start() return 0 except InitExit as e: log.error("%s: %s", info, e) return e.status except InitException as e: log.error("%s: %s", info, e) return 1 except Exception: log.error("run_sound%s error", (mode, error_cb, options, args), exc_info=True) return 1 finally: if ss: ss.stop()
# This file is part of Xpra. # Copyright (C) 2010-2015 Antoine Martin <*****@*****.**> # Xpra is released under the terms of the GNU GPL v2, or, at your option, any # later version. See the file COPYING for details. import os import time from xpra.log import Logger log = Logger("sound") gstlog = Logger("gstreamer") #must be done before importing gobject! from xpra.sound.gstreamer_util import import_gst, gst_major_version gst = import_gst() MESSAGE_ELEMENT = getattr(gst, "MESSAGE_ELEMENT", None) from xpra.sound.gstreamer_util import gst_version #must be done after import_gst() from xpra.util import csv from xpra.gtk_common.gobject_compat import import_glib from xpra.gtk_common.gobject_util import one_arg_signal, gobject FAULT_RATE = int(os.environ.get("XPRA_SOUND_FAULT_INJECTION_RATE", "0")) _counter = 0 def inject_fault(): global FAULT_RATE if FAULT_RATE<=0: return False global _counter _counter += 1