Logger tweaks
Commit amended for code style and minor cleanup by Adam Honse <calcprogrammer1@gmail.com>
This commit is contained in:
parent
0089852395
commit
f1d6c2953d
6 changed files with 387 additions and 125 deletions
240
LogManager.cpp
240
LogManager.cpp
|
|
@ -1,12 +1,15 @@
|
|||
#include "LogManager.h"
|
||||
|
||||
#include <stdarg.h>
|
||||
#include <iostream>
|
||||
#include "ResourceManager.h"
|
||||
|
||||
#define _SILENCE_EXPERIMENTAL_FILESYSTEM_DEPRECATION_WARNING
|
||||
#include <experimental/filesystem>
|
||||
namespace fs = std::experimental::filesystem;
|
||||
|
||||
static const char* log_codes[] = {"CRITICAL", "ERROR", "Message", "Warning", "Notice", "[verbose]", "Debug"};
|
||||
|
||||
LogManager::LogManager()
|
||||
{
|
||||
}
|
||||
|
|
@ -94,36 +97,11 @@ void LogManager::configure(json config, const std::string &defaultDir)
|
|||
const json& loglevel_obj = config["loglevel"];
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| If the log level is configured per section, set |
|
||||
| loglevel for each section |
|
||||
| Set the log level if configured |
|
||||
\*-------------------------------------------------*/
|
||||
if(loglevel_obj.is_object())
|
||||
if(loglevel_obj.is_number_integer())
|
||||
{
|
||||
for(size_t section = 0; section < sections.size(); ++section)
|
||||
{
|
||||
if(loglevel_obj.contains(sections[section]))
|
||||
{
|
||||
const json& val = loglevel_obj[sections[section]];
|
||||
|
||||
if(val.is_number_integer())
|
||||
{
|
||||
loglevels[section] = val;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| If the log level is configured globally, set same |
|
||||
| loglevel for each section |
|
||||
\*-------------------------------------------------*/
|
||||
else if(loglevel_obj.is_number_integer())
|
||||
{
|
||||
int l = loglevel_obj;
|
||||
for(size_t section = 0; section < sections.size(); ++section)
|
||||
{
|
||||
loglevels[section] = l;
|
||||
}
|
||||
loglevel = loglevel_obj;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -142,10 +120,18 @@ void LogManager::_flush()
|
|||
{
|
||||
for(size_t msg = 0; msg < temp_messages.size(); ++msg)
|
||||
{
|
||||
int sec = temp_sections[msg];
|
||||
if(temp_levels[msg] <= loglevels[sec])
|
||||
if(temp_messages[msg]->level <= loglevel)
|
||||
{
|
||||
log_stream << temp_messages[msg] << std::endl;
|
||||
// Put the timestamp here
|
||||
log_stream << log_codes[temp_messages[msg]->level] << ": ";
|
||||
log_stream << temp_messages[msg]->buffer;
|
||||
|
||||
if(print_source)
|
||||
{
|
||||
log_stream << " [" << temp_messages[msg]->filename << ":" << temp_messages[msg]->line << "]";
|
||||
}
|
||||
|
||||
log_stream << std::endl;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -153,8 +139,6 @@ void LogManager::_flush()
|
|||
| Clear temp message buffers after writing them out |
|
||||
\*-------------------------------------------------*/
|
||||
temp_messages.clear();
|
||||
temp_levels.clear();
|
||||
temp_sections.clear();
|
||||
}
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
|
|
@ -169,78 +153,164 @@ void LogManager::flush()
|
|||
_flush();
|
||||
}
|
||||
|
||||
void LogManager::append(int section, int level, const char* fmt, ...)
|
||||
void LogManager::_append(const char* filename, int line, unsigned int level, const char* fmt, va_list va)
|
||||
{
|
||||
std::lock_guard<std::mutex> grd(entry_mutex);
|
||||
|
||||
char buf[1024];
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Start the variable argument list |
|
||||
| If a critical message occurs, enable source |
|
||||
| printing and set loglevel and verbosity to highest|
|
||||
\*-------------------------------------------------*/
|
||||
va_list va;
|
||||
va_start(va, fmt);
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Return if the log is already open |
|
||||
\*-------------------------------------------------*/
|
||||
if(!log_stream.is_open() && level > loglevels[section])
|
||||
if(level == LL_CRITICAL)
|
||||
{
|
||||
return;
|
||||
print_source = true;
|
||||
loglevel = LL_DEBUG;
|
||||
verbosity = LL_DEBUG;
|
||||
}
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Print the section to the log entry |
|
||||
| Create a new message |
|
||||
\*-------------------------------------------------*/
|
||||
int off = sprintf(buf, "[%s]: ", sections[section].c_str());
|
||||
PLogMessage mes = std::make_shared<LogMessage>();
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Print the log text to the log entry |
|
||||
| Resize the buffer, then fill in the message text |
|
||||
\*-------------------------------------------------*/
|
||||
vsnprintf(buf + off, 1024 - off, fmt, va);
|
||||
int len = vsnprintf(nullptr, 0, fmt, va);
|
||||
mes->buffer.resize(len);
|
||||
vsnprintf(&mes->buffer[0], len + 1, fmt, va);
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Write the log entry |
|
||||
| Fill in message information |
|
||||
\*-------------------------------------------------*/
|
||||
if(log_stream.is_open())
|
||||
mes->level = level;
|
||||
mes->filename = filename;
|
||||
mes->line = line;
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| If the message is within the current verbosity, |
|
||||
| print it on the screen |
|
||||
| TODO: Put the timestamp here |
|
||||
\*-------------------------------------------------*/
|
||||
if(level <= verbosity)
|
||||
{
|
||||
log_stream << buf << std::endl;
|
||||
}
|
||||
else
|
||||
{
|
||||
temp_levels.push_back(level);
|
||||
temp_messages.push_back(buf);
|
||||
temp_sections.push_back(section);
|
||||
}
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| End the variable argument list |
|
||||
\*-------------------------------------------------*/
|
||||
va_end(va);
|
||||
}
|
||||
|
||||
int LogManager::registerSection(const char* name, int loglevel)
|
||||
{
|
||||
std::lock_guard<std::mutex> grd(section_mutex);
|
||||
size_t section;
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Check to see if section already exists, if so, |
|
||||
| return the existing section value |
|
||||
\*-------------------------------------------------*/
|
||||
for(section = 0; section < sections.size(); section++)
|
||||
{
|
||||
if(sections[section] == name)
|
||||
std::cout << mes->buffer;
|
||||
if(print_source)
|
||||
{
|
||||
return section;
|
||||
std::cout << " [" << mes->filename << ":" << mes->line << "]";
|
||||
}
|
||||
std::cout << std::endl;
|
||||
}
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| If the message level is LL_MESSAGE or lower, add |
|
||||
| it to the error queue |
|
||||
\*-------------------------------------------------*/
|
||||
if(level <= LL_MESSAGE)
|
||||
{
|
||||
for(size_t idx = 0; idx < error_callbacks.size(); ++idx)
|
||||
{
|
||||
error_callbacks[idx].first(error_callbacks[idx].second, mes);
|
||||
}
|
||||
}
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| If section does not already exist, create it |
|
||||
| Add the message to the logfile queue |
|
||||
\*-------------------------------------------------*/
|
||||
sections.push_back(name);
|
||||
loglevels.push_back(loglevel);
|
||||
temp_messages.push_back(mes);
|
||||
|
||||
return section;
|
||||
/*-------------------------------------------------*\
|
||||
| Flush the queues |
|
||||
\*-------------------------------------------------*/
|
||||
_flush();
|
||||
}
|
||||
|
||||
void LogManager::append(const char* filename, int line, unsigned int level, const char* fmt, va_list va)
|
||||
{
|
||||
std::lock_guard<std::mutex> grd(entry_mutex);
|
||||
|
||||
_append(filename, line, level, fmt, va);
|
||||
}
|
||||
|
||||
void LogManager::append(const char* filename, int line, unsigned int level, const char* fmt, ...)
|
||||
{
|
||||
va_list va;
|
||||
va_start(va, fmt);
|
||||
|
||||
std::lock_guard<std::mutex> grd(entry_mutex);
|
||||
_append(filename, line, level, fmt, va);
|
||||
|
||||
va_end(va);
|
||||
}
|
||||
|
||||
void LogManager::setLoglevel(unsigned int level)
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| Check that the new log level is valid, otherwise |
|
||||
| set it within the valid range |
|
||||
\*-------------------------------------------------*/
|
||||
if(level < LL_CRITICAL)
|
||||
{
|
||||
level = LL_CRITICAL;
|
||||
}
|
||||
|
||||
if(level > LL_DEBUG)
|
||||
{
|
||||
level = LL_DEBUG;
|
||||
}
|
||||
|
||||
LOG_DEBUG("Loglevel set to %d", level);
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Set the new log level |
|
||||
\*-------------------------------------------------*/
|
||||
loglevel = level;
|
||||
}
|
||||
|
||||
void LogManager::setVerbosity(unsigned int level)
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| Check that the new verbosity is valid, otherwise |
|
||||
| set it within the valid range |
|
||||
\*-------------------------------------------------*/
|
||||
if(level < LL_CRITICAL)
|
||||
{
|
||||
level = LL_CRITICAL;
|
||||
}
|
||||
|
||||
if(level > LL_DEBUG)
|
||||
{
|
||||
level = LL_DEBUG;
|
||||
}
|
||||
|
||||
LOG_DEBUG("Verbosity set to %d", level);
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Set the new verbosity |
|
||||
\*-------------------------------------------------*/
|
||||
verbosity = level;
|
||||
}
|
||||
|
||||
void LogManager::setPrintSource(bool v)
|
||||
{
|
||||
LOG_DEBUG("Source code location printouts were %s", v ? "enabled" : "disabled");
|
||||
print_source = v;
|
||||
}
|
||||
|
||||
void LogManager::registerErrorCallback(LogErrorCallback callback, void* receiver)
|
||||
{
|
||||
std::lock_guard<std::mutex> grd(entry_mutex);
|
||||
|
||||
error_callbacks.push_back(LogErrorBlock(callback, receiver));
|
||||
}
|
||||
|
||||
void LogManager::unregisterErrorCallback(LogErrorCallback callback, void* receiver)
|
||||
{
|
||||
std::lock_guard<std::mutex> grd(entry_mutex);
|
||||
|
||||
for(size_t idx = 0; idx < error_callbacks.size(); ++idx)
|
||||
{
|
||||
if(error_callbacks[idx].first == callback && error_callbacks[idx].second == receiver)
|
||||
{
|
||||
error_callbacks.erase(error_callbacks.begin() + idx);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
72
LogManager.h
72
LogManager.h
|
|
@ -4,20 +4,35 @@
|
|||
#include <fstream>
|
||||
#include <mutex>
|
||||
#include <vector>
|
||||
#include <queue>
|
||||
#include <memory>
|
||||
#include "json.hpp"
|
||||
|
||||
using json = nlohmann::json;
|
||||
|
||||
enum
|
||||
{
|
||||
LL_CRITICAL,
|
||||
LL_ERROR,
|
||||
LL_WARNING,
|
||||
LL_NOTICE,
|
||||
LL_VERBOSE,
|
||||
LL_DEBUG
|
||||
LL_CRITICAL, // Critical unrecoverable errors that cause a generalized crash of a module or of the entire app
|
||||
LL_ERROR, // Local errors that abort an operation
|
||||
LL_MESSAGE, // Things the user should be informed of, not necessarily errors
|
||||
LL_WARNING, // Local errors that may cause an operation to have an undefined behavior or may have dangerous/unforeseen consequences
|
||||
LL_NOTICE, // Initialization messages, significant actions and follow-up information
|
||||
LL_VERBOSE, // Tracing of commands and performed actions, usually for debug purposes, comments on the higher priority messages
|
||||
LL_DEBUG, // Deep tracing, "printf-style debugging" alternative, for debug purposes. Such messages should be put all over the code instead of comments
|
||||
};
|
||||
|
||||
struct LogMessage
|
||||
{
|
||||
std::string buffer;
|
||||
unsigned int level;
|
||||
const char* filename;
|
||||
int line;
|
||||
// int timestamp or float time_offset? TBD
|
||||
};
|
||||
typedef std::shared_ptr<LogMessage> PLogMessage;
|
||||
typedef void(*LogErrorCallback)(void*, PLogMessage);
|
||||
typedef std::pair<LogErrorCallback, void*> LogErrorBlock;
|
||||
|
||||
class LogManager
|
||||
{
|
||||
private:
|
||||
|
|
@ -27,23 +42,50 @@ private:
|
|||
~LogManager();
|
||||
std::mutex entry_mutex;
|
||||
std::mutex section_mutex;
|
||||
std::vector<std::string> sections;
|
||||
std::vector<int> loglevels;
|
||||
std::ofstream log_stream;
|
||||
std::vector<std::string> temp_messages;
|
||||
std::vector<int> temp_levels;
|
||||
std::vector<int> temp_sections;
|
||||
|
||||
std::vector<LogErrorBlock> error_callbacks;
|
||||
|
||||
// A temporary log message storage to hold them until the stream opens
|
||||
std::vector<PLogMessage> temp_messages;
|
||||
|
||||
// A flag that marks if the message source file name and line number should be printed on screen
|
||||
bool print_source = false;
|
||||
|
||||
// Logfile max level
|
||||
unsigned int loglevel = LL_NOTICE;
|
||||
|
||||
// Verbosity (stdout) max level
|
||||
unsigned int verbosity = LL_WARNING;
|
||||
|
||||
// A non-guarded append()
|
||||
void _append(const char* filename, int line, unsigned int level, const char* fmt, va_list va);
|
||||
|
||||
// A non-guarded flush()
|
||||
void _flush();
|
||||
|
||||
public:
|
||||
static LogManager* get();
|
||||
void configure(json config, const std::string& defaultDir);
|
||||
void flush();
|
||||
void append(int section, int level, const char* fmt, ...);
|
||||
int registerSection(const char* name, int loglevel);
|
||||
void append(const char* filename, int line, unsigned int level, const char* fmt, va_list va);
|
||||
void append(const char* filename, int line, unsigned int level, const char* fmt, ...);
|
||||
void setLoglevel(unsigned int);
|
||||
void setVerbosity(unsigned int);
|
||||
void setPrintSource(bool);
|
||||
void registerErrorCallback(LogErrorCallback callback, void* receiver);
|
||||
void unregisterErrorCallback(LogErrorCallback callback, void* receiver);
|
||||
unsigned int getLoglevel() {return loglevel;}
|
||||
unsigned int getVerbosity() {return verbosity;}
|
||||
};
|
||||
|
||||
#define LogSection(name,level) LogManager::get()->registerSection(name, level)
|
||||
#define LogAppend LogManager::get()->append
|
||||
#define LogAppend(level, ...) LogManager::get()->append(__FILE__, __LINE__, level, __VA_ARGS__)
|
||||
#define LOG_CRITICAL(...) LogAppend(LL_CRITICAL, __VA_ARGS__)
|
||||
#define LOG_ERROR(...) LogAppend(LL_ERROR, __VA_ARGS__)
|
||||
#define LOG_MESSAGE(...) LogAppend(LL_MESSAGE, __VA_ARGS__)
|
||||
#define LOG_WARNING(...) LogAppend(LL_WARNING, __VA_ARGS__)
|
||||
#define LOG_NOTICE(...) LogAppend(LL_NOTICE, __VA_ARGS__)
|
||||
#define LOG_VERBOSE(...) LogAppend(LL_VERBOSE, __VA_ARGS__)
|
||||
#define LOG_DEBUG(...) LogAppend(LL_DEBUG, __VA_ARGS__)
|
||||
|
||||
#endif // LOGMANAGER_H
|
||||
|
|
|
|||
|
|
@ -3,9 +3,7 @@
|
|||
|
||||
void PluginManager::ScanAndLoadPlugins(bool dark_theme)
|
||||
{
|
||||
int plugin_section = LogSection("Plugins", LL_DEBUG);
|
||||
|
||||
LogAppend(plugin_section, LL_DEBUG, "Loading plugins");
|
||||
LOG_NOTICE("Loading plugins");
|
||||
|
||||
std::string OpenRGBConfigDir = ResourceManager::get()->GetConfigurationDirectory();
|
||||
|
||||
|
|
@ -33,7 +31,7 @@ void PluginManager::ScanAndLoadPlugins(bool dark_theme)
|
|||
{
|
||||
const std::string filePath = pluginsDir.absoluteFilePath(QString().fromStdString(fileName)).toStdString();
|
||||
|
||||
LogAppend(plugin_section, LL_DEBUG, "Attempting to load: %s", filePath.c_str());
|
||||
LOG_VERBOSE("Attempting to load: %s", filePath.c_str());
|
||||
|
||||
QPluginLoader loader(pluginsDir.absoluteFilePath(QString().fromStdString(fileName)));
|
||||
|
||||
|
|
@ -46,7 +44,7 @@ void PluginManager::ScanAndLoadPlugins(bool dark_theme)
|
|||
\*-----------------------------------------------------*/
|
||||
OpenRGBPlugin->info = OpenRGBPlugin->Initialize(dark_theme, ResourceManager::get());
|
||||
|
||||
LogAppend(plugin_section, LL_DEBUG, "Loaded plugin %s", OpenRGBPlugin->info.PluginName.c_str());
|
||||
LOG_VERBOSE("Loaded plugin %s", OpenRGBPlugin->info.PluginName.c_str());
|
||||
|
||||
PluginManager::ActivePlugins.push_back(OpenRGBPlugin);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -74,6 +74,7 @@ ResourceManager::~ResourceManager()
|
|||
|
||||
void ResourceManager::RegisterI2CBus(i2c_smbus_interface *bus)
|
||||
{
|
||||
LOG_NOTICE("Registering an I2C bus: %s", bus->device_name);
|
||||
busses.push_back(bus);
|
||||
}
|
||||
|
||||
|
|
@ -84,7 +85,7 @@ std::vector<i2c_smbus_interface*> & ResourceManager::GetI2CBusses()
|
|||
|
||||
void ResourceManager::RegisterRGBController(RGBController *rgb_controller)
|
||||
{
|
||||
LogAppend(LogSection("Detection", LL_DEBUG), LL_DEBUG, "Registering RGB controller: %s", rgb_controller->name.c_str());
|
||||
LOG_NOTICE("Registering RGB controller: %s", rgb_controller->name.c_str());
|
||||
rgb_controllers_hw.push_back(rgb_controller);
|
||||
|
||||
DeviceListChanged();
|
||||
|
|
@ -431,14 +432,8 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
unsigned int prev_count = 0;
|
||||
bool save_settings = false;
|
||||
std::vector<bool> size_used;
|
||||
int detection_section;
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Create a log debug section named Detection |
|
||||
\*-------------------------------------------------*/
|
||||
detection_section = LogSection("Detection", LL_DEBUG);
|
||||
|
||||
LogAppend(detection_section, LL_NOTICE, "Detection started" );
|
||||
LOG_NOTICE("Detection started");
|
||||
|
||||
size_used.resize(rgb_controllers_sizes.size());
|
||||
|
||||
|
|
@ -493,7 +488,7 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
/*-------------------------------------------------*\
|
||||
| Detect i2c busses |
|
||||
\*-------------------------------------------------*/
|
||||
LogAppend(detection_section, LL_DEBUG, "Detecting I2C/SMBus busses");
|
||||
LOG_NOTICE("Detecting I2C/SMBus busses");
|
||||
|
||||
for(unsigned int i2c_bus_detector_idx = 0; i2c_bus_detector_idx < i2c_bus_detectors.size() && detection_is_required.load(); i2c_bus_detector_idx++)
|
||||
{
|
||||
|
|
@ -504,7 +499,7 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
/*-------------------------------------------------*\
|
||||
| Detect i2c devices |
|
||||
\*-------------------------------------------------*/
|
||||
LogAppend(detection_section, LL_DEBUG, "Detecting I2C/SMBus devices");
|
||||
LOG_NOTICE("Detecting I2C/SMBus devices");
|
||||
|
||||
for(unsigned int i2c_detector_idx = 0; i2c_detector_idx < i2c_device_detectors.size() && detection_is_required.load(); i2c_detector_idx++)
|
||||
{
|
||||
|
|
@ -582,7 +577,7 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
|
||||
if(hid_safe_mode)
|
||||
{
|
||||
LogAppend(detection_section, LL_NOTICE, "Detecting HID devices in safe mode");
|
||||
LOG_NOTICE("Detecting HID devices in safe mode");
|
||||
|
||||
/*-----------------------------------------------------------------------------*\
|
||||
| Loop through all available detectors. If all required information matches, |
|
||||
|
|
@ -592,7 +587,7 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
{
|
||||
hid_devices = hid_enumerate(hid_device_detectors[hid_detector_idx].address >> 16, hid_device_detectors[hid_detector_idx].address & 0x0000FFFF);
|
||||
|
||||
LogAppend(detection_section, LL_NOTICE, "Trying to run detector for [%s] (for 0x%08hx)", hid_device_detectors[hid_detector_idx].name.c_str(), hid_device_detectors[hid_detector_idx].address);
|
||||
LOG_VERBOSE("Trying to run detector for [%s] (for 0x%08hx)", hid_device_detectors[hid_detector_idx].name.c_str(), hid_device_detectors[hid_detector_idx].address);
|
||||
|
||||
current_hid_device = hid_devices;
|
||||
|
||||
|
|
@ -662,7 +657,7 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
}
|
||||
else
|
||||
{
|
||||
LogAppend(detection_section, LL_NOTICE, "Detecting HID devices");
|
||||
LOG_NOTICE("Detecting HID devices");
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Iterate through all devices in list and run |
|
||||
|
|
@ -672,6 +667,8 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
|
||||
while(current_hid_device)
|
||||
{
|
||||
LOG_DEBUG("HID device [0x%04x:$0x%04x]", current_hid_device->vendor_id, current_hid_device->product_id);
|
||||
|
||||
detection_string = "";
|
||||
DetectionProgressChanged();
|
||||
|
||||
|
|
@ -700,6 +697,7 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
)
|
||||
{
|
||||
detection_string = hid_device_detectors[hid_detector_idx].name.c_str();
|
||||
LOG_DEBUG("Detector found: %s", detection_string);
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Check if this detector is enabled or needs to be |
|
||||
|
|
@ -713,6 +711,8 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
|
||||
if(this_device_enabled)
|
||||
{
|
||||
LOG_DEBUG("Detector %s is enabled, running it", detection_string);
|
||||
|
||||
DetectionProgressChanged();
|
||||
|
||||
hid_device_detectors[hid_detector_idx].function(current_hid_device, hid_device_detectors[hid_detector_idx].name);
|
||||
|
|
@ -744,7 +744,7 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
/*-------------------------------------------------*\
|
||||
| Detect other devices |
|
||||
\*-------------------------------------------------*/
|
||||
LogAppend(detection_section, LL_NOTICE, "Detecting other devices");
|
||||
LOG_NOTICE("Detecting other devices");
|
||||
|
||||
for(unsigned int detector_idx = 0; detector_idx < device_detectors.size() && detection_is_required.load(); detector_idx++)
|
||||
{
|
||||
|
|
@ -812,18 +812,19 @@ void ResourceManager::DetectDevicesThreadFunction()
|
|||
|
||||
if(save_settings)
|
||||
{
|
||||
LogAppend(detection_section, LL_NOTICE, "Saving detector settings");
|
||||
LOG_NOTICE("Saving detector settings");
|
||||
|
||||
settings_manager->SetSettings("Detectors", detector_settings);
|
||||
|
||||
settings_manager->SaveSettings();
|
||||
}
|
||||
|
||||
LogAppend(detection_section, LL_NOTICE, "Detection completed");
|
||||
LOG_NOTICE("Detection completed");
|
||||
}
|
||||
|
||||
void ResourceManager::StopDeviceDetection()
|
||||
{
|
||||
LOG_NOTICE("Detection abort requested");
|
||||
detection_is_required = false;
|
||||
detection_percent = 100;
|
||||
detection_string = "Stopping";
|
||||
|
|
|
|||
108
cli.cpp
108
cli.cpp
|
|
@ -10,6 +10,7 @@
|
|||
#include "i2c_smbus.h"
|
||||
#include "NetworkClient.h"
|
||||
#include "NetworkServer.h"
|
||||
#include "LogManager.h"
|
||||
|
||||
/*-------------------------------------------------------------*\
|
||||
| Quirk for MSVC; which doesn't support this case-insensitive |
|
||||
|
|
@ -370,7 +371,7 @@ void OptionHelp()
|
|||
help_text += "-s, --size [0-N] Sets the new size of the specified device zone.\n";
|
||||
help_text += " Must be specified after specifying a zone.\n";
|
||||
help_text += " If the specified size is out of range, or the zone does not offer resizing capability, the size will not be changed\n";
|
||||
help_text += "-v, --version Display version and software build information\n";
|
||||
help_text += "-V, --version Display version and software build information\n";
|
||||
help_text += "-p, --profile filename.orp Load the profile from filename.orp\n";
|
||||
help_text += "-sp, --save-profile filename.orp Save the given settings to profile filename.orp\n";
|
||||
help_text += "--i2c-tools Shows the I2C/SMBus Tools page in the GUI. Implies --gui, even if not specified.\n";
|
||||
|
|
@ -380,6 +381,10 @@ void OptionHelp()
|
|||
help_text += "--config path Use a custom path instead of the global configuration directory.\n";
|
||||
help_text += "--nodetect Do not try to detect hardware at startup.\n";
|
||||
help_text += "--noautoconnect Do not try to autoconnect to a local server at startup.\n";
|
||||
help_text += "--loglevel Set the log level (0: critical to 6: debug).\n";
|
||||
help_text += "--print-source Print the source code file and line number for each log entry.\n";
|
||||
help_text += "-v, --verbose Print log messages to stdout.\n";
|
||||
help_text += "-vv, --very-verbose Print debug messages and log messages to stdout.\n";
|
||||
|
||||
std::cout << help_text << std::endl;
|
||||
}
|
||||
|
|
@ -951,6 +956,8 @@ unsigned int cli_pre_detection(int argc, char *argv[])
|
|||
std::string option = argv[arg_index];
|
||||
std::string argument = "";
|
||||
|
||||
LOG_DEBUG("Parsing CLI option: %s", option.c_str());
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Handle options that take an argument |
|
||||
\*---------------------------------------------------------*/
|
||||
|
|
@ -1087,6 +1094,75 @@ unsigned int cli_pre_detection(int argc, char *argv[])
|
|||
arg_index++;
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| --loglevel |
|
||||
\*---------------------------------------------------------*/
|
||||
else if(option == "--loglevel")
|
||||
{
|
||||
if (argument != "")
|
||||
{
|
||||
try
|
||||
{
|
||||
int level = std::stoi(argument);
|
||||
if (level >= 0 && level <= LL_DEBUG)
|
||||
{
|
||||
LogManager::get()->setLoglevel(level);
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cout << "Error: Loglevel out of range: " << level << " (0-6)" << std::endl;
|
||||
print_help = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
catch(std::invalid_argument& e)
|
||||
{
|
||||
if(!strcasecmp(argument.c_str(), "critical"))
|
||||
{
|
||||
LogManager::get()->setLoglevel(LL_CRITICAL);
|
||||
}
|
||||
else if(!strcasecmp(argument.c_str(), "error"))
|
||||
{
|
||||
LogManager::get()->setLoglevel(LL_ERROR);
|
||||
}
|
||||
else if(!strcasecmp(argument.c_str(), "message"))
|
||||
{
|
||||
LogManager::get()->setLoglevel(LL_MESSAGE);
|
||||
}
|
||||
else if(!strcasecmp(argument.c_str(), "warning"))
|
||||
{
|
||||
LogManager::get()->setLoglevel(LL_WARNING);
|
||||
}
|
||||
else if(!strcasecmp(argument.c_str(), "notice"))
|
||||
{
|
||||
LogManager::get()->setLoglevel(LL_NOTICE);
|
||||
}
|
||||
else if(!strcasecmp(argument.c_str(), "verbose"))
|
||||
{
|
||||
LogManager::get()->setLoglevel(LL_VERBOSE);
|
||||
}
|
||||
else if(!strcasecmp(argument.c_str(), "debug"))
|
||||
{
|
||||
LogManager::get()->setLoglevel(LL_DEBUG);
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cout << "Error: invalid loglevel" << std::endl;
|
||||
print_help = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
std::cout << "Error: Missing argument for --server-port" << std::endl;
|
||||
print_help = true;
|
||||
break;
|
||||
}
|
||||
cfg_args++;
|
||||
arg_index++;
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| --gui (no arguments) |
|
||||
\*---------------------------------------------------------*/
|
||||
|
|
@ -1104,7 +1180,7 @@ unsigned int cli_pre_detection(int argc, char *argv[])
|
|||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| --startminimized |
|
||||
| --startminimized (no arguments) |
|
||||
\*---------------------------------------------------------*/
|
||||
else if(option == "--startminimized")
|
||||
{
|
||||
|
|
@ -1121,14 +1197,38 @@ unsigned int cli_pre_detection(int argc, char *argv[])
|
|||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| -v / --version (no arguments) |
|
||||
| -V / --version (no arguments) |
|
||||
\*---------------------------------------------------------*/
|
||||
else if(option == "--version" || option == "-v")
|
||||
else if(option == "--version" || option == "-V")
|
||||
{
|
||||
OptionVersion();
|
||||
exit(0);
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| -v / --verbose (no arguments) |
|
||||
\*---------------------------------------------------------*/
|
||||
else if(option == "--verbose" || option == "-v")
|
||||
{
|
||||
LogManager::get()->setVerbosity(LL_VERBOSE);
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| -vv / --very-verbose (no arguments) |
|
||||
\*---------------------------------------------------------*/
|
||||
else if(option == "--very-verbose" || option == "-vv")
|
||||
{
|
||||
LogManager::get()->setVerbosity(LL_DEBUG);
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| --print-source (no arguments) |
|
||||
\*---------------------------------------------------------*/
|
||||
else if(option == "--print-source")
|
||||
{
|
||||
LogManager::get()->setPrintSource(true);
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Any unrecognized arguments trigger the post-detection CLI |
|
||||
\*---------------------------------------------------------*/
|
||||
|
|
|
|||
51
main.cpp
51
main.cpp
|
|
@ -13,10 +13,12 @@
|
|||
#include "ProfileManager.h"
|
||||
#include "RGBController.h"
|
||||
#include "i2c_smbus.h"
|
||||
#include "LogManager.h"
|
||||
#include <vector>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <thread>
|
||||
#include <QMessageBox>
|
||||
|
||||
#include "OpenRGBDialog2.h"
|
||||
|
||||
|
|
@ -132,6 +134,50 @@ bool AttemptLocalConnection()
|
|||
return success;
|
||||
}
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* MessageBoxCallback *
|
||||
* *
|
||||
* Displays a message box when an error occurs. Only call once GUI is initialized *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void MessageBoxCallback(void*, PLogMessage message)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Create a message box |
|
||||
\*---------------------------------------------------------*/
|
||||
QMessageBox box;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set the box main text to the log message text |
|
||||
\*---------------------------------------------------------*/
|
||||
box.setText(QString::fromStdString(message->buffer));
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set the informative text from the message information |
|
||||
\*---------------------------------------------------------*/
|
||||
QString info = "Occured in ";
|
||||
info += message->filename;
|
||||
info += " on line " + QVariant(message->line).toString();
|
||||
box.setInformativeText(info);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set the message box icon according to message level |
|
||||
\*---------------------------------------------------------*/
|
||||
switch(message->level)
|
||||
{
|
||||
case LL_CRITICAL: box.setIcon(QMessageBox::Critical); break;
|
||||
case LL_ERROR: box.setIcon(QMessageBox::Warning); break;
|
||||
case LL_MESSAGE: box.setIcon(QMessageBox::Information); break;
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Show the message box |
|
||||
\*---------------------------------------------------------*/
|
||||
box.exec();
|
||||
}
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* main *
|
||||
|
|
@ -232,6 +278,11 @@ int main(int argc, char* argv[])
|
|||
QApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
|
||||
QApplication a(argc, argv);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Register the message box callback with the log manager |
|
||||
\*---------------------------------------------------------*/
|
||||
LogManager::get()->registerErrorCallback(&MessageBoxCallback, nullptr);
|
||||
|
||||
Ui::OpenRGBDialog2 dlg;
|
||||
|
||||
if(ret_flags & RET_FLAG_I2C_TOOLS)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue