first commit
This commit is contained in:
commit
2dc9475ef7
6
Makefile
Normal file
6
Makefile
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
HDRS := $(wildcard *.hpp)
|
||||||
|
PREFIX ?= /usr/local/include
|
||||||
|
|
||||||
|
install: $(HDRS)
|
||||||
|
mkdir -p $(PREFIX)/sc
|
||||||
|
install -c -m 0666 $(HDRS) $(PREFIX)/sc
|
44
functools.hpp
Normal file
44
functools.hpp
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
//
|
||||||
|
// functools.hpp
|
||||||
|
// libcommon
|
||||||
|
//
|
||||||
|
// Created by Bob Polis at 2019-10-19
|
||||||
|
// Copyright (c) 2019 SwiftCoder. All rights reserved.
|
||||||
|
//
|
||||||
|
|
||||||
|
#ifndef _functools_H_
|
||||||
|
#define _functools_H_
|
||||||
|
|
||||||
|
#include <vector>
|
||||||
|
#include <functional>
|
||||||
|
#include <algorithm>
|
||||||
|
#include <iterator>
|
||||||
|
|
||||||
|
namespace sc {
|
||||||
|
|
||||||
|
template<class T, class M>
|
||||||
|
std::vector<M> map(const std::vector<T>& seq, std::function<M(T)> fun) {
|
||||||
|
std::vector<M> result;
|
||||||
|
std::transform(seq.begin(), seq.end(), back_inserter(result), fun);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class T>
|
||||||
|
std::vector<T> filter(const std::vector<T>& seq, std::function<bool(T)> fun) {
|
||||||
|
std::vector<T> result;
|
||||||
|
std::copy_if(seq.begin(), seq.end(), back_inserter(result), fun);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class T, class R>
|
||||||
|
R reduce(const std::vector<T>& seq, R seed, std::function<R(T, R)> fun) {
|
||||||
|
R result {seed};
|
||||||
|
for (const auto& elem : seq) {
|
||||||
|
result = fun(elem, result);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif // _functools_H_
|
29
integer_locale.hpp
Normal file
29
integer_locale.hpp
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
//
|
||||||
|
// integer_locale.h
|
||||||
|
// locales
|
||||||
|
//
|
||||||
|
// Created by Thalictrum on 13-05-2012.
|
||||||
|
// Copyright (c) 2012 __MyCompanyName__. All rights reserved.
|
||||||
|
//
|
||||||
|
|
||||||
|
#ifndef locales_integer_locale_h
|
||||||
|
#define locales_integer_locale_h
|
||||||
|
|
||||||
|
namespace sc {
|
||||||
|
|
||||||
|
class integer_locale : public std::numpunct<char> {
|
||||||
|
public:
|
||||||
|
typedef char char_type;
|
||||||
|
typedef std::string string_type;
|
||||||
|
|
||||||
|
explicit integer_locale(size_t r = 0) : std::numpunct<char>(r) {}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
char do_decimal_point() const { return ','; }
|
||||||
|
char do_thousands_sep() const { return '.'; }
|
||||||
|
std::string do_grouping() const { return "\003"; }
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
128
plugin.hpp
Normal file
128
plugin.hpp
Normal file
@ -0,0 +1,128 @@
|
|||||||
|
//
|
||||||
|
// plugin.hpp
|
||||||
|
// plugins
|
||||||
|
//
|
||||||
|
// Created by Bob Polis at 2019-06-09
|
||||||
|
// Copyright (c) 2019 SwiftCoder. All rights reserved.
|
||||||
|
//
|
||||||
|
|
||||||
|
#ifndef _plugin_H_
|
||||||
|
#define _plugin_H_
|
||||||
|
|
||||||
|
#include <memory>
|
||||||
|
#include <string>
|
||||||
|
#include <map>
|
||||||
|
#include <functional>
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
#include <dlfcn.h>
|
||||||
|
#include <dirent.h>
|
||||||
|
|
||||||
|
namespace sc {
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
class plugin {
|
||||||
|
public:
|
||||||
|
static void scan_plugins(const std::string& dir, const std::string& ext) {
|
||||||
|
DIR* plugins_dir = ::opendir(dir.c_str());
|
||||||
|
throw_if_null_msg(plugins_dir, (dir + " could not be opened").c_str());
|
||||||
|
struct dirent* info;
|
||||||
|
while ((info = ::readdir(plugins_dir)) != nullptr) {
|
||||||
|
if (info->d_name[0] != '.') {
|
||||||
|
std::string plugname {info->d_name};
|
||||||
|
std::string::size_type lastdot = plugname.rfind(".");
|
||||||
|
if (plugname.substr(lastdot + 1) == ext) {
|
||||||
|
|
||||||
|
}
|
||||||
|
plugin plugin {dir + '/' + plugname};
|
||||||
|
plugins.emplace(plugname.substr(0, lastdot), std::move(plugin));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
throw_if_min1(::closedir(plugins_dir));
|
||||||
|
}
|
||||||
|
|
||||||
|
using processor = std::function<void(const plugin&)>;
|
||||||
|
static void foreach(processor proc) {
|
||||||
|
for (const auto& elem : plugins) {
|
||||||
|
proc(elem.second);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static plugin& get(const std::string& name) {
|
||||||
|
return plugins.at(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
static std::vector<std::string> names() {
|
||||||
|
std::vector<std::string> result;
|
||||||
|
for (const auto& elem : plugins) {
|
||||||
|
result.emplace_back(elem.first);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
plugin(const std::string& path) : _path {path} {
|
||||||
|
_plugin = ::dlopen(path.c_str(), RTLD_LAZY);
|
||||||
|
std::cerr << path << (_plugin ? "" : " not") << " opened\n";
|
||||||
|
const char* err {::dlerror()};
|
||||||
|
if (err) std::cerr << err << '\n';
|
||||||
|
if (_plugin) {
|
||||||
|
_factory = reinterpret_cast<factory>(::dlsym(_plugin, "create_instance"));
|
||||||
|
if (!_factory) {
|
||||||
|
std::cerr << "create_instance() function not found in " << path << '\n';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
~plugin() {
|
||||||
|
if (_plugin) {
|
||||||
|
::dlclose(_plugin);
|
||||||
|
_plugin = nullptr;
|
||||||
|
std::cerr << _path << " closed\n";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
plugin(const plugin&) = delete;
|
||||||
|
plugin& operator=(const plugin&) = delete;
|
||||||
|
|
||||||
|
plugin(plugin&& other) {
|
||||||
|
_path = other._path;
|
||||||
|
_plugin = other._plugin;
|
||||||
|
_factory = other._factory;
|
||||||
|
other._plugin = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
plugin& operator=(plugin&& other) {
|
||||||
|
if (this != &other) {
|
||||||
|
_path = other._path;
|
||||||
|
_plugin = other._plugin;
|
||||||
|
_factory = other._factory;
|
||||||
|
other._plugin = nullptr;
|
||||||
|
}
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string path() const { return _path; }
|
||||||
|
|
||||||
|
std::unique_ptr<T> operator()() const {
|
||||||
|
std::unique_ptr<T> obj;
|
||||||
|
if (_factory) {
|
||||||
|
obj.reset(_factory());
|
||||||
|
}
|
||||||
|
return obj;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
static std::map<std::string, plugin<T>> plugins;
|
||||||
|
|
||||||
|
std::string _path;
|
||||||
|
void* _plugin {nullptr};
|
||||||
|
using factory = T*(*)();
|
||||||
|
factory _factory {nullptr};
|
||||||
|
};
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
std::map<std::string, plugin<T>> plugin<T>::plugins;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif // _plugin_H_
|
44
sync_queue.hpp
Normal file
44
sync_queue.hpp
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
//
|
||||||
|
// Sync_queue.h
|
||||||
|
// adapted from an example from Bjarne Stroustrup
|
||||||
|
//
|
||||||
|
|
||||||
|
#ifndef __Sync_queue__
|
||||||
|
#define __Sync_queue__
|
||||||
|
|
||||||
|
#include <mutex>
|
||||||
|
#include <condition_variable>
|
||||||
|
#include <list>
|
||||||
|
#include <future>
|
||||||
|
#include <thread>
|
||||||
|
|
||||||
|
namespace sc {
|
||||||
|
|
||||||
|
template<typename T>
|
||||||
|
class Sync_queue {
|
||||||
|
public:
|
||||||
|
void put(const T& val)
|
||||||
|
{
|
||||||
|
std::lock_guard<std::mutex> lck {mtx};
|
||||||
|
q.push_back(val);
|
||||||
|
cond.notify_one();
|
||||||
|
}
|
||||||
|
|
||||||
|
T get()
|
||||||
|
{
|
||||||
|
std::unique_lock<std::mutex> lck {mtx};
|
||||||
|
cond.wait(lck, [this]{ return !q.empty(); });
|
||||||
|
T val {q.front()};
|
||||||
|
q.pop_front();
|
||||||
|
return val;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
std::mutex mtx;
|
||||||
|
std::condition_variable cond;
|
||||||
|
std::list<T> q;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif /* defined(__Sync_queue__) */
|
Loading…
x
Reference in New Issue
Block a user