|
- /*
- ZynAddSubFX - a software synthesizer
-
- WatchPoint.cpp - Synthesis State Watcher
- Copyright (C) 2015-2015 Mark McCurry
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of version 2 of the GNU General Public License
- as published by the Free Software Foundation.
-
- This program 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 (version 2 or later) for more details.
-
- You should have received a copy of the GNU General Public License (version 2)
- along with this program; if not, write to the Free Software Foundation,
- Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
-
- */
-
- #include "WatchPoint.h"
- #include <cstring>
- #include <rtosc/thread-link.h>
-
- namespace zyncarla {
-
- WatchPoint::WatchPoint(WatchManager *ref, const char *prefix, const char *id)
- :active(false), samples_left(0), reference(ref)
- {
- identity[0] = 0;
- if(prefix)
- strncpy(identity, prefix, 128);
- if(id)
- strncat(identity, id, 128);
- }
-
- bool WatchPoint::is_active(void)
- {
- //Either the watchpoint is already active or the watchpoint manager has
- //received another activation this frame
- if(active)
- return true;
-
- if(reference && reference->active(identity)) {
- active = true;
- samples_left = 1;
- return true;
- }
-
- return false;
- }
-
- FloatWatchPoint::FloatWatchPoint(WatchManager *ref, const char *prefix, const char *id)
- :WatchPoint(ref, prefix, id)
- {}
-
- VecWatchPoint::VecWatchPoint(WatchManager *ref, const char *prefix, const char *id)
- :WatchPoint(ref, prefix, id)
- {}
-
- WatchManager::WatchManager(thrlnk *link)
- :write_back(link), new_active(false)
- {
- memset(active_list, 0, sizeof(active_list));
- memset(sample_list, 0, sizeof(sample_list));
- memset(data_list, 0, sizeof(data_list));
- memset(deactivate, 0, sizeof(deactivate));
- }
-
- void WatchManager::add_watch(const char *id)
- {
- //Don't add duplicate watchs
- for(int i=0; i<MAX_WATCH; ++i)
- if(!strcmp(active_list[i], id))
- return;
-
- //Apply to a free slot
- for(int i=0; i<MAX_WATCH; ++i) {
- if(!active_list[i][0]) {
- strncpy(active_list[i], id, 128);
- new_active = true;
- sample_list[i] = 0;
- break;
- }
- }
- }
-
- void WatchManager::del_watch(const char *id)
- {
- //Queue up the delete
- for(int i=0; i<MAX_WATCH; ++i)
- if(!strcmp(active_list[i], id))
- return (void) (deactivate[i] = true);
- }
-
- void WatchManager::tick(void)
- {
- //Try to send out any vector stuff
- for(int i=0; i<MAX_WATCH; ++i) {
- if(sample_list[i]) {
- char arg_types[MAX_SAMPLE+1] = {0};
- rtosc_arg_t arg_val[MAX_SAMPLE];
- for(int j=0; j<sample_list[i]; ++j) {
- arg_types[j] = 'f';
- arg_val[j].f = data_list[i][j];
- }
-
- write_back->writeArray(active_list[i], arg_types, arg_val);
- deactivate[i] = true;
- }
- }
-
- //Cleanup internal data
- new_active = false;
-
- //Clear deleted slots
- for(int i=0; i<MAX_WATCH; ++i) {
- if(deactivate[i]) {
- memset(active_list[i], 0, 128);
- sample_list[i] = 0;
- deactivate[i] = false;
- }
- }
-
- }
-
- bool WatchManager::active(const char *id) const
- {
- assert(this);
- assert(id);
- if(new_active || true)
- for(int i=0; i<MAX_WATCH; ++i)
- if(!strcmp(active_list[i], id))
- return true;
-
- return false;
- }
-
- int WatchManager::samples(const char *id) const
- {
- for(int i=0; i<MAX_WATCH; ++i)
- if(!strcmp(active_list[i], id))
- return sample_list[i];
- return 0;
- }
-
- void WatchManager::satisfy(const char *id, float f)
- {
- //printf("trying to satisfy '%s'\n", id);
- if(write_back)
- write_back->write(id, "f", f);
- del_watch(id);
- }
-
- void WatchManager::satisfy(const char *id, float *f, int n)
- {
- int selected = -1;
- for(int i=0; i<MAX_WATCH; ++i)
- if(!strcmp(active_list[i], id))
- selected = i;
-
- if(selected == -1)
- return;
-
- //FIXME buffer overflow
- for(int i=0; i<n; ++i)
- data_list[selected][sample_list[selected]++] = f[i];
- }
-
- }
|