Audio plugin host https://kx.studio/carla
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1766 lines
62KB

  1. /*
  2. * Carla DSSI Plugin
  3. * Copyright (C) 2011-2013 Filipe Coelho <falktx@falktx.com>
  4. *
  5. * This program is free software; you can redistribute it and/or
  6. * modify it under the terms of the GNU General Public License as
  7. * published by the Free Software Foundation; either version 2 of
  8. * the License, or any later version.
  9. *
  10. * This program is distributed in the hope that it will be useful,
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. * GNU General Public License for more details.
  14. *
  15. * For a full copy of the GNU General Public License see the GPL.txt file
  16. */
  17. #include "CarlaPluginInternal.hpp"
  18. #ifdef WANT_DSSI
  19. #include "CarlaLadspaUtils.hpp"
  20. #include "dssi/dssi.h"
  21. CARLA_BACKEND_START_NAMESPACE
  22. class DssiPlugin : public CarlaPlugin
  23. {
  24. public:
  25. DssiPlugin(CarlaEngine* const engine, const unsigned int id)
  26. : CarlaPlugin(engine, id)
  27. {
  28. carla_debug("DssiPlugin::DssiPlugin(%p, %i)", engine, id);
  29. fHandle = nullptr;
  30. fHandle2 = nullptr;
  31. fDescriptor = nullptr;
  32. fDssiDescriptor = nullptr;
  33. fAudioInBuffers = nullptr;
  34. fAudioOutBuffers = nullptr;
  35. fParamBuffers = nullptr;
  36. carla_zeroMem(fMidiEvents, sizeof(snd_seq_event_t)*MAX_MIDI_EVENTS);
  37. }
  38. ~DssiPlugin()
  39. {
  40. carla_debug("DssiPlugin::~DssiPlugin()");
  41. // close UI
  42. if (fHints & PLUGIN_HAS_GUI)
  43. {
  44. showGui(false);
  45. // Wait a bit first, then force kill
  46. if (kData->osc.thread.isRunning() && ! kData->osc.thread.stop(kData->engine->getOptions().oscUiTimeout))
  47. {
  48. carla_stderr("DSSI GUI thread still running, forcing termination now");
  49. kData->osc.thread.terminate();
  50. }
  51. }
  52. if (fDescriptor != nullptr)
  53. {
  54. if (fDescriptor->deactivate != nullptr && kData->activeBefore)
  55. {
  56. if (fHandle != nullptr)
  57. fDescriptor->deactivate(fHandle);
  58. if (fHandle2 != nullptr)
  59. fDescriptor->deactivate(fHandle2);
  60. }
  61. if (fDescriptor->cleanup != nullptr)
  62. {
  63. if (fHandle != nullptr)
  64. fDescriptor->cleanup(fHandle);
  65. if (fHandle2 != nullptr)
  66. fDescriptor->cleanup(fHandle2);
  67. }
  68. fHandle = nullptr;
  69. fHandle2 = nullptr;
  70. fDescriptor = nullptr;
  71. fDssiDescriptor = nullptr;
  72. }
  73. deleteBuffers();
  74. }
  75. // -------------------------------------------------------------------
  76. // Information (base)
  77. PluginType type() const
  78. {
  79. return PLUGIN_DSSI;
  80. }
  81. PluginCategory category() const
  82. {
  83. if (fHints & PLUGIN_IS_SYNTH)
  84. return PLUGIN_CATEGORY_SYNTH;
  85. return getPluginCategoryFromName(fName);
  86. }
  87. long uniqueId() const
  88. {
  89. CARLA_ASSERT(fDescriptor != nullptr);
  90. return (fDescriptor != nullptr) ? fDescriptor->UniqueID : 0;
  91. }
  92. // -------------------------------------------------------------------
  93. // Information (current data)
  94. int32_t chunkData(void** const dataPtr)
  95. {
  96. CARLA_ASSERT(fHints & PLUGIN_USES_CHUNKS);
  97. CARLA_ASSERT(fDssiDescriptor != nullptr);
  98. CARLA_ASSERT(fDssiDescriptor->get_custom_data != nullptr);
  99. CARLA_ASSERT(fHandle != nullptr);
  100. CARLA_ASSERT(fHandle2 == nullptr);
  101. CARLA_ASSERT(dataPtr != nullptr);
  102. unsigned long dataSize = 0;
  103. if (fDssiDescriptor->get_custom_data != nullptr && fDssiDescriptor->get_custom_data(fHandle, dataPtr, &dataSize))
  104. return dataSize;
  105. return 0;
  106. }
  107. // -------------------------------------------------------------------
  108. // Information (per-plugin data)
  109. float getParameterValue(const uint32_t parameterId)
  110. {
  111. CARLA_ASSERT(parameterId < kData->param.count);
  112. return fParamBuffers[parameterId];
  113. }
  114. void getLabel(char* const strBuf)
  115. {
  116. CARLA_ASSERT(fDescriptor != nullptr);
  117. if (fDescriptor != nullptr && fDescriptor->Label != nullptr)
  118. std::strncpy(strBuf, fDescriptor->Label, STR_MAX);
  119. else
  120. CarlaPlugin::getLabel(strBuf);
  121. }
  122. void getMaker(char* const strBuf)
  123. {
  124. CARLA_ASSERT(fDescriptor != nullptr);
  125. if (fDescriptor != nullptr && fDescriptor->Maker != nullptr)
  126. std::strncpy(strBuf, fDescriptor->Maker, STR_MAX);
  127. else
  128. CarlaPlugin::getMaker(strBuf);
  129. }
  130. void getCopyright(char* const strBuf)
  131. {
  132. CARLA_ASSERT(fDescriptor != nullptr);
  133. if (fDescriptor != nullptr && fDescriptor->Copyright != nullptr)
  134. std::strncpy(strBuf, fDescriptor->Copyright, STR_MAX);
  135. else
  136. CarlaPlugin::getCopyright(strBuf);
  137. }
  138. void getRealName(char* const strBuf)
  139. {
  140. CARLA_ASSERT(fDescriptor != nullptr);
  141. if (fDescriptor != nullptr && fDescriptor->Name != nullptr)
  142. std::strncpy(strBuf, fDescriptor->Name, STR_MAX);
  143. else
  144. CarlaPlugin::getRealName(strBuf);
  145. }
  146. void getParameterName(const uint32_t parameterId, char* const strBuf)
  147. {
  148. CARLA_ASSERT(fDescriptor != nullptr);
  149. CARLA_ASSERT(parameterId < kData->param.count);
  150. const int32_t rindex = kData->param.data[parameterId].rindex;
  151. if (fDescriptor != nullptr && rindex < static_cast<int32_t>(fDescriptor->PortCount))
  152. std::strncpy(strBuf, fDescriptor->PortNames[rindex], STR_MAX);
  153. else
  154. CarlaPlugin::getParameterName(parameterId, strBuf);
  155. }
  156. // -------------------------------------------------------------------
  157. // Set data (plugin-specific stuff)
  158. void setParameterValue(const uint32_t parameterId, const float value, const bool sendGui, const bool sendOsc, const bool sendCallback)
  159. {
  160. CARLA_ASSERT(parameterId < kData->param.count);
  161. const float fixedValue = kData->param.fixValue(parameterId, value);
  162. fParamBuffers[parameterId] = fixedValue;
  163. CarlaPlugin::setParameterValue(parameterId, fixedValue, sendGui, sendOsc, sendCallback);
  164. }
  165. void setCustomData(const char* const type, const char* const key, const char* const value, const bool sendGui)
  166. {
  167. CARLA_ASSERT(fDescriptor != nullptr);
  168. CARLA_ASSERT(fHandle != nullptr);
  169. CARLA_ASSERT(type != nullptr);
  170. CARLA_ASSERT(key != nullptr);
  171. CARLA_ASSERT(value != nullptr);
  172. if (type == nullptr)
  173. return carla_stderr2("DssiPlugin::setCustomData(\"%s\", \"%s\", \"%s\", %s) - type is invalid", type, key, value, bool2str(sendGui));
  174. if (std::strcmp(type, CUSTOM_DATA_STRING) != 0)
  175. return carla_stderr2("DssiPlugin::setCustomData(\"%s\", \"%s\", \"%s\", %s) - type is not string", type, key, value, bool2str(sendGui));
  176. if (key == nullptr)
  177. return carla_stderr2("DssiPlugin::setCustomData(\"%s\", \"%s\", \"%s\", %s) - key is null", type, key, value, bool2str(sendGui));
  178. if (value == nullptr)
  179. return carla_stderr2("DssiPlugin::setCustomData(\"%s\", \"%s\", \"%s\", %s) - value is null", type, key, value, bool2str(sendGui));
  180. if (fDssiDescriptor->configure != nullptr)
  181. {
  182. fDssiDescriptor->configure(fHandle, key, value);
  183. if (fHandle2)
  184. fDssiDescriptor->configure(fHandle2, key, value);
  185. }
  186. if (sendGui && kData->osc.data.target != nullptr)
  187. osc_send_configure(&kData->osc.data, key, value);
  188. if (strcmp(key, "reloadprograms") == 0 || strcmp(key, "load") == 0 || strncmp(key, "patches", 7) == 0)
  189. {
  190. const ScopedDisabler m(this); // FIXME
  191. reloadPrograms(false);
  192. }
  193. CarlaPlugin::setCustomData(type, key, value, sendGui);
  194. }
  195. void setChunkData(const char* const stringData)
  196. {
  197. CARLA_ASSERT(fHints & PLUGIN_USES_CHUNKS);
  198. CARLA_ASSERT(fDssiDescriptor != nullptr);
  199. CARLA_ASSERT(fDssiDescriptor->set_custom_data != nullptr);
  200. CARLA_ASSERT(fHandle != nullptr);
  201. CARLA_ASSERT(fHandle2 == nullptr);
  202. CARLA_ASSERT(stringData != nullptr);
  203. if (fDssiDescriptor->set_custom_data == nullptr)
  204. return;
  205. // FIXME
  206. fChunk = QByteArray::fromBase64(QByteArray(stringData));
  207. //fChunk.toBase64();
  208. if (kData->engine->isOffline())
  209. {
  210. //const CarlaEngine::ScopedLocker m(kData->engine);
  211. fDssiDescriptor->set_custom_data(fHandle, fChunk.data(), fChunk.size());
  212. }
  213. else
  214. {
  215. const CarlaPlugin::ScopedDisabler m(this);
  216. fDssiDescriptor->set_custom_data(fHandle, fChunk.data(), fChunk.size());
  217. }
  218. }
  219. void setMidiProgram(int32_t index, const bool sendGui, const bool sendOsc, const bool sendCallback, const bool block)
  220. {
  221. CARLA_ASSERT(fDssiDescriptor != nullptr);
  222. CARLA_ASSERT(fHandle != nullptr);
  223. CARLA_ASSERT(index >= -1 && index < static_cast<int32_t>(kData->midiprog.count));
  224. if (index < -1)
  225. index = -1;
  226. else if (index > static_cast<int32_t>(kData->midiprog.count))
  227. return;
  228. // FIXME
  229. if (fDssiDescriptor != nullptr && fHandle != nullptr && index >= 0)
  230. {
  231. const uint32_t bank = kData->midiprog.data[index].bank;
  232. const uint32_t program = kData->midiprog.data[index].program;
  233. if (kData->engine->isOffline())
  234. {
  235. //const CarlaEngine::ScopedLocker m(x_engine, block);
  236. fDssiDescriptor->select_program(fHandle, bank, program);
  237. if (fHandle2 != nullptr)
  238. fDssiDescriptor->select_program(fHandle2, bank, program);
  239. }
  240. else
  241. {
  242. //const ScopedDisabler m(this, block);
  243. fDssiDescriptor->select_program(fHandle, bank, program);
  244. if (fHandle2 != nullptr)
  245. fDssiDescriptor->select_program(fHandle2, bank, program);
  246. }
  247. }
  248. CarlaPlugin::setMidiProgram(index, sendGui, sendOsc, sendCallback, block);
  249. }
  250. // -------------------------------------------------------------------
  251. // Set gui stuff
  252. void showGui(const bool yesNo)
  253. {
  254. if (yesNo)
  255. {
  256. kData->osc.thread.start();
  257. }
  258. else
  259. {
  260. if (kData->osc.data.target != nullptr)
  261. {
  262. osc_send_hide(&kData->osc.data);
  263. osc_send_quit(&kData->osc.data);
  264. kData->osc.data.free();
  265. }
  266. if (kData->osc.thread.isRunning() && ! kData->osc.thread.stop(kData->engine->getOptions().oscUiTimeout))
  267. kData->osc.thread.terminate();
  268. }
  269. }
  270. // -------------------------------------------------------------------
  271. // Plugin state
  272. void reload()
  273. {
  274. carla_debug("DssiPlugin::reload() - start");
  275. CARLA_ASSERT(kData->engine != nullptr);
  276. CARLA_ASSERT(fDescriptor != nullptr);
  277. CARLA_ASSERT(fHandle != nullptr);
  278. const ProcessMode processMode(kData->engine->getProccessMode());
  279. // Safely disable plugin for reload
  280. const ScopedDisabler sd(this);
  281. if (kData->client->isActive())
  282. kData->client->deactivate();
  283. deleteBuffers();
  284. const double sampleRate = kData->engine->getSampleRate();
  285. const unsigned long portCount = fDescriptor->PortCount;
  286. uint32_t aIns, aOuts, mIns, params, j;
  287. aIns = aOuts = mIns = params = 0;
  288. bool forcedStereoIn, forcedStereoOut;
  289. forcedStereoIn = forcedStereoOut = false;
  290. bool needsCtrlIn, needsCtrlOut;
  291. needsCtrlIn = needsCtrlOut = false;
  292. for (unsigned long i=0; i < portCount; i++)
  293. {
  294. const LADSPA_PortDescriptor portType = fDescriptor->PortDescriptors[i];
  295. if (LADSPA_IS_PORT_AUDIO(portType))
  296. {
  297. if (LADSPA_IS_PORT_INPUT(portType))
  298. aIns += 1;
  299. else if (LADSPA_IS_PORT_OUTPUT(portType))
  300. aOuts += 1;
  301. }
  302. else if (LADSPA_IS_PORT_CONTROL(portType))
  303. params += 1;
  304. }
  305. if ((fOptions & PLUGIN_OPTION_FORCE_STEREO) != 0 && (aIns == 1 || aOuts == 1))
  306. {
  307. if (fHandle2 == nullptr)
  308. fHandle2 = fDescriptor->instantiate(fDescriptor, sampleRate);
  309. if (aIns == 1)
  310. {
  311. aIns = 2;
  312. forcedStereoIn = true;
  313. }
  314. if (aOuts == 1)
  315. {
  316. aOuts = 2;
  317. forcedStereoOut = true;
  318. }
  319. }
  320. if (fDssiDescriptor->run_synth != nullptr || fDssiDescriptor->run_multiple_synths != nullptr)
  321. {
  322. mIns = 1;
  323. needsCtrlIn = true;
  324. }
  325. if (aIns > 0)
  326. {
  327. kData->audioIn.createNew(aIns);
  328. fAudioInBuffers = new float*[aIns];
  329. for (uint32_t i=0; i < aIns; i++)
  330. fAudioInBuffers[i] = nullptr;
  331. }
  332. if (aOuts > 0)
  333. {
  334. kData->audioOut.createNew(aOuts);
  335. fAudioOutBuffers = new float*[aOuts];
  336. needsCtrlIn = true;
  337. for (uint32_t i=0; i < aOuts; i++)
  338. fAudioOutBuffers[i] = nullptr;
  339. }
  340. if (params > 0)
  341. {
  342. kData->param.createNew(params);
  343. fParamBuffers = new float[params];
  344. }
  345. const int portNameSize = kData->engine->maxPortNameSize();
  346. CarlaString portName;
  347. for (unsigned long i=0, iAudioIn=0, iAudioOut=0, iCtrl=0; i < portCount; i++)
  348. {
  349. const LADSPA_PortDescriptor portType = fDescriptor->PortDescriptors[i];
  350. const LADSPA_PortRangeHint portRangeHints = fDescriptor->PortRangeHints[i];
  351. if (LADSPA_IS_PORT_AUDIO(portType))
  352. {
  353. portName.clear();
  354. if (processMode == PROCESS_MODE_SINGLE_CLIENT)
  355. {
  356. portName = fName;
  357. portName += ":";
  358. }
  359. portName += fDescriptor->PortNames[i];
  360. portName.truncate(portNameSize);
  361. if (LADSPA_IS_PORT_INPUT(portType))
  362. {
  363. j = iAudioIn++;
  364. kData->audioIn.ports[j].port = (CarlaEngineAudioPort*)kData->client->addPort(kEnginePortTypeAudio, portName, true);
  365. kData->audioIn.ports[j].rindex = i;
  366. if (forcedStereoIn)
  367. {
  368. portName += "_2";
  369. kData->audioIn.ports[1].port = (CarlaEngineAudioPort*)kData->client->addPort(kEnginePortTypeAudio, portName, true);
  370. kData->audioIn.ports[1].rindex = i;
  371. }
  372. }
  373. else if (LADSPA_IS_PORT_OUTPUT(portType))
  374. {
  375. j = iAudioOut++;
  376. kData->audioOut.ports[j].port = (CarlaEngineAudioPort*)kData->client->addPort(kEnginePortTypeAudio, portName, false);
  377. kData->audioOut.ports[j].rindex = i;
  378. if (forcedStereoOut)
  379. {
  380. portName += "_2";
  381. kData->audioOut.ports[1].port = (CarlaEngineAudioPort*)kData->client->addPort(kEnginePortTypeAudio, portName, false);
  382. kData->audioOut.ports[1].rindex = i;
  383. }
  384. }
  385. else
  386. carla_stderr2("WARNING - Got a broken Port (Audio, but not input or output)");
  387. }
  388. else if (LADSPA_IS_PORT_CONTROL(portType))
  389. {
  390. j = iCtrl++;
  391. kData->param.data[j].index = j;
  392. kData->param.data[j].rindex = i;
  393. kData->param.data[j].hints = 0x0;
  394. kData->param.data[j].midiChannel = 0;
  395. kData->param.data[j].midiCC = -1;
  396. float min, max, def, step, stepSmall, stepLarge;
  397. // min value
  398. if (LADSPA_IS_HINT_BOUNDED_BELOW(portRangeHints.HintDescriptor))
  399. min = portRangeHints.LowerBound;
  400. else
  401. min = 0.0f;
  402. // max value
  403. if (LADSPA_IS_HINT_BOUNDED_ABOVE(portRangeHints.HintDescriptor))
  404. max = portRangeHints.UpperBound;
  405. else
  406. max = 1.0f;
  407. if (min > max)
  408. max = min;
  409. else if (max < min)
  410. min = max;
  411. if (max - min == 0.0f)
  412. {
  413. carla_stderr2("WARNING - Broken plugin parameter '%s': max - min == 0.0f", fDescriptor->PortNames[i]);
  414. max = min + 0.1f;
  415. }
  416. // default value
  417. def = get_default_ladspa_port_value(portRangeHints.HintDescriptor, min, max);
  418. if (def < min)
  419. def = min;
  420. else if (def > max)
  421. def = max;
  422. if (LADSPA_IS_HINT_SAMPLE_RATE(portRangeHints.HintDescriptor))
  423. {
  424. min *= sampleRate;
  425. max *= sampleRate;
  426. def *= sampleRate;
  427. kData->param.data[j].hints |= PARAMETER_USES_SAMPLERATE;
  428. }
  429. if (LADSPA_IS_HINT_TOGGLED(portRangeHints.HintDescriptor))
  430. {
  431. step = max - min;
  432. stepSmall = step;
  433. stepLarge = step;
  434. kData->param.data[j].hints |= PARAMETER_IS_BOOLEAN;
  435. }
  436. else if (LADSPA_IS_HINT_INTEGER(portRangeHints.HintDescriptor))
  437. {
  438. step = 1.0f;
  439. stepSmall = 1.0f;
  440. stepLarge = 10.0f;
  441. kData->param.data[j].hints |= PARAMETER_IS_INTEGER;
  442. }
  443. else
  444. {
  445. float range = max - min;
  446. step = range/100.0f;
  447. stepSmall = range/1000.0f;
  448. stepLarge = range/10.0f;
  449. }
  450. if (LADSPA_IS_PORT_INPUT(portType))
  451. {
  452. kData->param.data[j].type = PARAMETER_INPUT;
  453. kData->param.data[j].hints |= PARAMETER_IS_ENABLED;
  454. kData->param.data[j].hints |= PARAMETER_IS_AUTOMABLE;
  455. needsCtrlIn = true;
  456. // MIDI CC value
  457. if (fDssiDescriptor->get_midi_controller_for_port != nullptr)
  458. {
  459. int controller = fDssiDescriptor->get_midi_controller_for_port(fHandle, i);
  460. if (DSSI_CONTROLLER_IS_SET(controller) && DSSI_IS_CC(controller))
  461. {
  462. int16_t cc = DSSI_CC_NUMBER(controller);
  463. if (! MIDI_IS_CONTROL_BANK_SELECT(cc))
  464. kData->param.data[j].midiCC = cc;
  465. }
  466. }
  467. }
  468. else if (LADSPA_IS_PORT_OUTPUT(portType))
  469. {
  470. if (std::strcmp(fDescriptor->PortNames[i], "latency") == 0 || std::strcmp(fDescriptor->PortNames[i], "_latency") == 0)
  471. {
  472. min = 0.0f;
  473. max = sampleRate;
  474. def = 0.0f;
  475. step = 1.0f;
  476. stepSmall = 1.0f;
  477. stepLarge = 1.0f;
  478. kData->param.data[j].type = PARAMETER_LATENCY;
  479. kData->param.data[j].hints = 0;
  480. }
  481. else if (std::strcmp(fDescriptor->PortNames[i], "_sample-rate") == 0)
  482. {
  483. def = sampleRate;
  484. step = 1.0f;
  485. stepSmall = 1.0f;
  486. stepLarge = 1.0f;
  487. kData->param.data[j].type = PARAMETER_SAMPLE_RATE;
  488. kData->param.data[j].hints = 0;
  489. }
  490. else
  491. {
  492. kData->param.data[j].type = PARAMETER_OUTPUT;
  493. kData->param.data[j].hints |= PARAMETER_IS_ENABLED;
  494. kData->param.data[j].hints |= PARAMETER_IS_AUTOMABLE;
  495. needsCtrlOut = true;
  496. }
  497. }
  498. else
  499. {
  500. kData->param.data[j].type = PARAMETER_UNKNOWN;
  501. carla_stderr2("WARNING - Got a broken Port (Control, but not input or output)");
  502. }
  503. // extra parameter hints
  504. if (LADSPA_IS_HINT_LOGARITHMIC(portRangeHints.HintDescriptor))
  505. kData->param.data[j].hints |= PARAMETER_IS_LOGARITHMIC;
  506. kData->param.ranges[j].min = min;
  507. kData->param.ranges[j].max = max;
  508. kData->param.ranges[j].def = def;
  509. kData->param.ranges[j].step = step;
  510. kData->param.ranges[j].stepSmall = stepSmall;
  511. kData->param.ranges[j].stepLarge = stepLarge;
  512. // Start parameters in their default values
  513. fParamBuffers[j] = def;
  514. fDescriptor->connect_port(fHandle, i, &fParamBuffers[j]);
  515. if (fHandle2 != nullptr)
  516. fDescriptor->connect_port(fHandle2, i, &fParamBuffers[j]);
  517. }
  518. else
  519. {
  520. // Not Audio or Control
  521. carla_stderr2("ERROR - Got a broken Port (neither Audio or Control)");
  522. fDescriptor->connect_port(fHandle, i, nullptr);
  523. if (fHandle2 != nullptr)
  524. fDescriptor->connect_port(fHandle2, i, nullptr);
  525. }
  526. }
  527. if (needsCtrlIn)
  528. {
  529. portName.clear();
  530. if (processMode == PROCESS_MODE_SINGLE_CLIENT)
  531. {
  532. portName = fName;
  533. portName += ":";
  534. }
  535. portName += "event-in";
  536. portName.truncate(portNameSize);
  537. kData->event.portIn = (CarlaEngineEventPort*)kData->client->addPort(kEnginePortTypeEvent, portName, true);
  538. }
  539. if (needsCtrlOut)
  540. {
  541. portName.clear();
  542. if (processMode == PROCESS_MODE_SINGLE_CLIENT)
  543. {
  544. portName = fName;
  545. portName += ":";
  546. }
  547. portName += "event-out";
  548. portName.truncate(portNameSize);
  549. kData->event.portOut = (CarlaEngineEventPort*)kData->client->addPort(kEnginePortTypeEvent, portName, false);
  550. }
  551. // plugin checks
  552. fHints &= ~(PLUGIN_IS_SYNTH | PLUGIN_USES_CHUNKS | PLUGIN_CAN_DRYWET | PLUGIN_CAN_VOLUME | PLUGIN_CAN_BALANCE | PLUGIN_CAN_FORCE_STEREO);
  553. if (mIns == 1 && aIns == 0 && aOuts > 0)
  554. fHints |= PLUGIN_IS_SYNTH;
  555. if (kData->engine->getOptions().useDssiVstChunks && QString(fFilename).endsWith("dssi-vst.so", Qt::CaseInsensitive))
  556. {
  557. if (fDssiDescriptor->get_custom_data != nullptr && fDssiDescriptor->set_custom_data != nullptr)
  558. fHints |= PLUGIN_USES_CHUNKS;
  559. }
  560. if (aOuts > 0 && (aIns == aOuts || aIns == 1))
  561. fHints |= PLUGIN_CAN_DRYWET;
  562. if (aOuts > 0)
  563. fHints |= PLUGIN_CAN_VOLUME;
  564. if (aOuts >= 2 && aOuts % 2 == 0)
  565. fHints |= PLUGIN_CAN_BALANCE;
  566. if (aIns <= 2 && aOuts <= 2 && (aIns == aOuts || aIns == 0 || aOuts == 0))
  567. fHints |= PLUGIN_CAN_FORCE_STEREO;
  568. // check latency
  569. if (fHints & PLUGIN_CAN_DRYWET)
  570. {
  571. for (uint32_t i=0; i < kData->param.count; i++)
  572. {
  573. if (kData->param.data[i].type != PARAMETER_LATENCY)
  574. continue;
  575. // we need to pre-run the plugin so it can update its latency control-port
  576. float tmpIn[aIns][2];
  577. float tmpOut[aOuts][2];
  578. for (j=0; j < aIns; j++)
  579. {
  580. tmpIn[j][0] = 0.0f;
  581. tmpIn[j][1] = 0.0f;
  582. fDescriptor->connect_port(fHandle, kData->audioIn.ports[j].rindex, tmpIn[j]);
  583. }
  584. for (j=0; j < aOuts; j++)
  585. {
  586. tmpOut[j][0] = 0.0f;
  587. tmpOut[j][1] = 0.0f;
  588. fDescriptor->connect_port(fHandle, kData->audioOut.ports[j].rindex, tmpOut[j]);
  589. }
  590. if (fDescriptor->activate != nullptr)
  591. fDescriptor->activate(fHandle);
  592. fDescriptor->run(fHandle, 2);
  593. if (fDescriptor->deactivate != nullptr)
  594. fDescriptor->deactivate(fHandle);
  595. const uint32_t latency = std::rint(fParamBuffers[i]);
  596. if (kData->latency != latency)
  597. {
  598. kData->latency = latency;
  599. kData->client->setLatency(latency);
  600. recreateLatencyBuffers();
  601. }
  602. break;
  603. }
  604. }
  605. bufferSizeChanged(kData->engine->getBufferSize());
  606. reloadPrograms(true);
  607. kData->client->activate();
  608. carla_debug("DssiPlugin::reload() - end");
  609. }
  610. void reloadPrograms(const bool init)
  611. {
  612. carla_debug("DssiPlugin::reloadPrograms(%s)", bool2str(init));
  613. uint32_t i, oldCount = kData->midiprog.count;
  614. // Delete old programs
  615. kData->midiprog.clear();
  616. // Query new programs
  617. uint32_t count = 0;
  618. if (fDssiDescriptor->get_program != nullptr && fDssiDescriptor->select_program != nullptr)
  619. {
  620. while (fDssiDescriptor->get_program(fHandle, count))
  621. count++;
  622. }
  623. if (count > 0)
  624. kData->midiprog.createNew(count);
  625. // Update data
  626. for (i=0; i < kData->midiprog.count; i++)
  627. {
  628. const DSSI_Program_Descriptor* const pdesc = fDssiDescriptor->get_program(fHandle, i);
  629. CARLA_ASSERT(pdesc != nullptr);
  630. CARLA_ASSERT(pdesc->Name != nullptr);
  631. kData->midiprog.data[i].bank = pdesc->Bank;
  632. kData->midiprog.data[i].program = pdesc->Program;
  633. kData->midiprog.data[i].name = carla_strdup(pdesc->Name);
  634. }
  635. #ifndef BUILD_BRIDGE
  636. // Update OSC Names
  637. if (kData->engine->isOscControlRegistered())
  638. {
  639. kData->engine->osc_send_control_set_midi_program_count(fId, kData->midiprog.count);
  640. for (i=0; i < kData->midiprog.count; i++)
  641. kData->engine->osc_send_control_set_midi_program_data(fId, i, kData->midiprog.data[i].bank, kData->midiprog.data[i].program, kData->midiprog.data[i].name);
  642. }
  643. #endif
  644. if (init)
  645. {
  646. if (kData->midiprog.count > 0)
  647. setMidiProgram(0, false, false, false, true);
  648. }
  649. else
  650. {
  651. kData->engine->callback(CALLBACK_RELOAD_PROGRAMS, fId, 0, 0, 0.0f, nullptr);
  652. // Check if current program is invalid
  653. bool programChanged = false;
  654. if (kData->midiprog.count == oldCount+1)
  655. {
  656. // one midi program added, probably created by user
  657. kData->midiprog.current = oldCount;
  658. programChanged = true;
  659. }
  660. else if (kData->midiprog.current >= static_cast<int32_t>(kData->midiprog.count))
  661. {
  662. // current midi program > count
  663. kData->midiprog.current = 0;
  664. programChanged = true;
  665. }
  666. else if (kData->midiprog.current < 0 && kData->midiprog.count > 0)
  667. {
  668. // programs exist now, but not before
  669. kData->midiprog.current = 0;
  670. programChanged = true;
  671. }
  672. else if (kData->midiprog.current >= 0 && kData->midiprog.count == 0)
  673. {
  674. // programs existed before, but not anymore
  675. kData->midiprog.current = -1;
  676. programChanged = true;
  677. }
  678. if (programChanged)
  679. setMidiProgram(kData->midiprog.current, true, true, true, true);
  680. }
  681. }
  682. // -------------------------------------------------------------------
  683. // Plugin processing
  684. void process(float** const inBuffer, float** const outBuffer, const uint32_t frames, const uint32_t framesOffset)
  685. {
  686. uint32_t i, k;
  687. // --------------------------------------------------------------------------------------------------------
  688. // Check if active
  689. if (! kData->active)
  690. {
  691. // disable any output sound
  692. for (i=0; i < kData->audioOut.count; i++)
  693. carla_zeroFloat(outBuffer[i], frames);
  694. if (kData->activeBefore)
  695. {
  696. if (fDescriptor->deactivate != nullptr)
  697. {
  698. fDescriptor->deactivate(fHandle);
  699. if (fHandle2 != nullptr)
  700. fDescriptor->deactivate(fHandle2);
  701. }
  702. }
  703. kData->activeBefore = kData->active;
  704. return;
  705. }
  706. unsigned long midiEventCount = 0;
  707. // --------------------------------------------------------------------------------------------------------
  708. // Check if not active before
  709. if (! kData->activeBefore)
  710. {
  711. if (kData->event.portIn != nullptr)
  712. {
  713. for (k=0, i=MAX_MIDI_CHANNELS; k < MAX_MIDI_CHANNELS; k++)
  714. {
  715. carla_zeroStruct<snd_seq_event_t>(fMidiEvents[k]);
  716. carla_zeroStruct<snd_seq_event_t>(fMidiEvents[k+i]);
  717. fMidiEvents[k].type = SND_SEQ_EVENT_CONTROLLER;
  718. fMidiEvents[k].data.control.channel = k;
  719. fMidiEvents[k].data.control.param = MIDI_CONTROL_ALL_SOUND_OFF;
  720. fMidiEvents[k+i].type = SND_SEQ_EVENT_CONTROLLER;
  721. fMidiEvents[k+i].data.control.channel = k;
  722. fMidiEvents[k+i].data.control.param = MIDI_CONTROL_ALL_NOTES_OFF;
  723. }
  724. midiEventCount = MAX_MIDI_CHANNELS*2;
  725. }
  726. if (kData->latency > 0)
  727. {
  728. for (i=0; i < kData->audioIn.count; i++)
  729. carla_zeroFloat(kData->latencyBuffers[i], kData->latency);
  730. }
  731. if (fDescriptor->activate != nullptr)
  732. {
  733. fDescriptor->activate(fHandle);
  734. if (fHandle2 != nullptr)
  735. fDescriptor->activate(fHandle2);
  736. }
  737. }
  738. // --------------------------------------------------------------------------------------------------------
  739. // Event Input and Processing
  740. else if (kData->event.portIn != nullptr)
  741. {
  742. // ----------------------------------------------------------------------------------------------------
  743. // MIDI Input (External)
  744. if (kData->extNotes.mutex.tryLock())
  745. {
  746. while (midiEventCount < MAX_MIDI_EVENTS && ! kData->extNotes.data.isEmpty())
  747. {
  748. const ExternalMidiNote& note = kData->extNotes.data.getLast(true); // FIXME, should be first
  749. CARLA_ASSERT(note.channel >= 0);
  750. carla_zeroStruct<snd_seq_event_t>(fMidiEvents[midiEventCount]);
  751. fMidiEvents[midiEventCount].type = (note.velo > 0) ? SND_SEQ_EVENT_NOTEON : SND_SEQ_EVENT_NOTEOFF;
  752. fMidiEvents[midiEventCount].data.note.channel = note.channel;
  753. fMidiEvents[midiEventCount].data.note.note = note.note;
  754. fMidiEvents[midiEventCount].data.note.velocity = note.velo;
  755. midiEventCount += 1;
  756. }
  757. kData->extNotes.mutex.unlock();
  758. } // End of MIDI Input (External)
  759. // ----------------------------------------------------------------------------------------------------
  760. // Event Input (System)
  761. bool allNotesOffSent = false;
  762. bool sampleAccurate = (fHints & PLUGIN_OPTION_FIXED_BUFFER) == 0;
  763. uint32_t time, nEvents = kData->event.portIn->getEventCount();
  764. uint32_t timeOffset = 0;
  765. uint32_t nextBankId = 0;
  766. if (kData->midiprog.current >= 0 && kData->midiprog.count > 0)
  767. nextBankId = kData->midiprog.data[kData->midiprog.current].bank;
  768. for (i=0; i < nEvents; i++)
  769. {
  770. const EngineEvent& event = kData->event.portIn->getEvent(i);
  771. time = event.time - framesOffset;
  772. if (time >= frames)
  773. continue;
  774. CARLA_ASSERT_INT2(time >= timeOffset, time, timeOffset);
  775. if (time > timeOffset && sampleAccurate)
  776. {
  777. processSingle(inBuffer, outBuffer, time - timeOffset, timeOffset, midiEventCount);
  778. midiEventCount = 0;
  779. nextBankId = 0;
  780. timeOffset = time;
  781. }
  782. // Control change
  783. switch (event.type)
  784. {
  785. case kEngineEventTypeNull:
  786. break;
  787. case kEngineEventTypeControl:
  788. {
  789. const EngineControlEvent& ctrlEvent = event.ctrl;
  790. switch (ctrlEvent.type)
  791. {
  792. case kEngineControlEventTypeNull:
  793. break;
  794. case kEngineControlEventTypeParameter:
  795. {
  796. // Control backend stuff
  797. if (event.channel == kData->ctrlInChannel)
  798. {
  799. double value;
  800. if (MIDI_IS_CONTROL_BREATH_CONTROLLER(ctrlEvent.param) && (fHints & PLUGIN_CAN_DRYWET) > 0)
  801. {
  802. value = ctrlEvent.value;
  803. setDryWet(value, false, false);
  804. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_DRYWET, 0, value);
  805. continue;
  806. }
  807. if (MIDI_IS_CONTROL_CHANNEL_VOLUME(ctrlEvent.param) && (fHints & PLUGIN_CAN_VOLUME) > 0)
  808. {
  809. value = ctrlEvent.value*127/100;
  810. setVolume(value, false, false);
  811. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_VOLUME, 0, value);
  812. continue;
  813. }
  814. if (MIDI_IS_CONTROL_BALANCE(ctrlEvent.param) && (fHints & PLUGIN_CAN_BALANCE) > 0)
  815. {
  816. double left, right;
  817. value = ctrlEvent.value/0.5 - 1.0;
  818. if (value < 0.0)
  819. {
  820. left = -1.0;
  821. right = (value*2)+1.0;
  822. }
  823. else if (value > 0.0)
  824. {
  825. left = (value*2)-1.0;
  826. right = 1.0;
  827. }
  828. else
  829. {
  830. left = -1.0;
  831. right = 1.0;
  832. }
  833. setBalanceLeft(left, false, false);
  834. setBalanceRight(right, false, false);
  835. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_BALANCE_LEFT, 0, left);
  836. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_BALANCE_RIGHT, 0, right);
  837. continue;
  838. }
  839. }
  840. // Control plugin parameters
  841. for (k=0; k < kData->param.count; k++)
  842. {
  843. if (kData->param.data[k].midiChannel != event.channel)
  844. continue;
  845. if (kData->param.data[k].midiCC != ctrlEvent.param)
  846. continue;
  847. if (kData->param.data[k].type != PARAMETER_INPUT)
  848. continue;
  849. if ((kData->param.data[k].hints & PARAMETER_IS_AUTOMABLE) == 0)
  850. continue;
  851. double value;
  852. if (kData->param.data[k].hints & PARAMETER_IS_BOOLEAN)
  853. {
  854. value = (ctrlEvent.value < 0.5) ? kData->param.ranges[k].min : kData->param.ranges[k].max;
  855. }
  856. else
  857. {
  858. // FIXME - ranges call for this
  859. value = ctrlEvent.value * (kData->param.ranges[k].max - kData->param.ranges[k].min) + kData->param.ranges[k].min;
  860. if (kData->param.data[k].hints & PARAMETER_IS_INTEGER)
  861. value = std::rint(value);
  862. }
  863. setParameterValue(k, value, false, false, false);
  864. postponeRtEvent(kPluginPostRtEventParameterChange, k, 0, value);
  865. }
  866. break;
  867. }
  868. case kEngineControlEventTypeMidiBank:
  869. if (event.channel == kData->ctrlInChannel)
  870. nextBankId = ctrlEvent.param;
  871. break;
  872. case kEngineControlEventTypeMidiProgram:
  873. if (event.channel == kData->ctrlInChannel)
  874. {
  875. const uint32_t nextProgramId = ctrlEvent.param;
  876. for (k=0; k < kData->midiprog.count; k++)
  877. {
  878. if (kData->midiprog.data[k].bank == nextBankId && kData->midiprog.data[k].program == nextProgramId)
  879. {
  880. setMidiProgram(k, false, false, false, false);
  881. postponeRtEvent(kPluginPostRtEventMidiProgramChange, k, 0, 0.0);
  882. break;
  883. }
  884. }
  885. }
  886. break;
  887. case kEngineControlEventTypeAllSoundOff:
  888. if (event.channel == kData->ctrlInChannel)
  889. {
  890. if (! allNotesOffSent)
  891. sendMidiAllNotesOff();
  892. if (fDescriptor->deactivate != nullptr)
  893. {
  894. fDescriptor->deactivate(fHandle);
  895. if (fHandle2 != nullptr)
  896. fDescriptor->deactivate(fHandle2);
  897. }
  898. if (fDescriptor->activate != nullptr)
  899. {
  900. fDescriptor->activate(fHandle);
  901. if (fHandle2 != nullptr)
  902. fDescriptor->activate(fHandle2);
  903. }
  904. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_ACTIVE, 0, 0.0);
  905. postponeRtEvent(kPluginPostRtEventParameterChange, PARAMETER_ACTIVE, 0, 1.0);
  906. allNotesOffSent = true;
  907. }
  908. if (midiEventCount >= MAX_MIDI_EVENTS)
  909. continue;
  910. carla_zeroStruct<snd_seq_event_t>(fMidiEvents[midiEventCount]);
  911. if (! sampleAccurate)
  912. fMidiEvents[midiEventCount].time.tick = time;
  913. fMidiEvents[midiEventCount].type = SND_SEQ_EVENT_CONTROLLER;
  914. fMidiEvents[midiEventCount].data.control.channel = event.channel;
  915. fMidiEvents[midiEventCount].data.control.param = MIDI_CONTROL_ALL_SOUND_OFF;
  916. midiEventCount += 1;
  917. break;
  918. case kEngineControlEventTypeAllNotesOff:
  919. if (event.channel == kData->ctrlInChannel)
  920. {
  921. if (! allNotesOffSent)
  922. sendMidiAllNotesOff();
  923. allNotesOffSent = true;
  924. }
  925. if (midiEventCount >= MAX_MIDI_EVENTS)
  926. continue;
  927. carla_zeroStruct<snd_seq_event_t>(fMidiEvents[midiEventCount]);
  928. if (! sampleAccurate)
  929. fMidiEvents[midiEventCount].time.tick = time;
  930. fMidiEvents[midiEventCount].type = SND_SEQ_EVENT_CONTROLLER;
  931. fMidiEvents[midiEventCount].data.control.channel = event.channel;
  932. fMidiEvents[midiEventCount].data.control.param = MIDI_CONTROL_ALL_NOTES_OFF;
  933. midiEventCount += 1;
  934. break;
  935. }
  936. break;
  937. }
  938. case kEngineEventTypeMidi:
  939. {
  940. if (midiEventCount >= MAX_MIDI_EVENTS)
  941. continue;
  942. const EngineMidiEvent& midiEvent = event.midi;
  943. uint8_t status = MIDI_GET_STATUS_FROM_DATA(midiEvent.data);
  944. uint8_t channel = event.channel;
  945. // Fix bad note-off (per DSSI spec)
  946. if (MIDI_IS_STATUS_NOTE_ON(status) && midiEvent.data[2] == 0)
  947. status -= 0x10;
  948. carla_zeroStruct<snd_seq_event_t>(fMidiEvents[midiEventCount]);
  949. if (! sampleAccurate)
  950. fMidiEvents[midiEventCount].time.tick = time - timeOffset;
  951. if (MIDI_IS_STATUS_NOTE_OFF(status))
  952. {
  953. const uint8_t note = midiEvent.data[1];
  954. fMidiEvents[midiEventCount].type = SND_SEQ_EVENT_NOTEOFF;
  955. fMidiEvents[midiEventCount].data.note.channel = channel;
  956. fMidiEvents[midiEventCount].data.note.note = note;
  957. postponeRtEvent(kPluginPostRtEventNoteOff, channel, note, 0.0);
  958. }
  959. else if (MIDI_IS_STATUS_NOTE_ON(status))
  960. {
  961. const uint8_t note = midiEvent.data[1];
  962. const uint8_t velo = midiEvent.data[2];
  963. fMidiEvents[midiEventCount].type = SND_SEQ_EVENT_NOTEON;
  964. fMidiEvents[midiEventCount].data.note.channel = channel;
  965. fMidiEvents[midiEventCount].data.note.note = note;
  966. fMidiEvents[midiEventCount].data.note.velocity = velo;
  967. postponeRtEvent(kPluginPostRtEventNoteOn, channel, note, velo);
  968. }
  969. else if (MIDI_IS_STATUS_POLYPHONIC_AFTERTOUCH(status))
  970. {
  971. const uint8_t note = midiEvent.data[1];
  972. const uint8_t pressure = midiEvent.data[2];
  973. fMidiEvents[midiEventCount].type = SND_SEQ_EVENT_KEYPRESS;
  974. fMidiEvents[midiEventCount].data.note.channel = channel;
  975. fMidiEvents[midiEventCount].data.note.note = note;
  976. fMidiEvents[midiEventCount].data.note.velocity = pressure;
  977. }
  978. else if (MIDI_IS_STATUS_CONTROL_CHANGE(status) && (fHints & PLUGIN_OPTION_SELF_AUTOMATION) != 0)
  979. {
  980. const uint8_t control = midiEvent.data[1];
  981. const uint8_t value = midiEvent.data[2];
  982. fMidiEvents[midiEventCount].type = SND_SEQ_EVENT_CONTROLLER;
  983. fMidiEvents[midiEventCount].data.control.channel = channel;
  984. fMidiEvents[midiEventCount].data.control.param = control;
  985. fMidiEvents[midiEventCount].data.control.value = value;
  986. }
  987. else if (MIDI_IS_STATUS_AFTERTOUCH(status))
  988. {
  989. const uint8_t pressure = midiEvent.data[1];
  990. fMidiEvents[midiEventCount].type = SND_SEQ_EVENT_CHANPRESS;
  991. fMidiEvents[midiEventCount].data.control.channel = channel;
  992. fMidiEvents[midiEventCount].data.control.value = pressure;
  993. }
  994. else if (MIDI_IS_STATUS_PITCH_WHEEL_CONTROL(status))
  995. {
  996. const uint8_t lsb = midiEvent.data[1];
  997. const uint8_t msb = midiEvent.data[2];
  998. fMidiEvents[midiEventCount].type = SND_SEQ_EVENT_PITCHBEND;
  999. fMidiEvents[midiEventCount].data.control.channel = channel;
  1000. fMidiEvents[midiEventCount].data.control.value = ((msb << 7) | lsb) - 8192;
  1001. }
  1002. else
  1003. continue;
  1004. midiEventCount += 1;
  1005. break;
  1006. }
  1007. }
  1008. }
  1009. kData->postRtEvents.trySplice();
  1010. if (frames > timeOffset)
  1011. processSingle(inBuffer, outBuffer, frames - timeOffset, timeOffset, midiEventCount);
  1012. } // End of Event Input and Processing
  1013. // --------------------------------------------------------------------------------------------------------
  1014. // Plugin processing (no events)
  1015. else
  1016. {
  1017. processSingle(inBuffer, outBuffer, frames, 0, 0);
  1018. } // End of Plugin processing (no events)
  1019. // --------------------------------------------------------------------------------------------------------
  1020. // Special Parameters
  1021. #if 0
  1022. CARLA_PROCESS_CONTINUE_CHECK;
  1023. for (k=0; k < param.count; k++)
  1024. {
  1025. if (param.data[k].type == PARAMETER_LATENCY)
  1026. {
  1027. // TODO
  1028. }
  1029. }
  1030. CARLA_PROCESS_CONTINUE_CHECK;
  1031. #endif
  1032. CARLA_PROCESS_CONTINUE_CHECK;
  1033. // --------------------------------------------------------------------------------------------------------
  1034. // Post-processing (dry/wet, volume and balance)
  1035. {
  1036. const bool doDryWet = (fHints & PLUGIN_CAN_DRYWET) > 0 && kData->postProc.dryWet != 1.0f;
  1037. const bool doVolume = (fHints & PLUGIN_CAN_VOLUME) > 0 && kData->postProc.volume != 1.0f;
  1038. const bool doBalance = (fHints & PLUGIN_CAN_BALANCE) > 0 && (kData->postProc.balanceLeft != -1.0f || kData->postProc.balanceRight != 1.0f);
  1039. float bufValue, oldBufLeft[doBalance ? frames : 1];
  1040. for (i=0; i < kData->audioOut.count; i++)
  1041. {
  1042. // Dry/Wet
  1043. if (doDryWet)
  1044. {
  1045. #if 0
  1046. for (k=0; k < frames; k++)
  1047. {
  1048. if (k < m_latency && m_latency < frames)
  1049. bufValue = (aIn.count == 1) ? m_latencyBuffers[0][k] : m_latencyBuffers[i][k];
  1050. else
  1051. bufValue = (aIn.count == 1) ? inBuffer[0][k-m_latency] : inBuffer[i][k-m_latency];
  1052. outBuffer[i][k] = (outBuffer[i][k]*x_dryWet)+(bufValue*(1.0-x_dryWet));
  1053. }
  1054. #endif
  1055. for (k=0; k < frames; k++)
  1056. {
  1057. // TODO
  1058. //if (k < kData->latency && kData->latency < frames)
  1059. // bufValue = (kData->audioIn.count == 1) ? kData->latencyBuffers[0][k] : kData->latencyBuffers[i][k];
  1060. //else
  1061. // bufValue = (kData->audioIn.count == 1) ? inBuffer[0][k-m_latency] : inBuffer[i][k-m_latency];
  1062. bufValue = inBuffer[ (kData->audioIn.count == 1) ? 0 : i ][k];
  1063. outBuffer[i][k] = (outBuffer[i][k] * kData->postProc.dryWet) + (bufValue * (1.0f - kData->postProc.dryWet));
  1064. }
  1065. }
  1066. // Balance
  1067. if (doBalance)
  1068. {
  1069. if (i % 2 == 0)
  1070. std::memcpy(oldBufLeft, outBuffer[i], sizeof(float)*frames);
  1071. float balRangeL = (kData->postProc.balanceLeft + 1.0f)/2.0f;
  1072. float balRangeR = (kData->postProc.balanceRight + 1.0f)/2.0f;
  1073. for (k=0; k < frames; k++)
  1074. {
  1075. if (i % 2 == 0)
  1076. {
  1077. // left
  1078. outBuffer[i][k] = oldBufLeft[k] * (1.0f - balRangeL);
  1079. outBuffer[i][k] += outBuffer[i+1][k] * (1.0f - balRangeR);
  1080. }
  1081. else
  1082. {
  1083. // right
  1084. outBuffer[i][k] = outBuffer[i][k] * balRangeR;
  1085. outBuffer[i][k] += oldBufLeft[k] * balRangeL;
  1086. }
  1087. }
  1088. }
  1089. // Volume
  1090. if (doVolume)
  1091. {
  1092. for (k=0; k < frames; k++)
  1093. outBuffer[i][k] *= kData->postProc.volume;
  1094. }
  1095. }
  1096. #if 0
  1097. // Latency, save values for next callback, TODO
  1098. if (kData->latency > 0 && kData->latency < frames)
  1099. {
  1100. for (i=0; i < kData->audioIn.count; i++)
  1101. std::memcpy(kData->latencyBuffers[i], inBuffer[i] + (frames - kData->latency), sizeof(float)*kData->latency);
  1102. }
  1103. #endif
  1104. } // End of Post-processing
  1105. CARLA_PROCESS_CONTINUE_CHECK;
  1106. // --------------------------------------------------------------------------------------------------------
  1107. // Control Output
  1108. if (kData->event.portOut != nullptr)
  1109. {
  1110. float value;
  1111. for (k=0; k < kData->param.count; k++)
  1112. {
  1113. if (kData->param.data[k].type != PARAMETER_OUTPUT)
  1114. continue;
  1115. kData->param.ranges[k].fixValue(fParamBuffers[k]);
  1116. if (kData->param.data[k].midiCC > 0)
  1117. {
  1118. value = kData->param.ranges[k].normalizeValue(fParamBuffers[k]);
  1119. kData->event.portOut->writeControlEvent(framesOffset, kData->param.data[k].midiChannel, kEngineControlEventTypeParameter, kData->param.data[k].midiCC, value);
  1120. }
  1121. }
  1122. } // End of Control Output
  1123. // --------------------------------------------------------------------------------------------------------
  1124. kData->activeBefore = kData->active;
  1125. }
  1126. void processSingle(float** const inBuffer, float** const outBuffer, const uint32_t frames, const uint32_t timeOffset, const uint32_t midiEventCount)
  1127. {
  1128. for (uint32_t i=0; i < kData->audioIn.count; i++)
  1129. std::memcpy(fAudioInBuffers[i], inBuffer[i]+timeOffset, sizeof(float)*frames);
  1130. for (uint32_t i=0; i < kData->audioOut.count; i++)
  1131. carla_zeroFloat(fAudioOutBuffers[i], frames);
  1132. if (fDssiDescriptor->run_synth != nullptr)
  1133. {
  1134. fDssiDescriptor->run_synth(fHandle, frames, fMidiEvents, midiEventCount);
  1135. if (fHandle2 != nullptr)
  1136. fDssiDescriptor->run_synth(fHandle2, frames, fMidiEvents, midiEventCount);
  1137. }
  1138. else if (fDssiDescriptor->run_multiple_synths != nullptr)
  1139. {
  1140. unsigned long instances = (fHandle2 != nullptr) ? 2 : 1;
  1141. LADSPA_Handle handlePtr[2] = { fHandle, fHandle2 };
  1142. snd_seq_event_t* midiEventsPtr[2] = { fMidiEvents, fMidiEvents };
  1143. unsigned long midiEventCountPtr[2] = { midiEventCount, midiEventCount };
  1144. fDssiDescriptor->run_multiple_synths(instances, handlePtr, frames, midiEventsPtr, midiEventCountPtr);
  1145. }
  1146. else
  1147. {
  1148. fDescriptor->run(fHandle, frames);
  1149. if (fHandle2 != nullptr)
  1150. fDescriptor->run(fHandle2, frames);
  1151. }
  1152. for (uint32_t i=0, k; i < kData->audioOut.count; i++)
  1153. {
  1154. for (k=0; k < frames; k++)
  1155. outBuffer[i][k+timeOffset] = fAudioOutBuffers[i][k];
  1156. }
  1157. }
  1158. void bufferSizeChanged(const uint32_t newBufferSize)
  1159. {
  1160. for (uint32_t i=0; i < kData->audioIn.count; i++)
  1161. {
  1162. if (fAudioInBuffers[i] != nullptr)
  1163. delete[] fAudioInBuffers[i];
  1164. fAudioInBuffers[i] = new float[newBufferSize];
  1165. }
  1166. for (uint32_t i=0; i < kData->audioOut.count; i++)
  1167. {
  1168. if (fAudioOutBuffers[i] != nullptr)
  1169. delete[] fAudioOutBuffers[i];
  1170. fAudioOutBuffers[i] = new float[newBufferSize];
  1171. }
  1172. if (fHandle2 == nullptr)
  1173. {
  1174. for (uint32_t i=0; i < kData->audioIn.count; i++)
  1175. {
  1176. CARLA_ASSERT(fAudioInBuffers[i] != nullptr);
  1177. fDescriptor->connect_port(fHandle, kData->audioIn.ports[i].rindex, fAudioInBuffers[i]);
  1178. }
  1179. for (uint32_t i=0; i < kData->audioOut.count; i++)
  1180. {
  1181. CARLA_ASSERT(fAudioOutBuffers[i] != nullptr);
  1182. fDescriptor->connect_port(fHandle, kData->audioOut.ports[i].rindex, fAudioOutBuffers[i]);
  1183. }
  1184. }
  1185. else
  1186. {
  1187. if (kData->audioIn.count > 0)
  1188. {
  1189. CARLA_ASSERT(kData->audioIn.count == 2);
  1190. CARLA_ASSERT(fAudioInBuffers[0] != nullptr);
  1191. CARLA_ASSERT(fAudioInBuffers[1] != nullptr);
  1192. fDescriptor->connect_port(fHandle, kData->audioIn.ports[0].rindex, fAudioInBuffers[0]);
  1193. fDescriptor->connect_port(fHandle2, kData->audioIn.ports[1].rindex, fAudioInBuffers[1]);
  1194. }
  1195. if (kData->audioOut.count > 0)
  1196. {
  1197. CARLA_ASSERT(kData->audioOut.count == 2);
  1198. CARLA_ASSERT(fAudioOutBuffers[0] != nullptr);
  1199. CARLA_ASSERT(fAudioOutBuffers[1] != nullptr);
  1200. fDescriptor->connect_port(fHandle, kData->audioOut.ports[0].rindex, fAudioOutBuffers[0]);
  1201. fDescriptor->connect_port(fHandle2, kData->audioOut.ports[1].rindex, fAudioOutBuffers[1]);
  1202. }
  1203. }
  1204. }
  1205. // -------------------------------------------------------------------
  1206. // Post-poned events
  1207. void uiParameterChange(const uint32_t index, const float value)
  1208. {
  1209. CARLA_ASSERT(index < kData->param.count);
  1210. if (index >= kData->param.count)
  1211. return;
  1212. if (kData->osc.data.target == nullptr)
  1213. return;
  1214. osc_send_control(&kData->osc.data, kData->param.data[index].rindex, value);
  1215. }
  1216. void uiMidiProgramChange(const uint32_t index)
  1217. {
  1218. CARLA_ASSERT(index < kData->midiprog.count);
  1219. if (index >= kData->midiprog.count)
  1220. return;
  1221. if (kData->osc.data.target == nullptr)
  1222. return;
  1223. osc_send_program(&kData->osc.data, kData->midiprog.data[index].bank, kData->midiprog.data[index].program);
  1224. }
  1225. void uiNoteOn(const uint8_t channel, const uint8_t note, const uint8_t velo)
  1226. {
  1227. CARLA_ASSERT(channel < MAX_MIDI_CHANNELS);
  1228. CARLA_ASSERT(note < MAX_MIDI_NOTE);
  1229. CARLA_ASSERT(velo > 0 && velo < MAX_MIDI_VALUE);
  1230. if (channel >= MAX_MIDI_CHANNELS)
  1231. return;
  1232. if (note >= MAX_MIDI_NOTE)
  1233. return;
  1234. if (velo >= MAX_MIDI_VALUE)
  1235. return;
  1236. if (kData->osc.data.target == nullptr)
  1237. return;
  1238. uint8_t midiData[4] = { 0 };
  1239. midiData[1] = MIDI_STATUS_NOTE_ON + channel;
  1240. midiData[2] = note;
  1241. midiData[3] = velo;
  1242. osc_send_midi(&kData->osc.data, midiData);
  1243. }
  1244. void uiNoteOff(const uint8_t channel, const uint8_t note)
  1245. {
  1246. CARLA_ASSERT(channel < MAX_MIDI_CHANNELS);
  1247. CARLA_ASSERT(note < MAX_MIDI_NOTE);
  1248. if (channel >= MAX_MIDI_CHANNELS)
  1249. return;
  1250. if (note >= MAX_MIDI_NOTE)
  1251. return;
  1252. if (kData->osc.data.target == nullptr)
  1253. return;
  1254. uint8_t midiData[4] = { 0 };
  1255. midiData[1] = MIDI_STATUS_NOTE_OFF + channel;
  1256. midiData[2] = note;
  1257. osc_send_midi(&kData->osc.data, midiData);
  1258. }
  1259. // -------------------------------------------------------------------
  1260. // Cleanup
  1261. void deleteBuffers()
  1262. {
  1263. carla_debug("DssiPlugin::deleteBuffers() - start");
  1264. if (fAudioInBuffers != nullptr)
  1265. {
  1266. for (uint32_t i=0; i < kData->audioIn.count; i++)
  1267. {
  1268. if (fAudioInBuffers[i] != nullptr)
  1269. {
  1270. delete[] fAudioInBuffers[i];
  1271. fAudioInBuffers[i] = nullptr;
  1272. }
  1273. }
  1274. delete[] fAudioInBuffers;
  1275. fAudioInBuffers = nullptr;
  1276. }
  1277. if (fAudioOutBuffers != nullptr)
  1278. {
  1279. for (uint32_t i=0; i < kData->audioOut.count; i++)
  1280. {
  1281. if (fAudioOutBuffers[i] != nullptr)
  1282. {
  1283. delete[] fAudioOutBuffers[i];
  1284. fAudioOutBuffers[i] = nullptr;
  1285. }
  1286. }
  1287. delete[] fAudioOutBuffers;
  1288. fAudioOutBuffers = nullptr;
  1289. }
  1290. if (fParamBuffers != nullptr)
  1291. {
  1292. delete[] fParamBuffers;
  1293. fParamBuffers = nullptr;
  1294. }
  1295. CarlaPlugin::deleteBuffers();
  1296. carla_debug("DssiPlugin::deleteBuffers() - end");
  1297. }
  1298. // -------------------------------------------------------------------
  1299. bool init(const char* const filename, const char* const name, const char* const label, const char* const guiFilename)
  1300. {
  1301. CARLA_ASSERT(kData->engine != nullptr);
  1302. CARLA_ASSERT(kData->client == nullptr);
  1303. CARLA_ASSERT(filename != nullptr);
  1304. CARLA_ASSERT(label != nullptr);
  1305. // ---------------------------------------------------------------
  1306. // open DLL
  1307. if (! libOpen(filename))
  1308. {
  1309. kData->engine->setLastError(libError(filename));
  1310. return false;
  1311. }
  1312. // ---------------------------------------------------------------
  1313. // get DLL main entry
  1314. const DSSI_Descriptor_Function descFn = (DSSI_Descriptor_Function)libSymbol("dssi_descriptor");
  1315. if (descFn == nullptr)
  1316. {
  1317. kData->engine->setLastError("Could not find the DSSI Descriptor in the plugin library");
  1318. return false;
  1319. }
  1320. // ---------------------------------------------------------------
  1321. // get descriptor that matches label
  1322. unsigned long i = 0;
  1323. while ((fDssiDescriptor = descFn(i++)) != nullptr)
  1324. {
  1325. fDescriptor = fDssiDescriptor->LADSPA_Plugin;
  1326. if (fDescriptor != nullptr && fDescriptor->Label != nullptr && std::strcmp(fDescriptor->Label, label) == 0)
  1327. break;
  1328. }
  1329. if (fDescriptor == nullptr || fDssiDescriptor == nullptr)
  1330. {
  1331. kData->engine->setLastError("Could not find the requested plugin label in the plugin library");
  1332. return false;
  1333. }
  1334. // ---------------------------------------------------------------
  1335. // get info
  1336. if (name != nullptr)
  1337. fName = kData->engine->getNewUniquePluginName(name);
  1338. else if (fDescriptor->Name != nullptr)
  1339. fName = kData->engine->getNewUniquePluginName(fDescriptor->Name);
  1340. else
  1341. fName = kData->engine->getNewUniquePluginName(fDescriptor->Label);
  1342. fFilename = filename;
  1343. // ---------------------------------------------------------------
  1344. // register client
  1345. kData->client = kData->engine->addClient(this);
  1346. if (kData->client == nullptr || ! kData->client->isOk())
  1347. {
  1348. kData->engine->setLastError("Failed to register plugin client");
  1349. return false;
  1350. }
  1351. // ---------------------------------------------------------------
  1352. // initialize plugin
  1353. fHandle = fDescriptor->instantiate(fDescriptor, kData->engine->getSampleRate());
  1354. if (fHandle == nullptr)
  1355. {
  1356. kData->engine->setLastError("Plugin failed to initialize");
  1357. return false;
  1358. }
  1359. // ---------------------------------------------------------------
  1360. // gui stuff
  1361. if (guiFilename != nullptr)
  1362. {
  1363. kData->osc.thread.setMode(CarlaPluginThread::PLUGIN_THREAD_DSSI_GUI);
  1364. kData->osc.thread.setOscData(guiFilename, fDescriptor->Label);
  1365. fHints |= PLUGIN_HAS_GUI;
  1366. }
  1367. return true;
  1368. }
  1369. private:
  1370. LADSPA_Handle fHandle;
  1371. LADSPA_Handle fHandle2;
  1372. const LADSPA_Descriptor* fDescriptor;
  1373. const DSSI_Descriptor* fDssiDescriptor;
  1374. float** fAudioInBuffers;
  1375. float** fAudioOutBuffers;
  1376. float* fParamBuffers;
  1377. snd_seq_event_t fMidiEvents[MAX_MIDI_EVENTS];
  1378. QByteArray fChunk;
  1379. };
  1380. CARLA_BACKEND_END_NAMESPACE
  1381. #else // WANT_DSSI
  1382. # warning Building without DSSI support
  1383. #endif
  1384. CARLA_BACKEND_START_NAMESPACE
  1385. CarlaPlugin* CarlaPlugin::newDSSI(const Initializer& init, const char* const guiFilename)
  1386. {
  1387. carla_debug("CarlaPlugin::newDSSI({%p, \"%s\", \"%s\", \"%s\"}, \"%s\")", init.engine, init.filename, init.name, init.label, guiFilename);
  1388. #ifdef WANT_DSSI
  1389. DssiPlugin* const plugin = new DssiPlugin(init.engine, init.id);
  1390. if (! plugin->init(init.filename, init.name, init.label, guiFilename))
  1391. {
  1392. delete plugin;
  1393. return nullptr;
  1394. }
  1395. plugin->reload();
  1396. if (init.engine->getProccessMode() == PROCESS_MODE_CONTINUOUS_RACK && (plugin->hints() & PLUGIN_CAN_FORCE_STEREO) == 0)
  1397. {
  1398. init.engine->setLastError("Carla's rack mode can only work with Mono or Stereo DSSI plugins, sorry!");
  1399. delete plugin;
  1400. return nullptr;
  1401. }
  1402. plugin->registerToOscClient();
  1403. return plugin;
  1404. #else
  1405. init.engine->setLastError("DSSI support not available");
  1406. return nullptr;
  1407. #endif
  1408. }
  1409. CARLA_BACKEND_END_NAMESPACE