Collection of tools useful for audio production
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.

1554 lines
40KB

  1. /*
  2. * Carla Plugin
  3. * Copyright (C) 2011-2012 Filipe Coelho <falktx@falktx.com>
  4. *
  5. * This program is free software; you can redistribute it and/or modify
  6. * it under the terms of the GNU General Public License as published by
  7. * the Free Software Foundation; either version 2 of the License, or
  8. * 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 COPYING file
  16. */
  17. #include "carla_plugin.hpp"
  18. #include "carla_lib_utils.hpp"
  19. CARLA_BACKEND_START_NAMESPACE
  20. // -------------------------------------------------------------------
  21. // fallback data
  22. static ParameterData paramDataNull;
  23. static ParameterRanges paramRangesNull;
  24. static MidiProgramData midiProgramDataNull;
  25. static CustomData customDataNull;
  26. // -------------------------------------------------------------------
  27. CarlaPlugin::CarlaPlugin(CarlaEngine* const engine, const unsigned short id)
  28. : m_id(id),
  29. x_engine(engine),
  30. x_client(nullptr),
  31. x_dryWet(1.0),
  32. x_volume(1.0),
  33. x_balanceLeft(-1.0),
  34. x_balanceRight(1.0)
  35. {
  36. CARLA_ASSERT(engine);
  37. CARLA_ASSERT(id < x_engine->maxPluginNumber());
  38. qDebug("CarlaPlugin::CarlaPlugin(%p, %i)", engine, id);
  39. m_type = PLUGIN_NONE;
  40. m_hints = 0;
  41. m_active = false;
  42. m_activeBefore = false;
  43. m_enabled = false;
  44. m_lib = nullptr;
  45. m_name = nullptr;
  46. m_filename = nullptr;
  47. // options
  48. m_ctrlInChannel = 0;
  49. m_fixedBufferSize = true;
  50. m_processHighPrecision = false;
  51. #ifndef BUILD_BRIDGE
  52. {
  53. const CarlaEngineOptions& options(x_engine->getOptions());
  54. m_processHighPrecision = options.processHighPrecision;
  55. if (options.processMode == PROCESS_MODE_CONTINUOUS_RACK)
  56. m_ctrlInChannel = m_id;
  57. }
  58. #endif
  59. // latency
  60. m_latency = 0;
  61. m_latencyBuffers = nullptr;
  62. // Extra
  63. osc.data.path = nullptr;
  64. osc.data.source = nullptr;
  65. osc.data.target = nullptr;
  66. osc.thread = nullptr;
  67. }
  68. CarlaPlugin::~CarlaPlugin()
  69. {
  70. qDebug("CarlaPlugin::~CarlaPlugin()");
  71. // Remove client and ports
  72. if (x_client)
  73. {
  74. if (x_client->isActive())
  75. x_client->deactivate();
  76. removeClientPorts();
  77. delete x_client;
  78. }
  79. // Delete data
  80. deleteBuffers();
  81. // Unload DLL
  82. libClose();
  83. if (m_name)
  84. free((void*)m_name);
  85. if (m_filename)
  86. free((void*)m_filename);
  87. if (prog.count > 0)
  88. {
  89. for (uint32_t i=0; i < prog.count; i++)
  90. {
  91. if (prog.names[i])
  92. free((void*)prog.names[i]);
  93. }
  94. delete[] prog.names;
  95. }
  96. if (midiprog.count > 0)
  97. {
  98. for (uint32_t i=0; i < midiprog.count; i++)
  99. {
  100. if (midiprog.data[i].name)
  101. free((void*)midiprog.data[i].name);
  102. }
  103. delete[] midiprog.data;
  104. }
  105. if (custom.size() > 0)
  106. {
  107. for (size_t i=0; i < custom.size(); i++)
  108. {
  109. if (custom[i].key)
  110. free((void*)custom[i].key);
  111. if (custom[i].value)
  112. free((void*)custom[i].value);
  113. }
  114. custom.clear();
  115. }
  116. if (m_latencyBuffers)
  117. {
  118. for (uint32_t i=0; i < aIn.count; i++)
  119. delete[] m_latencyBuffers[i];
  120. delete[] m_latencyBuffers;
  121. }
  122. }
  123. // -------------------------------------------------------------------
  124. // Information (base)
  125. PluginType CarlaPlugin::type() const
  126. {
  127. return m_type;
  128. }
  129. unsigned short CarlaPlugin::id() const
  130. {
  131. return m_id;
  132. }
  133. unsigned int CarlaPlugin::hints() const
  134. {
  135. return m_hints;
  136. }
  137. bool CarlaPlugin::enabled() const
  138. {
  139. return m_enabled;
  140. }
  141. const char* CarlaPlugin::name() const
  142. {
  143. return m_name;
  144. }
  145. const char* CarlaPlugin::filename() const
  146. {
  147. return m_filename;
  148. }
  149. PluginCategory CarlaPlugin::category()
  150. {
  151. return PLUGIN_CATEGORY_NONE;
  152. }
  153. long CarlaPlugin::uniqueId()
  154. {
  155. return 0;
  156. }
  157. // -------------------------------------------------------------------
  158. // Information (count)
  159. uint32_t CarlaPlugin::audioInCount()
  160. {
  161. return aIn.count;
  162. }
  163. uint32_t CarlaPlugin::audioOutCount()
  164. {
  165. return aOut.count;
  166. }
  167. uint32_t CarlaPlugin::midiInCount()
  168. {
  169. return midi.portMin ? 1 : 0;
  170. }
  171. uint32_t CarlaPlugin::midiOutCount()
  172. {
  173. return midi.portMout ? 1 : 0;
  174. }
  175. uint32_t CarlaPlugin::parameterCount() const
  176. {
  177. return param.count;
  178. }
  179. uint32_t CarlaPlugin::parameterScalePointCount(const uint32_t parameterId)
  180. {
  181. CARLA_ASSERT(parameterId < param.count);
  182. return 0;
  183. }
  184. uint32_t CarlaPlugin::programCount() const
  185. {
  186. return prog.count;
  187. }
  188. uint32_t CarlaPlugin::midiProgramCount() const
  189. {
  190. return midiprog.count;
  191. }
  192. size_t CarlaPlugin::customDataCount() const
  193. {
  194. return custom.size();
  195. }
  196. // -------------------------------------------------------------------
  197. // Information (current data)
  198. int32_t CarlaPlugin::currentProgram() const
  199. {
  200. return prog.current;
  201. }
  202. int32_t CarlaPlugin::currentMidiProgram() const
  203. {
  204. return midiprog.current;
  205. }
  206. const ParameterData* CarlaPlugin::parameterData(const uint32_t parameterId) const
  207. {
  208. CARLA_ASSERT(parameterId < param.count);
  209. if (parameterId < param.count)
  210. return &param.data[parameterId];
  211. return &paramDataNull;
  212. }
  213. const ParameterRanges* CarlaPlugin::parameterRanges(const uint32_t parameterId) const
  214. {
  215. CARLA_ASSERT(parameterId < param.count);
  216. if (parameterId < param.count)
  217. return &param.ranges[parameterId];
  218. return &paramRangesNull;
  219. }
  220. bool CarlaPlugin::parameterIsOutput(const uint32_t parameterId) const
  221. {
  222. CARLA_ASSERT(parameterId < param.count);
  223. if (parameterId < param.count)
  224. return (param.data[parameterId].type == PARAMETER_OUTPUT);
  225. return false;
  226. }
  227. const MidiProgramData* CarlaPlugin::midiProgramData(const uint32_t index) const
  228. {
  229. CARLA_ASSERT(index < midiprog.count);
  230. if (index < midiprog.count)
  231. return &midiprog.data[index];
  232. return &midiProgramDataNull;
  233. }
  234. const CustomData* CarlaPlugin::customData(const size_t index) const
  235. {
  236. CARLA_ASSERT(index < custom.size());
  237. if (index < custom.size())
  238. return &custom[index];
  239. return &customDataNull;
  240. }
  241. int32_t CarlaPlugin::chunkData(void** const dataPtr)
  242. {
  243. CARLA_ASSERT(dataPtr);
  244. return 0;
  245. }
  246. // -------------------------------------------------------------------
  247. // Information (per-plugin data)
  248. double CarlaPlugin::getParameterValue(const uint32_t parameterId)
  249. {
  250. CARLA_ASSERT(parameterId < param.count);
  251. return 0.0;
  252. }
  253. double CarlaPlugin::getParameterScalePointValue(const uint32_t parameterId, const uint32_t scalePointId)
  254. {
  255. CARLA_ASSERT(parameterId < param.count);
  256. CARLA_ASSERT(scalePointId < parameterScalePointCount(parameterId));
  257. return 0.0;
  258. }
  259. void CarlaPlugin::getLabel(char* const strBuf)
  260. {
  261. *strBuf = 0;
  262. }
  263. void CarlaPlugin::getMaker(char* const strBuf)
  264. {
  265. *strBuf = 0;
  266. }
  267. void CarlaPlugin::getCopyright(char* const strBuf)
  268. {
  269. *strBuf = 0;
  270. }
  271. void CarlaPlugin::getRealName(char* const strBuf)
  272. {
  273. *strBuf = 0;;
  274. }
  275. void CarlaPlugin::getParameterName(const uint32_t parameterId, char* const strBuf)
  276. {
  277. CARLA_ASSERT(parameterId < param.count);
  278. *strBuf = 0;
  279. }
  280. void CarlaPlugin::getParameterSymbol(const uint32_t parameterId, char* const strBuf)
  281. {
  282. CARLA_ASSERT(parameterId < param.count);
  283. *strBuf = 0;
  284. }
  285. void CarlaPlugin::getParameterText(const uint32_t parameterId, char* const strBuf)
  286. {
  287. CARLA_ASSERT(parameterId < param.count);
  288. *strBuf = 0;
  289. }
  290. void CarlaPlugin::getParameterUnit(const uint32_t parameterId, char* const strBuf)
  291. {
  292. CARLA_ASSERT(parameterId < param.count);
  293. *strBuf = 0;
  294. }
  295. void CarlaPlugin::getParameterScalePointLabel(const uint32_t parameterId, const uint32_t scalePointId, char* const strBuf)
  296. {
  297. CARLA_ASSERT(parameterId < param.count);
  298. CARLA_ASSERT(scalePointId < parameterScalePointCount(parameterId));
  299. *strBuf = 0;
  300. }
  301. void CarlaPlugin::getProgramName(const uint32_t index, char* const strBuf)
  302. {
  303. CARLA_ASSERT(index < prog.count);
  304. if (index < prog.count && prog.names[index])
  305. strncpy(strBuf, prog.names[index], STR_MAX);
  306. else
  307. *strBuf = 0;
  308. }
  309. void CarlaPlugin::getMidiProgramName(const uint32_t index, char* const strBuf)
  310. {
  311. CARLA_ASSERT(index < midiprog.count);
  312. if (index < midiprog.count && midiprog.data[index].name)
  313. strncpy(strBuf, midiprog.data[index].name, STR_MAX);
  314. else
  315. *strBuf = 0;
  316. }
  317. void CarlaPlugin::getParameterCountInfo(uint32_t* const ins, uint32_t* const outs, uint32_t* const total)
  318. {
  319. *ins = 0;
  320. *outs = 0;
  321. *total = param.count;
  322. for (uint32_t i=0; i < param.count; i++)
  323. {
  324. if (param.data[i].type == PARAMETER_INPUT)
  325. *ins += 1;
  326. else if (param.data[i].type == PARAMETER_OUTPUT)
  327. *outs += 1;
  328. }
  329. }
  330. void CarlaPlugin::getGuiInfo(GuiType* const type, bool* const resizable)
  331. {
  332. *type = GUI_NONE;
  333. *resizable = false;
  334. }
  335. // -------------------------------------------------------------------
  336. // Set data (internal stuff)
  337. #ifndef BUILD_BRIDGE
  338. void CarlaPlugin::setId(const unsigned short id)
  339. {
  340. m_id = id;
  341. if (x_engine->getOptions().processMode == PROCESS_MODE_CONTINUOUS_RACK)
  342. m_ctrlInChannel = id;
  343. }
  344. #endif
  345. void CarlaPlugin::setEnabled(const bool yesNo)
  346. {
  347. m_enabled = yesNo;
  348. }
  349. void CarlaPlugin::setActive(const bool active, const bool sendOsc, const bool sendCallback)
  350. {
  351. m_active = active;
  352. double value = active ? 1.0 : 0.0;
  353. #ifndef BUILD_BRIDGE
  354. if (sendOsc)
  355. x_engine->osc_send_control_set_parameter_value(m_id, PARAMETER_ACTIVE, value);
  356. #else
  357. Q_UNUSED(sendOsc);
  358. #endif
  359. if (sendCallback)
  360. x_engine->callback(CALLBACK_PARAMETER_VALUE_CHANGED, m_id, PARAMETER_ACTIVE, 0, value, nullptr);
  361. #ifndef BUILD_BRIDGE
  362. else if (m_hints & PLUGIN_IS_BRIDGE)
  363. osc_send_control(&osc.data, PARAMETER_ACTIVE, value);
  364. #endif
  365. }
  366. void CarlaPlugin::setDryWet(double value, const bool sendOsc, const bool sendCallback)
  367. {
  368. CARLA_ASSERT(value >= 0.0 && value <= 1.0);
  369. if (value < 0.0)
  370. value = 0.0;
  371. else if (value > 1.0)
  372. value = 1.0;
  373. x_dryWet = value;
  374. #ifndef BUILD_BRIDGE
  375. if (sendOsc)
  376. x_engine->osc_send_control_set_parameter_value(m_id, PARAMETER_DRYWET, value);
  377. #else
  378. Q_UNUSED(sendOsc);
  379. #endif
  380. if (sendCallback)
  381. x_engine->callback(CALLBACK_PARAMETER_VALUE_CHANGED, m_id, PARAMETER_DRYWET, 0, value, nullptr);
  382. #ifndef BUILD_BRIDGE
  383. else if (m_hints & PLUGIN_IS_BRIDGE)
  384. osc_send_control(&osc.data, PARAMETER_DRYWET, value);
  385. #endif
  386. }
  387. void CarlaPlugin::setVolume(double value, const bool sendOsc, const bool sendCallback)
  388. {
  389. CARLA_ASSERT(value >= 0.0 && value <= 1.27);
  390. if (value < 0.0)
  391. value = 0.0;
  392. else if (value > 1.27)
  393. value = 1.27;
  394. x_volume = value;
  395. #ifndef BUILD_BRIDGE
  396. if (sendOsc)
  397. x_engine->osc_send_control_set_parameter_value(m_id, PARAMETER_VOLUME, value);
  398. #else
  399. Q_UNUSED(sendOsc);
  400. #endif
  401. if (sendCallback)
  402. x_engine->callback(CALLBACK_PARAMETER_VALUE_CHANGED, m_id, PARAMETER_VOLUME, 0, value, nullptr);
  403. #ifndef BUILD_BRIDGE
  404. else if (m_hints & PLUGIN_IS_BRIDGE)
  405. osc_send_control(&osc.data, PARAMETER_VOLUME, value);
  406. #endif
  407. }
  408. void CarlaPlugin::setBalanceLeft(double value, const bool sendOsc, const bool sendCallback)
  409. {
  410. CARLA_ASSERT(value >= -1.0 && value <= 1.0);
  411. if (value < -1.0)
  412. value = -1.0;
  413. else if (value > 1.0)
  414. value = 1.0;
  415. x_balanceLeft = value;
  416. #ifndef BUILD_BRIDGE
  417. if (sendOsc)
  418. x_engine->osc_send_control_set_parameter_value(m_id, PARAMETER_BALANCE_LEFT, value);
  419. #else
  420. Q_UNUSED(sendOsc);
  421. #endif
  422. if (sendCallback)
  423. x_engine->callback(CALLBACK_PARAMETER_VALUE_CHANGED, m_id, PARAMETER_BALANCE_LEFT, 0, value, nullptr);
  424. #ifndef BUILD_BRIDGE
  425. else if (m_hints & PLUGIN_IS_BRIDGE)
  426. osc_send_control(&osc.data, PARAMETER_BALANCE_LEFT, value);
  427. #endif
  428. }
  429. void CarlaPlugin::setBalanceRight(double value, const bool sendOsc, const bool sendCallback)
  430. {
  431. CARLA_ASSERT(value >= -1.0 && value <= 1.0);
  432. if (value < -1.0)
  433. value = -1.0;
  434. else if (value > 1.0)
  435. value = 1.0;
  436. x_balanceRight = value;
  437. #ifndef BUILD_BRIDGE
  438. if (sendOsc)
  439. x_engine->osc_send_control_set_parameter_value(m_id, PARAMETER_BALANCE_RIGHT, value);
  440. #else
  441. Q_UNUSED(sendOsc);
  442. #endif
  443. if (sendCallback)
  444. x_engine->callback(CALLBACK_PARAMETER_VALUE_CHANGED, m_id, PARAMETER_BALANCE_RIGHT, 0, value, nullptr);
  445. #ifndef BUILD_BRIDGE
  446. else if (m_hints & PLUGIN_IS_BRIDGE)
  447. osc_send_control(&osc.data, PARAMETER_BALANCE_RIGHT, value);
  448. #endif
  449. }
  450. #ifndef BUILD_BRIDGE
  451. int CarlaPlugin::setOscBridgeInfo(const PluginBridgeInfoType type, const int argc, const lo_arg* const* const argv, const char* const types)
  452. {
  453. return 1;
  454. Q_UNUSED(type);
  455. Q_UNUSED(argc);
  456. Q_UNUSED(argv);
  457. Q_UNUSED(types);
  458. }
  459. #endif
  460. // -------------------------------------------------------------------
  461. // Set data (plugin-specific stuff)
  462. void CarlaPlugin::setParameterValue(const uint32_t parameterId, double value, const bool sendGui, const bool sendOsc, const bool sendCallback)
  463. {
  464. CARLA_ASSERT(parameterId < param.count);
  465. if (sendGui)
  466. uiParameterChange(parameterId, value);
  467. #ifndef BUILD_BRIDGE
  468. if (sendOsc)
  469. x_engine->osc_send_control_set_parameter_value(m_id, parameterId, value);
  470. #else
  471. Q_UNUSED(sendOsc);
  472. #endif
  473. if (sendCallback)
  474. x_engine->callback(CALLBACK_PARAMETER_VALUE_CHANGED, m_id, parameterId, 0, value, nullptr);
  475. }
  476. void CarlaPlugin::setParameterValueByRIndex(const int32_t rindex, const double value, const bool sendGui, const bool sendOsc, const bool sendCallback)
  477. {
  478. CARLA_ASSERT(rindex >= PARAMETER_BALANCE_RIGHT && rindex != PARAMETER_NULL);
  479. if (rindex == PARAMETER_ACTIVE)
  480. return setActive(value > 0.0, sendOsc, sendCallback);
  481. if (rindex == PARAMETER_DRYWET)
  482. return setDryWet(value, sendOsc, sendCallback);
  483. if (rindex == PARAMETER_VOLUME)
  484. return setVolume(value, sendOsc, sendCallback);
  485. if (rindex == PARAMETER_BALANCE_LEFT)
  486. return setBalanceLeft(value, sendOsc, sendCallback);
  487. if (rindex == PARAMETER_BALANCE_RIGHT)
  488. return setBalanceRight(value, sendOsc, sendCallback);
  489. for (uint32_t i=0; i < param.count; i++)
  490. {
  491. if (param.data[i].rindex == rindex)
  492. return setParameterValue(i, value, sendGui, sendOsc, sendCallback);
  493. }
  494. }
  495. void CarlaPlugin::setParameterMidiChannel(const uint32_t parameterId, uint8_t channel, const bool sendOsc, const bool sendCallback)
  496. {
  497. CARLA_ASSERT(parameterId < param.count);
  498. CARLA_ASSERT(channel < 16);
  499. if (channel >= 16)
  500. channel = 16;
  501. param.data[parameterId].midiChannel = channel;
  502. #ifndef BUILD_BRIDGE
  503. if (sendOsc)
  504. x_engine->osc_send_control_set_parameter_midi_channel(m_id, parameterId, channel);
  505. #else
  506. Q_UNUSED(sendOsc);
  507. #endif
  508. if (sendCallback)
  509. x_engine->callback(CALLBACK_PARAMETER_MIDI_CHANNEL_CHANGED, m_id, parameterId, channel, 0.0, nullptr);
  510. }
  511. void CarlaPlugin::setParameterMidiCC(const uint32_t parameterId, int16_t cc, const bool sendOsc, const bool sendCallback)
  512. {
  513. CARLA_ASSERT(parameterId < param.count);
  514. CARLA_ASSERT(cc >= -1);
  515. if (cc < -1 || cc > 0x5F)
  516. cc = -1;
  517. param.data[parameterId].midiCC = cc;
  518. #ifndef BUILD_BRIDGE
  519. if (sendOsc)
  520. x_engine->osc_send_control_set_parameter_midi_cc(m_id, parameterId, cc);
  521. #else
  522. Q_UNUSED(sendOsc);
  523. #endif
  524. if (sendCallback)
  525. x_engine->callback(CALLBACK_PARAMETER_MIDI_CC_CHANGED, m_id, parameterId, cc, 0.0, nullptr);
  526. }
  527. void CarlaPlugin::setCustomData(const char* const type, const char* const key, const char* const value, const bool sendGui)
  528. {
  529. CARLA_ASSERT(type);
  530. CARLA_ASSERT(key);
  531. CARLA_ASSERT(value);
  532. if (! type)
  533. return qCritical("CarlaPlugin::setCustomData(\"%s\", \"%s\", \"%s\", %s) - type is invalid", type, key, value, bool2str(sendGui));
  534. if (! key)
  535. return qCritical("CarlaPlugin::setCustomData(\"%s\", \"%s\", \"%s\", %s) - key is null", type, key, value, bool2str(sendGui));
  536. if (! value)
  537. return qCritical("CarlaPlugin::setCustomData(\"%s\", \"%s\", \"%s\", %s) - value is null", type, key, value, bool2str(sendGui));
  538. bool saveData = true;
  539. if (strcmp(type, CUSTOM_DATA_STRING) == 0)
  540. {
  541. // Ignore some keys
  542. if (strncmp(key, "OSC:", 4) == 0 || strcmp(key, "guiVisible") == 0)
  543. saveData = false;
  544. else if (strcmp(key, CARLA_BRIDGE_MSG_SAVE_NOW) == 0 || strcmp(key, CARLA_BRIDGE_MSG_SET_CHUNK) == 0 || strcmp(key, CARLA_BRIDGE_MSG_SET_CUSTOM) == 0)
  545. saveData = false;
  546. }
  547. if (saveData)
  548. {
  549. // Check if we already have this key
  550. for (size_t i=0; i < custom.size(); i++)
  551. {
  552. if (strcmp(custom[i].key, key) == 0)
  553. {
  554. free((void*)custom[i].value);
  555. custom[i].value = strdup(value);
  556. return;
  557. }
  558. }
  559. // Otherwise store it
  560. CustomData newData;
  561. newData.type = strdup(type);
  562. newData.key = strdup(key);
  563. newData.value = strdup(value);
  564. custom.push_back(newData);
  565. }
  566. }
  567. void CarlaPlugin::setChunkData(const char* const stringData)
  568. {
  569. CARLA_ASSERT(stringData);
  570. }
  571. void CarlaPlugin::setProgram(int32_t index, const bool sendGui, const bool sendOsc, const bool sendCallback, const bool block)
  572. {
  573. CARLA_ASSERT(index >= -1 && index < (int32_t)prog.count);
  574. if (index < -1)
  575. index = -1;
  576. else if (index > (int32_t)prog.count)
  577. return;
  578. prog.current = index;
  579. if (sendGui && index >= 0)
  580. uiProgramChange(index);
  581. // Change default parameter values
  582. if (index >= 0)
  583. {
  584. for (uint32_t i=0; i < param.count; i++)
  585. {
  586. param.ranges[i].def = getParameterValue(i);
  587. fixParameterValue(param.ranges[i].def, param.ranges[i]);
  588. #ifndef BUILD_BRIDGE
  589. if (sendOsc)
  590. {
  591. x_engine->osc_send_control_set_default_value(m_id, i, param.ranges[i].def);
  592. x_engine->osc_send_control_set_parameter_value(m_id, i, param.ranges[i].def);
  593. }
  594. #endif
  595. }
  596. }
  597. #ifndef BUILD_BRIDGE
  598. if (sendOsc)
  599. x_engine->osc_send_control_set_program(m_id, index);
  600. #else
  601. Q_UNUSED(sendOsc);
  602. #endif
  603. if (sendCallback)
  604. x_engine->callback(CALLBACK_PROGRAM_CHANGED, m_id, index, 0, 0.0, nullptr);
  605. Q_UNUSED(block);
  606. }
  607. void CarlaPlugin::setMidiProgram(int32_t index, const bool sendGui, const bool sendOsc, const bool sendCallback, const bool block)
  608. {
  609. CARLA_ASSERT(index >= -1 && index < (int32_t)midiprog.count);
  610. if (index < -1)
  611. index = -1;
  612. else if (index > (int32_t)midiprog.count)
  613. return;
  614. midiprog.current = index;
  615. if (sendGui && index >= 0)
  616. uiMidiProgramChange(index);
  617. // Change default parameter values (sound banks never change defaults)
  618. if (index >= 0 && m_type != PLUGIN_GIG && m_type != PLUGIN_SF2 && m_type != PLUGIN_SFZ)
  619. {
  620. for (uint32_t i=0; i < param.count; i++)
  621. {
  622. param.ranges[i].def = getParameterValue(i);
  623. fixParameterValue(param.ranges[i].def, param.ranges[i]);
  624. #ifndef BUILD_BRIDGE
  625. if (sendOsc)
  626. {
  627. x_engine->osc_send_control_set_default_value(m_id, i, param.ranges[i].def);
  628. x_engine->osc_send_control_set_parameter_value(m_id, i, param.ranges[i].def);
  629. }
  630. #endif
  631. }
  632. }
  633. #ifndef BUILD_BRIDGE
  634. if (sendOsc)
  635. x_engine->osc_send_control_set_midi_program(m_id, index);
  636. #else
  637. Q_UNUSED(sendOsc);
  638. #endif
  639. if (sendCallback)
  640. x_engine->callback(CALLBACK_MIDI_PROGRAM_CHANGED, m_id, index, 0, 0.0, nullptr);
  641. Q_UNUSED(block);
  642. }
  643. void CarlaPlugin::setMidiProgramById(const uint32_t bank, const uint32_t program, const bool sendGui, const bool sendOsc, const bool sendCallback, const bool block)
  644. {
  645. for (uint32_t i=0; i < midiprog.count; i++)
  646. {
  647. if (midiprog.data[i].bank == bank && midiprog.data[i].program == program)
  648. return setMidiProgram(i, sendGui, sendOsc, sendCallback, block);
  649. }
  650. }
  651. // -------------------------------------------------------------------
  652. // Set gui stuff
  653. void CarlaPlugin::setGuiContainer(GuiContainer* const container)
  654. {
  655. Q_UNUSED(container);
  656. }
  657. void CarlaPlugin::showGui(const bool yesNo)
  658. {
  659. Q_UNUSED(yesNo);
  660. }
  661. void CarlaPlugin::idleGui()
  662. {
  663. if (! m_enabled)
  664. return;
  665. if (m_hints & PLUGIN_USES_SINGLE_THREAD)
  666. {
  667. // Process postponed events
  668. postEventsRun();
  669. // Update parameter outputs
  670. for (uint32_t i=0; i < param.count; i++)
  671. {
  672. if (param.data[i].type == PARAMETER_OUTPUT)
  673. uiParameterChange(i, getParameterValue(i));
  674. }
  675. }
  676. }
  677. // -------------------------------------------------------------------
  678. // Plugin state
  679. void CarlaPlugin::reload()
  680. {
  681. }
  682. void CarlaPlugin::reloadPrograms(const bool init)
  683. {
  684. Q_UNUSED(init);
  685. }
  686. void CarlaPlugin::prepareForSave()
  687. {
  688. }
  689. // -------------------------------------------------------------------
  690. // Plugin processing
  691. void CarlaPlugin::process(float** const inBuffer, float** const outBuffer, const uint32_t frames, const uint32_t framesOffset)
  692. {
  693. Q_UNUSED(inBuffer);
  694. Q_UNUSED(outBuffer);
  695. Q_UNUSED(frames);
  696. Q_UNUSED(framesOffset);
  697. }
  698. void CarlaPlugin::bufferSizeChanged(const uint32_t newBufferSize)
  699. {
  700. Q_UNUSED(newBufferSize);
  701. }
  702. void CarlaPlugin::recreateLatencyBuffers()
  703. {
  704. if (m_latencyBuffers)
  705. {
  706. for (uint32_t i=0; i < aIn.count; i++)
  707. delete[] m_latencyBuffers[i];
  708. delete[] m_latencyBuffers;
  709. }
  710. if (aIn.count > 0 && m_latency > 0)
  711. {
  712. m_latencyBuffers = new float* [aIn.count];
  713. for (uint32_t i=0; i < aIn.count; i++)
  714. m_latencyBuffers[i] = new float [m_latency];
  715. }
  716. else
  717. m_latencyBuffers = nullptr;
  718. }
  719. // -------------------------------------------------------------------
  720. // OSC stuff
  721. void CarlaPlugin::registerToOscClient()
  722. {
  723. #ifndef BUILD_BRIDGE
  724. if (! x_engine->isOscControlRegistered())
  725. return;
  726. #else
  727. if (! x_engine->isOscBridgeRegistered())
  728. return;
  729. #endif
  730. #ifndef BUILD_BRIDGE
  731. x_engine->osc_send_control_add_plugin_start(m_id, m_name);
  732. #endif
  733. // Base data
  734. {
  735. char bufName[STR_MAX] = { 0 };
  736. char bufLabel[STR_MAX] = { 0 };
  737. char bufMaker[STR_MAX] = { 0 };
  738. char bufCopyright[STR_MAX] = { 0 };
  739. getRealName(bufName);
  740. getLabel(bufLabel);
  741. getMaker(bufMaker);
  742. getCopyright(bufCopyright);
  743. #ifdef BUILD_BRIDGE
  744. x_engine->osc_send_bridge_plugin_info(category(), m_hints, bufName, bufLabel, bufMaker, bufCopyright, uniqueId());
  745. #else
  746. x_engine->osc_send_control_set_plugin_data(m_id, m_type, category(), m_hints, bufName, bufLabel, bufMaker, bufCopyright, uniqueId());
  747. #endif
  748. }
  749. // Base count
  750. {
  751. uint32_t cIns, cOuts, cTotals;
  752. getParameterCountInfo(&cIns, &cOuts, &cTotals);
  753. #ifdef BUILD_BRIDGE
  754. x_engine->osc_send_bridge_audio_count(audioInCount(), audioOutCount(), audioInCount() + audioOutCount());
  755. x_engine->osc_send_bridge_midi_count(midiInCount(), midiOutCount(), midiInCount() + midiOutCount());
  756. x_engine->osc_send_bridge_parameter_count(cIns, cOuts, cTotals);
  757. #else
  758. x_engine->osc_send_control_set_plugin_ports(m_id, audioInCount(), audioOutCount(), midiInCount(), midiOutCount(), cIns, cOuts, cTotals);
  759. #endif
  760. }
  761. // Plugin Parameters
  762. #ifdef BUILD_BRIDGE
  763. const uint32_t maxParameters = MAX_PARAMETERS;
  764. #else
  765. const uint32_t maxParameters = x_engine->getOptions().maxParameters;
  766. #endif
  767. if (param.count > 0 && param.count < maxParameters)
  768. {
  769. char bufName[STR_MAX], bufUnit[STR_MAX];
  770. for (uint32_t i=0; i < param.count; i++)
  771. {
  772. getParameterName(i, bufName);
  773. getParameterUnit(i, bufUnit);
  774. #ifdef BUILD_BRIDGE
  775. x_engine->osc_send_bridge_parameter_info(i, bufName, bufUnit);
  776. x_engine->osc_send_bridge_parameter_data(i, param.data[i].type, param.data[i].rindex, param.data[i].hints, param.data[i].midiChannel, param.data[i].midiCC);
  777. x_engine->osc_send_bridge_parameter_ranges(i, param.ranges[i].def, param.ranges[i].min, param.ranges[i].max, param.ranges[i].step, param.ranges[i].stepSmall, param.ranges[i].stepLarge);
  778. x_engine->osc_send_bridge_set_parameter_value(i, getParameterValue(i));
  779. #else
  780. x_engine->osc_send_control_set_parameter_data(m_id, i, param.data[i].type, param.data[i].hints, bufName, bufUnit, getParameterValue(i));
  781. x_engine->osc_send_control_set_parameter_ranges(m_id, i, param.ranges[i].min, param.ranges[i].max, param.ranges[i].def, param.ranges[i].step, param.ranges[i].stepSmall, param.ranges[i].stepLarge);
  782. x_engine->osc_send_control_set_parameter_midi_cc(m_id, i, param.data[i].midiCC);
  783. x_engine->osc_send_control_set_parameter_midi_channel(m_id, i, param.data[i].midiChannel);
  784. x_engine->osc_send_control_set_parameter_value(m_id, i, getParameterValue(i));
  785. #endif
  786. }
  787. }
  788. // Programs
  789. if (prog.count > 0)
  790. {
  791. #ifdef BUILD_BRIDGE
  792. x_engine->osc_send_bridge_program_count(prog.count);
  793. for (uint32_t i=0; i < prog.count; i++)
  794. x_engine->osc_send_bridge_program_info(i, prog.names[i]);
  795. x_engine->osc_send_bridge_set_program(prog.current);
  796. #else
  797. x_engine->osc_send_control_set_program_count(m_id, prog.count);
  798. for (uint32_t i=0; i < prog.count; i++)
  799. x_engine->osc_send_control_set_program_name(m_id, i, prog.names[i]);
  800. x_engine->osc_send_control_set_program(m_id, prog.current);
  801. #endif
  802. }
  803. // MIDI Programs
  804. if (midiprog.count > 0)
  805. {
  806. #ifdef BUILD_BRIDGE
  807. x_engine->osc_send_bridge_midi_program_count(midiprog.count);
  808. for (uint32_t i=0; i < midiprog.count; i++)
  809. x_engine->osc_send_bridge_midi_program_info(i, midiprog.data[i].bank, midiprog.data[i].program, midiprog.data[i].name);
  810. x_engine->osc_send_bridge_set_midi_program(prog.current);
  811. #else
  812. x_engine->osc_send_control_set_midi_program_count(m_id, midiprog.count);
  813. for (uint32_t i=0; i < midiprog.count; i++)
  814. x_engine->osc_send_control_set_midi_program_data(m_id, i, midiprog.data[i].bank, midiprog.data[i].program, midiprog.data[i].name);
  815. x_engine->osc_send_control_set_midi_program(m_id, midiprog.current);
  816. #endif
  817. }
  818. #ifndef BUILD_BRIDGE
  819. x_engine->osc_send_control_add_plugin_end(m_id);
  820. // Internal Parameters
  821. {
  822. x_engine->osc_send_control_set_parameter_value(m_id, PARAMETER_ACTIVE, m_active ? 1.0 : 0.0);
  823. x_engine->osc_send_control_set_parameter_value(m_id, PARAMETER_DRYWET, x_dryWet);
  824. x_engine->osc_send_control_set_parameter_value(m_id, PARAMETER_VOLUME, x_volume);
  825. x_engine->osc_send_control_set_parameter_value(m_id, PARAMETER_BALANCE_LEFT, x_balanceLeft);
  826. x_engine->osc_send_control_set_parameter_value(m_id, PARAMETER_BALANCE_RIGHT, x_balanceRight);
  827. }
  828. #endif
  829. }
  830. void CarlaPlugin::updateOscData(const lo_address source, const char* const url)
  831. {
  832. // FIXME - remove debug prints later
  833. qWarning("CarlaPlugin::updateOscData(%p, \"%s\")", source, url);
  834. const char* host;
  835. const char* port;
  836. const int proto = lo_address_get_protocol(source);
  837. osc.data.free();
  838. host = lo_address_get_hostname(source);
  839. port = lo_address_get_port(source);
  840. osc.data.source = lo_address_new_with_proto(proto, host, port);
  841. qWarning("CarlaPlugin::updateOscData() - source: host \"%s\", port \"%s\"", host, port);
  842. host = lo_url_get_hostname(url);
  843. port = lo_url_get_port(url);
  844. osc.data.path = lo_url_get_path(url);
  845. osc.data.target = lo_address_new_with_proto(proto, host, port);
  846. qWarning("CarlaPlugin::updateOscData() - target: host \"%s\", port \"%s\", path \"%s\"", host, port, osc.data.path);
  847. free((void*)host);
  848. free((void*)port);
  849. if (m_hints & PLUGIN_IS_BRIDGE)
  850. return;
  851. osc_send_sample_rate(&osc.data, x_engine->getSampleRate());
  852. for (size_t i=0; i < custom.size(); i++)
  853. {
  854. // TODO
  855. //if (m_type == PLUGIN_LV2)
  856. //osc_send_lv2_transfer_event(&osc.data, getCustomDataTypeString(custom[i].type), /*custom[i].key,*/ custom[i].value);
  857. //else
  858. if (custom[i].type == CUSTOM_DATA_STRING)
  859. osc_send_configure(&osc.data, custom[i].key, custom[i].value);
  860. }
  861. if (prog.current >= 0)
  862. osc_send_program(&osc.data, prog.current);
  863. if (midiprog.current >= 0)
  864. {
  865. if (m_type == PLUGIN_DSSI)
  866. osc_send_program(&osc.data, midiprog.data[midiprog.current].bank, midiprog.data[midiprog.current].program);
  867. else
  868. osc_send_midi_program(&osc.data, midiprog.data[midiprog.current].bank, midiprog.data[midiprog.current].program);
  869. }
  870. for (uint32_t i=0; i < param.count; i++)
  871. osc_send_control(&osc.data, param.data[i].rindex, getParameterValue(i));
  872. qWarning("CarlaPlugin::updateOscData() - done");
  873. }
  874. void CarlaPlugin::freeOscData()
  875. {
  876. osc.data.free();
  877. }
  878. bool CarlaPlugin::waitForOscGuiShow()
  879. {
  880. qWarning("CarlaPlugin::waitForOscGuiShow()");
  881. #ifndef BUILD_BRIDGE
  882. const uint oscUiTimeout = x_engine->getOptions().oscUiTimeout;
  883. #else
  884. const uint oscUiTimeout = 40;
  885. #endif
  886. // wait for UI 'update' call
  887. for (uint i=0; i < oscUiTimeout; i++)
  888. {
  889. if (osc.data.target)
  890. {
  891. qWarning("CarlaPlugin::waitForOscGuiShow() - got response, asking UI to show itself now");
  892. osc_send_show(&osc.data);
  893. return true;
  894. }
  895. else
  896. carla_msleep(100);
  897. }
  898. qWarning("CarlaPlugin::waitForOscGuiShow() - Timeout while waiting for UI to respond (waited %u msecs)", oscUiTimeout);
  899. return false;
  900. }
  901. // -------------------------------------------------------------------
  902. // MIDI events
  903. void CarlaPlugin::sendMidiSingleNote(const uint8_t channel, const uint8_t note, const uint8_t velo, const bool sendGui, const bool sendOsc, const bool sendCallback)
  904. {
  905. CARLA_ASSERT(channel < 16);
  906. CARLA_ASSERT(note < 128);
  907. CARLA_ASSERT(velo < 128);
  908. if (! m_active)
  909. return;
  910. engineMidiLock();
  911. for (unsigned short i=0; i < MAX_MIDI_EVENTS; i++)
  912. {
  913. if (extMidiNotes[i].channel < 0)
  914. {
  915. extMidiNotes[i].channel = channel;
  916. extMidiNotes[i].note = note;
  917. extMidiNotes[i].velo = velo;
  918. break;
  919. }
  920. }
  921. engineMidiUnlock();
  922. if (sendGui)
  923. {
  924. if (velo > 0)
  925. uiNoteOn(channel, note, velo);
  926. else
  927. uiNoteOff(channel, note);
  928. }
  929. #ifndef BUILD_BRIDGE
  930. if (sendOsc)
  931. {
  932. if (velo > 0)
  933. x_engine->osc_send_control_note_on(m_id, channel, note, velo);
  934. else
  935. x_engine->osc_send_control_note_off(m_id, channel, note);
  936. }
  937. #else
  938. Q_UNUSED(sendOsc);
  939. #endif
  940. if (sendCallback)
  941. x_engine->callback(velo ? CALLBACK_NOTE_ON : CALLBACK_NOTE_OFF, m_id, channel, note, velo, nullptr);
  942. }
  943. void CarlaPlugin::sendMidiAllNotesOff()
  944. {
  945. engineMidiLock();
  946. postEvents.mutex.lock();
  947. unsigned short postPad = 0;
  948. for (unsigned short i=0; i < MAX_POST_EVENTS; i++)
  949. {
  950. if (postEvents.data[i].type == PluginPostEventNull)
  951. {
  952. postPad = i;
  953. break;
  954. }
  955. }
  956. if (postPad == MAX_POST_EVENTS - 1)
  957. {
  958. qWarning("post-events buffer full, making room for all notes off now");
  959. postPad -= 128;
  960. }
  961. for (unsigned short i=0; i < 128; i++)
  962. {
  963. extMidiNotes[i].channel = m_ctrlInChannel;
  964. extMidiNotes[i].note = i;
  965. extMidiNotes[i].velo = 0;
  966. postEvents.data[i + postPad].type = PluginPostEventNoteOff;
  967. postEvents.data[i + postPad].value1 = m_ctrlInChannel;
  968. postEvents.data[i + postPad].value2 = i;
  969. postEvents.data[i + postPad].value3 = 0.0;
  970. }
  971. postEvents.mutex.unlock();
  972. engineMidiUnlock();
  973. }
  974. // -------------------------------------------------------------------
  975. // Post-poned events
  976. void CarlaPlugin::postponeEvent(const PluginPostEventType type, const int32_t value1, const int32_t value2, const double value3, const void* const cdata)
  977. {
  978. postEvents.mutex.lock();
  979. for (unsigned short i=0; i < MAX_POST_EVENTS; i++)
  980. {
  981. if (postEvents.data[i].type == PluginPostEventNull)
  982. {
  983. postEvents.data[i].type = type;
  984. postEvents.data[i].value1 = value1;
  985. postEvents.data[i].value2 = value2;
  986. postEvents.data[i].value3 = value3;
  987. postEvents.data[i].cdata = cdata;
  988. break;
  989. }
  990. }
  991. postEvents.mutex.unlock();
  992. }
  993. void CarlaPlugin::postEventsRun()
  994. {
  995. PluginPostEvent newPostEvents[MAX_POST_EVENTS];
  996. // Make a safe copy of events, and clear them
  997. postEvents.mutex.lock();
  998. memcpy(newPostEvents, postEvents.data, sizeof(PluginPostEvent)*MAX_POST_EVENTS);
  999. for (unsigned short i=0; i < MAX_POST_EVENTS; i++)
  1000. postEvents.data[i].type = PluginPostEventNull;
  1001. postEvents.mutex.unlock();
  1002. // Handle events now
  1003. for (uint32_t i=0; i < MAX_POST_EVENTS; i++)
  1004. {
  1005. const PluginPostEvent* const event = &newPostEvents[i];
  1006. switch (event->type)
  1007. {
  1008. case PluginPostEventNull:
  1009. break;
  1010. case PluginPostEventDebug:
  1011. x_engine->callback(CALLBACK_DEBUG, m_id, event->value1, event->value2, event->value3, nullptr);
  1012. break;
  1013. case PluginPostEventParameterChange:
  1014. // Update UI
  1015. if (event->value1 >= 0)
  1016. uiParameterChange(event->value1, event->value3);
  1017. #ifndef BUILD_BRIDGE
  1018. // Update OSC control client
  1019. if (x_engine->isOscControlRegistered())
  1020. x_engine->osc_send_control_set_parameter_value(m_id, event->value1, event->value3);
  1021. #endif
  1022. // Update Host
  1023. x_engine->callback(CALLBACK_PARAMETER_VALUE_CHANGED, m_id, event->value1, 0, event->value3, nullptr);
  1024. break;
  1025. case PluginPostEventProgramChange:
  1026. // Update UI
  1027. if (event->value1 >= 0)
  1028. uiProgramChange(event->value1);
  1029. #ifndef BUILD_BRIDGE
  1030. // Update OSC control client
  1031. if (x_engine->isOscControlRegistered())
  1032. {
  1033. x_engine->osc_send_control_set_program(m_id, event->value1);
  1034. for (uint32_t j=0; j < param.count; j++)
  1035. x_engine->osc_send_control_set_default_value(m_id, j, param.ranges[j].def);
  1036. }
  1037. #endif
  1038. // Update Host
  1039. x_engine->callback(CALLBACK_PROGRAM_CHANGED, m_id, event->value1, 0, 0.0, nullptr);
  1040. break;
  1041. case PluginPostEventMidiProgramChange:
  1042. // Update UI
  1043. if (event->value1 >= 0)
  1044. uiMidiProgramChange(event->value1);
  1045. #ifndef BUILD_BRIDGE
  1046. // Update OSC control client
  1047. if (x_engine->isOscControlRegistered())
  1048. {
  1049. x_engine->osc_send_control_set_midi_program(m_id, event->value1);
  1050. for (uint32_t j=0; j < param.count; j++)
  1051. x_engine->osc_send_control_set_default_value(m_id, j, param.ranges[j].def);
  1052. }
  1053. #endif
  1054. // Update Host
  1055. x_engine->callback(CALLBACK_MIDI_PROGRAM_CHANGED, m_id, event->value1, 0, 0.0, nullptr);
  1056. break;
  1057. case PluginPostEventNoteOn:
  1058. // Update UI
  1059. uiNoteOn(event->value1, event->value2, rint(event->value3));
  1060. #ifndef BUILD_BRIDGE
  1061. // Update OSC control client
  1062. if (x_engine->isOscControlRegistered())
  1063. x_engine->osc_send_control_note_on(m_id, event->value1, event->value2, rint(event->value3));
  1064. #endif
  1065. // Update Host
  1066. x_engine->callback(CALLBACK_NOTE_ON, m_id, event->value1, event->value2, rint(event->value3), nullptr);
  1067. break;
  1068. case PluginPostEventNoteOff:
  1069. // Update UI
  1070. uiNoteOff(event->value1, event->value2);
  1071. #ifndef BUILD_BRIDGE
  1072. // Update OSC control client
  1073. if (x_engine->isOscControlRegistered())
  1074. x_engine->osc_send_control_note_off(m_id, event->value1, event->value2);
  1075. #endif
  1076. // Update Host
  1077. x_engine->callback(CALLBACK_NOTE_OFF, m_id, event->value1, event->value2, 0.0, nullptr);
  1078. break;
  1079. case PluginPostEventCustom:
  1080. // Handle custom event
  1081. postEventHandleCustom(event->value1, event->value2, event->value3, event->cdata);
  1082. break;
  1083. }
  1084. }
  1085. }
  1086. void CarlaPlugin::postEventHandleCustom(const int32_t value1, const int32_t value2, const double value3, const void* const cdata)
  1087. {
  1088. Q_UNUSED(value1);
  1089. Q_UNUSED(value2);
  1090. Q_UNUSED(value3);
  1091. Q_UNUSED(cdata);
  1092. }
  1093. void CarlaPlugin::uiParameterChange(const uint32_t index, const double value)
  1094. {
  1095. CARLA_ASSERT(index < param.count);
  1096. Q_UNUSED(value);
  1097. }
  1098. void CarlaPlugin::uiProgramChange(const uint32_t index)
  1099. {
  1100. CARLA_ASSERT(index < prog.count);
  1101. }
  1102. void CarlaPlugin::uiMidiProgramChange(const uint32_t index)
  1103. {
  1104. CARLA_ASSERT(index < midiprog.count);
  1105. }
  1106. void CarlaPlugin::uiNoteOn(const uint8_t channel, const uint8_t note, const uint8_t velo)
  1107. {
  1108. CARLA_ASSERT(channel < 16);
  1109. CARLA_ASSERT(note < 128);
  1110. CARLA_ASSERT(velo > 0 && velo < 128);
  1111. }
  1112. void CarlaPlugin::uiNoteOff(const uint8_t channel, const uint8_t note)
  1113. {
  1114. CARLA_ASSERT(channel < 16);
  1115. CARLA_ASSERT(note < 128);
  1116. }
  1117. // -------------------------------------------------------------------
  1118. // Cleanup
  1119. void CarlaPlugin::removeClientPorts()
  1120. {
  1121. qDebug("CarlaPlugin::removeClientPorts() - start");
  1122. for (uint32_t i=0; i < aIn.count; i++)
  1123. {
  1124. delete aIn.ports[i];
  1125. aIn.ports[i] = nullptr;
  1126. }
  1127. for (uint32_t i=0; i < aOut.count; i++)
  1128. {
  1129. delete aOut.ports[i];
  1130. aOut.ports[i] = nullptr;
  1131. }
  1132. if (midi.portMin)
  1133. {
  1134. delete midi.portMin;
  1135. midi.portMin = nullptr;
  1136. }
  1137. if (midi.portMout)
  1138. {
  1139. delete midi.portMout;
  1140. midi.portMout = nullptr;
  1141. }
  1142. if (param.portCin)
  1143. {
  1144. delete param.portCin;
  1145. param.portCin = nullptr;
  1146. }
  1147. if (param.portCout)
  1148. {
  1149. delete param.portCout;
  1150. param.portCout = nullptr;
  1151. }
  1152. qDebug("CarlaPlugin::removeClientPorts() - end");
  1153. }
  1154. void CarlaPlugin::initBuffers()
  1155. {
  1156. for (uint32_t i=0; i < aIn.count; i++)
  1157. {
  1158. if (aIn.ports[i])
  1159. aIn.ports[i]->initBuffer(x_engine);
  1160. }
  1161. for (uint32_t i=0; i < aOut.count; i++)
  1162. {
  1163. if (aOut.ports[i])
  1164. aOut.ports[i]->initBuffer(x_engine);
  1165. }
  1166. if (param.portCin)
  1167. param.portCin->initBuffer(x_engine);
  1168. if (param.portCout)
  1169. param.portCout->initBuffer(x_engine);
  1170. if (midi.portMin)
  1171. midi.portMin->initBuffer(x_engine);
  1172. if (midi.portMout)
  1173. midi.portMout->initBuffer(x_engine);
  1174. }
  1175. void CarlaPlugin::deleteBuffers()
  1176. {
  1177. qDebug("CarlaPlugin::deleteBuffers() - start");
  1178. if (aIn.count > 0)
  1179. {
  1180. delete[] aIn.ports;
  1181. delete[] aIn.rindexes;
  1182. }
  1183. if (aOut.count > 0)
  1184. {
  1185. delete[] aOut.ports;
  1186. delete[] aOut.rindexes;
  1187. }
  1188. if (param.count > 0)
  1189. {
  1190. delete[] param.data;
  1191. delete[] param.ranges;
  1192. }
  1193. aIn.count = 0;
  1194. aIn.ports = nullptr;
  1195. aIn.rindexes = nullptr;
  1196. aOut.count = 0;
  1197. aOut.ports = nullptr;
  1198. aOut.rindexes = nullptr;
  1199. param.count = 0;
  1200. param.data = nullptr;
  1201. param.ranges = nullptr;
  1202. param.portCin = nullptr;
  1203. param.portCout = nullptr;
  1204. qDebug("CarlaPlugin::deleteBuffers() - end");
  1205. }
  1206. // -------------------------------------------------------------------
  1207. // Library functions
  1208. bool CarlaPlugin::libOpen(const char* const filename)
  1209. {
  1210. m_lib = lib_open(filename);
  1211. return bool(m_lib);
  1212. }
  1213. bool CarlaPlugin::libClose()
  1214. {
  1215. if (m_lib)
  1216. return lib_close(m_lib);
  1217. return false;
  1218. }
  1219. void* CarlaPlugin::libSymbol(const char* const symbol)
  1220. {
  1221. if (m_lib)
  1222. return lib_symbol(m_lib, symbol);
  1223. return nullptr;
  1224. }
  1225. const char* CarlaPlugin::libError(const char* const filename)
  1226. {
  1227. return lib_error(filename);
  1228. }
  1229. // -------------------------------------------------------------------
  1230. // Locks
  1231. void CarlaPlugin::engineProcessLock()
  1232. {
  1233. x_engine->processLock();
  1234. }
  1235. void CarlaPlugin::engineProcessUnlock()
  1236. {
  1237. x_engine->processUnlock();
  1238. }
  1239. void CarlaPlugin::engineMidiLock()
  1240. {
  1241. x_engine->midiLock();
  1242. }
  1243. void CarlaPlugin::engineMidiUnlock()
  1244. {
  1245. x_engine->midiUnlock();
  1246. }
  1247. CARLA_BACKEND_END_NAMESPACE