From 805ce707593a1dfb928341ef876e50016cfdf764 Mon Sep 17 00:00:00 2001 From: falkTX Date: Sat, 6 Jan 2024 20:44:13 +0100 Subject: [PATCH] A small utlity to convert binary plugin state to json Signed-off-by: falkTX --- utils/state2json.cpp | 139 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 139 insertions(+) create mode 100644 utils/state2json.cpp diff --git a/utils/state2json.cpp b/utils/state2json.cpp new file mode 100644 index 00000000..c145d970 --- /dev/null +++ b/utils/state2json.cpp @@ -0,0 +1,139 @@ +#include "extra/Base64.hpp" +#include "extra/String.hpp" + +int main(int argc, char* argv[]) +{ + if (argc != 2) + { + d_stdout("usage: %s [base64-dpf-state]", argv[0]); + return 1; + } + + const std::vector data(d_getChunkFromBase64String(argv[1])); + + if (data.empty()) + { + printf("{}\n"); + return 0; + } + + String key, value; + bool firstValue = true; + bool hasValue = false; + bool fillingKey = true; // if filling key or value + char queryingType = 'i'; // can be 'n', 's' or 'p' (none, states, parameters) + + const char* const buffer = reinterpret_cast(data.data()); + + printf("{"); + + for (size_t i = 0; i < data.size(); ++i) + { + // found terminator, stop here + if (buffer[i] == '\xfe') + { + break; + } + + // append to temporary vars + if (fillingKey) + { + key += buffer + i; + } + else + { + value += buffer + i; + hasValue = true; + } + + // increase buffer offset by length of string + i += std::strlen(buffer + i); + + // if buffer offset points to null, we found the end of a string, lets check + if (buffer[i] == '\0') + { + // special keys + if (key == "__dpf_state_begin__") + { + DISTRHO_SAFE_ASSERT_INT_RETURN(queryingType == 'i' || queryingType == 'n', queryingType, 1); + if (queryingType == 'n') + printf(","); + printf("\n \"states\": {"); + queryingType = 's'; + key.clear(); + value.clear(); + firstValue = true; + hasValue = false; + continue; + } + if (key == "__dpf_state_end__") + { + DISTRHO_SAFE_ASSERT_INT_RETURN(queryingType == 's', queryingType, 1); + printf("\n }"); + queryingType = 'n'; + key.clear(); + value.clear(); + hasValue = false; + continue; + } + if (key == "__dpf_parameters_begin__") + { + DISTRHO_SAFE_ASSERT_INT_RETURN(queryingType == 'i' || queryingType == 'n', queryingType, 1); + if (queryingType == 'n') + printf(","); + printf("\n \"parameters\": {"); + queryingType = 'p'; + key.clear(); + value.clear(); + firstValue = true; + hasValue = false; + continue; + } + if (key == "__dpf_parameters_end__") + { + DISTRHO_SAFE_ASSERT_INT_RETURN(queryingType == 'p', queryingType, 1); + printf("\n }"); + queryingType = 'x'; + key.clear(); + value.clear(); + hasValue = false; + continue; + } + + // no special key, swap between reading real key and value + fillingKey = !fillingKey; + + // if there is no value yet keep reading until we have one + if (! hasValue) + continue; + + if (key == "__dpf_program__") + { + DISTRHO_SAFE_ASSERT_INT_RETURN(queryingType == 'i', queryingType, 1); + queryingType = 'n'; + + printf("\n \"program\": %s", value.buffer()); + } + else if (queryingType == 's') + { + if (! firstValue) + printf(","); + // TODO safely encode value as json compatible string + printf("\n \"%s\": %s", key.buffer(), value.buffer()); + } + else if (queryingType == 'p') + { + if (! firstValue) + printf(","); + printf("\n \"%s\": %s", key.buffer(), value.buffer()); + } + + key.clear(); + value.clear(); + firstValue = hasValue = false; + } + } + + printf("\n}\n"); + return 0; +}