update spdlog

This commit is contained in:
Benjamin Sergeant
2019-12-06 22:05:12 -08:00
parent ba4cf75e0f
commit c86fa8ad3b
98 changed files with 3370 additions and 2262 deletions

View File

@@ -4,7 +4,7 @@
#pragma once
#ifndef SPDLOG_HEADER_ONLY
#include "spdlog/details/backtracer.h"
#include <spdlog/details/backtracer.h>
#endif
namespace spdlog {
namespace details {
@@ -26,7 +26,7 @@ SPDLOG_INLINE backtracer &backtracer::operator=(backtracer other)
{
std::lock_guard<std::mutex> lock(mutex_);
enabled_ = other.enabled();
messages_ = other.messages_;
messages_ = std::move(other.messages_);
return *this;
}
@@ -48,11 +48,6 @@ SPDLOG_INLINE bool backtracer::enabled() const
return enabled_.load(std::memory_order_relaxed);
}
SPDLOG_INLINE backtracer::operator bool() const
{
return enabled();
}
SPDLOG_INLINE void backtracer::push_back(const log_msg &msg)
{
std::lock_guard<std::mutex> lock{mutex_};

View File

@@ -3,8 +3,8 @@
#pragma once
#include "spdlog/details/log_msg_buffer.h"
#include "spdlog/details/circular_q.h"
#include <spdlog/details/log_msg_buffer.h>
#include <spdlog/details/circular_q.h>
#include <atomic>
#include <mutex>
@@ -31,7 +31,6 @@ public:
void enable(size_t size);
void disable();
bool enabled() const;
explicit operator bool() const;
void push_back(const log_msg &msg);
// pop all items in the q and apply the given fun on each of them.

View File

@@ -1,10 +1,11 @@
// Copyright(c) 2015-present, Gabi Melman & spdlog contributors.
// Distributed under the MIT License (http://opensource.org/licenses/MIT)
// cirucal q view of std::vector.
// circular q view of std::vector.
#pragma once
#include <vector>
#include <cassert>
namespace spdlog {
namespace details {
@@ -72,6 +73,27 @@ public:
return v_[head_];
}
// Return number of elements actually stored
size_t size() const
{
if (tail_ >= head_)
{
return tail_ - head_;
}
else
{
return max_items_ - (head_ - tail_);
}
}
// Return const reference to item by index.
// If index is out of range 0…size()-1, the behavior is undefined.
const T &at(size_t i) const
{
assert(i < size());
return v_[(head_ + i) % max_items_];
}
// Pop item from front.
// If there are no elements in the container, the behavior is undefined.
void pop_front()

View File

@@ -3,7 +3,7 @@
#pragma once
#include "spdlog/details/null_mutex.h"
#include <spdlog/details/null_mutex.h>
#include <mutex>
namespace spdlog {

View File

@@ -4,11 +4,11 @@
#pragma once
#ifndef SPDLOG_HEADER_ONLY
#include "spdlog/details/file_helper.h"
#include <spdlog/details/file_helper.h>
#endif
#include "spdlog/details/os.h"
#include "spdlog/common.h"
#include <spdlog/details/os.h>
#include <spdlog/common.h>
#include <cerrno>
#include <chrono>
@@ -28,28 +28,31 @@ SPDLOG_INLINE file_helper::~file_helper()
SPDLOG_INLINE void file_helper::open(const filename_t &fname, bool truncate)
{
close();
filename_ = fname;
auto *mode = truncate ? SPDLOG_FILENAME_T("wb") : SPDLOG_FILENAME_T("ab");
_filename = fname;
for (int tries = 0; tries < open_tries; ++tries)
for (int tries = 0; tries < open_tries_; ++tries)
{
// create containing folder if not exists already.
os::create_dir(os::dir_name(fname));
if (!os::fopen_s(&fd_, fname, mode))
{
return;
}
details::os::sleep_for_millis(open_interval);
details::os::sleep_for_millis(open_interval_);
}
SPDLOG_THROW(spdlog_ex("Failed opening file " + os::filename_to_str(_filename) + " for writing", errno));
SPDLOG_THROW(spdlog_ex("Failed opening file " + os::filename_to_str(filename_) + " for writing", errno));
}
SPDLOG_INLINE void file_helper::reopen(bool truncate)
{
if (_filename.empty())
if (filename_.empty())
{
SPDLOG_THROW(spdlog_ex("Failed re opening file - was not opened before"));
}
open(_filename, truncate);
this->open(filename_, truncate);
}
SPDLOG_INLINE void file_helper::flush()
@@ -72,7 +75,7 @@ SPDLOG_INLINE void file_helper::write(const memory_buf_t &buf)
auto data = buf.data();
if (std::fwrite(data, 1, msg_size, fd_) != msg_size)
{
SPDLOG_THROW(spdlog_ex("Failed writing to file " + os::filename_to_str(_filename), errno));
SPDLOG_THROW(spdlog_ex("Failed writing to file " + os::filename_to_str(filename_), errno));
}
}
@@ -80,19 +83,14 @@ SPDLOG_INLINE size_t file_helper::size() const
{
if (fd_ == nullptr)
{
SPDLOG_THROW(spdlog_ex("Cannot use size() on closed file " + os::filename_to_str(_filename)));
SPDLOG_THROW(spdlog_ex("Cannot use size() on closed file " + os::filename_to_str(filename_)));
}
return os::filesize(fd_);
}
SPDLOG_INLINE const filename_t &file_helper::filename() const
{
return _filename;
}
SPDLOG_INLINE bool file_helper::file_exists(const filename_t &fname)
{
return os::file_exists(fname);
return filename_;
}
//
@@ -119,7 +117,7 @@ SPDLOG_INLINE std::tuple<filename_t, filename_t> file_helper::split_by_extension
return std::make_tuple(fname, filename_t());
}
// treat casese like "/etc/rc.d/somelogfile or "/abc/.hiddenfile"
// treat cases like "/etc/rc.d/somelogfile or "/abc/.hiddenfile"
auto folder_index = fname.rfind(details::os::folder_sep);
if (folder_index != filename_t::npos && folder_index >= ext_index - 1)
{
@@ -129,5 +127,6 @@ SPDLOG_INLINE std::tuple<filename_t, filename_t> file_helper::split_by_extension
// finally - return a valid base and extension tuple
return std::make_tuple(fname.substr(0, ext_index), fname.substr(ext_index));
}
} // namespace details
} // namespace spdlog

