Skip to content

Commit

Permalink
parse: don't allow ANSI colors escape sequences in gui colors
Browse files Browse the repository at this point in the history
also some tweaks with config
  • Loading branch information
Toni500github committed Jun 22, 2024
1 parent 5102de9 commit 3b56cfc
Show file tree
Hide file tree
Showing 4 changed files with 64 additions and 37 deletions.
22 changes: 4 additions & 18 deletions include/config.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@
#define TOML_HEADER_ONLY 0

#include <array>
#include <unordered_map>

#include "fmt/color.h"
#include "toml++/toml.hpp"
Expand Down Expand Up @@ -46,7 +45,9 @@ struct colors_t

class Config
{
public:
public:
Config( const std::string_view configFile, const std::string_view configDir, colors_t& colors );

// config file
std::string source_path;
u_short offset = 0;
Expand All @@ -55,39 +56,24 @@ class Config
std::vector<std::string> includes;

// inner management
std::unordered_map<std::string, strOrBool> overrides;
std::string m_custom_distro;
bool m_disable_source = false;
bool m_display_distro = true;

// initialize Config, can only be ran once for each Config instance.
void init( const std::string_view& configFile, const std::string_view& configDir, colors_t& colors );
void loadConfigFile( std::string_view filename, colors_t& colors );
std::string getThemeValue( const std::string& value, const std::string& fallback );

template <typename T>
T getConfigValue( const std::string& value, T&& fallback )
{
auto overridePos = overrides.find( value );

// user wants a bool (overridable), we found an override matching the name, and the override is a bool.
if constexpr ( std::is_same<T, bool>() )
if ( overridePos != overrides.end() && overrides[value].valueType == BOOL )
return overrides[value].boolValue;

// user wants a str (overridable), we found an override matching the name, and the override is a str.
if constexpr ( std::is_same<T, std::string>() )
if ( overridePos != overrides.end() && overrides[value].valueType == STR )
return overrides[value].stringValue;

std::optional<T> ret = this->tbl.at_path( value ).value<T>();
if constexpr ( toml::is_string<T> ) // if we want to get a value that's a string
return ret ? expandVar( ret.value() ) : expandVar( fallback );
else
return ret.value_or( fallback );
}

private:
private:
toml::table tbl;
};

Expand Down
2 changes: 1 addition & 1 deletion src/config.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
#include <iostream>

