--- alsa-patch-bay-1.0.0-orig/src/driver/jack/jack-addr.cpp +++ alsa-patch-bay-1.0.0-orig/src/driver/jack/jack-addr.cpp @@ -10,7 +10,8 @@ */ #include - +#include +#include #include "jack-addr.h" namespace APB { --- alsa-patch-bay-1.0.0-orig/src/driver/jack/jack-addr.cpp~ +++ alsa-patch-bay-1.0.0-orig/src/driver/jack/jack-addr.cpp~ @@ -0,0 +1,99 @@ +/* + * ALSA Patch Bay + * + * Copyright (C) 2002 Robert Ham (node@users.sourceforge.net) + * + * You have permission to use this file under the GNU General + * Public License, version 2 or later. See the file COPYING + * for the full text. + * + */ + +#include + +#include "jack-addr.h" + +namespace APB { +namespace Jack { + +Addr:: Addr (const std::string &portName, Driver * driver) +: _portName (portName), + _driver (driver) +{ +} + +Addr:: Addr (const Addr& addr) +: _portName (addr._portName), + _driver (addr._driver) +{ +} + +Addr:: ~Addr () +{ +} + +std::string +Addr:: client () const +{ + char * client; + char * ptr; + + client = strdup (_portName.c_str()); + + ptr = strchr (client, ':'); + if (ptr) + *ptr = '\0'; + + + std::string clients (client); + free (client); + + return clients; +} + +std::string +Addr:: port () const +{ + char * ptr; + + ptr = strchr (_portName.c_str(), ':'); + ptr++; + + std::string ports (ptr); + + return ports; +} + +const char * +Addr:: portName () const +{ + return _portName.c_str (); +} + +bool +Addr:: equals (const APB::Addr * addr) const +{ + const Addr * a = (const Addr *) addr; + + return _portName == a->_portName; +} + +bool +Addr:: clientEquals (const APB::Addr * addr) const +{ + const Addr * a = (const Addr *) addr; + + return client() == a->client(); +} + +std::string +Addr:: getName () const +{ + return _portName; +} + +} /* namespace Jack */ +} /* namespace APB */ + +/* EOF */ + --- alsa-patch-bay-1.0.0-orig/src/driver/jack/jack-driver.cpp +++ alsa-patch-bay-1.0.0-orig/src/driver/jack/jack-driver.cpp @@ -18,7 +18,8 @@ #include "misc.h" #include "plugin.h" #include "ui.h" - +#include +#include namespace APB { namespace Jack { --- alsa-patch-bay-1.0.0-orig/src/driver/jack/jack-driver.cpp~ +++ alsa-patch-bay-1.0.0-orig/src/driver/jack/jack-driver.cpp~ @@ -0,0 +1,330 @@ +/* + * ALSA Patch Bay + * + * Copyright (C) 2002 Robert Ham (node@users.sourceforge.net) + * + * You have permission to use this file under the GNU General + * Public License, version 2 or later. See the file COPYING + * for the full text. + * + */ + +#include +#include +#include + +#include "jack-driver.h" +#include "jack-addr.h" +#include "misc.h" +#include "plugin.h" +#include "ui.h" + +#include +namespace APB { +namespace Jack { + +static int +jackGraphOrderCallback (void * data) +{ + char refresh = 1; + ssize_t err; + int refreshWriteFile = *(int *)data; + + err = write (refreshWriteFile, &refresh, sizeof (refresh)); + if (err == -1) + { + std::cerr << "error writing to refresh pipe: " + << strerror (errno) + << std::endl; + return 1; + } + + return 0; +} + +Driver:: Driver (const std::string& title, int * argc, char *** argv) +{ + char * client_name; + char * ptr; + + client_name = strdup (title.c_str ()); + ptr = client_name; + while ( (ptr = strchr (ptr, ' ')) ) + *ptr = '_'; + + _jackClient = jack_client_new (client_name); + if (!_jackClient) + { + std::cerr << __FUNCTION__ + << ": could not connect to jackd" + << std::endl; + abort (); + } + + free (client_name); + + jack_set_graph_order_callback (_jackClient, &jackGraphOrderCallback, &_refreshWriteFile); + + jack_activate (_jackClient); +} + +Driver:: ~Driver () +{ + jack_deactivate (_jackClient); + + jack_client_close (_jackClient); +} + +std::string +Driver:: findClientName (const APB::Addr * addr) const +{ + const Addr * a = (const Addr *) addr; + + return std::string (a->client ()); +} + +std::string +Driver:: findPortName (const APB::Addr * addr) const +{ + const Addr * a = (const Addr *) addr; + + return std::string (a->port ()); +} + +const std::list& +Driver:: getReadPorts () +{ + return _readPorts; +} + +const std::list& +Driver:: getWritePorts () +{ + return _writePorts; +} + +const std::list& +Driver:: getSubscriptions () +{ + static std::list subs; + + subs.clear (); + for (std::list::iterator i = _subscriptions.begin (); + i != _subscriptions.end(); + ++i) + { + if ((*i)->from () == 0) + std::cerr << DEBUG_STRING << "null from()" << std::endl; + if ((*i)->to () == 0) + std::cerr << DEBUG_STRING << "null to()" << std::endl; + subs.push_back (*i); + } + + return subs; +} + +void +Driver:: refreshPorts () +{ + refreshPortList (_readPorts, JackPortIsOutput); + refreshPortList (_writePorts, JackPortIsInput); + refreshSubscriptions (); +} + +void +Driver:: refreshPortList (std::list& portList, enum JackPortFlags flags) +{ + for (std::list::iterator ad = portList.begin(); + ad != portList.end (); + ++ad) + { +/* delete *ad; */ + } + portList.clear (); + + const char ** jack_ports = jack_get_ports (_jackClient, NULL, NULL, flags); + + if (!jack_ports) + return; + + Addr * addr; + for (unsigned long i = 0; jack_ports[i]; ++i) + { + addr = new Addr (std::string (jack_ports[i]), this); + + portList.push_back (addr); + } + + free (jack_ports); +} + +Addr * +Driver:: findWritePort (const char * portName) +{ + Addr * addr; + std::string port_name (portName); + for (std::list::const_iterator writeAddrIter = _writePorts.begin (); + writeAddrIter != _writePorts.end (); + writeAddrIter++) + { + addr = (Addr *) *writeAddrIter; + + if (port_name == addr->getName ()) + return addr; + } + + return 0; +} + +void +Driver:: refreshSubscriptions () +{ + for (std::list::iterator s = _subscriptions.begin (); + s != _subscriptions.end (); + ++s) + { + delete *s; + } + _subscriptions.clear (); + + jack_port_t * port; + Addr * addr; + const char ** connections; + + for (std::list::const_iterator readAddrIter = _readPorts.begin (); + readAddrIter != _readPorts.end (); + ++readAddrIter) + { + addr = (Addr *) *readAddrIter; + port = jack_port_by_name (_jackClient, addr->portName ()); + + if (!port) + { + std::cerr << __FUNCTION__ + << ": could not find port '" + << addr->portName () + << "'" + << std::endl; + continue; + } + + connections = jack_port_get_all_connections (_jackClient, port); + + if (!connections) + continue; + + for (unsigned long i = 0; connections[i]; ++i) + { + Addr * waddr = findWritePort (connections[i]); + + if (!waddr) + continue; + + Subscription * sub = new Subscription (addr, waddr); + _subscriptions.push_back (sub); + } + + free (connections); + } +} + +void +Driver:: subscribePorts (const APB::Addr * readAddr, const APB::Addr * writeAddr) +{ + Addr * raddr = (Addr *) readAddr; + Addr * waddr = (Addr *) writeAddr; + + int err = jack_connect (_jackClient, raddr->portName (), waddr->portName ()); + + if (err) + { + throw Exception ("Jack server could not connect ports"); + } + + _ui->log (std::string ("Subscribed ports '") + raddr->portName () + "' and '" + + waddr->portName () + "'"); +} + +void +Driver:: subscribeClients (const APB::Addr * readAddr, const APB::Addr * writeAddr) +{ + Addr * raddr; + Addr * waddr = NULL; + std::string rclient (((const Addr *)readAddr)->client ()); + std::string wclient (((const Addr *)writeAddr)->client ()); + + unsigned long rcount = 0; + for (std::list::iterator riter = _readPorts.begin (); + riter != _readPorts.end (); + ++riter) + { + raddr = (Addr *) *riter; + if (raddr->client() == rclient) + { + unsigned long wcount = 0; + std::list::iterator witer; + for (witer = _writePorts.begin (); + witer != _writePorts.end (); + ++witer) + { + waddr = (Addr *) *witer; + if (waddr->client() == wclient) + { + if (wcount == rcount) + break; + + ++wcount; + } + } + + if (witer == _writePorts.end () || wcount != rcount) + continue; + + subscribePorts (raddr, waddr); + + rcount++; + } + } +} + +void +Driver:: removeSubscription (const Subscription * sub) +{ + Addr * raddr = (Addr *) sub->from (); + Addr * waddr = (Addr *) sub->to (); + + int err = jack_disconnect (_jackClient, raddr->portName (), waddr->portName ()); + + if (err) + { + throw Exception ("Jack server could not disconnect ports"); + } + + _ui->log (std::string ("Removed subscription ") + sub->getName ()); +} + +} /* namespace Jack */ + +class JackPlugin : public DriverPlugin +{ + public: + virtual Driver * getDriver (const std::string& title, int * argc, char *** argv); +}; + + +Driver * +JackPlugin:: getDriver (const std::string& title, int * argc, char *** argv) +{ + return new Jack::Driver (title, argc, argv); +} + +} /* namespace APB */ + +APB::DriverPlugin * +getDriverPlugin () +{ + return new APB::JackPlugin (); +} + +/* EOF */ + --- alsa-patch-bay-1.0.0-orig/src/driver.cpp +++ alsa-patch-bay-1.0.0-orig/src/driver.cpp @@ -15,7 +15,7 @@ #include #include #include - +#include #include "driver.h" namespace APB { --- alsa-patch-bay-1.0.0-orig/src/driver.cpp~ +++ alsa-patch-bay-1.0.0-orig/src/driver.cpp~ @@ -0,0 +1,83 @@ +/* + * ALSA Patch Bay + * + * Copyright (C) 2002 Robert Ham (node@users.sourceforge.net) + * + * You have permission to use this file under the GNU General + * Public License, version 2 or later. See the file COPYING + * for the full text. + * + */ + +#include + +#include +#include +#include +#include + +#include "driver.h" + +namespace APB { + +Driver:: Driver () + : _ui (0), + _jfd (true) +{ + int err; + int files[2]; + + err = pipe (files); + if (err) + { + std::cerr << "error creating pipe, exiting: " << strerror (errno) << std::endl; + exit (1); + } + + _refreshReadFile = files[0]; + _refreshWriteFile = files[1]; + + /* set the read file to not block */ + err = fcntl (_refreshReadFile, F_SETFL, O_NONBLOCK); + if (err) + { + std::cerr << "error setting read end of pipe to non-blocking mode, exiting: " << strerror (errno) << std::endl; + exit (1); + } +} + +void +Driver:: setJFD (bool jfd) +{ + _jfd = jfd; +} + +void +Driver:: setUI (UI * ui) +{ + _ui = ui; +} + +int +Driver:: getRefreshReadFile () +{ + return _refreshReadFile; +} + +#ifdef HAVE_LADCCA +void +Driver:: setCCAClient (cca_client_t * client) +{ + _ccaClient = client; +} + +cca_client_t * +Driver:: getCCAClient () +{ + return _ccaClient; +} +#endif /* HAVE_LADCCA */ + + + +} /* namespace APB */ --- alsa-patch-bay-1.0.0-orig/src/misc.cpp +++ alsa-patch-bay-1.0.0-orig/src/misc.cpp @@ -10,7 +10,7 @@ */ #include - +#include #include "misc.h" namespace APB { --- alsa-patch-bay-1.0.0-orig/src/misc.cpp~ +++ alsa-patch-bay-1.0.0-orig/src/misc.cpp~ @@ -0,0 +1,40 @@ +/* + * ALSA Patch Bay + * + * Copyright (C) 2002 Robert Ham (node@users.sourceforge.net) + * + * You have permission to use this file under the GNU General + * Public License, version 2 or later. See the file COPYING + * for the full text. + * + */ + +#include + +#include "misc.h" + +namespace APB { + +Exception:: Exception (const std::string& d, int e) +: desc (d), + err (e) +{ +} + +std::string int2string (int i) { + static std::string str; + + std::ostringstream ss; + + ss << i; + + str = ss.str(); + + return str; +} + +int randomNumber (double lower, double upper) { + return (int) ((lower-1)+(int) ((upper+1)*rand()/(RAND_MAX+1.0))); +} + +} /* namespace APB */ --- alsa-patch-bay-1.0.0-orig/src/plugins.cpp +++ alsa-patch-bay-1.0.0-orig/src/plugins.cpp @@ -14,7 +14,7 @@ #include #include #include - +#include #include #include #include --- alsa-patch-bay-1.0.0-orig/src/plugins.cpp~ +++ alsa-patch-bay-1.0.0-orig/src/plugins.cpp~ @@ -0,0 +1,220 @@ +/* + * ALSA Patch Bay + * + * Copyright (C) 2002 Robert Ham (node@users.sourceforge.net) + * + * You have permission to use this file under the GNU General + * Public License, version 2 or later. See the file COPYING + * for the full text. + * + */ + +#include +#include +#include +#include +#include + +#include +#include +#include + +#include "plugin.h" +#include "plugins.h" + +namespace APB { + +static void * uiPluginHandle; +static void * driverPluginHandle; + +PluginSet * +getPluginSet () +{ + static PluginSet plugs; + return &plugs; +} + +UIPlugin * +openUIPlugin (std::string pluginName) +{ + std::string fqn; + void * dlhandle; + GetUIPluginFunc getUIPlugin; + UIPlugin * plugin; + const char * error; + + fqn = std::string (PKGLIBDIR) + "/ui/" + pluginName + ".so"; + + dlhandle = dlopen (fqn.c_str(), RTLD_LAZY|RTLD_GLOBAL); + + if (!dlhandle) + { + std::cerr << __FUNCTION__ + << ": could not open ui plugin '" + << fqn + << "': " + << dlerror () + << std::endl; + exit (1); + } + + dlerror(); + + /* gcc 3.x */ + getUIPlugin = (GetUIPluginFunc) dlsym (dlhandle, "_Z11getUIPluginv"); + error = dlerror (); + if (error) + { + /* gcc 2.95.x */ + getUIPlugin = (GetUIPluginFunc) dlsym (dlhandle, "getUIPlugin__Fv"); + error = dlerror (); + if (error) + { + std::cerr << __FUNCTION__ + << ": could not find getUIPlugin function in plugin '" + << fqn + << "': " + << error + << std::endl; + dlclose (dlhandle); + exit (1); + } + } + + plugin = getUIPlugin (); + + uiPluginHandle = dlhandle; + + return plugin; +} + +DriverPlugin * +openDriverPlugin (std::string pluginName) +{ + std::string fqn; + void * dlhandle; + GetDriverPluginFunc getDriverPlugin; + DriverPlugin * plugin; + const char * error; + + fqn = std::string (PKGLIBDIR) + "/driver/" + pluginName + ".so"; + + dlhandle = dlopen (fqn.c_str(), RTLD_LAZY|RTLD_GLOBAL); + + if (!dlhandle) + { + std::cerr << __FUNCTION__ + << ": could not open driver plugin '" + << fqn + << "': " + << dlerror () + << std::endl; + exit (1); + } + + dlerror(); + + getDriverPlugin = (GetDriverPluginFunc) dlsym (dlhandle, "_Z15getDriverPluginv"); + error = dlerror (); + if (error) + { + getDriverPlugin = (GetDriverPluginFunc) dlsym (dlhandle, "getDriverPlugin__Fv"); + error = dlerror (); + if (error) + { + std::cerr << __FUNCTION__ + << ": could not find getDriverPlugin function in plugin '" + << fqn + << "': " + << error + << std::endl; + dlclose (dlhandle); + exit (1); + } + } + + plugin = getDriverPlugin (); + + driverPluginHandle = dlhandle; + + return plugin; +} + +void +readDir (std::string dirname, std::list& plugins) +{ + struct dirent * dir_entry; + DIR * dir; + char * plugin, * ptr; + + dir = opendir (dirname.c_str()); + + if (!dir) + { + std::cerr << __FUNCTION__ + << ": could not open plugin directory '" + << dirname + << "': " + << strerror (errno) + << std::endl; + exit (1); + } + + while ( (dir_entry = readdir (dir)) ) + { + plugin = strdup (dir_entry->d_name); + dirname = plugin; + if (dirname == "." || dirname == "..") + continue; + + ptr = strrchr (plugin, '.'); + if (!ptr) { + free (plugin); + continue; + } + *ptr = '\0'; + plugins.push_back (plugin); + free (plugin); + } +} + +void +initPlugins () +{ + std::string dir; + + dir = std::string (PKGLIBDIR) + "/driver"; + readDir (dir, getPluginSet()->driverPlugins); + + dir = std::string (PKGLIBDIR) + "/ui"; + readDir (dir, getPluginSet()->uiPlugins); + + + if (getPluginSet()->driverPlugins.size () == 0) + { + std::cerr << __FUNCTION__ + << ": no driver plugins" + << std::endl; + exit (1); + } + + if (getPluginSet()->uiPlugins.size () == 0) + { + std::cerr << __FUNCTION__ + << ": no ui plugins" + << std::endl; + exit (1); + } +} + +void +closePlugins () +{ +} + +} /* namespace APB */ + + +/* EOF */ + +