View File

@@ -3,7 +3,7 @@
#pragma once
#include "spdlog/common.h"
#include <spdlog/common.h>
#include <tuple>
namespace spdlog {
@@ -29,7 +29,6 @@ public:
void write(const memory_buf_t &buf);
size_t size() const;
const filename_t &filename() const;
static bool file_exists(const filename_t &fname);
//
// return file path and its extension:
@@ -47,10 +46,10 @@ public:
static std::tuple<filename_t, filename_t> split_by_extension(const filename_t &fname);
private:
const int open_tries = 5;
const int open_interval = 10;
const int open_tries_ = 5;
const int open_interval_ = 10;
std::FILE *fd_{nullptr};
filename_t _filename;
filename_t filename_;
};
} // namespace details
} // namespace spdlog

View File

@@ -4,8 +4,8 @@
#include <chrono>
#include <type_traits>
#include "spdlog/fmt/fmt.h"
#include "spdlog/common.h"
#include <spdlog/fmt/fmt.h>
#include <spdlog/common.h>
// Some fmt helpers to efficiently format and pad ints and strings
namespace spdlog {

View File

@@ -4,21 +4,19 @@
#pragma once
#ifndef SPDLOG_HEADER_ONLY
#include "spdlog/details/log_msg.h"
#include <spdlog/details/log_msg.h>
#endif
#include "spdlog/details/os.h"
#include <spdlog/details/os.h>
namespace spdlog {
namespace details {
SPDLOG_INLINE log_msg::log_msg(spdlog::source_loc loc, string_view_t logger_name, spdlog::level::level_enum lvl, spdlog::string_view_t msg)
: logger_name(logger_name)
SPDLOG_INLINE log_msg::log_msg(
spdlog::source_loc loc, string_view_t a_logger_name, spdlog::level::level_enum lvl, spdlog::string_view_t msg)
: logger_name(a_logger_name)
, level(lvl)
#ifndef SPDLOG_NO_DATETIME
, time(os::now())
#endif
#ifndef SPDLOG_NO_THREAD_ID
, thread_id(os::thread_id())
#endif
@@ -26,8 +24,8 @@ SPDLOG_INLINE log_msg::log_msg(spdlog::source_loc loc, string_view_t logger_name
, payload(msg)
{}
SPDLOG_INLINE log_msg::log_msg(string_view_t logger_name, spdlog::level::level_enum lvl, spdlog::string_view_t msg)
: log_msg(source_loc{}, logger_name, lvl, msg)
SPDLOG_INLINE log_msg::log_msg(string_view_t a_logger_name, spdlog::level::level_enum lvl, spdlog::string_view_t msg)
: log_msg(source_loc{}, a_logger_name, lvl, msg)
{}
} // namespace details

View File

@@ -3,7 +3,7 @@
#pragma once
#include "spdlog/common.h"
#include <spdlog/common.h>
#include <string>
namespace spdlog {

View File

@@ -4,7 +4,7 @@
#pragma once
#ifndef SPDLOG_HEADER_ONLY
#include "spdlog/details/log_msg_buffer.h"
#include <spdlog/details/log_msg_buffer.h>
#endif
namespace spdlog {
@@ -26,9 +26,7 @@ SPDLOG_INLINE log_msg_buffer::log_msg_buffer(const log_msg_buffer &other)
update_string_views();
}
SPDLOG_INLINE log_msg_buffer::log_msg_buffer(log_msg_buffer &&other)
: log_msg{std::move(other)}
, buffer{std::move(other.buffer)}
SPDLOG_INLINE log_msg_buffer::log_msg_buffer(log_msg_buffer &&other) SPDLOG_NOEXCEPT : log_msg{other}, buffer{std::move(other.buffer)}
{
update_string_views();
}
@@ -42,9 +40,9 @@ SPDLOG_INLINE log_msg_buffer &log_msg_buffer::operator=(const log_msg_buffer &ot
return *this;
}
SPDLOG_INLINE log_msg_buffer &log_msg_buffer::operator=(log_msg_buffer &&other)
SPDLOG_INLINE log_msg_buffer &log_msg_buffer::operator=(log_msg_buffer &&other) SPDLOG_NOEXCEPT
{
log_msg::operator=(std::move(other));
log_msg::operator=(other);
buffer = std::move(other.buffer);
update_string_views();
return *this;

View File

@@ -3,7 +3,7 @@
#pragma once
#include "spdlog/details/log_msg.h"
#include <spdlog/details/log_msg.h>
namespace spdlog {
namespace details {
@@ -20,9 +20,9 @@ public:
log_msg_buffer() = default;
explicit log_msg_buffer(const log_msg &orig_msg);
log_msg_buffer(const log_msg_buffer &other);
log_msg_buffer(log_msg_buffer &&other);
log_msg_buffer(log_msg_buffer &&other) SPDLOG_NOEXCEPT;
log_msg_buffer &operator=(const log_msg_buffer &other);
log_msg_buffer &operator=(log_msg_buffer &&other);
log_msg_buffer &operator=(log_msg_buffer &&other) SPDLOG_NOEXCEPT;
};
} // namespace details

View File

@@ -10,7 +10,7 @@
// dequeue_for(..) - will block until the queue is not empty or timeout have
// passed.
#include "spdlog/details/circular_q.h"
#include <spdlog/details/circular_q.h>
#include <condition_variable>
#include <mutex>

View File

@@ -4,10 +4,10 @@
#pragma once
#ifndef SPDLOG_HEADER_ONLY
#include "spdlog/details/os.h"
#include <spdlog/details/os.h>
#endif
#include "spdlog/common.h"
#include <spdlog/common.h>
#include <algorithm>
#include <chrono>
@@ -42,6 +42,8 @@
#include <limits>
#endif
#include <direct.h> // for _mkdir/_wmkdir
#else // unix
#include <fcntl.h>
@@ -91,17 +93,17 @@ SPDLOG_INLINE std::tm localtime(const std::time_t &time_tt) SPDLOG_NOEXCEPT
#ifdef _WIN32
std::tm tm;
localtime_s(&tm, &time_tt);
::localtime_s(&tm, &time_tt);
#else
std::tm tm;
localtime_r(&time_tt, &tm);
::localtime_r(&time_tt, &tm);
#endif
return tm;
}
SPDLOG_INLINE std::tm localtime() SPDLOG_NOEXCEPT
{
std::time_t now_t = time(nullptr);
std::time_t now_t = ::time(nullptr);
return localtime(now_t);
}
@@ -110,52 +112,52 @@ SPDLOG_INLINE std::tm gmtime(const std::time_t &time_tt) SPDLOG_NOEXCEPT
#ifdef _WIN32
std::tm tm;
gmtime_s(&tm, &time_tt);
::gmtime_s(&tm, &time_tt);
#else
std::tm tm;
gmtime_r(&time_tt, &tm);
::gmtime_r(&time_tt, &tm);
#endif
return tm;
}
SPDLOG_INLINE std::tm gmtime() SPDLOG_NOEXCEPT
{
std::time_t now_t = time(nullptr);
std::time_t now_t = ::time(nullptr);
return gmtime(now_t);
}
#ifdef SPDLOG_PREVENT_CHILD_FD
SPDLOG_INLINE void prevent_child_fd(FILE *f)
{
#ifdef _WIN32
#if !defined(__cplusplus_winrt)
auto file_handle = reinterpret_cast<HANDLE>(_get_osfhandle(_fileno(f)));
auto file_handle = reinterpret_cast<HANDLE>(_get_osfhandle(::_fileno(f)));
if (!::SetHandleInformation(file_handle, HANDLE_FLAG_INHERIT, 0))
SPDLOG_THROW(spdlog_ex("SetHandleInformation failed", errno));
#endif
#else
auto fd = fileno(f);
if (fcntl(fd, F_SETFD, FD_CLOEXEC) == -1)
auto fd = ::fileno(f);
if (::fcntl(fd, F_SETFD, FD_CLOEXEC) == -1)
{
SPDLOG_THROW(spdlog_ex("fcntl with FD_CLOEXEC failed", errno));
}
#endif
}
#endif // SPDLOG_PREVENT_CHILD_FD
// fopen_s on non windows for writing
SPDLOG_INLINE bool fopen_s(FILE **fp, const filename_t &filename, const filename_t &mode)
{
#ifdef _WIN32
#ifdef SPDLOG_WCHAR_FILENAMES
*fp = _wfsopen((filename.c_str()), mode.c_str(), _SH_DENYNO);
*fp = ::_wfsopen((filename.c_str()), mode.c_str(), _SH_DENYNO);
#else
*fp = _fsopen((filename.c_str()), mode.c_str(), _SH_DENYNO);
*fp = ::_fsopen((filename.c_str()), mode.c_str(), _SH_DENYNO);
#endif
#else // unix
*fp = fopen((filename.c_str()), mode.c_str());
*fp = ::fopen((filename.c_str()), mode.c_str());
#endif
#ifdef SPDLOG_PREVENT_CHILD_FD
// prevent child processes from inheriting log file descriptors
if (*fp != nullptr)
{
prevent_child_fd(*fp);
@@ -167,7 +169,7 @@ SPDLOG_INLINE bool fopen_s(FILE **fp, const filename_t &filename, const filename
SPDLOG_INLINE int remove(const filename_t &filename) SPDLOG_NOEXCEPT
{
#if defined(_WIN32) && defined(SPDLOG_WCHAR_FILENAMES)
return _wremove(filename.c_str());
return ::_wremove(filename.c_str());
#else
return std::remove(filename.c_str());
#endif
@@ -175,28 +177,28 @@ SPDLOG_INLINE int remove(const filename_t &filename) SPDLOG_NOEXCEPT
SPDLOG_INLINE int remove_if_exists(const filename_t &filename) SPDLOG_NOEXCEPT
{
return file_exists(filename) ? remove(filename) : 0;
return path_exists(filename) ? remove(filename) : 0;
}
SPDLOG_INLINE int rename(const filename_t &filename1, const filename_t &filename2) SPDLOG_NOEXCEPT
{
#if defined(_WIN32) && defined(SPDLOG_WCHAR_FILENAMES)
return _wrename(filename1.c_str(), filename2.c_str());
return ::_wrename(filename1.c_str(), filename2.c_str());
#else
return std::rename(filename1.c_str(), filename2.c_str());
#endif
}
// Return true if file exists
SPDLOG_INLINE bool file_exists(const filename_t &filename) SPDLOG_NOEXCEPT
// Return true if path exists (file or directory)
SPDLOG_INLINE bool path_exists(const filename_t &filename) SPDLOG_NOEXCEPT
{
#ifdef _WIN32
#ifdef SPDLOG_WCHAR_FILENAMES
auto attribs = GetFileAttributesW(filename.c_str());
auto attribs = ::GetFileAttributesW(filename.c_str());
#else
auto attribs = GetFileAttributesA(filename.c_str());
auto attribs = ::GetFileAttributesA(filename.c_str());
#endif
return (attribs != INVALID_FILE_ATTRIBUTES && !(attribs & FILE_ATTRIBUTE_DIRECTORY));
return attribs != INVALID_FILE_ATTRIBUTES;
#else // common linux/unix all have the stat system call
struct stat buffer;
return (::stat(filename.c_str(), &buffer) == 0);
@@ -211,16 +213,16 @@ SPDLOG_INLINE size_t filesize(FILE *f)
SPDLOG_THROW(spdlog_ex("Failed getting file size. fd is null"));
}
#if defined(_WIN32) && !defined(__CYGWIN__)
int fd = _fileno(f);
int fd = ::_fileno(f);
#if _WIN64 // 64 bits
__int64 ret = _filelengthi64(fd);
__int64 ret = ::_filelengthi64(fd);
if (ret >= 0)
{
return static_cast<size_t>(ret);
}
#else // windows 32 bits
long ret = _filelength(fd);
long ret = ::_filelength(fd);
if (ret >= 0)
{
return static_cast<size_t>(ret);
@@ -228,7 +230,12 @@ SPDLOG_INLINE size_t filesize(FILE *f)
#endif
#else // unix
// OpenBSD doesn't compile with :: before the fileno(..)
#if defined(__OpenBSD__)
int fd = fileno(f);
#else
int fd = ::fileno(f);
#endif
// 64 bits(but not in osx or cygwin, where fstat64 is deprecated)
#if (defined(__linux__) || defined(__sun) || defined(_AIX)) && (defined(__LP64__) || defined(_LP64))
struct stat64 st;
@@ -236,9 +243,8 @@ SPDLOG_INLINE size_t filesize(FILE *f)
{
return static_cast<size_t>(st.st_size);
}
#else // unix 32 bits or cygwin
#else // other unix or linux 32 bits or cygwin
struct stat st;
if (::fstat(fd, &st) == 0)
{
return static_cast<size_t>(st.st_size);
@@ -255,10 +261,10 @@ SPDLOG_INLINE int utc_minutes_offset(const std::tm &tm)
#ifdef _WIN32
#if _WIN32_WINNT < _WIN32_WINNT_WS08
TIME_ZONE_INFORMATION tzinfo;
auto rv = GetTimeZoneInformation(&tzinfo);
auto rv = ::GetTimeZoneInformation(&tzinfo);
#else
DYNAMIC_TIME_ZONE_INFORMATION tzinfo;
auto rv = GetDynamicTimeZoneInformation(&tzinfo);
auto rv = ::GetDynamicTimeZoneInformation(&tzinfo);
#endif
if (rv == TIME_ZONE_ID_INVALID)
SPDLOG_THROW(spdlog::spdlog_ex("Failed getting timezone info. ", errno));
@@ -275,7 +281,7 @@ SPDLOG_INLINE int utc_minutes_offset(const std::tm &tm)
return offset;
#else
#if defined(sun) || defined(__sun) || defined(_AIX)
#if defined(sun) || defined(__sun) || defined(_AIX) || (!defined(_BSD_SOURCE) && !defined(_GNU_SOURCE))
// 'tm_gmtoff' field is BSD extension and it's missing on SunOS/Solaris
struct helper
{
@@ -324,15 +330,15 @@ SPDLOG_INLINE size_t _thread_id() SPDLOG_NOEXCEPT
#if defined(__ANDROID__) && defined(__ANDROID_API__) && (__ANDROID_API__ < 21)
#define SYS_gettid __NR_gettid
#endif
return static_cast<size_t>(syscall(SYS_gettid));
return static_cast<size_t>(::syscall(SYS_gettid));
#elif defined(_AIX) || defined(__DragonFly__) || defined(__FreeBSD__)
return static_cast<size_t>(pthread_getthreadid_np());
return static_cast<size_t>(::pthread_getthreadid_np());
#elif defined(__NetBSD__)
return static_cast<size_t>(_lwp_self());
return static_cast<size_t>(::_lwp_self());
#elif defined(__OpenBSD__)
return static_cast<size_t>(getthrid());
return static_cast<size_t>(::getthrid());
#elif defined(__sun)
return static_cast<size_t>(thr_self());
return static_cast<size_t>(::thr_self());
#elif __APPLE__
uint64_t tid;
pthread_threadid_np(nullptr, &tid);
@@ -417,16 +423,16 @@ SPDLOG_INLINE bool in_terminal(FILE *file) SPDLOG_NOEXCEPT
{
#ifdef _WIN32
return _isatty(_fileno(file)) != 0;
return ::_isatty(_fileno(file)) != 0;
#else
return isatty(fileno(file)) != 0;
return ::isatty(fileno(file)) != 0;
#endif
}
#if (defined(SPDLOG_WCHAR_TO_UTF8_SUPPORT) || defined(SPDLOG_WCHAR_FILENAMES)) && defined(_WIN32)
SPDLOG_INLINE void wstr_to_utf8buf(wstring_view_t wstr, memory_buf_t &target)
{
if (wstr.size() > static_cast<size_t>(std::numeric_limits<int>::max()))
if (wstr.size() > static_cast<size_t>((std::numeric_limits<int>::max)()))
{
SPDLOG_THROW(spdlog::spdlog_ex("UTF-16 string is too big to be converted to UTF-8"));
}
@@ -460,6 +466,76 @@ SPDLOG_INLINE void wstr_to_utf8buf(wstring_view_t wstr, memory_buf_t &target)
}
#endif // (defined(SPDLOG_WCHAR_TO_UTF8_SUPPORT) || defined(SPDLOG_WCHAR_FILENAMES)) && defined(_WIN32)
// return true on success
static SPDLOG_INLINE bool mkdir_(const filename_t &path)
{
#ifdef _WIN32
#ifdef SPDLOG_WCHAR_FILENAMES
return ::_wmkdir(path.c_str()) == 0;
#else
return ::_mkdir(path.c_str()) == 0;
#endif
#else
return ::mkdir(path.c_str(), mode_t(0755)) == 0;
#endif
}
// create the given directory - and all directories leading to it
// return true on success or if the directory already exists
SPDLOG_INLINE bool create_dir(filename_t path)
{
if (path_exists(path))
{
return true;
}
if (path.empty())
{
return false;
}
#ifdef _WIN32
// support forward slash in windows
std::replace(path.begin(), path.end(), '/', folder_sep);
#endif
size_t search_offset = 0;
do
{
auto token_pos = path.find(folder_sep, search_offset);
// treat the entire path as a folder if no folder separator not found
if (token_pos == filename_t::npos)
{
token_pos = path.size();
}
auto subdir = path.substr(0, token_pos);
if (!subdir.empty() && !path_exists(subdir) && !mkdir_(subdir))
{
return false; // return error if failed creating dir
}
search_offset = token_pos + 1;
} while (search_offset < path.size());
return true;
}
// Return directory name from given path or empty string
// "abc/file" => "abc"
// "abc/" => "abc"
// "abc" => ""
// "abc///" => "abc//"
SPDLOG_INLINE filename_t dir_name(filename_t path)
{
#ifdef _WIN32
// support forward slash in windows
std::replace(path.begin(), path.end(), '/', folder_sep);
#endif
auto pos = path.find_last_of(folder_sep);
return pos != filename_t::npos ? path.substr(0, pos) : filename_t{};
}
} // namespace os
} // namespace details
} // namespace spdlog

View File

@@ -3,7 +3,7 @@
#pragma once
#include "spdlog/common.h"
#include <spdlog/common.h>
#include <ctime> // std::time_t
namespace spdlog {
@@ -33,12 +33,14 @@ SPDLOG_CONSTEXPR static const char *default_eol = SPDLOG_EOL;
// folder separator
#ifdef _WIN32
const char folder_sep = '\\';
static const char folder_sep = '\\';
#else
SPDLOG_CONSTEXPR static const char folder_sep = '/';
#endif
#ifdef SPDLOG_PREVENT_CHILD_FD
void prevent_child_fd(FILE *f);
#endif
// fopen_s on non windows for writing
bool fopen_s(FILE **fp, const filename_t &filename, const filename_t &mode);
@@ -53,7 +55,7 @@ int remove_if_exists(const filename_t &filename) SPDLOG_NOEXCEPT;
int rename(const filename_t &filename1, const filename_t &filename2) SPDLOG_NOEXCEPT;
// Return if file exists.
bool file_exists(const filename_t &filename) SPDLOG_NOEXCEPT;
bool path_exists(const filename_t &filename) SPDLOG_NOEXCEPT;
// Return file size according to open FILE* object
size_t filesize(FILE *f);
@@ -81,7 +83,7 @@ int pid() SPDLOG_NOEXCEPT;
// Source: https://github.com/agauniyal/rang/
bool is_color_terminal() SPDLOG_NOEXCEPT;
// Detrmine if the terminal attached
// Determine if the terminal attached
// Source: https://github.com/agauniyal/rang/
bool in_terminal(FILE *file) SPDLOG_NOEXCEPT;
@@ -89,6 +91,17 @@ bool in_terminal(FILE *file) SPDLOG_NOEXCEPT;
void wstr_to_utf8buf(wstring_view_t wstr, memory_buf_t &target);
#endif
// Return directory name from given path or empty string
// "abc/file" => "abc"
// "abc/" => "abc"
// "abc" => ""
// "abc///" => "abc//"
filename_t dir_name(filename_t path);
// Create a dir from the given path.
// Return true if succeeded or if this dir already exists.
bool create_dir(filename_t path);
} // namespace os
} // namespace details
} // namespace spdlog

View File

@@ -4,14 +4,14 @@
#pragma once
#ifndef SPDLOG_HEADER_ONLY
#include "spdlog/details/pattern_formatter.h"
#include <spdlog/details/pattern_formatter.h>
#endif
#include "spdlog/details/fmt_helper.h"
#include "spdlog/details/log_msg.h"
#include "spdlog/details/os.h"
#include "spdlog/fmt/fmt.h"
#include "spdlog/formatter.h"
#include <spdlog/details/fmt_helper.h>
#include <spdlog/details/log_msg.h>
#include <spdlog/details/os.h>
#include <spdlog/fmt/fmt.h>
#include <spdlog/formatter.h>
#include <array>
#include <chrono>
@@ -39,47 +39,48 @@ public:
: padinfo_(padinfo)
, dest_(dest)
{
if (padinfo_.width_ <= wrapped_size)
remaining_pad_ = static_cast<long>(padinfo.width_) - static_cast<long>(wrapped_size);
if (remaining_pad_ <= 0)
{
total_pad_ = 0;
return;
}
total_pad_ = padinfo.width_ - wrapped_size;
if (padinfo_.side_ == padding_info::left)
{
pad_it(total_pad_);
total_pad_ = 0;
pad_it(remaining_pad_);
remaining_pad_ = 0;
}
else if (padinfo_.side_ == padding_info::center)
{
auto half_pad = total_pad_ / 2;
auto reminder = total_pad_ & 1;
auto half_pad = remaining_pad_ / 2;
auto reminder = remaining_pad_ & 1;
pad_it(half_pad);
total_pad_ = half_pad + reminder; // for the right side
remaining_pad_ = half_pad + reminder; // for the right side
}
}
~scoped_padder()
{
if (total_pad_)
if (remaining_pad_ >= 0)
{
pad_it(total_pad_);
pad_it(remaining_pad_);
}
else if (padinfo_.truncate_)
{
long new_size = static_cast<long>(dest_.size()) + remaining_pad_;
dest_.resize(static_cast<size_t>(new_size));
}
}
private:
void pad_it(size_t count)
void pad_it(long count)
{
// count = std::min(count, spaces_.size());
assert(count <= spaces_.size());
fmt_helper::append_string_view(string_view_t(spaces_.data(), count), dest_);
fmt_helper::append_string_view(string_view_t(spaces_.data(), static_cast<size_t>(count)), dest_);
}
const padding_info &padinfo_;
memory_buf_t &dest_;
size_t total_pad_;
long remaining_pad_;
string_view_t spaces_{" ", 64};
};
@@ -593,14 +594,7 @@ public:
const size_t field_size = 6;
ScopedPadder p(field_size, padinfo_, dest);
#ifdef _WIN32
int total_minutes = get_cached_offset(msg, tm_time);
#else
// No need to chache under gcc,
// it is very fast (already stored in tm.tm_gmtoff)
(void)(msg);
int total_minutes = os::utc_minutes_offset(tm_time);
#endif
auto total_minutes = get_cached_offset(msg, tm_time);
bool is_negative = total_minutes < 0;
if (is_negative)
{
@@ -619,7 +613,6 @@ public:
private:
log_clock::time_point last_update_{std::chrono::seconds(0)};
#ifdef _WIN32
int offset_minutes_{0};
int get_cached_offset(const log_msg &msg, const std::tm &tm_time)
@@ -632,7 +625,6 @@ private:
}
return offset_minutes_;
}
#endif
};
// Thread id
@@ -881,11 +873,13 @@ public:
auto delta = (std::max)(msg.time - last_message_time_, log_clock::duration::zero());
auto delta_units = std::chrono::duration_cast<DurationUnits>(delta);
last_message_time_ = msg.time;
ScopedPadder p(6, padinfo_, dest);
fmt_helper::pad6(static_cast<size_t>(delta_units.count()), dest);
auto delta_count = static_cast<size_t>(delta_units.count());
auto n_digits = static_cast<size_t>(fmt_helper::count_digits(delta_count));
ScopedPadder p(n_digits, padinfo_, dest);
fmt_helper::append_int(delta_count, dest);
}
protected:
private:
log_clock::time_point last_message_time_;
};
@@ -904,8 +898,6 @@ public:
using std::chrono::milliseconds;
using std::chrono::seconds;
#ifndef SPDLOG_NO_DATETIME
// cache the date/time part for the next second.
auto duration = msg.time.time_since_epoch();
auto secs = duration_cast<seconds>(duration);
@@ -941,10 +933,6 @@ public:
dest.push_back(']');
dest.push_back(' ');
#else // no datetime needed
(void)tm_time;
#endif
#ifndef SPDLOG_NO_NAME
if (msg.logger_name.size() > 0)
{
@@ -1014,14 +1002,13 @@ SPDLOG_INLINE std::unique_ptr<formatter> pattern_formatter::clone() const
SPDLOG_INLINE void pattern_formatter::format(const details::log_msg &msg, memory_buf_t &dest)
{
#ifndef SPDLOG_NO_DATETIME
auto secs = std::chrono::duration_cast<std::chrono::seconds>(msg.time.time_since_epoch());
if (secs != last_log_secs_)
{
cached_tm_ = get_time_(msg);
last_log_secs_ = secs;
}
#endif
for (auto &f : formatters_)
{
f->format(msg, cached_tm_, dest);
@@ -1225,7 +1212,7 @@ SPDLOG_INLINE void pattern_formatter::handle_flag_(char flag, details::padding_i
}
}
// Extract given pad spec (e.g. %8X)
// Extract given pad spec (e.g. %8X, %=8X, %-8!X, %8!X, %=8!X, %-8!X, %+8!X)
// Advance the given it pass the end of the padding spec found (if any)
// Return padding.
SPDLOG_INLINE details::padding_info pattern_formatter::handle_padspec_(std::string::const_iterator &it, std::string::const_iterator end)
@@ -1256,7 +1243,7 @@ SPDLOG_INLINE details::padding_info pattern_formatter::handle_padspec_(std::stri
if (it == end || !std::isdigit(static_cast<unsigned char>(*it)))
{
return padding_info{0, side};
return padding_info{}; // no padding if no digit found here
}
auto width = static_cast<size_t>(*it) - '0';
@@ -1265,7 +1252,20 @@ SPDLOG_INLINE details::padding_info pattern_formatter::handle_padspec_(std::stri
auto digit = static_cast<size_t>(*it) - '0';
width = width * 10 + digit;
}
return details::padding_info{std::min<size_t>(width, max_width), side};
// search for the optional truncate marker '!'
bool truncate;
if (it != end && *it == '!')
{
truncate = true;
++it;
}
else
{
truncate = false;
}
return details::padding_info{std::min<size_t>(width, max_width), side, truncate};
}
SPDLOG_INLINE void pattern_formatter::compile_pattern_(const std::string &pattern)

View File

@@ -3,10 +3,10 @@
#pragma once
#include "spdlog/common.h"
#include "spdlog/details/log_msg.h"
#include "spdlog/details/os.h"
#include "spdlog/formatter.h"
#include <spdlog/common.h>
#include <spdlog/details/log_msg.h>
#include <spdlog/details/os.h>
#include <spdlog/formatter.h>
#include <chrono>
#include <ctime>
@@ -29,17 +29,21 @@ struct padding_info
};
padding_info() = default;
padding_info(size_t width, padding_info::pad_side side)
padding_info(size_t width, padding_info::pad_side side, bool truncate)
: width_(width)
, side_(side)
, truncate_(truncate)
, enabled_(true)
{}
bool enabled() const
{
return width_ != 0;
return enabled_;
}
const size_t width_ = 0;
const pad_side side_ = left;
bool truncate_ = false;
bool enabled_ = false;
};
class flag_formatter

