Browse Source

plugin bridges are now saving chunk

tags/1.9.4
falkTX 10 years ago
parent
commit
c070c1a027
10 changed files with 167 additions and 141 deletions
  1. +1
    -1
      source/backend/CarlaPlugin.hpp
  2. +0
    -1
      source/backend/CarlaStandalone.cpp
  3. +44
    -25
      source/backend/engine/CarlaEngineBridge.cpp
  4. +66
    -62
      source/backend/plugin/BridgePlugin.cpp
  5. +1
    -1
      source/backend/plugin/CarlaPlugin.cpp
  6. +2
    -2
      source/backend/plugin/DssiPlugin.cpp
  7. +47
    -11
      source/backend/plugin/JucePlugin.cpp
  8. +4
    -2
      source/backend/plugin/VstPlugin.cpp
  9. +0
    -34
      source/bridges-plugin/CarlaBridgePlugin.cpp
  10. +2
    -2
      source/utils/CarlaBridgeUtils.hpp

+ 1
- 1
source/backend/CarlaPlugin.hpp View File

@@ -263,7 +263,7 @@ public:
*
* \see setChunkData()
*/
virtual int32_t getChunkData(void** const dataPtr) const noexcept;
virtual std::size_t getChunkData(void** const dataPtr) noexcept;

// -------------------------------------------------------------------
// Information (per-plugin data)


+ 0
- 1
source/backend/CarlaStandalone.cpp View File

@@ -1682,7 +1682,6 @@ const char* carla_get_chunk_data(uint pluginId)
if (data != nullptr && dataSize > 0)
{
chunkData = CarlaString::asBase64(data, static_cast<std::size_t>(dataSize));

return chunkData;
}
else


+ 44
- 25
source/backend/engine/CarlaEngineBridge.cpp View File

@@ -31,6 +31,9 @@
#include <cerrno>
#include <ctime>

using juce::File;
using juce::String;

#ifdef JACKBRIDGE_EXPORT
// -------------------------------------------------------------------

@@ -44,10 +47,6 @@ bool jackbridge_is_ok() noexcept

CARLA_BACKEND_START_NAMESPACE

#if 0
} // Fix editor indentation
#endif

// -------------------------------------------------------------------

template<typename T>
@@ -478,6 +477,38 @@ public:
break;
}

case kPluginBridgeOpcodeSetChunkFile: {
const uint32_t size(fShmControl.readUInt());
CARLA_SAFE_ASSERT_BREAK(size > 0);

char chunkFilePathTry[size+1];
carla_zeroChar(chunkFilePathTry, size+1);
fShmControl.readCustomData(chunkFilePathTry, size);

CARLA_SAFE_ASSERT_BREAK(chunkFilePathTry[0] != '\0');

String chunkFilePath(chunkFilePathTry);
#ifdef CARLA_OS_WIN
if (chunkFilePath.startsWith("/"))
{
// running under Wine, posix host
chunkFilePath = chunkFilePath.replaceSection(0, 1, "Z:\\");
chunkFilePath = chunkFilePath.replace("/", "\\");
}
#endif

File chunkFile(chunkFilePath);
CARLA_SAFE_ASSERT_BREAK(chunkFile.existsAsFile());

String chunkData(chunkFile.loadFileAsString());
chunkFile.deleteFile();
CARLA_SAFE_ASSERT_BREAK(chunkData.isNotEmpty());

carla_set_chunk_data(0, chunkData.toRawUTF8());
carla_stdout("chunk sent, size:%i", chunkData.length());
break;
}

