annotate src/vamp-sdk/PluginAdapter.cpp @ 525:8c18bdaad04f c++11-mutex

Avoid simple static allocation of mutex, as it could lead to mutex being destroyed before last adapter that needs to use it (since adapters are usually also static)
author Chris Cannam
date Mon, 09 Sep 2019 10:24:13 +0100
parents e0ff22b3c888
children bc5e76e90e95
rev   line source
cannam@3 1 /* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */
cannam@3 2
cannam@3 3 /*
cannam@3 4 Vamp
cannam@3 5
cannam@3 6 An API for audio analysis and feature extraction plugins.
cannam@3 7
cannam@3 8 Centre for Digital Music, Queen Mary, University of London.
cannam@3 9 Copyright 2006 Chris Cannam.
cannam@3 10
cannam@3 11 Permission is hereby granted, free of charge, to any person
cannam@3 12 obtaining a copy of this software and associated documentation
cannam@3 13 files (the "Software"), to deal in the Software without
cannam@3 14 restriction, including without limitation the rights to use, copy,
cannam@3 15 modify, merge, publish, distribute, sublicense, and/or sell copies
cannam@3 16 of the Software, and to permit persons to whom the Software is
cannam@3 17 furnished to do so, subject to the following conditions:
cannam@3 18
cannam@3 19 The above copyright notice and this permission notice shall be
cannam@3 20 included in all copies or substantial portions of the Software.
cannam@3 21
cannam@3 22 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
cannam@3 23 EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
cannam@3 24 MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
cannam@6 25 NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR
cannam@3 26 ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
cannam@3 27 CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
cannam@3 28 WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
cannam@3 29
cannam@3 30 Except as contained in this notice, the names of the Centre for
cannam@3 31 Digital Music; Queen Mary, University of London; and Chris Cannam
cannam@3 32 shall not be used in advertising or otherwise to promote the sale,
cannam@3 33 use or other dealings in this Software without prior written
cannam@3 34 authorization.
cannam@3 35 */
cannam@3 36
cannam@230 37 #include <vamp-sdk/PluginAdapter.h>
cannam@3 38
cannam@130 39 #include <cstring>
cannam@130 40 #include <cstdlib>
cannam@130 41
Chris@523 42 #include <mutex>
Chris@523 43
Chris@516 44 #if ( VAMP_SDK_MAJOR_VERSION != 2 || VAMP_SDK_MINOR_VERSION != 8 )
cannam@308 45 #error Unexpected version of Vamp SDK header included
cannam@234 46 #endif
cannam@234 47
Chris@523 48 using std::map;
Chris@523 49 using std::vector;
Chris@523 50 using std::string;
Chris@523 51 using std::cerr;
Chris@523 52 using std::endl;
Chris@523 53 using std::mutex;
Chris@523 54 using std::lock_guard;
cannam@234 55
cannam@23 56 //#define DEBUG_PLUGIN_ADAPTER 1
cannam@22 57
cannam@233 58 _VAMP_SDK_PLUGSPACE_BEGIN(PluginAdapter.cpp)
cannam@230 59
cannam@3 60 namespace Vamp {
cannam@3 61
cannam@76 62 class PluginAdapterBase::Impl
cannam@3 63 {
cannam@76 64 public:
cannam@76 65 Impl(PluginAdapterBase *);
cannam@76 66 ~Impl();
cannam@76 67
cannam@76 68 const VampPluginDescriptor *getDescriptor();
cannam@76 69
cannam@76 70 protected:
cannam@76 71 PluginAdapterBase *m_base;
cannam@76 72
cannam@76 73 static VampPluginHandle vampInstantiate(const VampPluginDescriptor *desc,
cannam@167 74 float inputSampleRate);
cannam@76 75
cannam@76 76 static void vampCleanup(VampPluginHandle handle);
cannam@76 77
cannam@76 78 static int vampInitialise(VampPluginHandle handle, unsigned int channels,
cannam@76 79 unsigned int stepSize, unsigned int blockSize);
cannam@76 80
cannam@76 81 static void vampReset(VampPluginHandle handle);
cannam@76 82
cannam@76 83 static float vampGetParameter(VampPluginHandle handle, int param);
cannam@76 84 static void vampSetParameter(VampPluginHandle handle, int param, float value);
cannam@76 85
cannam@76 86 static unsigned int vampGetCurrentProgram(VampPluginHandle handle);
cannam@76 87 static void vampSelectProgram(VampPluginHandle handle, unsigned int program);
cannam@76 88
cannam@76 89 static unsigned int vampGetPreferredStepSize(VampPluginHandle handle);
cannam@76 90 static unsigned int vampGetPreferredBlockSize(VampPluginHandle handle);
cannam@76 91 static unsigned int vampGetMinChannelCount(VampPluginHandle handle);
cannam@76 92 static unsigned int vampGetMaxChannelCount(VampPluginHandle handle);
cannam@76 93
cannam@76 94 static unsigned int vampGetOutputCount(VampPluginHandle handle);
cannam@76 95
cannam@76 96 static VampOutputDescriptor *vampGetOutputDescriptor(VampPluginHandle handle,
cannam@76 97 unsigned int i);
cannam@76 98
cannam@76 99 static void vampReleaseOutputDescriptor(VampOutputDescriptor *desc);
cannam@76 100
cannam@76 101 static VampFeatureList *vampProcess(VampPluginHandle handle,
cannam@76 102 const float *const *inputBuffers,
cannam@76 103 int sec,
cannam@76 104 int nsec);
cannam@76 105
cannam@76 106 static VampFeatureList *vampGetRemainingFeatures(VampPluginHandle handle);
cannam@76 107
cannam@76 108 static void vampReleaseFeatureSet(VampFeatureList *fs);
cannam@76 109
cannam@268 110 void checkOutputMap(Plugin *plugin);
cannam@268 111 void markOutputsChanged(Plugin *plugin);
cannam@268 112
cannam@76 113 void cleanup(Plugin *plugin);
cannam@76 114 unsigned int getOutputCount(Plugin *plugin);
cannam@76 115 VampOutputDescriptor *getOutputDescriptor(Plugin *plugin,
cannam@76 116 unsigned int i);
cannam@76 117 VampFeatureList *process(Plugin *plugin,
cannam@76 118 const float *const *inputBuffers,
cannam@76 119 int sec, int nsec);
cannam@76 120 VampFeatureList *getRemainingFeatures(Plugin *plugin);
cannam@76 121 VampFeatureList *convertFeatures(Plugin *plugin,
cannam@76 122 const Plugin::FeatureSet &features);
cannam@76 123
cannam@76 124 // maps both plugins and descriptors to adapters
Chris@523 125 typedef map<const void *, Impl *> AdapterMap;
cannam@76 126 static AdapterMap *m_adapterMap;
Chris@525 127 static mutex *m_adapterMapMutex;
cannam@76 128 static Impl *lookupAdapter(VampPluginHandle);
cannam@76 129
Chris@523 130 mutex m_mutex; // guards all of the below
Chris@523 131
cannam@76 132 bool m_populated;
cannam@76 133 VampPluginDescriptor m_descriptor;
cannam@76 134 Plugin::ParameterList m_parameters;
cannam@76 135 Plugin::ProgramList m_programs;
cannam@76 136
Chris@523 137 typedef map<Plugin *, Plugin::OutputList *> OutputMap;
cannam@76 138 OutputMap m_pluginOutputs;
cannam@76 139
Chris@523 140 map<Plugin *, VampFeatureList *> m_fs;
Chris@523 141 map<Plugin *, vector<size_t> > m_fsizes;
Chris@523 142 map<Plugin *, vector<vector<size_t> > > m_fvsizes;
cannam@76 143 void resizeFS(Plugin *plugin, int n);
cannam@76 144 void resizeFL(Plugin *plugin, int n, size_t sz);
cannam@76 145 void resizeFV(Plugin *plugin, int n, int j, size_t sz);
cannam@76 146 };
cannam@76 147
cannam@76 148 PluginAdapterBase::PluginAdapterBase()
cannam@76 149 {
cannam@76 150 m_impl = new Impl(this);
cannam@76 151 }
cannam@76 152
cannam@76 153 PluginAdapterBase::~PluginAdapterBase()
cannam@76 154 {
cannam@76 155 delete m_impl;
cannam@3 156 }
cannam@3 157
cannam@3 158 const VampPluginDescriptor *
cannam@3 159 PluginAdapterBase::getDescriptor()
cannam@3 160 {
cannam@76 161 return m_impl->getDescriptor();
cannam@76 162 }
cannam@76 163
cannam@76 164 PluginAdapterBase::Impl::Impl(PluginAdapterBase *base) :
cannam@76 165 m_base(base),
cannam@76 166 m_populated(false)
cannam@76 167 {
cannam@22 168 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 169 cerr << "PluginAdapterBase::Impl[" << this << "]::Impl" << endl;
cannam@76 170 #endif
cannam@76 171 }
cannam@76 172
cannam@76 173 const VampPluginDescriptor *
cannam@76 174 PluginAdapterBase::Impl::getDescriptor()
cannam@76 175 {
cannam@76 176 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 177 cerr << "PluginAdapterBase::Impl[" << this << "]::getDescriptor" << endl;
cannam@22 178 #endif
cannam@22 179
Chris@523 180 lock_guard<mutex> guard(m_mutex);
Chris@523 181
cannam@3 182 if (m_populated) return &m_descriptor;
Chris@467 183
cannam@76 184 Plugin *plugin = m_base->createPlugin(48000);
cannam@285 185
cannam@285 186 if (!plugin) {
Chris@523 187 cerr << "PluginAdapterBase::Impl::getDescriptor: Failed to create plugin" << endl;
cannam@285 188 return 0;
cannam@285 189 }
cannam@3 190
cannam@50 191 if (plugin->getVampApiVersion() != VAMP_API_VERSION) {
Chris@523 192 cerr << "Vamp::PluginAdapterBase::Impl::getDescriptor: ERROR: "
Chris@523 193 << "API version " << plugin->getVampApiVersion()
Chris@523 194 << " for\nplugin \"" << plugin->getIdentifier() << "\" "
Chris@523 195 << "differs from version "
Chris@523 196 << VAMP_API_VERSION << " for adapter.\n"
Chris@523 197 << "This plugin is probably linked against a different version of the Vamp SDK\n"
Chris@523 198 << "from the version it was compiled with. It will need to be re-linked correctly\n"
Chris@523 199 << "before it can be used." << endl;
cannam@50 200 delete plugin;
cannam@50 201 return 0;
cannam@50 202 }
cannam@50 203
cannam@3 204 m_parameters = plugin->getParameterDescriptors();
cannam@3 205 m_programs = plugin->getPrograms();
cannam@50 206
cannam@50 207 m_descriptor.vampApiVersion = plugin->getVampApiVersion();
cannam@49 208 m_descriptor.identifier = strdup(plugin->getIdentifier().c_str());
cannam@3 209 m_descriptor.name = strdup(plugin->getName().c_str());
cannam@3 210 m_descriptor.description = strdup(plugin->getDescription().c_str());
cannam@3 211 m_descriptor.maker = strdup(plugin->getMaker().c_str());
cannam@3 212 m_descriptor.pluginVersion = plugin->getPluginVersion();
cannam@3 213 m_descriptor.copyright = strdup(plugin->getCopyright().c_str());
cannam@3 214
cannam@3 215 m_descriptor.parameterCount = m_parameters.size();
cannam@3 216 m_descriptor.parameters = (const VampParameterDescriptor **)
cannam@3 217 malloc(m_parameters.size() * sizeof(VampParameterDescriptor));
cannam@7 218
cannam@7 219 unsigned int i;
cannam@3 220
cannam@7 221 for (i = 0; i < m_parameters.size(); ++i) {
cannam@3 222 VampParameterDescriptor *desc = (VampParameterDescriptor *)
cannam@3 223 malloc(sizeof(VampParameterDescriptor));
cannam@49 224 desc->identifier = strdup(m_parameters[i].identifier.c_str());
cannam@3 225 desc->name = strdup(m_parameters[i].name.c_str());
cannam@3 226 desc->description = strdup(m_parameters[i].description.c_str());
cannam@3 227 desc->unit = strdup(m_parameters[i].unit.c_str());
cannam@3 228 desc->minValue = m_parameters[i].minValue;
cannam@3 229 desc->maxValue = m_parameters[i].maxValue;
cannam@3 230 desc->defaultValue = m_parameters[i].defaultValue;
cannam@3 231 desc->isQuantized = m_parameters[i].isQuantized;
cannam@3 232 desc->quantizeStep = m_parameters[i].quantizeStep;
cannam@9 233 desc->valueNames = 0;
cannam@9 234 if (desc->isQuantized && !m_parameters[i].valueNames.empty()) {
cannam@9 235 desc->valueNames = (const char **)
cannam@9 236 malloc((m_parameters[i].valueNames.size()+1) * sizeof(char *));
cannam@9 237 for (unsigned int j = 0; j < m_parameters[i].valueNames.size(); ++j) {
cannam@9 238 desc->valueNames[j] = strdup(m_parameters[i].valueNames[j].c_str());
cannam@9 239 }
cannam@9 240 desc->valueNames[m_parameters[i].valueNames.size()] = 0;
cannam@9 241 }
cannam@3 242 m_descriptor.parameters[i] = desc;
cannam@3 243 }
cannam@3 244
cannam@3 245 m_descriptor.programCount = m_programs.size();
cannam@3 246 m_descriptor.programs = (const char **)
cannam@3 247 malloc(m_programs.size() * sizeof(const char *));
cannam@3 248
cannam@7 249 for (i = 0; i < m_programs.size(); ++i) {
cannam@3 250 m_descriptor.programs[i] = strdup(m_programs[i].c_str());
cannam@3 251 }
cannam@3 252
cannam@3 253 if (plugin->getInputDomain() == Plugin::FrequencyDomain) {
cannam@3 254 m_descriptor.inputDomain = vampFrequencyDomain;
cannam@3 255 } else {
cannam@3 256 m_descriptor.inputDomain = vampTimeDomain;
cannam@3 257 }
cannam@3 258
cannam@3 259 m_descriptor.instantiate = vampInstantiate;
cannam@3 260 m_descriptor.cleanup = vampCleanup;
cannam@3 261 m_descriptor.initialise = vampInitialise;
cannam@3 262 m_descriptor.reset = vampReset;
cannam@3 263 m_descriptor.getParameter = vampGetParameter;
cannam@3 264 m_descriptor.setParameter = vampSetParameter;
cannam@3 265 m_descriptor.getCurrentProgram = vampGetCurrentProgram;
cannam@3 266 m_descriptor.selectProgram = vampSelectProgram;
cannam@3 267 m_descriptor.getPreferredStepSize = vampGetPreferredStepSize;
cannam@3 268 m_descriptor.getPreferredBlockSize = vampGetPreferredBlockSize;
cannam@3 269 m_descriptor.getMinChannelCount = vampGetMinChannelCount;
cannam@3 270 m_descriptor.getMaxChannelCount = vampGetMaxChannelCount;
cannam@3 271 m_descriptor.getOutputCount = vampGetOutputCount;
cannam@3 272 m_descriptor.getOutputDescriptor = vampGetOutputDescriptor;
cannam@3 273 m_descriptor.releaseOutputDescriptor = vampReleaseOutputDescriptor;
cannam@3 274 m_descriptor.process = vampProcess;
cannam@3 275 m_descriptor.getRemainingFeatures = vampGetRemainingFeatures;
cannam@3 276 m_descriptor.releaseFeatureSet = vampReleaseFeatureSet;
Chris@523 277
Chris@525 278 lock_guard<mutex> adapterMapGuard(*m_adapterMapMutex);
cannam@3 279
cannam@13 280 if (!m_adapterMap) {
cannam@13 281 m_adapterMap = new AdapterMap;
cannam@13 282 }
cannam@15 283 (*m_adapterMap)[&m_descriptor] = this;
cannam@3 284
cannam@3 285 delete plugin;
cannam@3 286
cannam@3 287 m_populated = true;
cannam@3 288 return &m_descriptor;
cannam@3 289 }
cannam@3 290
cannam@76 291 PluginAdapterBase::Impl::~Impl()
cannam@3 292 {
cannam@22 293 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 294 cerr << "PluginAdapterBase::Impl[" << this << "]::~Impl" << endl;
cannam@22 295 #endif
cannam@22 296
Chris@523 297 lock_guard<mutex> guard(m_mutex);
Chris@523 298
cannam@3 299 if (!m_populated) return;
cannam@3 300
cannam@49 301 free((void *)m_descriptor.identifier);
cannam@3 302 free((void *)m_descriptor.name);
cannam@3 303 free((void *)m_descriptor.description);
cannam@3 304 free((void *)m_descriptor.maker);
cannam@3 305 free((void *)m_descriptor.copyright);
cannam@3 306
cannam@3 307 for (unsigned int i = 0; i < m_descriptor.parameterCount; ++i) {
cannam@3 308 const VampParameterDescriptor *desc = m_descriptor.parameters[i];
cannam@49 309 free((void *)desc->identifier);
cannam@3 310 free((void *)desc->name);
cannam@3 311 free((void *)desc->description);
cannam@3 312 free((void *)desc->unit);
cannam@9 313 if (desc->valueNames) {
cannam@9 314 for (unsigned int j = 0; desc->valueNames[j]; ++j) {
cannam@9 315 free((void *)desc->valueNames[j]);
cannam@9 316 }
cannam@9 317 free((void *)desc->valueNames);
cannam@9 318 }
Chris@467 319 free((void *)desc);
cannam@3 320 }
cannam@3 321 free((void *)m_descriptor.parameters);
cannam@3 322
cannam@3 323 for (unsigned int i = 0; i < m_descriptor.programCount; ++i) {
cannam@3 324 free((void *)m_descriptor.programs[i]);
cannam@3 325 }
cannam@3 326 free((void *)m_descriptor.programs);
cannam@3 327
Chris@525 328 lock_guard<mutex> adapterMapGuard(*m_adapterMapMutex);
Chris@523 329
cannam@13 330 if (m_adapterMap) {
cannam@13 331
cannam@13 332 m_adapterMap->erase(&m_descriptor);
Chris@525 333
cannam@13 334 if (m_adapterMap->empty()) {
cannam@13 335 delete m_adapterMap;
cannam@13 336 m_adapterMap = 0;
cannam@13 337 }
cannam@13 338 }
cannam@3 339 }
cannam@3 340
cannam@76 341 PluginAdapterBase::Impl *
cannam@76 342 PluginAdapterBase::Impl::lookupAdapter(VampPluginHandle handle)
cannam@3 343 {
cannam@22 344 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 345 cerr << "PluginAdapterBase::Impl::lookupAdapter(" << handle << ")" << endl;
cannam@22 346 #endif
cannam@22 347
Chris@525 348 lock_guard<mutex> adapterMapGuard(*m_adapterMapMutex);
Chris@523 349
cannam@13 350 if (!m_adapterMap) return 0;
cannam@13 351 AdapterMap::const_iterator i = m_adapterMap->find(handle);
cannam@13 352 if (i == m_adapterMap->end()) return 0;
cannam@3 353 return i->second;
cannam@3 354 }
cannam@3 355
cannam@3 356 VampPluginHandle
cannam@76 357 PluginAdapterBase::Impl::vampInstantiate(const VampPluginDescriptor *desc,
cannam@268 358 float inputSampleRate)
cannam@3 359 {
cannam@22 360 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 361 cerr << "PluginAdapterBase::Impl::vampInstantiate(" << desc << ")" << endl;
cannam@22 362 #endif
cannam@22 363
Chris@525 364 lock_guard<mutex> adapterMapGuard(*m_adapterMapMutex);
Chris@523 365
cannam@15 366 if (!m_adapterMap) {
cannam@15 367 m_adapterMap = new AdapterMap();
cannam@15 368 }
cannam@15 369
cannam@15 370 if (m_adapterMap->find(desc) == m_adapterMap->end()) {
Chris@523 371 cerr << "WARNING: PluginAdapterBase::Impl::vampInstantiate: Descriptor " << desc << " not in adapter map" << endl;
cannam@15 372 return 0;
cannam@15 373 }
cannam@15 374
cannam@76 375 Impl *adapter = (*m_adapterMap)[desc];
cannam@3 376 if (desc != &adapter->m_descriptor) return 0;
cannam@3 377
cannam@76 378 Plugin *plugin = adapter->m_base->createPlugin(inputSampleRate);
cannam@3 379 if (plugin) {
cannam@13 380 (*m_adapterMap)[plugin] = adapter;
cannam@3 381 }
cannam@3 382
cannam@22 383 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 384 cerr << "PluginAdapterBase::Impl::vampInstantiate(" << desc << "): returning handle " << plugin << endl;
cannam@22 385 #endif
cannam@22 386
cannam@3 387 return plugin;
cannam@3 388 }
cannam@3 389
cannam@3 390 void
cannam@76 391 PluginAdapterBase::Impl::vampCleanup(VampPluginHandle handle)
cannam@3 392 {
cannam@22 393 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 394 cerr << "PluginAdapterBase::Impl::vampCleanup(" << handle << ")" << endl;
cannam@22 395 #endif
cannam@22 396
cannam@76 397 Impl *adapter = lookupAdapter(handle);
cannam@3 398 if (!adapter) {
cannam@3 399 delete ((Plugin *)handle);
cannam@3 400 return;
cannam@3 401 }
cannam@3 402 adapter->cleanup(((Plugin *)handle));
cannam@3 403 }
cannam@3 404
cannam@3 405 int
cannam@76 406 PluginAdapterBase::Impl::vampInitialise(VampPluginHandle handle,
cannam@268 407 unsigned int channels,
cannam@268 408 unsigned int stepSize,
cannam@268 409 unsigned int blockSize)
cannam@3 410 {
cannam@22 411 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 412 cerr << "PluginAdapterBase::Impl::vampInitialise(" << handle << ", " << channels << ", " << stepSize << ", " << blockSize << ")" << endl;
cannam@22 413 #endif
cannam@22 414
cannam@268 415 Impl *adapter = lookupAdapter(handle);
cannam@268 416 if (!adapter) return 0;
cannam@268 417 bool result = ((Plugin *)handle)->initialise(channels, stepSize, blockSize);
cannam@268 418 adapter->markOutputsChanged((Plugin *)handle);
cannam@3 419 return result ? 1 : 0;
cannam@3 420 }
cannam@3 421
cannam@3 422 void
cannam@76 423 PluginAdapterBase::Impl::vampReset(VampPluginHandle handle)
cannam@3 424 {
cannam@22 425 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 426 cerr << "PluginAdapterBase::Impl::vampReset(" << handle << ")" << endl;
cannam@22 427 #endif
cannam@22 428
cannam@3 429 ((Plugin *)handle)->reset();
cannam@3 430 }
cannam@3 431
cannam@3 432 float
cannam@76 433 PluginAdapterBase::Impl::vampGetParameter(VampPluginHandle handle,
cannam@3 434 int param)
cannam@3 435 {
cannam@22 436 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 437 cerr << "PluginAdapterBase::Impl::vampGetParameter(" << handle << ", " << param << ")" << endl;
cannam@22 438 #endif
cannam@22 439
cannam@76 440 Impl *adapter = lookupAdapter(handle);
cannam@3 441 if (!adapter) return 0.0;
cannam@3 442 Plugin::ParameterList &list = adapter->m_parameters;
cannam@49 443 return ((Plugin *)handle)->getParameter(list[param].identifier);
cannam@3 444 }
cannam@3 445
cannam@3 446 void
cannam@76 447 PluginAdapterBase::Impl::vampSetParameter(VampPluginHandle handle,
cannam@3 448 int param, float value)
cannam@3 449 {
cannam@22 450 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 451 cerr << "PluginAdapterBase::Impl::vampSetParameter(" << handle << ", " << param << ", " << value << ")" << endl;
cannam@22 452 #endif
cannam@22 453
cannam@76 454 Impl *adapter = lookupAdapter(handle);
cannam@3 455 if (!adapter) return;
cannam@3 456 Plugin::ParameterList &list = adapter->m_parameters;
cannam@49 457 ((Plugin *)handle)->setParameter(list[param].identifier, value);
cannam@268 458 adapter->markOutputsChanged((Plugin *)handle);
cannam@3 459 }
cannam@3 460
cannam@3 461 unsigned int
cannam@76 462 PluginAdapterBase::Impl::vampGetCurrentProgram(VampPluginHandle handle)
cannam@3 463 {
cannam@22 464 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 465 cerr << "PluginAdapterBase::Impl::vampGetCurrentProgram(" << handle << ")" << endl;
cannam@22 466 #endif
cannam@22 467
cannam@76 468 Impl *adapter = lookupAdapter(handle);
cannam@3 469 if (!adapter) return 0;
cannam@3 470 Plugin::ProgramList &list = adapter->m_programs;
Chris@523 471 string program = ((Plugin *)handle)->getCurrentProgram();
cannam@3 472 for (unsigned int i = 0; i < list.size(); ++i) {
cannam@3 473 if (list[i] == program) return i;
cannam@3 474 }
cannam@3 475 return 0;
cannam@3 476 }
cannam@3 477
cannam@3 478 void
cannam@76 479 PluginAdapterBase::Impl::vampSelectProgram(VampPluginHandle handle,
cannam@268 480 unsigned int program)
cannam@3 481 {
cannam@22 482 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 483 cerr << "PluginAdapterBase::Impl::vampSelectProgram(" << handle << ", " << program << ")" << endl;
cannam@22 484 #endif
cannam@22 485
cannam@76 486 Impl *adapter = lookupAdapter(handle);
cannam@3 487 if (!adapter) return;
cannam@268 488
cannam@3 489 Plugin::ProgramList &list = adapter->m_programs;
cannam@3 490 ((Plugin *)handle)->selectProgram(list[program]);
cannam@268 491
cannam@268 492 adapter->markOutputsChanged((Plugin *)handle);
cannam@3 493 }
cannam@3 494
cannam@3 495 unsigned int
cannam@76 496 PluginAdapterBase::Impl::vampGetPreferredStepSize(VampPluginHandle handle)
cannam@3 497 {
cannam@22 498 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 499 cerr << "PluginAdapterBase::Impl::vampGetPreferredStepSize(" << handle << ")" << endl;
cannam@22 500 #endif
cannam@22 501
cannam@3 502 return ((Plugin *)handle)->getPreferredStepSize();
cannam@3 503 }
cannam@3 504
cannam@3 505 unsigned int
cannam@76 506 PluginAdapterBase::Impl::vampGetPreferredBlockSize(VampPluginHandle handle)
cannam@3 507 {
cannam@22 508 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 509 cerr << "PluginAdapterBase::Impl::vampGetPreferredBlockSize(" << handle << ")" << endl;
cannam@22 510 #endif
cannam@22 511
cannam@3 512 return ((Plugin *)handle)->getPreferredBlockSize();
cannam@3 513 }
cannam@3 514
cannam@3 515 unsigned int
cannam@76 516 PluginAdapterBase::Impl::vampGetMinChannelCount(VampPluginHandle handle)
cannam@3 517 {
cannam@22 518 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 519 cerr << "PluginAdapterBase::Impl::vampGetMinChannelCount(" << handle << ")" << endl;
cannam@22 520 #endif
cannam@22 521
cannam@3 522 return ((Plugin *)handle)->getMinChannelCount();
cannam@3 523 }
cannam@3 524
cannam@3 525 unsigned int
cannam@76 526 PluginAdapterBase::Impl::vampGetMaxChannelCount(VampPluginHandle handle)
cannam@3 527 {
cannam@22 528 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 529 cerr << "PluginAdapterBase::Impl::vampGetMaxChannelCount(" << handle << ")" << endl;
cannam@22 530 #endif
cannam@22 531
cannam@3 532 return ((Plugin *)handle)->getMaxChannelCount();
cannam@3 533 }
cannam@3 534
cannam@3 535 unsigned int
cannam@76 536 PluginAdapterBase::Impl::vampGetOutputCount(VampPluginHandle handle)
cannam@3 537 {
cannam@22 538 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 539 cerr << "PluginAdapterBase::Impl::vampGetOutputCount(" << handle << ")" << endl;
cannam@22 540 #endif
cannam@22 541
cannam@76 542 Impl *adapter = lookupAdapter(handle);
cannam@15 543
Chris@523 544 // cerr << "vampGetOutputCount: handle " << handle << " -> adapter "<< adapter << endl;
cannam@15 545
cannam@3 546 if (!adapter) return 0;
cannam@3 547 return adapter->getOutputCount((Plugin *)handle);
cannam@3 548 }
cannam@3 549
cannam@3 550 VampOutputDescriptor *
cannam@76 551 PluginAdapterBase::Impl::vampGetOutputDescriptor(VampPluginHandle handle,
cannam@268 552 unsigned int i)
cannam@3 553 {
cannam@22 554 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 555 cerr << "PluginAdapterBase::Impl::vampGetOutputDescriptor(" << handle << ", " << i << ")" << endl;
cannam@22 556 #endif
cannam@22 557
cannam@76 558 Impl *adapter = lookupAdapter(handle);
cannam@15 559
Chris@523 560 // cerr << "vampGetOutputDescriptor: handle " << handle << " -> adapter "<< adapter << endl;
cannam@15 561
cannam@3 562 if (!adapter) return 0;
cannam@3 563 return adapter->getOutputDescriptor((Plugin *)handle, i);
cannam@3 564 }
cannam@3 565
cannam@3 566 void
cannam@76 567 PluginAdapterBase::Impl::vampReleaseOutputDescriptor(VampOutputDescriptor *desc)
cannam@3 568 {
cannam@22 569 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 570 cerr << "PluginAdapterBase::Impl::vampReleaseOutputDescriptor(" << desc << ")" << endl;
cannam@22 571 #endif
cannam@22 572
cannam@49 573 if (desc->identifier) free((void *)desc->identifier);
cannam@3 574 if (desc->name) free((void *)desc->name);
cannam@3 575 if (desc->description) free((void *)desc->description);
cannam@3 576 if (desc->unit) free((void *)desc->unit);
cannam@40 577 if (desc->hasFixedBinCount && desc->binNames) {
cannam@40 578 for (unsigned int i = 0; i < desc->binCount; ++i) {
cannam@40 579 if (desc->binNames[i]) {
cannam@40 580 free((void *)desc->binNames[i]);
cannam@40 581 }
cannam@40 582 }
cannam@3 583 }
cannam@9 584 if (desc->binNames) free((void *)desc->binNames);
cannam@3 585 free((void *)desc);
cannam@3 586 }
cannam@3 587
cannam@12 588 VampFeatureList *
cannam@76 589 PluginAdapterBase::Impl::vampProcess(VampPluginHandle handle,
cannam@108 590 const float *const *inputBuffers,
cannam@108 591 int sec,
cannam@108 592 int nsec)
cannam@3 593 {
cannam@22 594 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 595 cerr << "PluginAdapterBase::Impl::vampProcess(" << handle << ", " << sec << ", " << nsec << ")" << endl;
cannam@22 596 #endif
cannam@22 597
cannam@76 598 Impl *adapter = lookupAdapter(handle);
cannam@3 599 if (!adapter) return 0;
cannam@268 600 return adapter->process((Plugin *)handle, inputBuffers, sec, nsec);
cannam@3 601 }
cannam@3 602
cannam@12 603 VampFeatureList *
cannam@76 604 PluginAdapterBase::Impl::vampGetRemainingFeatures(VampPluginHandle handle)
cannam@3 605 {
cannam@22 606 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 607 cerr << "PluginAdapterBase::Impl::vampGetRemainingFeatures(" << handle << ")" << endl;
cannam@22 608 #endif
cannam@22 609
cannam@76 610 Impl *adapter = lookupAdapter(handle);
cannam@3 611 if (!adapter) return 0;
cannam@3 612 return adapter->getRemainingFeatures((Plugin *)handle);
cannam@3 613 }
cannam@3 614
cannam@3 615 void
Chris@398 616 PluginAdapterBase::Impl::vampReleaseFeatureSet(VampFeatureList *)
cannam@3 617 {
cannam@22 618 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 619 cerr << "PluginAdapterBase::Impl::vampReleaseFeatureSet" << endl;
cannam@22 620 #endif
cannam@3 621 }
cannam@3 622
cannam@3 623 void
cannam@76 624 PluginAdapterBase::Impl::cleanup(Plugin *plugin)
cannam@3 625 {
Chris@523 626 // at this point no mutex is held
Chris@523 627
Chris@525 628 lock_guard<mutex> adapterMapGuard(*m_adapterMapMutex);
Chris@523 629 lock_guard<mutex> guard(m_mutex);
Chris@523 630
cannam@12 631 if (m_fs.find(plugin) != m_fs.end()) {
cannam@12 632 size_t outputCount = 0;
cannam@12 633 if (m_pluginOutputs[plugin]) {
cannam@12 634 outputCount = m_pluginOutputs[plugin]->size();
cannam@12 635 }
Chris@471 636 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 637 cerr << "PluginAdapterBase::Impl::cleanup: " << outputCount << " output(s)" << endl;
Chris@471 638 #endif
cannam@12 639 VampFeatureList *list = m_fs[plugin];
cannam@12 640 for (unsigned int i = 0; i < outputCount; ++i) {
cannam@12 641 for (unsigned int j = 0; j < m_fsizes[plugin][i]; ++j) {
cannam@168 642 if (list[i].features[j].v1.label) {
cannam@168 643 free(list[i].features[j].v1.label);
cannam@12 644 }
cannam@168 645 if (list[i].features[j].v1.values) {
cannam@168 646 free(list[i].features[j].v1.values);
cannam@12 647 }
cannam@12 648 }
cannam@12 649 if (list[i].features) free(list[i].features);
cannam@12 650 }
Chris@467 651 if (list) free((void *)list);
cannam@12 652 m_fs.erase(plugin);
cannam@12 653 m_fsizes.erase(plugin);
cannam@12 654 m_fvsizes.erase(plugin);
cannam@12 655 }
cannam@12 656
cannam@3 657 if (m_pluginOutputs.find(plugin) != m_pluginOutputs.end()) {
cannam@3 658 delete m_pluginOutputs[plugin];
cannam@3 659 m_pluginOutputs.erase(plugin);
cannam@3 660 }
cannam@13 661
cannam@13 662 if (m_adapterMap) {
cannam@13 663 m_adapterMap->erase(plugin);
cannam@13 664
cannam@13 665 if (m_adapterMap->empty()) {
cannam@13 666 delete m_adapterMap;
cannam@13 667 m_adapterMap = 0;
cannam@13 668 }
cannam@13 669 }
cannam@13 670
cannam@3 671 delete ((Plugin *)plugin);
cannam@3 672 }
cannam@3 673
cannam@3 674 void
cannam@76 675 PluginAdapterBase::Impl::checkOutputMap(Plugin *plugin)
cannam@3 676 {
Chris@523 677 // must be called with m_mutex held
Chris@523 678
cannam@268 679 OutputMap::iterator i = m_pluginOutputs.find(plugin);
cannam@268 680
cannam@268 681 if (i == m_pluginOutputs.end() || !i->second) {
cannam@268 682
cannam@3 683 m_pluginOutputs[plugin] = new Plugin::OutputList
cannam@3 684 (plugin->getOutputDescriptors());
cannam@268 685
Chris@523 686 // cerr << "PluginAdapterBase::Impl::checkOutputMap: Have " << m_pluginOutputs[plugin]->size() << " outputs for plugin " << plugin->getIdentifier() << endl;
cannam@3 687 }
cannam@3 688 }
cannam@3 689
cannam@268 690 void
cannam@268 691 PluginAdapterBase::Impl::markOutputsChanged(Plugin *plugin)
cannam@268 692 {
Chris@523 693 lock_guard<mutex> guard(m_mutex);
Chris@523 694
cannam@268 695 OutputMap::iterator i = m_pluginOutputs.find(plugin);
cannam@268 696
Chris@523 697 // cerr << "PluginAdapterBase::Impl::markOutputsChanged" << endl;
cannam@268 698
cannam@268 699 if (i != m_pluginOutputs.end()) {
cannam@268 700
cannam@268 701 Plugin::OutputList *list = i->second;
cannam@268 702 m_pluginOutputs.erase(i);
cannam@268 703 delete list;
cannam@268 704 }
cannam@268 705 }
cannam@268 706
cannam@3 707 unsigned int
cannam@76 708 PluginAdapterBase::Impl::getOutputCount(Plugin *plugin)
cannam@3 709 {
Chris@523 710 lock_guard<mutex> guard(m_mutex);
Chris@523 711
cannam@3 712 checkOutputMap(plugin);
cannam@268 713
cannam@3 714 return m_pluginOutputs[plugin]->size();
cannam@3 715 }
cannam@3 716
cannam@3 717 VampOutputDescriptor *
cannam@76 718 PluginAdapterBase::Impl::getOutputDescriptor(Plugin *plugin,
cannam@268 719 unsigned int i)
cannam@3 720 {
Chris@523 721 lock_guard<mutex> guard(m_mutex);
Chris@523 722
cannam@3 723 checkOutputMap(plugin);
cannam@268 724
cannam@3 725 Plugin::OutputDescriptor &od =
cannam@3 726 (*m_pluginOutputs[plugin])[i];
cannam@3 727
cannam@3 728 VampOutputDescriptor *desc = (VampOutputDescriptor *)
cannam@3 729 malloc(sizeof(VampOutputDescriptor));
cannam@3 730
cannam@49 731 desc->identifier = strdup(od.identifier.c_str());
cannam@3 732 desc->name = strdup(od.name.c_str());
cannam@3 733 desc->description = strdup(od.description.c_str());
cannam@3 734 desc->unit = strdup(od.unit.c_str());
cannam@9 735 desc->hasFixedBinCount = od.hasFixedBinCount;
cannam@9 736 desc->binCount = od.binCount;
cannam@3 737
cannam@240 738 if (od.hasFixedBinCount && od.binCount > 0
cannam@240 739 // We would like to do "&& !od.binNames.empty()" here -- but we
cannam@240 740 // can't, because it will crash older versions of the host adapter
cannam@240 741 // which try to copy the names across whenever the bin count is
cannam@240 742 // non-zero, regardless of whether they exist or not
cannam@240 743 ) {
cannam@9 744 desc->binNames = (const char **)
cannam@9 745 malloc(od.binCount * sizeof(const char *));
cannam@3 746
cannam@9 747 for (unsigned int i = 0; i < od.binCount; ++i) {
cannam@9 748 if (i < od.binNames.size()) {
cannam@9 749 desc->binNames[i] = strdup(od.binNames[i].c_str());
cannam@7 750 } else {
cannam@9 751 desc->binNames[i] = 0;
cannam@7 752 }
cannam@3 753 }
cannam@7 754 } else {
cannam@9 755 desc->binNames = 0;
cannam@3 756 }
cannam@3 757
cannam@3 758 desc->hasKnownExtents = od.hasKnownExtents;
cannam@3 759 desc->minValue = od.minValue;
cannam@3 760 desc->maxValue = od.maxValue;
cannam@3 761 desc->isQuantized = od.isQuantized;
cannam@3 762 desc->quantizeStep = od.quantizeStep;
cannam@3 763
cannam@3 764 switch (od.sampleType) {
cannam@3 765 case Plugin::OutputDescriptor::OneSamplePerStep:
cannam@3 766 desc->sampleType = vampOneSamplePerStep; break;
cannam@3 767 case Plugin::OutputDescriptor::FixedSampleRate:
cannam@3 768 desc->sampleType = vampFixedSampleRate; break;
cannam@3 769 case Plugin::OutputDescriptor::VariableSampleRate:
cannam@3 770 desc->sampleType = vampVariableSampleRate; break;
cannam@3 771 }
cannam@3 772
cannam@3 773 desc->sampleRate = od.sampleRate;
cannam@192 774 desc->hasDuration = od.hasDuration;
cannam@3 775
cannam@3 776 return desc;
cannam@3 777 }
cannam@3 778
cannam@12 779 VampFeatureList *
cannam@76 780 PluginAdapterBase::Impl::process(Plugin *plugin,
cannam@108 781 const float *const *inputBuffers,
cannam@108 782 int sec, int nsec)
cannam@3 783 {
Chris@523 784 // cerr << "PluginAdapterBase::Impl::process" << endl;
Chris@523 785
cannam@3 786 RealTime rt(sec, nsec);
Chris@523 787
Chris@523 788 // We don't want to hold the mutex during the actual process call,
Chris@523 789 // only while looking up the associated metadata
Chris@523 790 {
Chris@523 791 lock_guard<mutex> guard(m_mutex);
Chris@523 792 checkOutputMap(plugin);
Chris@523 793 }
Chris@523 794
cannam@12 795 return convertFeatures(plugin, plugin->process(inputBuffers, rt));
cannam@3 796 }
cannam@3 797
cannam@12 798 VampFeatureList *
cannam@76 799 PluginAdapterBase::Impl::getRemainingFeatures(Plugin *plugin)
cannam@3 800 {
Chris@523 801 // cerr << "PluginAdapterBase::Impl::getRemainingFeatures" << endl;
Chris@523 802
Chris@523 803 // We don't want to hold the mutex during the actual call, only
Chris@523 804 // while looking up the associated metadata
Chris@523 805 {
Chris@523 806 lock_guard<mutex> guard(m_mutex);
Chris@523 807 checkOutputMap(plugin);
Chris@523 808 }
Chris@523 809
cannam@12 810 return convertFeatures(plugin, plugin->getRemainingFeatures());
cannam@3 811 }
cannam@3 812
cannam@12 813 VampFeatureList *
cannam@76 814 PluginAdapterBase::Impl::convertFeatures(Plugin *plugin,
cannam@167 815 const Plugin::FeatureSet &features)
cannam@3 816 {
Chris@523 817 lock_guard<mutex> guard(m_mutex);
Chris@523 818
cannam@12 819 int lastN = -1;
cannam@3 820
cannam@12 821 int outputCount = 0;
cannam@12 822 if (m_pluginOutputs[plugin]) outputCount = m_pluginOutputs[plugin]->size();
cannam@12 823
cannam@12 824 resizeFS(plugin, outputCount);
cannam@12 825 VampFeatureList *fs = m_fs[plugin];
cannam@3 826
Chris@523 827 // cerr << "PluginAdapter(v2)::convertFeatures: NOTE: sizeof(Feature) == " << sizeof(Plugin::Feature) << ", sizeof(VampFeature) == " << sizeof(VampFeature) << ", sizeof(VampFeatureList) == " << sizeof(VampFeatureList) << endl;
cannam@168 828
cannam@12 829 for (Plugin::FeatureSet::const_iterator fi = features.begin();
cannam@12 830 fi != features.end(); ++fi) {
cannam@3 831
cannam@12 832 int n = fi->first;
cannam@12 833
Chris@523 834 // cerr << "PluginAdapterBase::Impl::convertFeatures: n = " << n << endl;
cannam@7 835
cannam@12 836 if (n >= int(outputCount)) {
Chris@523 837 cerr << "WARNING: PluginAdapterBase::Impl::convertFeatures: Too many outputs from plugin (" << n+1 << ", only should be " << outputCount << ")" << endl;
cannam@7 838 continue;
cannam@7 839 }
cannam@7 840
cannam@12 841 if (n > lastN + 1) {
cannam@12 842 for (int i = lastN + 1; i < n; ++i) {
cannam@12 843 fs[i].featureCount = 0;
cannam@12 844 }
cannam@12 845 }
cannam@7 846
cannam@7 847 const Plugin::FeatureList &fl = fi->second;
cannam@7 848
cannam@12 849 size_t sz = fl.size();
cannam@12 850 if (sz > m_fsizes[plugin][n]) resizeFL(plugin, n, sz);
cannam@12 851 fs[n].featureCount = sz;
cannam@12 852
cannam@12 853 for (size_t j = 0; j < sz; ++j) {
cannam@7 854
Chris@523 855 // cerr << "PluginAdapterBase::Impl::convertFeatures: j = " << j << endl;
cannam@7 856
cannam@168 857 VampFeature *feature = &fs[n].features[j].v1;
cannam@7 858
cannam@7 859 feature->hasTimestamp = fl[j].hasTimestamp;
cannam@7 860 feature->sec = fl[j].timestamp.sec;
cannam@7 861 feature->nsec = fl[j].timestamp.nsec;
cannam@7 862 feature->valueCount = fl[j].values.size();
cannam@7 863
cannam@168 864 VampFeatureV2 *v2 = &fs[n].features[j + sz].v2;
cannam@167 865
cannam@167 866 v2->hasDuration = fl[j].hasDuration;
cannam@167 867 v2->durationSec = fl[j].duration.sec;
cannam@167 868 v2->durationNsec = fl[j].duration.nsec;
cannam@167 869
cannam@12 870 if (feature->label) free(feature->label);
cannam@12 871
cannam@12 872 if (fl[j].label.empty()) {
cannam@12 873 feature->label = 0;
cannam@12 874 } else {
cannam@12 875 feature->label = strdup(fl[j].label.c_str());
cannam@7 876 }
cannam@7 877
cannam@12 878 if (feature->valueCount > m_fvsizes[plugin][n][j]) {
cannam@12 879 resizeFV(plugin, n, j, feature->valueCount);
cannam@12 880 }
cannam@7 881
cannam@7 882 for (unsigned int k = 0; k < feature->valueCount; ++k) {
Chris@523 883 // cerr << "PluginAdapterBase::Impl::convertFeatures: k = " << k << endl;
cannam@7 884 feature->values[k] = fl[j].values[k];
cannam@3 885 }
cannam@3 886 }
cannam@12 887
cannam@12 888 lastN = n;
cannam@3 889 }
cannam@3 890
cannam@12 891 if (lastN == -1) return 0;
cannam@12 892
cannam@12 893 if (int(outputCount) > lastN + 1) {
cannam@12 894 for (int i = lastN + 1; i < int(outputCount); ++i) {
cannam@12 895 fs[i].featureCount = 0;
cannam@12 896 }
cannam@12 897 }
cannam@3 898
Chris@523 899 // cerr << "PluginAdapter(v2)::convertFeatures: NOTE: have " << outputCount << " outputs" << endl;
cannam@168 900 // for (int i = 0; i < outputCount; ++i) {
Chris@523 901 // cerr << "PluginAdapter(v2)::convertFeatures: NOTE: output " << i << " has " << fs[i].featureCount << " features" << endl;
cannam@168 902 // }
cannam@168 903
cannam@168 904
cannam@3 905 return fs;
cannam@3 906 }
cannam@3 907
cannam@12 908 void
cannam@76 909 PluginAdapterBase::Impl::resizeFS(Plugin *plugin, int n)
cannam@12 910 {
Chris@523 911 // called with m_mutex held
Chris@523 912
Chris@467 913 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 914 cerr << "PluginAdapterBase::Impl::resizeFS(" << plugin << ", " << n << ")" << endl;
Chris@467 915 #endif
cannam@12 916
cannam@12 917 int i = m_fsizes[plugin].size();
cannam@12 918 if (i >= n) return;
cannam@12 919
Chris@467 920 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 921 cerr << "resizing from " << i << endl;
Chris@467 922 #endif
cannam@12 923
cannam@12 924 m_fs[plugin] = (VampFeatureList *)realloc
cannam@12 925 (m_fs[plugin], n * sizeof(VampFeatureList));
cannam@12 926
cannam@12 927 while (i < n) {
cannam@12 928 m_fs[plugin][i].featureCount = 0;
cannam@12 929 m_fs[plugin][i].features = 0;
cannam@12 930 m_fsizes[plugin].push_back(0);
Chris@523 931 m_fvsizes[plugin].push_back(vector<size_t>());
cannam@12 932 i++;
cannam@12 933 }
cannam@12 934 }
cannam@12 935
cannam@12 936 void
cannam@76 937 PluginAdapterBase::Impl::resizeFL(Plugin *plugin, int n, size_t sz)
cannam@12 938 {
Chris@523 939 // called with m_mutex held
Chris@523 940
Chris@467 941 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 942 cerr << "PluginAdapterBase::Impl::resizeFL(" << plugin << ", " << n << ", "
Chris@523 943 << sz << ")" << endl;
Chris@467 944 #endif
Chris@467 945
cannam@12 946 size_t i = m_fsizes[plugin][n];
cannam@12 947 if (i >= sz) return;
cannam@12 948
Chris@467 949 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 950 cerr << "resizing from " << i << endl;
Chris@467 951 #endif
cannam@12 952
cannam@168 953 m_fs[plugin][n].features = (VampFeatureUnion *)realloc
cannam@168 954 (m_fs[plugin][n].features, 2 * sz * sizeof(VampFeatureUnion));
cannam@167 955
cannam@12 956 while (m_fsizes[plugin][n] < sz) {
cannam@168 957 m_fs[plugin][n].features[m_fsizes[plugin][n]].v1.hasTimestamp = 0;
cannam@168 958 m_fs[plugin][n].features[m_fsizes[plugin][n]].v1.valueCount = 0;
cannam@168 959 m_fs[plugin][n].features[m_fsizes[plugin][n]].v1.values = 0;
cannam@168 960 m_fs[plugin][n].features[m_fsizes[plugin][n]].v1.label = 0;
cannam@189 961 m_fs[plugin][n].features[m_fsizes[plugin][n] + sz].v2.hasDuration = 0;
cannam@12 962 m_fvsizes[plugin][n].push_back(0);
cannam@12 963 m_fsizes[plugin][n]++;
cannam@12 964 }
cannam@12 965 }
cannam@12 966
cannam@12 967 void
cannam@76 968 PluginAdapterBase::Impl::resizeFV(Plugin *plugin, int n, int j, size_t sz)
cannam@12 969 {
Chris@523 970 // called with m_mutex held
Chris@523 971
Chris@467 972 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 973 cerr << "PluginAdapterBase::Impl::resizeFV(" << plugin << ", " << n << ", "
Chris@523 974 << j << ", " << sz << ")" << endl;
Chris@467 975 #endif
Chris@467 976
cannam@12 977 size_t i = m_fvsizes[plugin][n][j];
cannam@12 978 if (i >= sz) return;
cannam@12 979
Chris@467 980 #ifdef DEBUG_PLUGIN_ADAPTER
Chris@523 981 cerr << "resizing from " << i << endl;
Chris@467 982 #endif
Chris@467 983
cannam@168 984 m_fs[plugin][n].features[j].v1.values = (float *)realloc
cannam@168 985 (m_fs[plugin][n].features[j].v1.values, sz * sizeof(float));
cannam@12 986
cannam@12 987 m_fvsizes[plugin][n][j] = sz;
cannam@12 988 }
cannam@12 989
cannam@76 990 PluginAdapterBase::Impl::AdapterMap *
cannam@76 991 PluginAdapterBase::Impl::m_adapterMap = 0;
cannam@3 992
Chris@525 993 // This is allocated on the heap so that we can be sure it outlives
Chris@525 994 // the adapters themselves, which are typically static within the
Chris@525 995 // plugin library. If this was also static, then it might be destroyed
Chris@525 996 // before the last adapter, and we would end up trying to lock an
Chris@525 997 // invalid mutex when removing an adapter from the adapter map.
Chris@525 998 mutex *
Chris@525 999 PluginAdapterBase::Impl::m_adapterMapMutex = new mutex;
Chris@523 1000
cannam@3 1001 }
cannam@3 1002
cannam@233 1003 _VAMP_SDK_PLUGSPACE_END(PluginAdapter.cpp)
cannam@230 1004