View File

@@ -4,7 +4,7 @@
#pragma once
#ifndef SPDLOG_HEADER_ONLY
#include "spdlog/details/periodic_worker.h"
#include <spdlog/details/periodic_worker.h>
#endif
namespace spdlog {

View File

@@ -4,20 +4,20 @@
#pragma once
#ifndef SPDLOG_HEADER_ONLY
#include "spdlog/details/registry.h"
#include <spdlog/details/registry.h>
#endif
#include "spdlog/common.h"
#include "spdlog/details/periodic_worker.h"
#include "spdlog/logger.h"
#include "spdlog/details/pattern_formatter.h"
#include <spdlog/common.h>
#include <spdlog/details/periodic_worker.h>
#include <spdlog/logger.h>
#include <spdlog/details/pattern_formatter.h>
#ifndef SPDLOG_DISABLE_DEFAULT_LOGGER
// support for the default stdout color logger
#ifdef _WIN32
#include "spdlog/sinks/wincolor_sink.h"
#include <spdlog/sinks/wincolor_sink.h>
#else
#include "spdlog/sinks/ansicolor_sink.h"
#include <spdlog/sinks/ansicolor_sink.h>
#endif
#endif // SPDLOG_DISABLE_DEFAULT_LOGGER
@@ -254,10 +254,10 @@ SPDLOG_INLINE std::recursive_mutex &registry::tp_mutex()
return tp_mutex_;
}
SPDLOG_INLINE void registry::set_automatic_registration(bool automatic_regsistration)
SPDLOG_INLINE void registry::set_automatic_registration(bool automatic_registration)
{
std::lock_guard<std::mutex> lock(logger_map_mutex_);
automatic_registration_ = automatic_regsistration;
automatic_registration_ = automatic_registration;
}
SPDLOG_INLINE registry &registry::instance()