case kPluginBridgeOpcodePrepareForSave: {
carla_prepare_for_save(0);

@@ -491,28 +522,16 @@ public:

//if (fPlugin->getOptionsEnabled() & CarlaBackend::PLUGIN_OPTION_USE_CHUNKS)
{
//if (const char* const chunkData = carla_get_chunk_data(0))
if (const char* const chunkData = carla_get_chunk_data(0))
{
#if 0
QString filePath;
filePath = QDir::tempPath();
#ifdef Q_OS_WIN
filePath += "\\.CarlaChunk_";
#else
filePath += "/.CarlaChunk_";
#endif
filePath += fPlugin->getName();

QFile file(filePath);

if (file.open(QIODevice::WriteOnly))
{
QByteArray chunk((const char*)data, dataSize);
file.write(chunk);
file.close();
fEngine->oscSend_bridge_set_chunk_data(filePath.toUtf8().constData());
}
#endif
String filePath(File::getSpecialLocation(File::tempDirectory).getFullPathName());

filePath += OS_SEP_STR;
filePath += ".CarlaChunk_";
filePath += fShmAudioPool.filename.buffer() + 18;

if (File(filePath).replaceWithText(chunkData))
oscSend_bridge_set_chunk_data(filePath.toRawUTF8());
}
}



+ 66
- 62
source/backend/plugin/BridgePlugin.cpp View File

@@ -21,6 +21,7 @@
#ifndef BUILD_BRIDGE

#include "CarlaBackendUtils.hpp"
#include "CarlaBase64Utils.hpp"
#include "CarlaBridgeUtils.hpp"
#include "CarlaMathUtils.hpp"
#include "CarlaShmUtils.hpp"
@@ -54,6 +55,13 @@
} \
}

// -------------------------------------------------------------------------------------------------------------------

using juce::File;
using juce::MemoryBlock;
using juce::String;
using juce::StringArray;

CARLA_BACKEND_START_NAMESPACE

// -------------------------------------------------------------------------------------------------------------------
@@ -282,7 +290,6 @@ struct BridgeTime {

// -------------------------------------------------------------------------------------------------------------------

// FIXME - use CarlaString
struct BridgeParamInfo {
float value;
CarlaString name;
@@ -362,7 +369,7 @@ public:

clearBuffers();

//info.chunk.clear();
fInfo.chunk.clear();
}

// -------------------------------------------------------------------
@@ -404,20 +411,14 @@ public:
// -------------------------------------------------------------------
// Information (current data)

int32_t getChunkData(void** const dataPtr) const noexcept override
std::size_t getChunkData(void** const dataPtr) noexcept override
{
CARLA_ASSERT(pData->options & PLUGIN_OPTION_USE_CHUNKS);
CARLA_ASSERT(dataPtr != nullptr);
CARLA_SAFE_ASSERT_RETURN(pData->options & PLUGIN_OPTION_USE_CHUNKS, 0);
CARLA_SAFE_ASSERT_RETURN(dataPtr != nullptr, 0);
CARLA_SAFE_ASSERT_RETURN(fInfo.chunk.size() > 0, 0);

#if 0
if (! info.chunk.isEmpty())
{
*dataPtr = info.chunk.data();
return info.chunk.size();
}
#endif

return 0;
*dataPtr = fInfo.chunk.data();
return fInfo.chunk.size();
}

// -------------------------------------------------------------------
@@ -588,32 +589,29 @@ public:

CarlaPlugin::setCustomData(type, key, value, sendGui);
}
#endif

void setChunkData(const char* const stringData) override
{
CARLA_ASSERT(m_hints & PLUGIN_USES_CHUNKS);
CARLA_ASSERT(stringData);
CARLA_SAFE_ASSERT_RETURN(pData->options & PLUGIN_OPTION_USE_CHUNKS,);
CARLA_SAFE_ASSERT_RETURN(stringData != nullptr,);

QString filePath;
filePath = QDir::tempPath();
filePath += "/.CarlaChunk_";
filePath += m_name;
String filePath(File::getSpecialLocation(File::tempDirectory).getFullPathName());

filePath = QDir::toNativeSeparators(filePath);
filePath += OS_SEP_STR;
filePath += ".CarlaChunk_";
filePath += fShmAudioPool.filename.buffer() + 18;

QFile file(filePath);

if (file.open(QIODevice::WriteOnly | QIODevice::Text))
if (File(filePath).replaceWithText(stringData))
{
QTextStream out(&file);
out << stringData;
file.close();
osc_send_configure(&osc.data, CARLA_BRIDGE_MSG_SET_CHUNK, filePath.toUtf8().constData());
}
const CarlaMutexLocker _cml(fShmControl.lock);

pData->updateParameterValues(this, pData->engine->isOscControlRegistered(), true, false);
fShmControl.writeOpcode(kPluginBridgeOpcodeSetChunkFile);
fShmControl.writeInt(filePath.length());
fShmControl.writeCustomData(filePath.toRawUTF8(), filePath.length());
fShmControl.commitWrite();
}
}
#endif

// -------------------------------------------------------------------
// Set ui stuff
@@ -1707,51 +1705,45 @@ public:

