diff options
author | David Robillard <d@drobilla.net> | 2006-06-10 02:43:54 +0000 |
---|---|---|
committer | David Robillard <d@drobilla.net> | 2006-06-10 02:43:54 +0000 |
commit | 47246db7e9d71ba694b719001033fba1766a58c4 (patch) | |
tree | 25614ea4f2c92033a3cd37f6413df742f09a5369 /src/progs/demolition | |
parent | 98fe0e7056e6697396249531785d3899f94d79be (diff) | |
download | ingen-47246db7e9d71ba694b719001033fba1766a58c4.tar.gz ingen-47246db7e9d71ba694b719001033fba1766a58c4.tar.bz2 ingen-47246db7e9d71ba694b719001033fba1766a58c4.zip |
More juggling
git-svn-id: http://svn.drobilla.net/lad/grauph@16 a436a847-0d15-0410-975c-d299462d15a1
Diffstat (limited to 'src/progs/demolition')
-rw-r--r-- | src/progs/demolition/DemolitionClientInterface.cpp | 109 | ||||
-rw-r--r-- | src/progs/demolition/DemolitionClientInterface.h | 75 | ||||
-rw-r--r-- | src/progs/demolition/DemolitionModel.cpp | 246 | ||||
-rw-r--r-- | src/progs/demolition/DemolitionModel.h | 60 | ||||
-rw-r--r-- | src/progs/demolition/Makefile.am | 17 | ||||
-rw-r--r-- | src/progs/demolition/README | 7 | ||||
-rw-r--r-- | src/progs/demolition/cmdline.c | 149 | ||||
-rw-r--r-- | src/progs/demolition/cmdline.ggo | 7 | ||||
-rw-r--r-- | src/progs/demolition/cmdline.h | 45 | ||||
-rw-r--r-- | src/progs/demolition/demolition.cpp | 334 |
10 files changed, 1049 insertions, 0 deletions
diff --git a/src/progs/demolition/DemolitionClientInterface.cpp b/src/progs/demolition/DemolitionClientInterface.cpp new file mode 100644 index 00000000..e58371d4 --- /dev/null +++ b/src/progs/demolition/DemolitionClientInterface.cpp @@ -0,0 +1,109 @@ +/* This file is part of Om. Copyright (C) 2005 Dave Robillard. + * + * Om is free software; you can redistribute it and/or modify it under the + * terms of the GNU General Public License as published by the Free Software + * Foundation; either version 2 of the License, or (at your option) any later + * version. + * + * Om is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#include "DemolitionClientInterface.h" +#include "DemolitionModel.h" + + +DemolitionClientInterface::DemolitionClientInterface(DemolitionModel* model) +: m_model(model) +{ +} + + +DemolitionClientInterface::~DemolitionClientInterface() +{ +} + + +void +DemolitionClientInterface::error(const string& msg) +{ +} + + +void +DemolitionClientInterface::new_patch_model(PatchModel* pm) +{ + m_model->add_patch(pm); +} + + +void +DemolitionClientInterface::new_port_model(PortModel* port_model) +{ + m_model->add_port(port_model); +} + + +void +DemolitionClientInterface::object_destroyed(const string& path) +{ + m_model->remove_object(path); +} + +void +DemolitionClientInterface::patch_enabled(const string& path) +{ +} + + +void +DemolitionClientInterface::patch_disabled(const string& path) +{ +} + + +void +DemolitionClientInterface::new_node_model(NodeModel* nm) +{ + m_model->add_node(nm); +} + + +void +DemolitionClientInterface::object_renamed(const string& old_path, const string& new_path) +{ + m_model->object_renamed(old_path, new_path); +} + + +void +DemolitionClientInterface::connection_model(ConnectionModel* cm) +{ + m_model->add_connection(cm); +} + + +void +DemolitionClientInterface::disconnection(const string& src_port_path, const string& dst_port_path) +{ + m_model->remove_connection(src_port_path, dst_port_path); +} + + +void +DemolitionClientInterface::control_change(const string& port_path, float value) +{ +} + + +void +DemolitionClientInterface::new_plugin_model(PluginModel* pi) +{ + m_model->add_plugin(pi); +} + diff --git a/src/progs/demolition/DemolitionClientInterface.h b/src/progs/demolition/DemolitionClientInterface.h new file mode 100644 index 00000000..374008b5 --- /dev/null +++ b/src/progs/demolition/DemolitionClientInterface.h @@ -0,0 +1,75 @@ +/* This file is part of Om. Copyright (C) 2005 Dave Robillard. + * + * Om is free software; you can redistribute it and/or modify it under the + * terms of the GNU General Public License as published by the Free Software + * Foundation; either version 2 of the License, or (at your option) any later + * version. + * + * Om is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + + +#ifndef DEMOLITIONCLIENTHOOKS_H +#define DEMOLITIONCLIENTHOOKS_H + +#include <cstdlib> +#include <string> +#include "ModelClientInterface.h" +#include "DemolitionModel.h" +#include "PluginModel.h" +using std::string; + +using namespace LibOmClient; + + +/** ModelClientInterface implementation for the Gtk client. + * + * These are the hooks into the GUI for the Comm class. + * + * \ingroup OmGtk + */ +class DemolitionClientInterface : public ModelClientInterface +{ +public: + DemolitionClientInterface(DemolitionModel* model); + virtual ~DemolitionClientInterface(); + + void bundle_begin() {} + void bundle_end() {} + + void num_plugins(size_t num) {} + + // OSC thread functions + void error(const string& msg); + + void new_plugin(const string& type, + const string& uri, + const string& name) {} + void new_patch_model(PatchModel* const pm); + void new_port_model(PortModel* const port_model); + void object_destroyed(const string& path); + void patch_enabled(const string& path); + void patch_disabled(const string& path); + void patch_cleared(const string& path) { throw; } + void new_node_model(NodeModel* const nm); + void object_renamed(const string& old_path, const string& new_path); + void connection_model(ConnectionModel* const cm); + void disconnection(const string& src_port_path, const string& dst_port_path); + void metadata_update(const string& path, const string& key, const string& value) {} + void control_change(const string& port_path, float value); + void new_plugin_model(PluginModel* const pi); + void program_add(const string& path, uint32_t bank, uint32_t program, const string& name) {}; + void program_remove(const string& path, uint32_t bank, uint32_t program) {}; + +private: + DemolitionModel* m_model; +}; + + +#endif // DEMOLITIONCLIENTHOOKS_H diff --git a/src/progs/demolition/DemolitionModel.cpp b/src/progs/demolition/DemolitionModel.cpp new file mode 100644 index 00000000..786c08cd --- /dev/null +++ b/src/progs/demolition/DemolitionModel.cpp @@ -0,0 +1,246 @@ +/* This file is part of Om. Copyright (C) 2005 Dave Robillard. + * + * Om is free software; you can redistribute it and/or modify it under the + * terms of the GNU General Public License as published by the Free Software + * Foundation; either version 2 of the License, or (at your option) any later + * version. + * + * Om is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#include "DemolitionModel.h" +#include "util/Path.h" +#include "PluginModel.h" +#include <stdlib.h> +#include <iostream> +using std::cout; using std::cerr; using std::endl; + + +DemolitionModel::~DemolitionModel() +{ + for (vector<PluginModel*>::iterator i = m_plugins.begin(); i != m_plugins.end(); ++i) + delete *i; + + for (vector<PatchModel*>::iterator i = m_patches.begin(); i != m_patches.end(); ++i) + delete *i; +} + + +PatchModel* +DemolitionModel::random_patch() +{ + if (m_patches.size() == 0) + return NULL; + else + return m_patches.at(rand() % m_patches.size()); +} + + +NodeModel* +DemolitionModel::random_node() +{ + int max_attempts = m_patches.size()*4; + int attempts = 0; + + while (attempts++ < max_attempts) { + PatchModel* pm = random_patch(); + + if (pm == NULL) { + return NULL; + } else { + int size = pm->nodes().size(); + if (size == 0) + continue; + int index = rand() % size; + NodeModelMap::const_iterator i = pm->nodes().begin(); + for (int j=0; j < index; ++j) { + ++i; + if (i == pm->nodes().end()) + return NULL; + } + return (*i).second; + } + } + //cout << "***************************** Not returning node *********" << endl; + return NULL; +} + + +NodeModel* +DemolitionModel::random_node_in_patch(PatchModel* pm) +{ + if (pm == NULL) + return NULL; + + int size = pm->nodes().size(); + if (size == 0) + return NULL; + + int index = rand() % size; + NodeModelMap::const_iterator i = pm->nodes().begin(); + for (int j=0; j < index; ++j) { + ++i; + if (i == pm->nodes().end()) + return NULL; + } + return (*i).second; +} + + +PortModel* +DemolitionModel::random_port() +{ + NodeModel* node = random_node(); + + if (node == NULL) return NULL; + + PortModelList ports = node->ports(); + + int num_ports = ports.size(); + int index = rand() % num_ports; + int i = 0; + + for (PortModelList::iterator p = ports.begin(); p != ports.end(); ++p, ++i) + if (i == index) + return (*p); + + return NULL; // shouldn't happen +} + + +PortModel* +DemolitionModel::random_port_in_node(NodeModel* node) +{ + if (node == NULL) + return NULL; + + PortModelList ports = node->ports(); + + int num_ports = ports.size(); + int index = rand() % num_ports; + int i = 0; + + for (PortModelList::iterator p = ports.begin(); p != ports.end(); ++p, ++i) + if (i == index) + return (*p); + + return NULL; // shouldn't happen +} + + +PluginModel* +DemolitionModel::random_plugin() +{ + if (m_plugins.size() == 0) + return NULL; + else + return m_plugins.at(rand() % m_plugins.size()); +} + + +PatchModel* +DemolitionModel::patch(const Path& path) +{ + for (vector<PatchModel*>::iterator i = m_patches.begin(); i != m_patches.end(); ++i) { + if ((*i)->path() == path) + return (*i); + } + return NULL; +} + + +NodeModel* +DemolitionModel::node(const Path& path) +{ + NodeModel* ret = NULL; + + for (vector<PatchModel*>::iterator i = m_patches.begin(); i != m_patches.end(); ++i) { + ret = (*i)->get_node(path.name()); + if (ret != NULL) + break; + } + return ret; +} + + +void +DemolitionModel::remove_object(const Path& path) +{ + // Patch + for (vector<PatchModel*>::iterator i = m_patches.begin(); i != m_patches.end(); ++i) { + if ((*i)->path() == path) { + delete (*i); + m_patches.erase(i); + break; + } + } + + // Node + PatchModel* parent = patch(path.parent()); + if (parent != NULL) + parent->remove_node(path.name()); +} + + +void +DemolitionModel::add_node(NodeModel* nm) +{ + PatchModel* parent = patch(nm->path().parent()); + if (parent == NULL) { + cout << "**** ERROR: Parent for new Node does not exist." << endl; + } else { + parent->add_node(nm); + } +} + + +void +DemolitionModel::add_port(PortModel* pm) +{ +} + + +void +DemolitionModel::add_connection(ConnectionModel* cm) +{ +} + + +void +DemolitionModel::remove_connection(const Path& src_port_path, const Path& dst_port_path) +{ +} + +void +DemolitionModel::object_renamed(const Path& old_path, const Path& new_path) +{ + /* FIXME: broken, does not rename children + assert(OmPath::parent(old_path) == OmPath::parent(new_path)); + + // Rename node + NodeModel* nm = get_node(old_path); + if (nm != NULL) { + if (nm->parent() != NULL) { + nm->parent()->remove_node(OmPath::name(old_path)); + nm->path(new_path); + nm->parent()->add_node(OmPath::name(new_path)); + } + } + + // Rename patch + for (vector<PatchModel*>::iterator i = m_patches.begin(); i != m_patches.end(); ++i) { + if ((*i)->path() == path) { + delete (*i); + m_patches.erase(i); + return; + } + } + */ +} + diff --git a/src/progs/demolition/DemolitionModel.h b/src/progs/demolition/DemolitionModel.h new file mode 100644 index 00000000..64e0cc61 --- /dev/null +++ b/src/progs/demolition/DemolitionModel.h @@ -0,0 +1,60 @@ +/* This file is part of Om. Copyright (C) 2005 Dave Robillard. + * + * Om is free software; you can redistribute it and/or modify it under the + * terms of the GNU General Public License as published by the Free Software + * Foundation; either version 2 of the License, or (at your option) any later + * version. + * + * Om is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#ifndef DEMOLITIONMODEL_H +#define DEMOLITIONMODEL_H + +#include <vector> +#include "PatchModel.h" +#include "util/Path.h" +using Om::Path; +using std::vector; + +using namespace LibOmClient; + +class DemolitionModel { +public: + ~DemolitionModel(); + + PatchModel* random_patch(); + NodeModel* random_node(); + NodeModel* random_node_in_patch(PatchModel* patch); + PortModel* random_port(); + PortModel* random_port_in_node(NodeModel* node); + PluginModel* random_plugin(); + + PatchModel* patch(const Path& path); + NodeModel* node(const Path& path); + + void add_patch(PatchModel* pm) { m_patches.push_back(pm); } + void add_node(NodeModel* nm); + void add_port(PortModel* pm); + void remove_object(const Path& path); + void add_connection(ConnectionModel* cm); + void remove_connection(const Path& src_port_path, const Path& dst_port_path); + void add_plugin(PluginModel* pi) { m_plugins.push_back(pi); } + + void object_renamed(const Path& old_path, const Path& new_path); + + int num_patches() { return m_patches.size(); } + +private: + vector<PluginModel*> m_plugins; + vector<PatchModel*> m_patches; +}; + + +#endif // DEMOLITIONMODEL_H diff --git a/src/progs/demolition/Makefile.am b/src/progs/demolition/Makefile.am new file mode 100644 index 00000000..4854f045 --- /dev/null +++ b/src/progs/demolition/Makefile.am @@ -0,0 +1,17 @@ +EXTRA_DIST = README + +om_demolition_CXXFLAGS = -I$(top_srcdir)/src/clients -I$(top_srcdir)/src/common -DPKGDATADIR=\"$(pkgdatadir)\" $(LXML2_CFLAGS) $(LOSC_CFLAGS) +om_demolition_LDADD = ../libomclient.a $(LOSC_LIBS) $(LXML2_LIBS) + +bin_PROGRAMS = om_demolition + +om_demolition_DEPENDENCIES = ../libomclient.a + +om_demolition_SOURCES = \ + DemolitionClientInterface.h \ + DemolitionClientInterface.cpp \ + DemolitionModel.h \ + DemolitionModel.cpp \ + demolition.cpp \ + cmdline.h \ + cmdline.c diff --git a/src/progs/demolition/README b/src/progs/demolition/README new file mode 100644 index 00000000..536d3481 --- /dev/null +++ b/src/progs/demolition/README @@ -0,0 +1,7 @@ +This is a stress tester for the Om engine. + +It constantly sends random events (with a bias towards sane events) to the +engine, to test for potential segfaults (or assertion failures, etc). + +It's not very clever at the moment, and doesn't hit all test cases. Renaming +is also not supported yet. diff --git a/src/progs/demolition/cmdline.c b/src/progs/demolition/cmdline.c new file mode 100644 index 00000000..11fcd108 --- /dev/null +++ b/src/progs/demolition/cmdline.c @@ -0,0 +1,149 @@ +/* + File autogenerated by gengetopt version 2.10 + generated with the following command: + gengetopt + + The developers of gengetopt consider the fixed text that goes in all + gengetopt output files to be in the public domain: + we make no copyright claims on it. +*/ + + +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +/* If we use autoconf. */ +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include "getopt.h" + +#include "cmdline.h" + +void +cmdline_parser_print_version (void) +{ + printf ("%s %s\n", CMDLINE_PARSER_PACKAGE, CMDLINE_PARSER_VERSION); +} + +void +cmdline_parser_print_help (void) +{ + cmdline_parser_print_version (); + printf("\n" + "Usage: %s [OPTIONS]...\n", CMDLINE_PARSER_PACKAGE); + printf(" -h --help Print help and exit\n"); + printf(" -V --version Print version and exit\n"); + printf(" -uSTRING --engine-url=STRING Om engine URL to connect to\n"); + printf(" -pINT --client-port=INT Client port to listen on\n"); +} + + +static char *gengetopt_strdup (const char *s); + +/* gengetopt_strdup() */ +/* strdup.c replacement of strdup, which is not standard */ +char * +gengetopt_strdup (const char *s) +{ + char *result = (char*)malloc(strlen(s) + 1); + if (result == (char*)0) + return (char*)0; + strcpy(result, s); + return result; +} + +int +cmdline_parser (int argc, char * const *argv, struct gengetopt_args_info *args_info) +{ + int c; /* Character of the parsed option. */ + int missing_required_options = 0; + + args_info->help_given = 0 ; + args_info->version_given = 0 ; + args_info->engine_url_given = 0 ; + args_info->client_port_given = 0 ; +#define clear_args() { \ + args_info->engine_url_arg = NULL; \ +} + + clear_args(); + + optarg = 0; + optind = 1; + opterr = 1; + optopt = '?'; + + while (1) + { + int option_index = 0; + char *stop_char; + + static struct option long_options[] = { + { "help", 0, NULL, 'h' }, + { "version", 0, NULL, 'V' }, + { "engine-url", 1, NULL, 'u' }, + { "client-port", 1, NULL, 'p' }, + { NULL, 0, NULL, 0 } + }; + + stop_char = 0; + c = getopt_long (argc, argv, "hVu:p:", long_options, &option_index); + + if (c == -1) break; /* Exit from `while (1)' loop. */ + + switch (c) + { + case 'h': /* Print help and exit. */ + clear_args (); + cmdline_parser_print_help (); + exit (EXIT_SUCCESS); + + case 'V': /* Print version and exit. */ + clear_args (); + cmdline_parser_print_version (); + exit (EXIT_SUCCESS); + + case 'u': /* Om engine URL to connect to. */ + if (args_info->engine_url_given) + { + fprintf (stderr, "%s: `--engine-url' (`-u') option given more than once\n", CMDLINE_PARSER_PACKAGE); + clear_args (); + exit (EXIT_FAILURE); + } + args_info->engine_url_given = 1; + args_info->engine_url_arg = gengetopt_strdup (optarg); + break; + + case 'p': /* Client port to listen on. */ + if (args_info->client_port_given) + { + fprintf (stderr, "%s: `--client-port' (`-p') option given more than once\n", CMDLINE_PARSER_PACKAGE); + clear_args (); + exit (EXIT_FAILURE); + } + args_info->client_port_given = 1; + args_info->client_port_arg = strtol (optarg,&stop_char,0); + break; + + + case 0: /* Long option with no short option */ + + case '?': /* Invalid option. */ + /* `getopt_long' already printed an error message. */ + exit (EXIT_FAILURE); + + default: /* bug: option not considered. */ + fprintf (stderr, "%s: option unknown: %c\n", CMDLINE_PARSER_PACKAGE, c); + abort (); + } /* switch */ + } /* while */ + + + if ( missing_required_options ) + exit (EXIT_FAILURE); + + return 0; +} diff --git a/src/progs/demolition/cmdline.ggo b/src/progs/demolition/cmdline.ggo new file mode 100644 index 00000000..8fb68170 --- /dev/null +++ b/src/progs/demolition/cmdline.ggo @@ -0,0 +1,7 @@ +# Process this file with gengetopt -u to generate the necessary code (in cmdline.h, cmdline.c) + +package "om_demolition - A stress testing client for Om" + +option "engine-url" u "Om engine URL to connect to" string no +option "client-port" p "Client port to listen on" int no + diff --git a/src/progs/demolition/cmdline.h b/src/progs/demolition/cmdline.h new file mode 100644 index 00000000..be56aafe --- /dev/null +++ b/src/progs/demolition/cmdline.h @@ -0,0 +1,45 @@ +/* cmdline.h */ + +/* File autogenerated by gengetopt version 2.10 */ + +#ifndef CMDLINE_H +#define CMDLINE_H + +/* If we use autoconf. */ +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#ifdef __cplusplus +extern "C" { +#endif /* __cplusplus */ + +#ifndef CMDLINE_PARSER_PACKAGE +#define CMDLINE_PARSER_PACKAGE "om_demolotion - A stress testing client for Om" +#endif + +#ifndef CMDLINE_PARSER_VERSION +#define CMDLINE_PARSER_VERSION VERSION +#endif + +struct gengetopt_args_info +{ + char * engine_url_arg; /* Om engine URL to connect to. */ + int client_port_arg; /* Client port to listen on. */ + + int help_given ; /* Whether help was given. */ + int version_given ; /* Whether version was given. */ + int engine_url_given ; /* Whether engine-url was given. */ + int client_port_given ; /* Whether client-port was given. */ + +} ; + +int cmdline_parser (int argc, char * const *argv, struct gengetopt_args_info *args_info); + +void cmdline_parser_print_help(void); +void cmdline_parser_print_version(void); + +#ifdef __cplusplus +} +#endif /* __cplusplus */ +#endif /* CMDLINE_H */ diff --git a/src/progs/demolition/demolition.cpp b/src/progs/demolition/demolition.cpp new file mode 100644 index 00000000..84a08c84 --- /dev/null +++ b/src/progs/demolition/demolition.cpp @@ -0,0 +1,334 @@ +/* This file is part of Om. Copyright (C) 2005 Dave Robillard. + * + * Om is free software; you can redistribute it and/or modify it under the + * terms of the GNU General Public License as published by the Free Software + * Foundation; either version 2 of the License, or (at your option) any later + * version. + * + * Om is distributed in the hope that it will be useful, but WITHOUT ANY + * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#include "OSCModelEngineInterface.h" +#include "OSCModelEngineInterface.h" // FIXME: make conditional +#include "PatchLibrarian.h" +#include "DemolitionClientInterface.h" +#include "interface/ClientInterface.h" +#include "interface/ClientKey.h" +#include "util/CountedPtr.h" +#include <iostream> +#include <unistd.h> +#include <stdlib.h> +#include "cmdline.h" // generated by gengetopt + +using std::cout; +using std::endl; + +using namespace LibOmClient; + +void do_something(); + +string random_name(); + +void create_patch(); +void destroy(); +void add_node(); +void connect(); +void disconnect(); +void disconnect_all(); +void set_port_value(); +void set_port_value_queued(); +void rename_object(); + + +// Yay globals! +DemolitionModel* model; +OSCModelEngineInterface* engine; + + +int +main(int argc, char** argv) +{ + const char* engine_url = NULL; + int client_port = 0; + + /* Parse command line options */ + gengetopt_args_info args_info; + if (cmdline_parser (argc, argv, &args_info) != 0) + return 1; + + if (args_info.engine_url_given) { + engine_url = args_info.engine_url_arg; + } else { + cout << "[Main] No engine URL specified. Attempting to use osc.udp://localhost:16180" << endl; + engine_url = "osc.udp://localhost:16180"; + } + + if (args_info.client_port_given) + client_port = args_info.client_port_arg; + else + client_port = 0; // will choose a free port automatically + + model = new DemolitionModel(); + + // Create this first so engine interface (liblo) uses the port + CountedPtr<DemolitionClientInterface> client + = CountedPtr<DemolitionClientInterface>(new DemolitionClientInterface(model)); + + engine = new OSCModelEngineInterface(engine_url); + engine->activate(); + + /* Connect to engine */ + //engine->attach(engine_url); + engine->register_client(ClientKey(), (CountedPtr<ClientInterface>)client); + + engine->load_plugins(); + engine->request_plugins(); + + //int id = engine->get_next_request_id(); + engine->request_all_objects(/*id*/); + //engine->set_wait_response_id(id); + //engine->wait_for_response(); + + // Disable DSP for stress testing + engine->disable_patch("/"); + + while (true) { + do_something(); + usleep(100000); + } + + sleep(2); + engine->unregister_client(ClientKey()); + //engine->detach(); + + delete engine; + delete model; + + return 0; +} + +/** Does some random action + */ +void +do_something() +{ + int action = rand() % 10; + + switch(action) { + case 0: + create_patch(); break; + case 1: + destroy(); break; + case 2: + add_node(); break; + case 3: + connect(); break; + case 4: + disconnect(); break; + case 5: + disconnect_all(); break; + case 6: + set_port_value(); break; + case 7: + set_port_value_queued(); break; + case 8: + rename_object(); break; + default: + break; + } +} + + +string +random_name() +{ + int length = (rand()%10)+1; + string name(length, '-'); + + for (int i=0; i < length; ++i) + name[i] = 'a' + rand()%26; + + return name; +} + + +void +create_patch() +{ + // Make the probability of this happening inversely proportionate to the number + // of patches to keep the # in a sane range + //if (model->num_patches() > 0 && (rand() % model->num_patches())) + // return; + + bool subpatch = rand()%2; + PatchModel* parent = NULL; + string name = random_name(); + PatchModel* pm = NULL; + + if (subpatch) + parent = model->random_patch(); + + if (parent != NULL) + pm = new PatchModel(parent->path() +"/"+ name, (rand()%8)+1); + else + pm = new PatchModel(string("/") + name, (rand()%8)+1); + + cout << "Creating patch " << pm->path() << endl; + + engine->create_patch_from_model(pm); + + // Spread them out a bit for easier monitoring with om_gtk + char tmp_buf[8]; + snprintf(tmp_buf, 8, "%d", 1600 + rand()%800 - 400); + engine->set_metadata(pm->path(), "module-x", string(tmp_buf)); + snprintf(tmp_buf, 8, "%d", 1200 + rand()%700 - 350); + engine->set_metadata(pm->path(), "module-y", string(tmp_buf)); + + delete pm; +} + + +void +destroy() +{ + // Make the probability of this happening proportionate to the number + // of patches to keep the # in a sane range + if (model->num_patches() == 0 || !(rand() % model->num_patches())) + return; + + NodeModel* nm = NULL; + + if (rand()%2) + nm = model->random_patch(); + else + nm = model->random_node(); + + if (nm != NULL) { + cout << "Destroying " << nm->path() << endl; + engine->destroy(nm->path()); + } +} + + +void +add_node() +{ + PatchModel* parent = model->random_patch(); + PluginModel* plugin = model->random_plugin(); + + if (parent != NULL && plugin != NULL) { + NodeModel* nm = new NodeModel(parent->path() +"/"+ random_name()); + nm->plugin(plugin); + cout << "Adding node " << nm->path() << endl; + engine->create_node_from_model(nm); + // Spread them out a bit for easier monitoring with om_gtk + char tmp_buf[8]; + snprintf(tmp_buf, 8, "%d", 1600 + rand()%800 - 400); + engine->set_metadata(nm->path(), "module-x", tmp_buf); + snprintf(tmp_buf, 8, "%d", 1200 + rand()%700 - 350); + engine->set_metadata(nm->path(), "module-y", tmp_buf); + } +} + + +void +connect() +{ + if (!(rand() % 10)) { // Attempt a connection between two nodes in the same patch + PatchModel* parent = model->random_patch(); + NodeModel* n1 = model->random_node_in_patch(parent); + NodeModel* n2 = model->random_node_in_patch(parent); + PortModel* p1 = model->random_port_in_node(n1); + PortModel* p2 = model->random_port_in_node(n2); + + if (p1 != NULL && p2 != NULL) { + cout << "Connecting " << p1->path() << " -> " << p2->path() << endl; + engine->connect(p1->path(), p2->path()); + } + + } else { // Attempt a connection between two truly random nodes + PortModel* p1 = model->random_port(); + PortModel* p2 = model->random_port(); + + if (p1 != NULL && p2 != NULL) { + cout << "Connecting " << p1->path() << " -> " << p2->path() << endl; + engine->connect(p1->path(), p2->path()); + } + } +} + + +void +disconnect() +{ + PortModel* p1 = model->random_port(); + PortModel* p2 = model->random_port(); + + if (p1 != NULL && p2 != NULL) { + cout << "Disconnecting " << p1->path() << " -> " << p2->path() << endl; + engine->disconnect(p1->path(), p2->path()); + } +} + + +void +disconnect_all() +{ + PortModel* p = model->random_port(); + + if (p != NULL) { + cout << "Disconnecting all from" << p->path() << endl; + engine->disconnect_all(p->path()); + } +} + + +void +set_port_value() +{ + PortModel* pm = model->random_port(); + float val = (float)rand() / (float)RAND_MAX; + + if (pm != NULL) { + cout << "Setting control for port " << pm->path() << " to " << val << endl; + engine->set_port_value(pm->path(), val); + } +} + + +void +set_port_value_queued() +{ + PortModel* pm = model->random_port(); + float val = (float)rand() / (float)RAND_MAX; + + if (pm != NULL) { + cout << "Setting control (slow) for port " << pm->path() << " to " << val << endl; + engine->set_port_value_queued(pm->path(), val); + } +} + + +void +rename_object() +{ + // 1/6th chance of it being a patch + /*int type = rand()%6; + + if (type == 0) { + NodeModel* n = model->random_node(); + if (n != NULL) + engine->rename(n->path(), random_name()); + } else { + PatchModel* p = model->random_patch(); + if (p != NULL) + engine->rename(p->path(), random_name()); + }*/ +} + |