From 149ee87dca5797738ce3d07b782a84840ea680dc Mon Sep 17 00:00:00 2001 From: casey langen Date: Sun, 26 Jan 2020 15:34:26 -0800 Subject: [PATCH] Untested environment initialization. --- src/core_c/CMakeLists.txt | 7 +- src/core_c/context.cpp | 195 +++++++++++++++++++++++++++++++++----- src/core_c/musikcore_c.h | 9 +- 3 files changed, 185 insertions(+), 26 deletions(-) diff --git a/src/core_c/CMakeLists.txt b/src/core_c/CMakeLists.txt index eb754a287..e5e073840 100644 --- a/src/core_c/CMakeLists.txt +++ b/src/core_c/CMakeLists.txt @@ -13,4 +13,9 @@ add_library(musikcore_c SHARED ${CORE_C_SOURCES}) set_target_properties(musikcore_c PROPERTIES LIBRARY_OUTPUT_DIRECTORY ${musikcube_SOURCE_DIR}/bin) -target_link_libraries(musikcore_c ${musikcube_LINK_LIBS}) +if (${LINK_STATICALLY} MATCHES "true") + find_library(EVLIB NAMES libev.a ev) + target_link_libraries(musikcore_c ${musikcube_LINK_LIBS} ${EVLIB}) +else() + target_link_libraries(musikcore_c ${musikcube_LINK_LIBS} ev) +endif() diff --git a/src/core_c/context.cpp b/src/core_c/context.cpp index 53caa9180..62a61954a 100644 --- a/src/core_c/context.cpp +++ b/src/core_c/context.cpp @@ -34,32 +34,181 @@ #include "musikcore_c.h" -// #include -// #include -// #include -// #include -// #include -// #include -// #include -// #include -// #include +#include +#include -// using namespace musik::core::sdk; +#include +#include +#include +#include +#include +#include +#include -// #define R(x) reinterpret_cast(x) -// #define V(x) reinterpret_cast(x) -// #define M(x) reinterpret_cast(x) -// #define VL(x) reinterpret_cast(x) -// #define ML(x) reinterpret_cast(x) -// #define TRACK(x) reinterpret_cast(x) -// #define TRACKLIST(x) reinterpret_cast(x) -// #define TRACKLISTEDITOR(x) reinterpret_cast(x) -// #define METADATA(x) reinterpret_cast(x) +#include +#include +#include -mcsdk_export bool mcsdk_context_init(mcsdk_context* context) { - return false; +using namespace musik; +using namespace musik::core; +using namespace musik::core::db::local; +using namespace musik::core::audio; +using namespace musik::core::sdk; +using namespace musik::core::runtime; + +/* + * + * ev_message_queue + * + */ + +static const short EVENT_DISPATCH = 1; +static const short EVENT_QUIT = 2; + +class ev_message_queue: public MessageQueue { + public: + ev_message_queue(): MessageQueue() { + if (pipe(pipeFd) != 0) { + std::cerr << "\n ERROR! couldn't create pipe\n\n"; + exit(EXIT_FAILURE); + } + } + + virtual ~ev_message_queue() { + if (pipeFd[0]) { + close(pipeFd[0]); + } + if (pipeFd[1]) { + close(pipeFd[1]); + } + } + + void Post(IMessagePtr message, int64_t delayMs) { + MessageQueue::Post(message, delayMs); + + if (delayMs <= 0) { + write(pipeFd[1], &EVENT_DISPATCH, sizeof(EVENT_DISPATCH)); + } + else { + double delayTs = (double) delayMs / 1000.0; + loop.once< + ev_message_queue, + &ev_message_queue::DelayedDispatch + >(-1, ev::TIMER, (ev::tstamp) delayTs, this); + } + } + + void DelayedDispatch(int revents) { + this->Dispatch(); + } + + void SignalQuit() { + write(pipeFd[1], &EVENT_QUIT, sizeof(EVENT_QUIT)); + } + + void ReadCallback(ev::io& watcher, int revents) { + short type; + if (read(pipeFd[0], &type, sizeof(type)) == 0) { + std::cerr << "read() failed.\n"; + exit(EXIT_FAILURE); + } + switch (type) { + case EVENT_DISPATCH: this->Dispatch(); break; + case EVENT_QUIT: loop.break_loop(ev::ALL); break; + } + } + + void Run() { + io.set(loop); + io.set(pipeFd[0], ev::READ); + io.set(this); + io.start(); + + sio.set(loop); + + write(pipeFd[1], &EVENT_DISPATCH, sizeof(EVENT_DISPATCH)); + + loop.run(0); + } + + private: + int pipeFd[2]; + ev::dynamic_loop loop; + ev::io io; + ev::sig sio; +}; + +/* + * + * instance context + * + */ + +struct mcsdk_context_internal { + ev_message_queue message_queue; + std::thread thread; + ILibraryPtr library; + LocalMetadataProxy* metadata; + PlaybackService* playback; + std::shared_ptr preferences; +}; + +static mcsdk_context* plugin_context = nullptr; + +mcsdk_export void mcsdk_context_init(mcsdk_context** context) { + std::locale locale = std::locale(); + std::locale utf8Locale(locale, new boost::filesystem::detail::utf8_codecvt_facet); + boost::filesystem::path::imbue(utf8Locale); + auto c = new mcsdk_context(); + memset(c, 0, sizeof(mcsdk_context)); + auto internal = new mcsdk_context_internal(); + internal->library = LibraryFactory::Default(); + internal->library->SetMessageQueue(internal->message_queue); + internal->playback = new PlaybackService(internal->message_queue, internal->library); + internal->metadata = new LocalMetadataProxy(internal->library); + internal->preferences = Preferences::ForComponent(prefs::components::Settings); + c->internal = internal; + c->metadata = (mcsdk_svc_metadata) internal->metadata; + c->preferences = (mcsdk_preferences) internal->preferences.get(); + internal->thread = std::thread([internal] { + internal->message_queue.Run(); + }); + if (!plugin_context) { + mcsdk_set_plugin_context(c); + } + *context = c; } -mcsdk_export bool mcsdk_context_release(mcsdk_context* context) { - return false; +mcsdk_export void mcsdk_context_release(mcsdk_context** context) { + auto c = *context; + auto internal = static_cast(c->internal); + delete internal->playback; + internal->playback = nullptr; + internal->library->Indexer()->Stop(); + internal->message_queue.SignalQuit(); + internal->thread.join(); + internal->library.reset(); + internal->preferences.reset(); + delete internal->metadata; + delete internal; + delete c; + if (plugin_context == c) { + mcsdk_set_plugin_context(nullptr); + } + *context = 0; } + +mcsdk_export void mcsdk_set_plugin_context(mcsdk_context* context) { + if (plugin_context && plugin_context != context) { + plugin::Deinit(); + } + plugin_context = context; + if (plugin_context) { + auto internal = static_cast(context->internal); + plugin::Init(&internal->message_queue, internal->playback, internal->library); + } +} + +mcsdk_export bool mcsdk_is_plugin_context(mcsdk_context* context) { + return context && context == plugin_context; +} \ No newline at end of file diff --git a/src/core_c/musikcore_c.h b/src/core_c/musikcore_c.h index bef59917e..1f006c385 100644 --- a/src/core_c/musikcore_c.h +++ b/src/core_c/musikcore_c.h @@ -188,6 +188,7 @@ mcsdk_export typedef mcsdk_handle mcsdk_track_list; mcsdk_export typedef mcsdk_handle mcsdk_track_list_editor; mcsdk_export typedef mcsdk_handle mcsdk_svc_metadata; mcsdk_export typedef mcsdk_handle mcsdk_svc_playback; +mcsdk_export typedef mcsdk_handle mcsdk_preferences; /* * @@ -198,10 +199,14 @@ mcsdk_export typedef mcsdk_handle mcsdk_svc_playback; struct mcsdk_context { mcsdk_svc_metadata metadata; mcsdk_svc_playback playback; + mcsdk_preferences preferences; + mcsdk_handle internal; }; -mcsdk_export bool mcsdk_context_init(mcsdk_context* context); -mcsdk_export bool mcsdk_context_release(mcsdk_context* context); +mcsdk_export void mcsdk_context_init(mcsdk_context** context); +mcsdk_export void mcsdk_context_release(mcsdk_context** context); +mcsdk_export void mcsdk_set_plugin_context(mcsdk_context* context); +mcsdk_export bool mcsdk_is_plugin_context(mcsdk_context* context); /* *