case kPluginBridgeSetChunkData: {
CARLA_BRIDGE_CHECK_OSC_TYPES(1, "s");
#if 0
const char* const chunkFileChar = (const char*)&argv[0]->s;

CARLA_ASSERT(chunkFileChar);
const char* const chunkFilePath = (const char*)&argv[0]->s;

CARLA_SAFE_ASSERT_BREAK(chunkFilePath != nullptr);

QString chunkFileStr(chunkFileChar);
String realChunkFilePath(chunkFilePath);
carla_stdout("chunk save path BEFORE => %s", realChunkFilePath.toRawUTF8());

#ifndef CARLA_OS_WIN
// Using Wine, fix temp dir
if (m_binary == BINARY_WIN32 || m_binary == BINARY_WIN64)
if (fBinaryType == BINARY_WIN32 || fBinaryType == BINARY_WIN64)
{
// Get WINEPREFIX
QString wineDir;
String wineDir;
if (const char* const WINEPREFIX = getenv("WINEPREFIX"))
wineDir = QString(WINEPREFIX);
wineDir = String(WINEPREFIX);
else
wineDir = QDir::homePath() + "/.wine";

QStringList chunkFileStrSplit1 = chunkFileStr.split(":/");
QStringList chunkFileStrSplit2 = chunkFileStrSplit1.at(1).split("\\");

QString wineDrive = chunkFileStrSplit1.at(0).toLower();
QString wineTMP = chunkFileStrSplit2.at(0);
QString baseName = chunkFileStrSplit2.at(1);

chunkFileStr = wineDir;
chunkFileStr += "/drive_";
chunkFileStr += wineDrive;
chunkFileStr += "/";
chunkFileStr += wineTMP;
chunkFileStr += "/";
chunkFileStr += baseName;
chunkFileStr = QDir::toNativeSeparators(chunkFileStr);
wineDir = File::getSpecialLocation(File::userHomeDirectory).getFullPathName() + "/.wine";

const StringArray driveLetterSplit(StringArray::fromTokens(realChunkFilePath, ":/", ""));

realChunkFilePath = wineDir;
realChunkFilePath += "/drive_";
realChunkFilePath += driveLetterSplit[0].toLowerCase();
realChunkFilePath += "/";
realChunkFilePath += driveLetterSplit[1];

realChunkFilePath = realChunkFilePath.replace("\\", "/");
carla_stdout("chunk save path AFTER => %s", realChunkFilePath.toRawUTF8());
}
#endif

QFile chunkFile(chunkFileStr);
File chunkFile(realChunkFilePath);

if (chunkFile.open(QIODevice::ReadOnly))
if (chunkFile.existsAsFile())
{
info.chunk = chunkFile.readAll();
chunkFile.close();
chunkFile.remove();
fInfo.chunk = carla_getChunkFromBase64String(chunkFile.loadFileAsString().toRawUTF8());
chunkFile.deleteFile();
}
#endif
break;
}

@@ -1994,6 +1986,18 @@ public:
return false;
}

// ---------------------------------------------------------------
// set default options

pData->options = 0x0;
pData->options |= PLUGIN_OPTION_MAP_PROGRAM_CHANGES;
pData->options |= PLUGIN_OPTION_USE_CHUNKS;
pData->options |= PLUGIN_OPTION_SEND_CONTROL_CHANGES;
pData->options |= PLUGIN_OPTION_SEND_CHANNEL_PRESSURE;
pData->options |= PLUGIN_OPTION_SEND_NOTE_AFTERTOUCH;
pData->options |= PLUGIN_OPTION_SEND_PITCHBEND;
pData->options |= PLUGIN_OPTION_SEND_ALL_SOUND_OFF;

return true;
}

@@ -2024,7 +2028,7 @@ private:
CarlaString label;
CarlaString maker;
CarlaString copyright;
//QByteArray chunk;
std::vector<uint8_t> chunk;

Info()
: aIns(0),


+ 1
- 1
source/backend/plugin/CarlaPlugin.cpp View File

@@ -261,7 +261,7 @@ const CustomData& CarlaPlugin::getCustomData(const uint32_t index) const noexcep
return pData->custom.getAt(index, kCustomDataNull);
}

