2020-04-27 09:43:05 -04:00
|
|
|
#include "pch.h"
|
|
|
|
|
#include "utility.h"
|
|
|
|
|
#include "conf.h"
|
|
|
|
|
#include "op.h"
|
2020-04-29 16:42:50 -04:00
|
|
|
#include "net.h"
|
2020-05-02 02:46:51 -04:00
|
|
|
#include "process.h"
|
2020-05-03 03:32:40 -04:00
|
|
|
#include "context.h"
|
2020-04-27 09:43:05 -04:00
|
|
|
|
2020-05-02 03:12:34 -04:00
|
|
|
namespace mob
|
2020-04-27 09:43:05 -04:00
|
|
|
{
|
|
|
|
|
|
|
|
|
|
std::string replace_all(
|
|
|
|
|
std::string s, const std::string& from, const std::string& to)
|
|
|
|
|
{
|
|
|
|
|
for (;;)
|
|
|
|
|
{
|
|
|
|
|
const auto pos = s.find(from);
|
|
|
|
|
if (pos == std::string::npos)
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
s.replace(pos, from.size(), to);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return s;
|
|
|
|
|
}
|
|
|
|
|
|
2020-04-28 22:14:47 -04:00
|
|
|
std::string join(const std::vector<std::string>& v, const std::string& sep)
|
|
|
|
|
{
|
|
|
|
|
std::string s;
|
|
|
|
|
|
|
|
|
|
for (auto&& e : v)
|
|
|
|
|
{
|
|
|
|
|
if (!s.empty())
|
|
|
|
|
s += sep;
|
|
|
|
|
|
|
|
|
|
s += e;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return s;
|
|
|
|
|
}
|
|
|
|
|
|
2020-05-04 03:02:33 -04:00
|
|
|
std::string pad_right(std::string s, std::size_t n, char c)
|
2020-05-04 01:13:11 -04:00
|
|
|
{
|
|
|
|
|
if (s.size() < n)
|
2020-05-04 03:02:33 -04:00
|
|
|
s.append(n - s.size() , c);
|
|
|
|
|
|
|
|
|
|
return s;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
std::string pad_left(std::string s, std::size_t n, char c)
|
|
|
|
|
{
|
|
|
|
|
if (s.size() < n)
|
|
|
|
|
s.insert(s.begin(), n - s.size() , c);
|
2020-04-29 19:56:36 -04:00
|
|
|
|
2020-05-04 01:13:11 -04:00
|
|
|
return s;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
file_deleter::file_deleter(const context& cx, fs::path p)
|
2020-05-03 05:42:56 -04:00
|
|
|
: cx_(cx), p_(std::move(p)), delete_(true)
|
2020-04-28 19:29:05 -04:00
|
|
|
{
|
2020-05-04 01:13:11 -04:00
|
|
|
cx_.trace(context::fs, "will delete " + p_.string() + " if things go bad");
|
2020-04-28 19:29:05 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
file_deleter::~file_deleter()
|
|
|
|
|
{
|
|
|
|
|
if (delete_)
|
|
|
|
|
delete_now();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void file_deleter::delete_now()
|
|
|
|
|
{
|
2020-05-04 01:13:11 -04:00
|
|
|
cx_.debug(context::fs, "something went bad, deleting " + p_.string());
|
|
|
|
|
op::delete_file(cx_, p_, op::optional);
|
2020-04-28 19:29:05 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void file_deleter::cancel()
|
|
|
|
|
{
|
2020-05-04 01:13:11 -04:00
|
|
|
cx_.trace(context::fs, "everything okay, keeping " + p_.string());
|
2020-04-28 19:29:05 -04:00
|
|
|
delete_ = false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
2020-05-04 01:13:11 -04:00
|
|
|
directory_deleter::directory_deleter(const context& cx, fs::path p)
|
2020-05-03 05:42:56 -04:00
|
|
|
: cx_(cx), p_(std::move(p)), delete_(true)
|
2020-04-28 19:29:05 -04:00
|
|
|
{
|
2020-05-04 01:13:11 -04:00
|
|
|
cx_.trace(context::fs, "will delete " + p_.string() + " if things go bad");
|
2020-04-28 19:29:05 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
directory_deleter::~directory_deleter()
|
|
|
|
|
{
|
|
|
|
|
if (delete_)
|
|
|
|
|
delete_now();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void directory_deleter::delete_now()
|
|
|
|
|
{
|
2020-05-04 01:13:11 -04:00
|
|
|
cx_.debug(context::fs, "something went bad, deleting " + p_.string());
|
|
|
|
|
op::delete_directory(cx_, p_, op::optional);
|
2020-04-28 19:29:05 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void directory_deleter::cancel()
|
|
|
|
|
{
|
2020-05-04 01:13:11 -04:00
|
|
|
cx_.trace(context::fs, "everything okay, keeping " + p_.string());
|
2020-04-28 19:29:05 -04:00
|
|
|
delete_ = false;
|
|
|
|
|
}
|
|
|
|
|
|
2020-05-03 05:42:56 -04:00
|
|
|
|
|
|
|
|
interruption_file::interruption_file(
|
2020-05-04 01:13:11 -04:00
|
|
|
const context& cx, fs::path dir, std::string name)
|
2020-05-03 05:42:56 -04:00
|
|
|
: cx_(cx), dir_(std::move(dir)), name_(std::move(name))
|
|
|
|
|
{
|
|
|
|
|
if (fs::exists(file()))
|
2020-05-04 03:27:22 -04:00
|
|
|
{
|
|
|
|
|
cx_.trace(context::interruption,
|
|
|
|
|
"found interrupt file " + file().string());
|
|
|
|
|
}
|
2020-05-03 05:42:56 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool interruption_file::exists() const
|
|
|
|
|
{
|
|
|
|
|
return fs::exists(file());
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
fs::path interruption_file::file() const
|
|
|
|
|
{
|
|
|
|
|
return dir_ / ("_mo_interrupted_" + name_);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void interruption_file::create()
|
|
|
|
|
{
|
2020-05-04 03:27:22 -04:00
|
|
|
cx_.trace(context::interruption,
|
|
|
|
|
"creating interrupt file " + file().string());
|
|
|
|
|
|
2020-05-04 01:13:11 -04:00
|
|
|
op::touch(cx_, file());
|
2020-05-03 05:42:56 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void interruption_file::remove()
|
|
|
|
|
{
|
2020-05-04 03:27:22 -04:00
|
|
|
cx_.trace(context::interruption,
|
|
|
|
|
"removing interrupt file " + file().string());
|
|
|
|
|
|
2020-05-04 01:13:11 -04:00
|
|
|
op::delete_file(cx_, file());
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
2020-05-04 08:02:43 -04:00
|
|
|
bypass_file::bypass_file(const context& cx, fs::path dir, std::string name)
|
|
|
|
|
: cx_(cx), file_(dir / ("_mob_" + name))
|
|
|
|
|
{
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
bool bypass_file::exists() const
|
|
|
|
|
{
|
|
|
|
|
if (fs::exists(file_))
|
|
|
|
|
{
|
|
|
|
|
if (conf::rebuild())
|
|
|
|
|
{
|
|
|
|
|
cx_.trace(context::bypass,
|
|
|
|
|
"bypass file " + file_.string() + " exists, deleting");
|
|
|
|
|
|
|
|
|
|
op::delete_file(cx_, file_, op::optional);
|
|
|
|
|
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
cx_.trace(context::bypass,
|
|
|
|
|
"bypass file " + file_.string() + " exists");
|
|
|
|
|
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
cx_.trace(context::bypass,
|
|
|
|
|
"bypass file " + file_.string() + " not found");
|
|
|
|
|
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void bypass_file::create()
|
|
|
|
|
{
|
|
|
|
|
cx_.trace(context::bypass,
|
|
|
|
|
"create bypass file " + file_.string());
|
|
|
|
|
|
|
|
|
|
op::touch(cx_, file_);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
2020-05-04 01:13:11 -04:00
|
|
|
enum class color_methods
|
|
|
|
|
{
|
|
|
|
|
none = 0,
|
|
|
|
|
ansi,
|
|
|
|
|
console
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
static color_methods g_color_method = []
|
|
|
|
|
{
|
|
|
|
|
DWORD d = 0;
|
|
|
|
|
if (GetConsoleMode(GetStdHandle(STD_OUTPUT_HANDLE), &d))
|
|
|
|
|
{
|
|
|
|
|
if ((d & ENABLE_VIRTUAL_TERMINAL_PROCESSING) == 0)
|
|
|
|
|
return color_methods::console;
|
|
|
|
|
else
|
|
|
|
|
return color_methods::ansi;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return color_methods::none;
|
|
|
|
|
}();
|
|
|
|
|
|
|
|
|
|
console_color::console_color()
|
|
|
|
|
: reset_(false), old_atts_(0)
|
|
|
|
|
{
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
console_color::console_color(colors c)
|
|
|
|
|
: reset_(false), old_atts_(0)
|
|
|
|
|
{
|
|
|
|
|
if (g_color_method == color_methods::ansi)
|
|
|
|
|
{
|
|
|
|
|
switch (c)
|
|
|
|
|
{
|
|
|
|
|
case colors::white:
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case colors::grey:
|
|
|
|
|
reset_ = true;
|
|
|
|
|
std::cout << "\033[38;2;150;150;150m";
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case colors::yellow:
|
|
|
|
|
reset_ = true;
|
|
|
|
|
std::cout << "\033[38;2;240;240;50m";
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case colors::red:
|
|
|
|
|
reset_ = true;
|
|
|
|
|
std::cout << "\033[38;2;240;50;50m";
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
else if (g_color_method == color_methods::console)
|
|
|
|
|
{
|
|
|
|
|
CONSOLE_SCREEN_BUFFER_INFO bi = {};
|
|
|
|
|
GetConsoleScreenBufferInfo(GetStdHandle(STD_OUTPUT_HANDLE), &bi);
|
|
|
|
|
old_atts_ = bi.wAttributes;
|
|
|
|
|
|
|
|
|
|
WORD atts = 0;
|
|
|
|
|
|
|
|
|
|
switch (c)
|
|
|
|
|
{
|
|
|
|
|
case colors::white:
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case colors::grey:
|
|
|
|
|
reset_ = true;
|
|
|
|
|
atts = FOREGROUND_BLUE|FOREGROUND_GREEN|FOREGROUND_RED;
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case colors::yellow:
|
|
|
|
|
reset_ = true;
|
|
|
|
|
atts = FOREGROUND_GREEN|FOREGROUND_RED;
|
|
|
|
|
break;
|
|
|
|
|
|
|
|
|
|
case colors::red:
|
|
|
|
|
reset_ = true;
|
|
|
|
|
atts = FOREGROUND_RED;
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (atts != 0)
|
|
|
|
|
SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), atts);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
console_color::~console_color()
|
|
|
|
|
{
|
|
|
|
|
if (!reset_)
|
|
|
|
|
return;
|
|
|
|
|
|
|
|
|
|
if (g_color_method == color_methods::ansi)
|
|
|
|
|
{
|
|
|
|
|
std::cout << "\033[39m\033[49m";
|
|
|
|
|
}
|
|
|
|
|
else if (g_color_method == color_methods::console)
|
|
|
|
|
{
|
|
|
|
|
SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), old_atts_);
|
|
|
|
|
}
|
2020-05-03 05:42:56 -04:00
|
|
|
}
|
|
|
|
|
|
2020-04-27 09:43:05 -04:00
|
|
|
} // namespace
|
2020-05-04 01:13:11 -04:00
|
|
|
|