diff options
| author | Josh Ferrell <josh@vector35.com> | 2024-01-24 16:37:50 -0500 |
|---|---|---|
| committer | Josh Ferrell <josh@vector35.com> | 2024-02-02 15:40:49 -0500 |
| commit | 1e0b3ca09efa1739e2f00181c7ab2435ca5eae7a (patch) | |
| tree | 039e12a90e05b72b32ae908acf504bc4c8a3fe2a /dmonwrapper.cpp | |
| parent | 668f9cb0e0ea45c6d2cdc802dbe99b12f5623fff (diff) | |
Add dmon
Diffstat (limited to 'dmonwrapper.cpp')
| -rw-r--r-- | dmonwrapper.cpp | 101 |
1 files changed, 101 insertions, 0 deletions
diff --git a/dmonwrapper.cpp b/dmonwrapper.cpp new file mode 100644 index 00000000..6e1b14ea --- /dev/null +++ b/dmonwrapper.cpp @@ -0,0 +1,101 @@ +#include "binaryninjaapi.h" +#define DMON_IMPL + +#include "dmonwrapper.h" + + +bool DMonWrapper::DMON_INITIALIZED = false; +std::mutex DMonWrapper::DMON_MUTEX; + + +DMonWrapper::DMonWrapper() +{ + std::unique_lock<std::mutex> lock(DMON_MUTEX); + + if (!DMON_INITIALIZED) + { + dmon_init(); + DMON_INITIALIZED = true; + } +} + + +DMonWrapper::~DMonWrapper() +{ + std::unique_lock<std::mutex> lock(DMON_MUTEX); + + if (DMON_INITIALIZED) + { + for (const auto& i : m_callbacks) + { + dmon_watch_id id; + id.id = i.first; + + dmon_unwatch(id); + free(i.second); + } + m_callbacks.clear(); + } +} + + +dmon_watch_id DMonWrapper::Watch(const std::filesystem::path& path, CallbackFunction callback, bool recursive) +{ + std::unique_lock<std::mutex> lock(DMON_MUTEX); + + auto flags = recursive ? DMON_WATCHFLAGS_RECURSIVE : 0; + + CallbackContext* ctxt = new CallbackContext(); + ctxt->callback = callback; + + dmon_watch_id dmonId = dmon_watch(path.string().c_str(), [](dmon_watch_id watch_id, dmon_action action, const char* rootdir, const char* filepath, const char* oldfilepath, void* userData) { + CallbackContext* ctxt = reinterpret_cast<CallbackContext*>(userData); + BinaryNinja::ExecuteOnMainThreadAndWait([ctxt, action, rootdir, filepath, oldfilepath](){ + if (ctxt->callback) + ctxt->callback(action, rootdir, filepath, oldfilepath == NULL ? "" : oldfilepath); + }); + }, flags, (void*)ctxt); + + if (dmonId.id == 0) + { + BinaryNinja::LogError("Failed to watch path %s", path.string().c_str()); + free(ctxt); + return dmonId; + } + + m_callbacks[dmonId.id] = ctxt; + + return dmonId; +} + + +std::vector<dmon_watch_id> DMonWrapper::GetWatchIds() +{ + std::unique_lock<std::mutex> lock(DMON_MUTEX); + + std::vector<dmon_watch_id> out; + out.reserve(m_callbacks.size()); + + for (const auto& i : m_callbacks) + { + dmon_watch_id id; + id.id = i.first; + out.push_back(id); + } + + return out; +} + + +void DMonWrapper::Unwatch(dmon_watch_id watchId) +{ + std::unique_lock<std::mutex> lock(DMON_MUTEX); + + auto itr = m_callbacks.find(watchId.id); + if (itr != m_callbacks.end()) + { + dmon_unwatch(watchId); + free(itr->second); + m_callbacks.erase(itr); + } +} |