View File

@@ -8,7 +8,7 @@
// If user requests a non existing logger, nullptr will be returned
// This class is thread safe
#include "spdlog/common.h"
#include <spdlog/common.h>
#include <chrono>
#include <functional>
@@ -77,7 +77,7 @@ public:
std::recursive_mutex &tp_mutex();
void set_automatic_registration(bool automatic_regsistration);
void set_automatic_registration(bool automatic_registration);
static registry &instance();

View File

@@ -4,10 +4,11 @@
#pragma once
#ifndef SPDLOG_HEADER_ONLY
#include "spdlog/details/thread_pool.h"
#include <spdlog/details/thread_pool.h>
#endif
#include "spdlog/common.h"
#include <spdlog/common.h>
#include <cassert>
namespace spdlog {
namespace details {
@@ -81,7 +82,7 @@ void SPDLOG_INLINE thread_pool::post_async_msg_(async_msg &&new_msg, async_overf
void SPDLOG_INLINE thread_pool::worker_loop_()
{
while (process_next_msg_()) {};
while (process_next_msg_()) {}
}
// process next message in the queue
@@ -98,24 +99,20 @@ bool SPDLOG_INLINE thread_pool::process_next_msg_()
switch (incoming_async_msg.msg_type)
{
case async_msg_type::log:
{
case async_msg_type::log: {
incoming_async_msg.worker_ptr->backend_sink_it_(incoming_async_msg);
return true;
}
case async_msg_type::flush:
{
case async_msg_type::flush: {
incoming_async_msg.worker_ptr->backend_flush_();
return true;
}
case async_msg_type::terminate:
{
case async_msg_type::terminate: {
return false;
}
default:
{
default: {
assert(false && "Unexpected async_msg_type");
}
}

View File

@@ -3,9 +3,9 @@
#pragma once
#include "spdlog/details/log_msg_buffer.h"
#include "spdlog/details/mpmc_blocking_q.h"
#include "spdlog/details/os.h"
#include <spdlog/details/log_msg_buffer.h>
#include <spdlog/details/mpmc_blocking_q.h>
#include <spdlog/details/os.h>
#include <chrono>
#include <memory>
@@ -27,7 +27,7 @@ enum class async_msg_type
terminate
};
#include "spdlog/details/log_msg_buffer.h"
#include <spdlog/details/log_msg_buffer.h>
// Async msg to move to/from the queue
// Movable only. should never be copied
struct async_msg : log_msg_buffer