mirror of
https://github.com/Cyrix126/gupaxx.git
synced 2024-11-17 07:47:35 +00:00
update: sanity check p2pool/xmrig path from user before starting
Define a strict list [&str; 4] of valid path endings for p2pool/xmrig. This prevents users (for some reason) inputting a path to some other (maybe very important) file which Gupax would have completely overridden with the update binary. Windows paths end with [.exe].
This commit is contained in:
parent
6af2ffcc16
commit
290db4b95b
3 changed files with 100 additions and 29 deletions
13
src/gupax.rs
13
src/gupax.rs
|
@ -23,9 +23,12 @@ use egui::{
|
|||
RichText,
|
||||
Vec2,
|
||||
};
|
||||
use crate::constants::*;
|
||||
use crate::disk::{Gupax,Version};
|
||||
use crate::update::*;
|
||||
use crate::{
|
||||
constants::*,
|
||||
disk::{Gupax,Version},
|
||||
update::*,
|
||||
ErrorState,ErrorFerris,ErrorButtons,
|
||||
};
|
||||
use std::{
|
||||
thread,
|
||||
sync::{Arc,Mutex},
|
||||
|
@ -75,7 +78,7 @@ pub enum Ratio {
|
|||
|
||||
//---------------------------------------------------------------------------------------------------- Gupax
|
||||
impl Gupax {
|
||||
pub fn show(&mut self, og: &Arc<Mutex<State>>, state_ver: &Arc<Mutex<Version>>, update: &Arc<Mutex<Update>>, file_window: &Arc<Mutex<FileWindow>>, state_path: &Path, width: f32, height: f32, frame: &mut eframe::Frame, ctx: &egui::Context, ui: &mut egui::Ui) {
|
||||
pub fn show(&mut self, og: &Arc<Mutex<State>>, state_path: &Path, update: &Arc<Mutex<Update>>, file_window: &Arc<Mutex<FileWindow>>, error_state: &mut ErrorState, width: f32, height: f32, frame: &mut eframe::Frame, ctx: &egui::Context, ui: &mut egui::Ui) {
|
||||
// Update button + Progress bar
|
||||
ui.group(|ui| {
|
||||
// These are in unnecessary [ui.vertical()]'s
|
||||
|
@ -88,7 +91,7 @@ impl Gupax {
|
|||
ui.vertical(|ui| {
|
||||
ui.set_enabled(!updating);
|
||||
if ui.add_sized([width, height], Button::new("Check for updates")).on_hover_text(GUPAX_UPDATE).clicked() {
|
||||
Update::spawn_thread(og, update, state_ver, state_path);
|
||||
Update::spawn_thread(og, &self, state_path, update, error_state);
|
||||
}
|
||||
});
|
||||
ui.vertical(|ui| {
|
||||
|
|
|
@ -479,7 +479,7 @@ fn init_options(initial_window_size: Option<Vec2>) -> NativeOptions {
|
|||
options
|
||||
}
|
||||
|
||||
fn init_auto(app: &App) {
|
||||
fn init_auto(app: &mut App) {
|
||||
// Return early if [--no-startup] was not passed
|
||||
if app.no_startup {
|
||||
info!("[--no-startup] flag passed, skipping init_auto()...");
|
||||
|
@ -493,7 +493,7 @@ fn init_auto(app: &App) {
|
|||
|
||||
// [Auto-Update]
|
||||
if app.state.gupax.auto_update {
|
||||
Update::spawn_thread(&app.og, &app.update, &app.state.version, &app.state_path);
|
||||
Update::spawn_thread(&app.og, &app.state.gupax, &app.state_path, &app.update, &mut app.error_state);
|
||||
} else {
|
||||
info!("Skipping auto-update...");
|
||||
}
|
||||
|
@ -636,7 +636,7 @@ fn main() {
|
|||
init_logger(now);
|
||||
let mut app = App::new();
|
||||
app.now = now;
|
||||
init_auto(&app);
|
||||
init_auto(&mut app);
|
||||
let initial_window_size = match app.state.gupax.simple {
|
||||
true => Some(Vec2::new(app.state.gupax.selected_width as f32, app.state.gupax.selected_height as f32)),
|
||||
false => Some(Vec2::new(APP_DEFAULT_WIDTH, APP_DEFAULT_HEIGHT)),
|
||||
|
@ -1001,7 +1001,7 @@ impl eframe::App for App {
|
|||
Status::show(self, self.width, self.height, ctx, ui);
|
||||
}
|
||||
Tab::Gupax => {
|
||||
Gupax::show(&mut self.state.gupax, &self.og, &self.state.version, &self.update, &self.file_window, &self.state_path, self.width, self.height, frame, ctx, ui);
|
||||
Gupax::show(&mut self.state.gupax, &self.og, &self.state_path, &self.update, &self.file_window, &mut self.error_state, self.width, self.height, frame, ctx, ui);
|
||||
}
|
||||
Tab::P2pool => {
|
||||
P2pool::show(&mut self.state.p2pool, &mut self.node_vec, &self.og, self.p2pool, &self.ping, &self.regex, self.width, self.height, ctx, ui);
|
||||
|
|
108
src/update.rs
108
src/update.rs
|
@ -27,10 +27,12 @@
|
|||
use anyhow::{anyhow,Error};
|
||||
use arti_client::{TorClient};
|
||||
use arti_hyper::*;
|
||||
use crate::constants::GUPAX_VERSION;
|
||||
//use crate::{Name::*,State};
|
||||
use crate::disk::*;
|
||||
use crate::update::Name::*;
|
||||
use crate::{
|
||||
constants::GUPAX_VERSION,
|
||||
disk::*,
|
||||
update::Name::*,
|
||||
ErrorState,ErrorFerris,ErrorButtons,
|
||||
};
|
||||
use hyper::{
|
||||
Client,Body,Request,
|
||||
header::{HeaderValue,LOCATION},
|
||||
|
@ -81,18 +83,18 @@ const P2POOL_HASH: &str = "sha256sums.txt.asc";
|
|||
const XMRIG_HASH: &str = "SHA256SUMS";
|
||||
|
||||
#[cfg(target_os = "windows")]
|
||||
const GUPAX_EXTENSION: &'static str = "-windows-x64-standalone.zip";
|
||||
const GUPAX_EXTENSION: &str = "-windows-x64-standalone.zip";
|
||||
#[cfg(target_os = "windows")]
|
||||
const P2POOL_EXTENSION: &'static str = "-windows-x64.zip";
|
||||
const P2POOL_EXTENSION: &str = "-windows-x64.zip";
|
||||
#[cfg(target_os = "windows")]
|
||||
const XMRIG_EXTENSION: &'static str = "-msvc-win64.zip";
|
||||
const XMRIG_EXTENSION: &str = "-msvc-win64.zip";
|
||||
|
||||
#[cfg(target_os = "macos")]
|
||||
const GUPAX_EXTENSION: &'static str = "-macos-x64-standalone.tar.gz";
|
||||
const GUPAX_EXTENSION: &str = "-macos-x64-standalone.tar.gz";
|
||||
#[cfg(target_os = "macos")]
|
||||
const P2POOL_EXTENSION: &'static str = "-macos-x64.tar.gz";
|
||||
const P2POOL_EXTENSION: &str = "-macos-x64.tar.gz";
|
||||
#[cfg(target_os = "macos")]
|
||||
const XMRIG_EXTENSION: &'static str = "-macos-x64.tar.gz";
|
||||
const XMRIG_EXTENSION: &str = "-macos-x64.tar.gz";
|
||||
|
||||
#[cfg(target_os = "linux")]
|
||||
const GUPAX_EXTENSION: &str = "-linux-x64-standalone.tar.gz";
|
||||
|
@ -102,22 +104,32 @@ const P2POOL_EXTENSION: &str = "-linux-x64.tar.gz";
|
|||
const XMRIG_EXTENSION: &str = "-linux-static-x64.tar.gz";
|
||||
|
||||
#[cfg(target_os = "windows")]
|
||||
const GUPAX_BINARY: &'static str = "Gupax.exe";
|
||||
const GUPAX_BINARY: &str = "Gupax.exe";
|
||||
#[cfg(target_os = "macos")]
|
||||
const GUPAX_BINARY: &'static str = "Gupax";
|
||||
const GUPAX_BINARY: &str = "Gupax";
|
||||
#[cfg(target_os = "linux")]
|
||||
const GUPAX_BINARY: &str = "gupax";
|
||||
|
||||
#[cfg(target_os = "windows")]
|
||||
const P2POOL_BINARY: &'static str = "p2pool.exe";
|
||||
const P2POOL_BINARY: &str = "p2pool.exe";
|
||||
#[cfg(target_family = "unix")]
|
||||
const P2POOL_BINARY: &str = "p2pool";
|
||||
|
||||
#[cfg(target_os = "windows")]
|
||||
const XMRIG_BINARY: &'static str = "xmrig.exe";
|
||||
const XMRIG_BINARY: &str = "xmrig.exe";
|
||||
#[cfg(target_family = "unix")]
|
||||
const XMRIG_BINARY: &str = "xmrig";
|
||||
|
||||
#[cfg(target_os = "windows")]
|
||||
const ACCEPTABLE_XMRIG: [&str; 4] = ["XMRIG.exe", "XMRig.exe", "Xmrig.exe", "xmrig.exe"];
|
||||
#[cfg(target_family = "unix")]
|
||||
const ACCEPTABLE_XMRIG: [&str; 4] = ["XMRIG", "XMRig", "Xmrig", "xmrig"];
|
||||
|
||||
#[cfg(target_os = "windows")]
|
||||
const ACCEPTABLE_P2POOL: [&str; 4] = ["P2POOL.exe", "P2Pool.exe", "P2pool.exe", "p2pool.exe"];
|
||||
#[cfg(target_family = "unix")]
|
||||
const ACCEPTABLE_P2POOL: [&str; 4] = ["P2POOL", "P2Pool", "P2pool", "p2pool"];
|
||||
|
||||
// Some fake Curl/Wget user-agents because GitHub API requires one and a Tor browser
|
||||
// user-agent might be fingerprintable without all the associated headers.
|
||||
const FAKE_USER_AGENT: [&str; 50] = [
|
||||
|
@ -253,14 +265,70 @@ impl Update {
|
|||
// actually contains the code. This is so that everytime
|
||||
// an update needs to happen (Gupax tab, auto-update), the
|
||||
// code only needs to be edited once, here.
|
||||
pub fn spawn_thread(og: &Arc<Mutex<State>>, update: &Arc<Mutex<Update>>, state_ver: &Arc<Mutex<Version>>, state_path: &Path) {
|
||||
update.lock().unwrap().path_p2pool = og.lock().unwrap().gupax.absolute_p2pool_path.display().to_string();
|
||||
update.lock().unwrap().path_xmrig = og.lock().unwrap().gupax.absolute_xmrig_path.display().to_string();
|
||||
update.lock().unwrap().tor = og.lock().unwrap().gupax.update_via_tor;
|
||||
pub fn spawn_thread(og: &Arc<Mutex<State>>, gupax: &crate::disk::Gupax, state_path: &Path, update: &Arc<Mutex<Update>>, error_state: &mut ErrorState) {
|
||||
// Check P2Pool path for safety
|
||||
// Attempt relative to absolute path
|
||||
let p2pool_path = match into_absolute_path(gupax.p2pool_path.clone()) {
|
||||
Ok(p) => p,
|
||||
Err(e) => { error_state.set("Provided P2Pool path could not be turned into an absolute path", ErrorFerris::Error, ErrorButtons::Okay); return; },
|
||||
};
|
||||
// Attempt to get basename
|
||||
let file = match p2pool_path.file_name() {
|
||||
Some(p) => {
|
||||
// Attempt to turn into str
|
||||
match p.to_str() {
|
||||
Some(p) => p,
|
||||
None => { error_state.set("Provided P2Pool path could not be turned into a UTF-8 string (are you using non-English characters?)", ErrorFerris::Error, ErrorButtons::Okay); return; },
|
||||
}
|
||||
},
|
||||
None => { error_state.set("Provided P2Pool path could not be found", ErrorFerris::Error, ErrorButtons::Okay); return; },
|
||||
};
|
||||
// If it doesn't look like [P2Pool], its probably a bad move
|
||||
// to overwrite it with an update, so set an error.
|
||||
// Doesnt seem like you can [match] on array indexes
|
||||
// so that explains the ridiculous if/else.
|
||||
if file == ACCEPTABLE_P2POOL[0] || file == ACCEPTABLE_P2POOL[1] || file == ACCEPTABLE_P2POOL[2] || file == ACCEPTABLE_P2POOL[3] {
|
||||
info!("Update | Using P2Pool path: [{}]", p2pool_path.display());
|
||||
} else {
|
||||
warn!("Update | Aborting update, incorrect P2Pool path: [{}]", file);
|
||||
let text = format!("Provided P2Pool path seems incorrect. Not starting update for safety.\nTry one of these: {:?}", ACCEPTABLE_P2POOL);
|
||||
error_state.set(text, ErrorFerris::Error, ErrorButtons::Okay);
|
||||
return;
|
||||
}
|
||||
|
||||
// Check XMRig path for safety
|
||||
let xmrig_path = match into_absolute_path(gupax.xmrig_path.clone()) {
|
||||
Ok(p) => p,
|
||||
Err(e) => { error_state.set("Provided XMRig path could not be turned into an absolute path", ErrorFerris::Error, ErrorButtons::Okay); return; },
|
||||
};
|
||||
let file = match xmrig_path.file_name() {
|
||||
Some(p) => {
|
||||
// Attempt to turn into str
|
||||
match p.to_str() {
|
||||
Some(p) => p,
|
||||
None => { error_state.set("Provided XMRig path could not be turned into a UTF-8 string (are you using non-English characters?)", ErrorFerris::Error, ErrorButtons::Okay); return; },
|
||||
}
|
||||
},
|
||||
None => { error_state.set("Provided XMRig path could not be found", ErrorFerris::Error, ErrorButtons::Okay); return; },
|
||||
};
|
||||
if file == ACCEPTABLE_XMRIG[0] || file == ACCEPTABLE_XMRIG[1] || file == ACCEPTABLE_XMRIG[2] || file == ACCEPTABLE_XMRIG[3] {
|
||||
info!("Update | Using XMRig path: [{}]", xmrig_path.display());
|
||||
} else {
|
||||
warn!("Update | Aborting update, incorrect XMRig path: [{}]", file);
|
||||
let text = format!("Provided XMRig path seems incorrect. Not starting update for safety.\nTry one of these: {:?}", ACCEPTABLE_XMRIG);
|
||||
error_state.set(text, ErrorFerris::Error, ErrorButtons::Okay);
|
||||
return;
|
||||
}
|
||||
|
||||
update.lock().unwrap().path_p2pool = p2pool_path.display().to_string();
|
||||
update.lock().unwrap().path_xmrig = xmrig_path.display().to_string();
|
||||
update.lock().unwrap().tor = gupax.update_via_tor;
|
||||
|
||||
// Clone before thread spawn
|
||||
let og = Arc::clone(og);
|
||||
let state_ver = Arc::clone(state_ver);
|
||||
let update = Arc::clone(update);
|
||||
let state_ver = Arc::clone(&og.lock().unwrap().version);
|
||||
let state_path = state_path.to_path_buf();
|
||||
let update = Arc::clone(update);
|
||||
std::thread::spawn(move|| {
|
||||
info!("Spawning update thread...");
|
||||
match Update::start(update.clone(), og.clone(), state_ver.clone()) {
|
||||
|
|
Loading…
Reference in a new issue