// initialize Config, can only be ran once for each Config instance.
void Config::init(const std::string_view& configFile, const std::string_view& configDir, colors_t& colors) {
Config::Config(const std::string_view configFile, const std::string_view configDir, colors_t& colors) {

if (!std::filesystem::exists(configDir)) {
fmt::println("customfetch config folder was not found, Creating folders at {}!", configDir);
Expand Down
54 changes: 44 additions & 10 deletions src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -71,9 +71,42 @@ cpu
std::exit(0);
}

static bool parseargs(int argc, char* argv[], Config& config, std::string& configFile) {
// parseargs() but only for parsing the user config path trough args
// and so we can directly construct Config
static bool parse_config_path(int argc, char* argv[], std::string& configFile) {
int opt = 0;
int option_index = 0;
opterr = 0;
const char *optstring = "C:";
static const struct option opts[] =
{
{"config", required_argument, 0, 'C'},
{0,0,0,0}
};

while ((opt = getopt_long(argc, argv, optstring, opts, &option_index)) != -1) {
if (opt == 0 || opt == '?')
continue;

switch (opt) {
case 'C':
configFile = strndup(optarg, PATH_MAX);
if (!std::filesystem::exists(configFile))
die("config file '{}' doesn't exist", configFile);

break;
default:
return false;
}
}

return true;
}

static bool parseargs(int argc, char* argv[], Config& config) {
int opt = 0;
int option_index = 0;
opterr = 1; // re-enable since before we disabled for "invalid option" error
const char *optstring = "VhnlgC:d:s:";
static const struct option opts[] =
{
Expand All @@ -89,6 +122,7 @@ static bool parseargs(int argc, char* argv[], Config& config, std::string& confi
};

/* parse operation */
optind = 0;
while ((opt = getopt_long(argc, argv, optstring, opts, &option_index)) != -1) {
if (opt == 0)
continue;
Expand All @@ -105,13 +139,13 @@ static bool parseargs(int argc, char* argv[], Config& config, std::string& confi
case 'l':
components_list(); break;
case 'g':
config.overrides["gui.enable"] = {BOOL, "", true}; break;
case 'C':
configFile = strndup(optarg, PATH_MAX); break;
config.gui = true; break;
case 'C': // we have already did it in parse_config_path()
continue;
case 'd':
config.m_custom_distro = str_tolower(strndup(optarg, PATH_MAX)); break;
case 's':
config.overrides["config.source-path"] = {STR, strndup(optarg, PATH_MAX)}; break;
config.source_path = strndup(optarg, PATH_MAX); break;
default:
return false;
}
Expand Down Expand Up @@ -169,16 +203,16 @@ int main (int argc, char *argv[]) {
fmt::println("NVIDIA: {}", binarySearchPCIArray("10de"));
#endif

Config config;
struct colors_t colors;

std::string configDir = getConfigDir();
std::string configFile = configDir + "/config.toml";
std::string configFile = configDir + "/config.toml";
parse_config_path(argc, argv, configFile);

Config config(configFile, configDir, colors);

if (!parseargs(argc, argv, config, configFile))
if (!parseargs(argc, argv, config))
return 1;

config.init(configFile, configDir, colors);

if ( config.source_path.empty() || config.source_path == "off" )
config.m_disable_source = true;
Expand Down
23 changes: 15 additions & 8 deletions src/query.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,13 @@ static std::array<std::string, 3> get_ansi_color( const std::string_view str, co
return { col, weight, type };
}

static std::string check_gui_ansi_clr(std::string& str) {
if (hasStart(str, "\033") || hasStart(str, "\\e"))
die("GUI colors can't be in ANSI escape sequence");

return str;
}

static std::string getInfoFromName( systemInfo_t& systemInfo, const std::string& name )
{
std::vector<std::string> sections = split( name, '.' );
Expand Down Expand Up @@ -213,14 +220,14 @@ std::string parse( const std::string& input, systemInfo_t& systemInfo, const std
{
switch ( fnv1a32::hash(command) )
{
case "black"_fnv1a32: str_clr = colors.gui_black; break;
case "red"_fnv1a32: str_clr = colors.gui_red;break;
case "blue"_fnv1a32: str_clr = colors.gui_blue; break;
case "green"_fnv1a32: str_clr = colors.gui_green; break;
case "cyan"_fnv1a32: str_clr = colors.gui_cyan; break;
case "yellow"_fnv1a32: str_clr = colors.gui_yellow; break;
case "magenta"_fnv1a32: str_clr = colors.gui_magenta; break;
case "white"_fnv1a32: str_clr = colors.gui_white; break;
case "black"_fnv1a32: str_clr = check_gui_ansi_clr(colors.gui_black); break;
case "red"_fnv1a32: str_clr = check_gui_ansi_clr(colors.gui_red); break;
case "blue"_fnv1a32: str_clr = check_gui_ansi_clr(colors.gui_blue); break;
case "green"_fnv1a32: str_clr = check_gui_ansi_clr(colors.gui_green); break;
case "cyan"_fnv1a32: str_clr = check_gui_ansi_clr(colors.gui_cyan); break;
case "yellow"_fnv1a32: str_clr = check_gui_ansi_clr(colors.gui_yellow); break;
case "magenta"_fnv1a32: str_clr = check_gui_ansi_clr(colors.gui_magenta);break;
case "white"_fnv1a32: str_clr = check_gui_ansi_clr(colors.gui_white); break;
default:
str_clr = command;
break;
Expand Down

0 comments on commit 3b56cfc

Please sign in to comment.