int32_t CarlaPlugin::getChunkData(void** const dataPtr) const noexcept
std::size_t CarlaPlugin::getChunkData(void** const dataPtr) noexcept
{
CARLA_SAFE_ASSERT_RETURN(dataPtr != nullptr, 0);
CARLA_SAFE_ASSERT(false); // this should never happen


+ 2
- 2
source/backend/plugin/DssiPlugin.cpp View File

@@ -143,7 +143,7 @@ public:
// -------------------------------------------------------------------
// Information (current data)

int32_t getChunkData(void** const dataPtr) const noexcept override
std::size_t getChunkData(void** const dataPtr) noexcept override
{
CARLA_SAFE_ASSERT_RETURN(fUsesCustomData, 0);
CARLA_SAFE_ASSERT_RETURN(pData->options & PLUGIN_OPTION_USE_CHUNKS, 0);
@@ -162,7 +162,7 @@ public:
ret = fDssiDescriptor->get_custom_data(fHandle, dataPtr, &dataSize);
} CARLA_SAFE_EXCEPTION_RETURN("DssiPlugin::getChunkData", 0);

return (ret != 0) ? static_cast<int32_t>(dataSize) : 0;
return (ret != 0) ? dataSize : 0;
}

// -------------------------------------------------------------------


+ 47
- 11
source/backend/plugin/JucePlugin.cpp View File

@@ -21,6 +21,7 @@
#if (defined(CARLA_OS_MAC) || defined(CARLA_OS_WIN))

#include "CarlaBackendUtils.hpp"
#include "CarlaBase64Utils.hpp"
#include "JucePluginWindow.hpp"

#include "juce_audio_processors.h"
@@ -113,7 +114,27 @@ public:
// -------------------------------------------------------------------
// Information (current data)

// nothing
std::size_t getChunkData(void** const dataPtr) noexcept override
{
CARLA_SAFE_ASSERT_RETURN(pData->options & PLUGIN_OPTION_USE_CHUNKS, 0);
CARLA_SAFE_ASSERT_RETURN(fInstance != nullptr, 0);
CARLA_SAFE_ASSERT_RETURN(dataPtr != nullptr, 0);

*dataPtr = nullptr;

try {
fChunk.reset();
fInstance->getStateInformation(fChunk);
} CARLA_SAFE_EXCEPTION_RETURN("JucePlugin::getChunkData", 0);

if (const std::size_t size = fChunk.getSize())
{
*dataPtr = fChunk.getData();
return size;
}

return 0;
}

// -------------------------------------------------------------------
// Information (per-plugin data)
@@ -125,7 +146,7 @@ public:
uint options = 0x0;

options |= PLUGIN_OPTION_MAP_PROGRAM_CHANGES;
//options |= PLUGIN_OPTION_USE_CHUNKS;
options |= PLUGIN_OPTION_USE_CHUNKS;

if (fInstance->acceptsMidi())
{
@@ -227,6 +248,28 @@ public:
CarlaPlugin::setParameterValue(parameterId, fixedValue, sendGui, sendOsc, sendCallback);
}

void setChunkData(const char* const stringData) override
{
CARLA_SAFE_ASSERT_RETURN(pData->options & PLUGIN_OPTION_USE_CHUNKS,);
CARLA_SAFE_ASSERT_RETURN(fInstance != nullptr,);
CARLA_SAFE_ASSERT_RETURN(stringData != nullptr,);

std::vector<uint8_t> chunk(carla_getChunkFromBase64String(stringData));
CARLA_SAFE_ASSERT_RETURN(chunk.size() > 0,);

{
const ScopedSingleProcessLocker spl(this, true);
fInstance->setStateInformation(chunk.data(), chunk.size());
}

#ifdef BUILD_BRIDGE
const bool sendOsc(false);
#else
const bool sendOsc(pData->engine->isOscControlRegistered());
#endif
pData->updateParameterValues(this, sendOsc, true, false);
}

// -------------------------------------------------------------------
// Set ui stuff

