diff options
Diffstat (limited to 'louloulibs/utils')
-rw-r--r-- | louloulibs/utils/encoding.cpp | 253 | ||||
-rw-r--r-- | louloulibs/utils/encoding.hpp | 43 | ||||
-rw-r--r-- | louloulibs/utils/get_first_non_empty.cpp | 11 | ||||
-rw-r--r-- | louloulibs/utils/get_first_non_empty.hpp | 20 | ||||
-rw-r--r-- | louloulibs/utils/revstr.cpp | 9 | ||||
-rw-r--r-- | louloulibs/utils/revstr.hpp | 11 | ||||
-rw-r--r-- | louloulibs/utils/scopeguard.hpp | 96 | ||||
-rw-r--r-- | louloulibs/utils/sha1.cpp | 121 | ||||
-rw-r--r-- | louloulibs/utils/sha1.hpp | 33 | ||||
-rw-r--r-- | louloulibs/utils/split.cpp | 19 | ||||
-rw-r--r-- | louloulibs/utils/split.hpp | 12 | ||||
-rw-r--r-- | louloulibs/utils/string.cpp | 28 | ||||
-rw-r--r-- | louloulibs/utils/string.hpp | 10 | ||||
-rw-r--r-- | louloulibs/utils/time.cpp | 70 | ||||
-rw-r--r-- | louloulibs/utils/time.hpp | 10 | ||||
-rw-r--r-- | louloulibs/utils/timed_events.cpp | 49 | ||||
-rw-r--r-- | louloulibs/utils/timed_events.hpp | 132 | ||||
-rw-r--r-- | louloulibs/utils/timed_events_manager.cpp | 73 | ||||
-rw-r--r-- | louloulibs/utils/tolower.cpp | 13 | ||||
-rw-r--r-- | louloulibs/utils/tolower.hpp | 11 | ||||
-rw-r--r-- | louloulibs/utils/xdg.cpp | 29 | ||||
-rw-r--r-- | louloulibs/utils/xdg.hpp | 14 |
22 files changed, 0 insertions, 1067 deletions
diff --git a/louloulibs/utils/encoding.cpp b/louloulibs/utils/encoding.cpp deleted file mode 100644 index 60f2212..0000000 --- a/louloulibs/utils/encoding.cpp +++ /dev/null @@ -1,253 +0,0 @@ -#include <utils/encoding.hpp> - -#include <utils/scopeguard.hpp> - -#include <stdexcept> - -#include <assert.h> -#include <string.h> -#include <iconv.h> - -#include <map> -#include <bitset> - -/** - * The UTF-8-encoded character used as a place holder when a character conversion fails. - * This is U+FFFD � "replacement character" - */ -static const char* invalid_char = "\xef\xbf\xbd"; -static const size_t invalid_char_len = 3; - -namespace utils -{ - /** - * Based on http://en.wikipedia.org/wiki/UTF-8#Description - */ - std::size_t get_next_codepoint_size(const unsigned char c) - { - if ((c & 0b11111000) == 0b11110000) // 4 bytes: 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx - return 4; - else if ((c & 0b11110000) == 0b11100000) // 3 bytes: 1110xxx 10xxxxxx 10xxxxxx - return 3; - else if ((c & 0b11100000) == 0b11000000) // 2 bytes: 110xxxxx 10xxxxxx - return 2; - return 1; // 1 byte: 0xxxxxxx - } - - bool is_valid_utf8(const char* s) - { - if (!s) - return false; - - const unsigned char* str = reinterpret_cast<const unsigned char*>(s); - - while (*str) - { - const auto codepoint_size = get_next_codepoint_size(str[0]); - if (codepoint_size == 4) - { - if (!str[1] || !str[2] || !str[3] - || ((str[1] & 0b11000000) != 0b10000000) - || ((str[2] & 0b11000000) != 0b10000000) - || ((str[3] & 0b11000000) != 0b10000000)) - return false; - } - else if (codepoint_size == 3) - { - if (!str[1] || !str[2] - || ((str[1] & 0b11000000) != 0b10000000) - || ((str[2] & 0b11000000) != 0b10000000)) - return false; - } - else if (codepoint_size == 2) - { - if (!str[1] || - ((str[1] & 0b11000000) != 0b10000000)) - return false; - } - else if ((str[0] & 0b10000000) != 0) - return false; - str += codepoint_size; - } - return true; - } - - std::string remove_invalid_xml_chars(const std::string& original) - { - // The given string MUST be a valid utf-8 string - std::vector<char> res(original.size(), '\0'); - - // pointer where we write valid chars - char* r = res.data(); - - const char* str = original.c_str(); - std::bitset<20> codepoint; - - while (*str) - { - // 4 bytes: 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx - if ((str[0] & 0b11111000) == 0b11110000) - { - codepoint = ((str[0] & 0b00000111) << 18); - codepoint |= ((str[1] & 0b00111111) << 12); - codepoint |= ((str[2] & 0b00111111) << 6 ); - codepoint |= ((str[3] & 0b00111111) << 0 ); - if (codepoint.to_ulong() <= 0x10FFFF) - { - ::memcpy(r, str, 4); - r += 4; - } - str += 4; - } - // 3 bytes: 1110xxx 10xxxxxx 10xxxxxx - else if ((str[0] & 0b11110000) == 0b11100000) - { - codepoint = ((str[0] & 0b00001111) << 12); - codepoint |= ((str[1] & 0b00111111) << 6); - codepoint |= ((str[2] & 0b00111111) << 0 ); - if (codepoint.to_ulong() <= 0xD7FF || - (codepoint.to_ulong() >= 0xE000 && codepoint.to_ulong() <= 0xFFFD)) - { - ::memcpy(r, str, 3); - r += 3; - } - str += 3; - } - // 2 bytes: 110xxxxx 10xxxxxx - else if (((str[0]) & 0b11100000) == 0b11000000) - { - // All 2 bytes char are valid, don't even bother calculating - // the codepoint - ::memcpy(r, str, 2); - r += 2; - str += 2; - } - // 1 byte: 0xxxxxxx - else if ((str[0] & 0b10000000) == 0) - { - codepoint = ((str[0] & 0b01111111)); - if (codepoint.to_ulong() == 0x09 || - codepoint.to_ulong() == 0x0A || - codepoint.to_ulong() == 0x0D || - codepoint.to_ulong() >= 0x20) - { - ::memcpy(r, str, 1); - r += 1; - } - str += 1; - } - else - throw std::runtime_error("Invalid UTF-8 passed to remove_invalid_xml_chars"); - } - return {res.data(), static_cast<size_t>(r - res.data())}; - } - - std::string convert_to_utf8(const std::string& str, const char* charset) - { - std::string res; - - const iconv_t cd = iconv_open("UTF-8", charset); - if (cd == (iconv_t)-1) - throw std::runtime_error("Cannot convert into UTF-8"); - - // Make sure cd is always closed when we leave this function - const auto sg = utils::make_scope_guard([&cd](auto&&){ iconv_close(cd); }); - - size_t inbytesleft = str.size(); - - // iconv will not attempt to modify this buffer, but some plateform - // require a char** anyway -#ifdef ICONV_SECOND_ARGUMENT_IS_CONST - const char* inbuf_ptr = str.c_str(); -#else - char* inbuf_ptr = const_cast<char*>(str.c_str()); -#endif - - size_t outbytesleft = str.size() * 4; - char* outbuf = new char[outbytesleft]; - char* outbuf_ptr = outbuf; - - // Make sure outbuf is always deleted when we leave this function - const auto sg2 = utils::make_scope_guard([outbuf](auto&&){ delete[] outbuf; }); - - bool done = false; - while (done == false) - { - size_t error = iconv(cd, &inbuf_ptr, &inbytesleft, &outbuf_ptr, &outbytesleft); - if ((size_t)-1 == error) - { - switch (errno) - { - case EILSEQ: - // Invalid byte found. Insert a placeholder instead of the - // converted character, jump one byte and continue - memcpy(outbuf_ptr, invalid_char, invalid_char_len); - outbuf_ptr += invalid_char_len; - inbytesleft--; - inbuf_ptr++; - break; - case EINVAL: - // A multibyte sequence is not terminated, but we can't - // provide any more data, so we just add a placeholder to - // indicate that the character is not properly converted, - // and we stop the conversion - memcpy(outbuf_ptr, invalid_char, invalid_char_len); - outbuf_ptr += invalid_char_len; - outbuf_ptr++; - done = true; - break; - case E2BIG: // This should never happen - default: // This should happen even neverer - done = true; - break; - } - } - else - { - // The conversion finished without any error, stop converting - done = true; - } - } - // Terminate the converted buffer, and copy that buffer it into the - // string we return - *outbuf_ptr = '\0'; - res = outbuf; - return res; - } - -} - -namespace xep0106 -{ - static const std::map<const char, const std::string> encode_map = { - {' ', "\\20"}, - {'"', "\\22"}, - {'&', "\\26"}, - {'\'',"\\27"}, - {'/', "\\2f"}, - {':', "\\3a"}, - {'<', "\\3c"}, - {'>', "\\3e"}, - {'@', "\\40"}, - }; - - void decode(std::string& s) - { - std::string::size_type pos; - for (const auto& pair: encode_map) - while ((pos = s.find(pair.second)) != std::string::npos) - s.replace(pos, pair.second.size(), - 1, pair.first); - } - - void encode(std::string& s) - { - std::string::size_type pos; - while ((pos = s.find_first_of(" \"&'/:<>@")) != std::string::npos) - { - auto it = encode_map.find(s[pos]); - assert(it != encode_map.end()); - s.replace(pos, 1, it->second); - } - } -} diff --git a/louloulibs/utils/encoding.hpp b/louloulibs/utils/encoding.hpp deleted file mode 100644 index 586edd8..0000000 --- a/louloulibs/utils/encoding.hpp +++ /dev/null @@ -1,43 +0,0 @@ -#pragma once - - -#include <string> - -namespace utils -{ - /** - * Return the size, in bytes, of the next UTF-8 codepoint, based on - * the given char. - */ - std::size_t get_next_codepoint_size(const unsigned char c); - /** - * Returns true if the given null-terminated string is valid utf-8. - * - * Based on http://en.wikipedia.org/wiki/UTF-8#Description - */ - bool is_valid_utf8(const char* s); - /** - * Remove all invalid codepoints from the given utf-8-encoded string. - * The value returned is a copy of the string, without the removed chars. - * - * See http://www.w3.org/TR/xml/#charsets for the list of valid characters - * in XML. - */ - std::string remove_invalid_xml_chars(const std::string& original); - /** - * Convert the given string (encoded is "encoding") into valid utf-8. - * If some decoding fails, insert an utf-8 placeholder character instead. - */ - std::string convert_to_utf8(const std::string& str, const char* encoding); -} - -namespace xep0106 -{ - /** - * Decode and encode inplace. - */ - void decode(std::string&); - void encode(std::string&); -} - - diff --git a/louloulibs/utils/get_first_non_empty.cpp b/louloulibs/utils/get_first_non_empty.cpp deleted file mode 100644 index 5b3bedb..0000000 --- a/louloulibs/utils/get_first_non_empty.cpp +++ /dev/null @@ -1,11 +0,0 @@ -#include <utils/get_first_non_empty.hpp> - -bool is_empty(const std::string& val) -{ - return val.empty(); -} - -bool is_empty(const int& val) -{ - return val == 0; -} diff --git a/louloulibs/utils/get_first_non_empty.hpp b/louloulibs/utils/get_first_non_empty.hpp deleted file mode 100644 index a38f5fb..0000000 --- a/louloulibs/utils/get_first_non_empty.hpp +++ /dev/null @@ -1,20 +0,0 @@ -#pragma once - -#include <string> - -bool is_empty(const std::string& val); -bool is_empty(const int& val); - -template <typename T> -T get_first_non_empty(T&& last) -{ - return last; -} - -template <typename T, typename... Args> -T get_first_non_empty(T&& first, Args&&... args) -{ - if (!is_empty(first)) - return first; - return get_first_non_empty(std::forward<Args>(args)...); -} diff --git a/louloulibs/utils/revstr.cpp b/louloulibs/utils/revstr.cpp deleted file mode 100644 index 87fd801..0000000 --- a/louloulibs/utils/revstr.cpp +++ /dev/null @@ -1,9 +0,0 @@ -#include <utils/revstr.hpp> - -namespace utils -{ - std::string revstr(const std::string& original) - { - return {original.rbegin(), original.rend()}; - } -} diff --git a/louloulibs/utils/revstr.hpp b/louloulibs/utils/revstr.hpp deleted file mode 100644 index 8e521ea..0000000 --- a/louloulibs/utils/revstr.hpp +++ /dev/null @@ -1,11 +0,0 @@ -#pragma once - - -#include <string> - -namespace utils -{ - std::string revstr(const std::string& original); -} - - diff --git a/louloulibs/utils/scopeguard.hpp b/louloulibs/utils/scopeguard.hpp deleted file mode 100644 index cd0e89e..0000000 --- a/louloulibs/utils/scopeguard.hpp +++ /dev/null @@ -1,96 +0,0 @@ -#pragma once - -#include <functional> -#include <memory> -#include <vector> - -/** - * A class to be used to make sure some functions are called when the scope - * is left, because they will be called in the ScopeGuard's destructor. It - * can for example be used to delete some pointer whenever any exception is - * called. Example: - - * { - * ScopeGuard scope; - * int* number = new int(2); - * scope.add_callback([number]() { delete number; }); - * // Do some other stuff with the number. But these stuff might throw an exception: - * throw std::runtime_error("Some error not caught here, but in our caller"); - * return true; - * } - - * In this example, our pointer will always be deleted, even when the - * exception is thrown. If we want the functions to be called only when the - * scope is left because of an unexpected exception, we can use - * ScopeGuard::disable(); - */ - -namespace utils -{ - -class ScopeGuard -{ -public: - /** - * The constructor can take a callback. But additional callbacks can be - * added later with add_callback() - */ - explicit ScopeGuard(std::function<void()>&& func): - enabled(true) - { - this->add_callback(std::move(func)); - } - - ScopeGuard(const ScopeGuard&) = delete; - ScopeGuard& operator=(ScopeGuard&&) = delete; - ScopeGuard(ScopeGuard&&) = delete; - ScopeGuard& operator=(const ScopeGuard&) = delete; - - /** - * default constructor, the scope guard is enabled but empty, use - * add_callback() - */ - explicit ScopeGuard(): - enabled(true) - { - } - /** - * Call all callbacks in the desctructor, unless it has been disabled. - */ - ~ScopeGuard() - { - if (this->enabled) - for (auto& func: this->callbacks) - func(); - } - /** - * Add a callback to be called in our destructor, one scope guard can be - * used for more than one task, if needed. - */ - void add_callback(std::function<void()>&& func) - { - this->callbacks.emplace_back(std::move(func)); - } - /** - * Disable that scope guard, nothing will be done when the scope is - * exited. - */ - void disable() - { - this->enabled = false; - } - -private: - bool enabled; - std::vector<std::function<void()>> callbacks; - -}; - -template<typename F> -auto make_scope_guard(F&& f) -{ - return std::unique_ptr<void, std::decay_t<F>>{(void*)1, std::forward<F>(f)}; -} - -} - diff --git a/louloulibs/utils/sha1.cpp b/louloulibs/utils/sha1.cpp deleted file mode 100644 index f75bc2a..0000000 --- a/louloulibs/utils/sha1.cpp +++ /dev/null @@ -1,121 +0,0 @@ -/* This code is public-domain - it is based on libcrypt - * placed in the public domain by Wei Dai and other contributors. - */ - -#include "sha1.hpp" - -#define SHA1_K0 0x5a827999 -#define SHA1_K20 0x6ed9eba1 -#define SHA1_K40 0x8f1bbcdc -#define SHA1_K60 0xca62c1d6 - -const uint8_t sha1InitState[] = { - 0x01,0x23,0x45,0x67, // H0 - 0x89,0xab,0xcd,0xef, // H1 - 0xfe,0xdc,0xba,0x98, // H2 - 0x76,0x54,0x32,0x10, // H3 - 0xf0,0xe1,0xd2,0xc3 // H4 -}; - -void sha1_init(sha1nfo *s) { - memcpy(s->state.b,sha1InitState,HASH_LENGTH); - s->byteCount = 0; - s->bufferOffset = 0; -} - -uint32_t sha1_rol32(uint32_t number, uint8_t bits) { - return ((number << bits) | (number >> (32-bits))); -} - -void sha1_hashBlock(sha1nfo *s) { - uint8_t i; - uint32_t a,b,c,d,e,t; - - a=s->state.w[0]; - b=s->state.w[1]; - c=s->state.w[2]; - d=s->state.w[3]; - e=s->state.w[4]; - for (i=0; i<80; i++) { - if (i>=16) { - t = s->buffer.w[(i+13)&15] ^ s->buffer.w[(i+8)&15] ^ s->buffer.w[(i+2)&15] ^ s->buffer.w[i&15]; - s->buffer.w[i&15] = sha1_rol32(t,1); - } - if (i<20) { - t = (d ^ (b & (c ^ d))) + SHA1_K0; - } else if (i<40) { - t = (b ^ c ^ d) + SHA1_K20; - } else if (i<60) { - t = ((b & c) | (d & (b | c))) + SHA1_K40; - } else { - t = (b ^ c ^ d) + SHA1_K60; - } - t+=sha1_rol32(a,5) + e + s->buffer.w[i&15]; - e=d; - d=c; - c=sha1_rol32(b,30); - b=a; - a=t; - } - s->state.w[0] += a; - s->state.w[1] += b; - s->state.w[2] += c; - s->state.w[3] += d; - s->state.w[4] += e; -} - -void sha1_addUncounted(sha1nfo *s, uint8_t data) { - s->buffer.b[s->bufferOffset ^ 3] = data; - s->bufferOffset++; - if (s->bufferOffset == BLOCK_LENGTH) { - sha1_hashBlock(s); - s->bufferOffset = 0; - } -} - -void sha1_writebyte(sha1nfo *s, uint8_t data) { - ++s->byteCount; - sha1_addUncounted(s, data); -} - -void sha1_write(sha1nfo *s, const char *data, size_t len) { - for (;len--;) sha1_writebyte(s, (uint8_t) *data++); -} - -void sha1_pad(sha1nfo *s) { - // Implement SHA-1 padding (fips180-2 §5.1.1) - - // Pad with 0x80 followed by 0x00 until the end of the block - sha1_addUncounted(s, 0x80); - while (s->bufferOffset != 56) sha1_addUncounted(s, 0x00); - - // Append length in the last 8 bytes - sha1_addUncounted(s, 0); // We're only using 32 bit lengths - sha1_addUncounted(s, 0); // But SHA-1 supports 64 bit lengths - sha1_addUncounted(s, 0); // So zero pad the top bits - sha1_addUncounted(s, s->byteCount >> 29); // Shifting to multiply by 8 - sha1_addUncounted(s, s->byteCount >> 21); // as SHA-1 supports bitstreams as well as - sha1_addUncounted(s, s->byteCount >> 13); // byte. - sha1_addUncounted(s, s->byteCount >> 5); - sha1_addUncounted(s, s->byteCount << 3); -} - -uint8_t* sha1_result(sha1nfo *s) { - int i; - // Pad to complete the last block - sha1_pad(s); - - // Swap byte order back - for (i=0; i<5; i++) { - uint32_t a,b; - a=s->state.w[i]; - b=a<<24; - b|=(a<<8) & 0x00ff0000; - b|=(a>>8) & 0x0000ff00; - b|=a>>24; - s->state.w[i]=b; - } - - // Return pointer to hash (20 characters) - return s->state.b; -} diff --git a/louloulibs/utils/sha1.hpp b/louloulibs/utils/sha1.hpp deleted file mode 100644 index d436782..0000000 --- a/louloulibs/utils/sha1.hpp +++ /dev/null @@ -1,33 +0,0 @@ -/* This code is public-domain - it is based on libcrypt - * placed in the public domain by Wei Dai and other contributors. - */ - -#include <stdint.h> -#include <string.h> - -#define HASH_LENGTH 20 -#define BLOCK_LENGTH 64 - -union _buffer { - uint8_t b[BLOCK_LENGTH]; - uint32_t w[BLOCK_LENGTH/4]; -}; - -union _state { - uint8_t b[HASH_LENGTH]; - uint32_t w[HASH_LENGTH/4]; -}; - -typedef struct sha1nfo { - union _buffer buffer; - uint8_t bufferOffset; - union _state state; - uint32_t byteCount; - uint8_t keyBuffer[BLOCK_LENGTH]; - uint8_t innerHash[HASH_LENGTH]; -} sha1nfo; - -void sha1_init(sha1nfo *s); -void sha1_writebyte(sha1nfo *s, uint8_t data); -void sha1_write(sha1nfo *s, const char *data, size_t len); -uint8_t* sha1_result(sha1nfo *s); diff --git a/louloulibs/utils/split.cpp b/louloulibs/utils/split.cpp deleted file mode 100644 index 80f8dae..0000000 --- a/louloulibs/utils/split.cpp +++ /dev/null @@ -1,19 +0,0 @@ -#include <utils/split.hpp> -#include <sstream> - -namespace utils -{ - std::vector<std::string> split(const std::string& s, const char delim, const bool allow_empty) - { - std::vector<std::string> ret; - std::stringstream ss(s); - std::string item; - while (std::getline(ss, item, delim)) - { - if (item.empty() && !allow_empty) - continue ; - ret.emplace_back(std::move(item)); - } - return ret; - } -} diff --git a/louloulibs/utils/split.hpp b/louloulibs/utils/split.hpp deleted file mode 100644 index 3755ef8..0000000 --- a/louloulibs/utils/split.hpp +++ /dev/null @@ -1,12 +0,0 @@ -#pragma once - - -#include <string> -#include <vector> - -namespace utils -{ - std::vector<std::string> split(const std::string &s, const char delim, const bool allow_empty=true); -} - - diff --git a/louloulibs/utils/string.cpp b/louloulibs/utils/string.cpp deleted file mode 100644 index 635e71a..0000000 --- a/louloulibs/utils/string.cpp +++ /dev/null @@ -1,28 +0,0 @@ -#include <utils/string.hpp> -#include <utils/encoding.hpp> - -bool to_bool(const std::string& val) -{ - return (val == "1" || val == "true"); -} - -std::vector<std::string> cut(const std::string& val, const std::size_t size) -{ - std::vector<std::string> res; - std::string::size_type pos = 0; - while (pos < val.size()) - { - // Get the number of chars, <= size, that contain only whole - // UTF-8 codepoints. - std::size_t s = 0; - auto codepoint_size = utils::get_next_codepoint_size(val[pos + s]); - while (s + codepoint_size <= size && pos + s < val.size()) - { - s += codepoint_size; - codepoint_size = utils::get_next_codepoint_size(val[pos + s]); - } - res.emplace_back(val.substr(pos, s)); - pos += s; - } - return res; -} diff --git a/louloulibs/utils/string.hpp b/louloulibs/utils/string.hpp deleted file mode 100644 index 84ba101..0000000 --- a/louloulibs/utils/string.hpp +++ /dev/null @@ -1,10 +0,0 @@ -#pragma once - - -#include <vector> -#include <string> - -bool to_bool(const std::string& val); -std::vector<std::string> cut(const std::string& val, const std::size_t size); - - diff --git a/louloulibs/utils/time.cpp b/louloulibs/utils/time.cpp deleted file mode 100644 index afd6117..0000000 --- a/louloulibs/utils/time.cpp +++ /dev/null @@ -1,70 +0,0 @@ -#include <utils/time.hpp> -#include <time.h> - -#include <sstream> -#include <iomanip> -#include <locale> - -#include "louloulibs.h" - -namespace utils -{ -std::string to_string(const std::time_t& timestamp) -{ - constexpr std::size_t stamp_size = 21; - char date_buf[stamp_size]; - if (std::strftime(date_buf, stamp_size, "%FT%TZ", std::gmtime(×tamp)) != stamp_size - 1) - return ""; - return {std::begin(date_buf), std::end(date_buf) - 1}; -} - -std::time_t parse_datetime(const std::string& stamp) -{ - static const char* format = "%Y-%m-%dT%H:%M:%S"; - std::tm t = {}; -#ifdef HAS_GET_TIME - std::istringstream ss(stamp); - ss.imbue(std::locale("en_US.utf-8")); - - std::string timezone; - ss >> std::get_time(&t, format) >> timezone; - if (ss.fail()) - return -1; -#else - /* Y - m - d T H : M : S */ - constexpr std::size_t stamp_size_without_tz = 4 + 1 + 2 + 1 + 2 + 1 + 2 + 1 + 2 + 1 + 2; - if (!strptime(stamp.data(), format, &t)) { - return -1; - } - const std::string timezone(stamp.data() + stamp_size_without_tz); -#endif - - if (timezone.empty()) - return -1; - - if (timezone.compare(0, 1, "Z") != 0) - { - std::stringstream tz_ss; - tz_ss << timezone; - int multiplier = -1; - char prefix; - int hours; - char sep; - int minutes; - tz_ss >> prefix >> hours >> sep >> minutes; - if (tz_ss.fail()) - return -1; - if (prefix == '-') - multiplier = +1; - else if (prefix != '+') - return -1; - - t.tm_hour += multiplier * hours; - t.tm_min += multiplier * minutes; - } - return ::timegm(&t); -} - -} - - diff --git a/louloulibs/utils/time.hpp b/louloulibs/utils/time.hpp deleted file mode 100644 index c71cd9c..0000000 --- a/louloulibs/utils/time.hpp +++ /dev/null @@ -1,10 +0,0 @@ -#pragma once - -#include <ctime> -#include <string> - -namespace utils -{ -std::string to_string(const std::time_t& timestamp); -std::time_t parse_datetime(const std::string& stamp); -}
\ No newline at end of file diff --git a/louloulibs/utils/timed_events.cpp b/louloulibs/utils/timed_events.cpp deleted file mode 100644 index 68d009c..0000000 --- a/louloulibs/utils/timed_events.cpp +++ /dev/null @@ -1,49 +0,0 @@ -#include <utils/timed_events.hpp> - -TimedEvent::TimedEvent(std::chrono::steady_clock::time_point&& time_point, - std::function<void()> callback, const std::string& name): - time_point(std::move(time_point)), - callback(callback), - repeat(false), - repeat_delay(0), - name(name) -{ -} - -TimedEvent::TimedEvent(std::chrono::milliseconds&& duration, - std::function<void()> callback, const std::string& name): - time_point(std::chrono::steady_clock::now() + duration), - callback(callback), - repeat(true), - repeat_delay(std::move(duration)), - name(name) -{ -} - -bool TimedEvent::is_after(const TimedEvent& other) const -{ - return this->is_after(other.time_point); -} - -bool TimedEvent::is_after(const std::chrono::steady_clock::time_point& time_point) const -{ - return this->time_point > time_point; -} - -std::chrono::milliseconds TimedEvent::get_timeout() const -{ - auto now = std::chrono::steady_clock::now(); - if (now > this->time_point) - return std::chrono::milliseconds(0); - return std::chrono::duration_cast<std::chrono::milliseconds>(this->time_point - now); -} - -void TimedEvent::execute() const -{ - this->callback(); -} - -const std::string& TimedEvent::get_name() const -{ - return this->name; -} diff --git a/louloulibs/utils/timed_events.hpp b/louloulibs/utils/timed_events.hpp deleted file mode 100644 index 6e28206..0000000 --- a/louloulibs/utils/timed_events.hpp +++ /dev/null @@ -1,132 +0,0 @@ -#pragma once - -#include <functional> -#include <string> -#include <chrono> -#include <vector> - -using namespace std::literals::chrono_literals; - -namespace utils { -static constexpr std::chrono::milliseconds no_timeout = std::chrono::milliseconds(-1); -} - -class TimedEventsManager; - -/** - * A callback with an associated date. - */ - -class TimedEvent -{ - friend class TimedEventsManager; -public: - /** - * An event the occurs only once, at the given time_point - */ - explicit TimedEvent(std::chrono::steady_clock::time_point&& time_point, - std::function<void()> callback, const std::string& name=""); - explicit TimedEvent(std::chrono::milliseconds&& duration, - std::function<void()> callback, const std::string& name=""); - - explicit TimedEvent(TimedEvent&&) = default; - TimedEvent& operator=(TimedEvent&&) = default; - ~TimedEvent() = default; - - TimedEvent(const TimedEvent&) = delete; - TimedEvent& operator=(const TimedEvent&) = delete; - - /** - * Whether or not this event happens after the other one. - */ - bool is_after(const TimedEvent& other) const; - bool is_after(const std::chrono::steady_clock::time_point& time_point) const; - /** - * Return the duration difference between now and the event time point. - * If the difference would be negative (i.e. the event is expired), the - * returned value is 0 instead. The value cannot then be negative. - */ - std::chrono::milliseconds get_timeout() const; - void execute() const; - const std::string& get_name() const; - -private: - /** - * The next time point at which the event is executed. - */ - std::chrono::steady_clock::time_point time_point; - /** - * The function to execute. - */ - std::function<void()> callback; - /** - * Whether or not this events repeats itself until it is destroyed. - */ - bool repeat; - /** - * This value is added to the time_point each time the event is executed, - * if repeat is true. Otherwise it is ignored. - */ - std::chrono::milliseconds repeat_delay; - /** - * A name that is used to identify that event. If you want to find your - * event (for example if you want to cancel it), the name should be - * unique. - */ - std::string name; -}; - -/** - * A class managing a list of TimedEvents. - * They are sorted, new events can be added, removed, fetch, etc. - */ - -class TimedEventsManager -{ -public: - ~TimedEventsManager() = default; - - TimedEventsManager(const TimedEventsManager&) = delete; - TimedEventsManager(TimedEventsManager&&) = delete; - TimedEventsManager& operator=(const TimedEventsManager&) = delete; - TimedEventsManager& operator=(TimedEventsManager&&) = delete; - - /** - * Return the unique instance of this class - */ - static TimedEventsManager& instance(); - /** - * Add an event to the list of managed events. The list is sorted after - * this call. - */ - void add_event(TimedEvent&& event); - /** - * Returns the duration, in milliseconds, between now and the next - * available event. If the event is already expired (the duration is - * negative), 0 is returned instead (as in “it's not too late, execute it - * now”) - * Returns a negative value if no event is available. - */ - std::chrono::milliseconds get_timeout() const; - /** - * Execute all the expired events (if their expiration time is exactly - * now, or before now). The event is then removed from the list. If the - * event does repeat, its expiration time is updated and it is reinserted - * in the list at the correct position. - * Returns the number of executed events. - */ - std::size_t execute_expired_events(); - /** - * Remove (and thus cancel) all the timed events with the given name. - * Returns the number of canceled events. - */ - std::size_t cancel(const std::string& name); - /** - * Return the number of managed events. - */ - std::size_t size() const; - -private: - std::vector<TimedEvent> events; - explicit TimedEventsManager() = default; -}; diff --git a/louloulibs/utils/timed_events_manager.cpp b/louloulibs/utils/timed_events_manager.cpp deleted file mode 100644 index 67d61fe..0000000 --- a/louloulibs/utils/timed_events_manager.cpp +++ /dev/null @@ -1,73 +0,0 @@ -#include <utils/timed_events.hpp> - -TimedEventsManager& TimedEventsManager::instance() -{ - static TimedEventsManager inst; - return inst; -} - -void TimedEventsManager::add_event(TimedEvent&& event) -{ - for (auto it = this->events.begin(); it != this->events.end(); ++it) - { - if (it->is_after(event)) - { - this->events.emplace(it, std::move(event)); - return; - } - } - this->events.emplace_back(std::move(event)); -} - -std::chrono::milliseconds TimedEventsManager::get_timeout() const -{ - if (this->events.empty()) - return utils::no_timeout; - return this->events.front().get_timeout(); -} - -std::size_t TimedEventsManager::execute_expired_events() -{ - std::size_t count = 0; - const auto now = std::chrono::steady_clock::now(); - for (auto it = this->events.begin(); it != this->events.end();) - { - if (!it->is_after(now)) - { - TimedEvent copy(std::move(*it)); - it = this->events.erase(it); - ++count; - copy.execute(); - if (copy.repeat) - { - copy.time_point += copy.repeat_delay; - this->add_event(std::move(copy)); - } - continue; - } - else - break; - } - return count; -} - -std::size_t TimedEventsManager::cancel(const std::string& name) -{ - std::size_t res = 0; - for (auto it = this->events.begin(); it != this->events.end();) - { - if (it->get_name() == name) - { - it = this->events.erase(it); - res++; - } - else - ++it; - } - return res; -} - -std::size_t TimedEventsManager::size() const -{ - return this->events.size(); -} diff --git a/louloulibs/utils/tolower.cpp b/louloulibs/utils/tolower.cpp deleted file mode 100644 index 3e518bd..0000000 --- a/louloulibs/utils/tolower.cpp +++ /dev/null @@ -1,13 +0,0 @@ -#include <utils/tolower.hpp> - -namespace utils -{ - std::string tolower(const std::string& original) - { - std::string res; - res.reserve(original.size()); - for (const char c: original) - res += static_cast<char>(std::tolower(c)); - return res; - } -} diff --git a/louloulibs/utils/tolower.hpp b/louloulibs/utils/tolower.hpp deleted file mode 100644 index 650e05d..0000000 --- a/louloulibs/utils/tolower.hpp +++ /dev/null @@ -1,11 +0,0 @@ -#pragma once - - -#include <string> - -namespace utils -{ - std::string tolower(const std::string& original); -} - - diff --git a/louloulibs/utils/xdg.cpp b/louloulibs/utils/xdg.cpp deleted file mode 100644 index 48212a1..0000000 --- a/louloulibs/utils/xdg.cpp +++ /dev/null @@ -1,29 +0,0 @@ -#include <utils/xdg.hpp> -#include <cstdlib> - -#include "louloulibs.h" - -std::string xdg_path(const std::string& filename, const char* env_var) -{ - const char* xdg_home = ::getenv(env_var); - if (xdg_home && xdg_home[0] == '/') - return std::string{xdg_home} + "/" PROJECT_NAME "/" + filename; - else - { - const char* home = ::getenv("HOME"); - if (home) - return std::string{home} + "/" ".config" "/" PROJECT_NAME "/" + filename; - else - return filename; - } -} - -std::string xdg_config_path(const std::string& filename) -{ - return xdg_path(filename, "XDG_CONFIG_HOME"); -} - -std::string xdg_data_path(const std::string& filename) -{ - return xdg_path(filename, "XDG_DATA_HOME"); -} diff --git a/louloulibs/utils/xdg.hpp b/louloulibs/utils/xdg.hpp deleted file mode 100644 index 56e11da..0000000 --- a/louloulibs/utils/xdg.hpp +++ /dev/null @@ -1,14 +0,0 @@ -#pragma once - - -#include <string> - -/** - * Returns a path for the given filename, according to the XDG base - * directory specification, see - * http://standards.freedesktop.org/basedir-spec/basedir-spec-latest.html - */ -std::string xdg_config_path(const std::string& filename); -std::string xdg_data_path(const std::string& filename); - - |