@@ -234,10 +277,6 @@ public:
{
CARLA_SAFE_ASSERT_RETURN(fInstance != nullptr,);

#ifdef CARLA_OS_LINUX
const MessageManagerLock mmLock;
#endif

if (yesNo)
{
if (fWindow == nullptr)
@@ -1032,10 +1071,6 @@ public:
return false;
}

#ifdef CARLA_OS_LINUX
const MessageManagerLock mmLock;
#endif

// ---------------------------------------------------------------
// fix path for wine usage

@@ -1096,7 +1131,7 @@ public:
pData->options = 0x0;
pData->options |= PLUGIN_OPTION_FIXED_BUFFERS;
pData->options |= PLUGIN_OPTION_MAP_PROGRAM_CHANGES;
//pData->options |= PLUGIN_OPTION_USE_CHUNKS;
pData->options |= PLUGIN_OPTION_USE_CHUNKS;

if (fInstance->acceptsMidi())
{
@@ -1117,6 +1152,7 @@ private:
AudioSampleBuffer fAudioBuffer;
MidiBuffer fMidiBuffer;
CurrentPositionInfo fPosInfo;
MemoryBlock fChunk;

const char* fUniqueId;



+ 4
- 2
source/backend/plugin/VstPlugin.cpp View File

@@ -182,7 +182,7 @@ public:
// -------------------------------------------------------------------
// Information (current data)

int32_t getChunkData(void** const dataPtr) const noexcept override
std::size_t getChunkData(void** const dataPtr) noexcept override
{
CARLA_SAFE_ASSERT_RETURN(pData->options & PLUGIN_OPTION_USE_CHUNKS, 0);
CARLA_SAFE_ASSERT_RETURN(fEffect != nullptr, 0);
@@ -191,7 +191,9 @@ public:
*dataPtr = nullptr;

try {
return static_cast<int32_t>(dispatcher(effGetChunk, 0 /* bank */, 0, dataPtr, 0.0f));
const intptr_t ret = dispatcher(effGetChunk, 0 /* bank */, 0, dataPtr, 0.0f);
CARLA_SAFE_ASSERT_RETURN(ret >= 0, 0);
return static_cast<std::size_t>(ret);
} CARLA_SAFE_EXCEPTION_RETURN("VstPlugin::getChunkData", 0);
}



+ 0
- 34
source/bridges-plugin/CarlaBridgePlugin.cpp View File

@@ -362,40 +362,6 @@ private:
}
};

#if 0
int CarlaBridgeOsc::handleMsgPluginSetChunk(CARLA_BRIDGE_OSC_HANDLE_ARGS)
{
CARLA_BRIDGE_OSC_CHECK_OSC_TYPES(1, "s");
CARLA_SAFE_ASSERT_RETURN(fClient != nullptr, 1);
carla_debug("CarlaBridgeOsc::handleMsgPluginSetChunk()");

const char* const chunkFilePathTry = (const char*)&argv[0]->s;

CARLA_SAFE_ASSERT_RETURN(chunkFilePathTry != nullptr && chunkFilePathTry[0] != '\0', 0);

String chunkFilePath(chunkFilePathTry);

#ifdef CARLA_OS_WIN
if (chunkFilePath.startsWith("/"))
{
// running under Wine, posix host
chunkFilePath = chunkFilePath.replaceSection(0, 1, "Z:\\");
chunkFilePath = chunkFilePath.replace("/", "\\");
}
#endif

File chunkFile(chunkFilePath);
CARLA_SAFE_ASSERT_RETURN(chunkFile.existsAsFile(), 0);

String chunkData(chunkFile.loadFileAsString());
chunkFile.deleteFile();
CARLA_SAFE_ASSERT_RETURN(chunkData.isNotEmpty(), 0);

carla_set_chunk_data(0, chunkData.toRawUTF8());
return 0;
}
#endif

// -------------------------------------------------------------------------

int main(int argc, char* argv[])


+ 2
- 2
source/utils/CarlaBridgeUtils.hpp View File

@@ -60,8 +60,8 @@ enum PluginBridgeOpcode {
kPluginBridgeOpcodeSetParameterMidiCC = 7, // int, float
kPluginBridgeOpcodeSetProgram = 8, // int
kPluginBridgeOpcodeSetMidiProgram = 9, // int
kPluginBridgeOpcodeSetCustomData = 10, // str, str, str
kPluginBridgeOpcodeSetChunkFile = 11, // str
kPluginBridgeOpcodeSetCustomData = 10, // int/size, str, int/size, str, int/size, str
kPluginBridgeOpcodeSetChunkFile = 11, // int/size, str
kPluginBridgeOpcodePrepareForSave = 12,
kPluginBridgeOpcodeMidiEvent = 13, // long, int, char[] (long = timeFrame, int = size max 4)
kPluginBridgeOpcodeProcess = 14,


Loading…
Cancel
Save