Merge pull request #118 from mxve/deps

Deps
This commit is contained in:
2024-07-13 19:53:04 +02:00
committed by GitHub
7 changed files with 144 additions and 22 deletions

40
Cargo.lock generated
View File

@@ -28,6 +28,7 @@ dependencies = [
"openssl", "openssl",
"rand", "rand",
"reqwest", "reqwest",
"runas",
"self-replace", "self-replace",
"semver", "semver",
"serde", "serde",
@@ -272,6 +273,12 @@ dependencies = [
"windows-sys 0.48.0", "windows-sys 0.48.0",
] ]
[[package]]
name = "either"
version = "1.13.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "60b1af1c220855b6ceac025d3f6ecdd2b7c4894bfe9cd9bda4fbb4bc7c0d4cf0"
[[package]] [[package]]
name = "encode_unicode" name = "encode_unicode"
version = "0.3.6" version = "0.3.6"
@@ -483,6 +490,15 @@ version = "0.3.2"
source = "registry+https://github.com/rust-lang/crates.io-index" source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "443144c8cdadd93ebf52ddb4056d257f5b52c04d3c804e657d19eb73fc33668b" checksum = "443144c8cdadd93ebf52ddb4056d257f5b52c04d3c804e657d19eb73fc33668b"
[[package]]
name = "home"
version = "0.5.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e3d1354bf6b7235cb4a0576c2619fd4ed18183f689b12b006a0ee7329eeff9a5"
dependencies = [
"windows-sys 0.52.0",
]
[[package]] [[package]]
name = "http" name = "http"
version = "1.1.0" version = "1.1.0"
@@ -1246,6 +1262,18 @@ dependencies = [
"windows-sys 0.52.0", "windows-sys 0.52.0",
] ]
[[package]]
name = "runas"
version = "1.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b96d6b6c505282b007a9b009f2aa38b2fd0359b81a0430ceacc60f69ade4c6a0"
dependencies = [
"libc",
"security-framework-sys",
"which",
"windows-sys 0.48.0",
]
[[package]] [[package]]
name = "rustc-demangle" name = "rustc-demangle"
version = "0.1.23" version = "0.1.23"
@@ -1948,6 +1976,18 @@ dependencies = [
"wasm-bindgen", "wasm-bindgen",
] ]
[[package]]
name = "which"
version = "4.4.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "87ba24419a2078cd2b0f2ede2691b6c66d8e47836da3b6db8265ebad47afbfc7"
dependencies = [
"either",
"home",
"once_cell",
"rustix",
]
[[package]] [[package]]
name = "winapi" name = "winapi"
version = "0.3.9" version = "0.3.9"

View File

@@ -30,6 +30,7 @@ openssl = { version = "0.10.64", default-features = false, features = ["vendored
steamlocate = "=2.0.0-beta.2" steamlocate = "=2.0.0-beta.2"
mslnk = "0.1.8" mslnk = "0.1.8"
self-replace = "1.3.7" self-replace = "1.3.7"
runas = "1.2.0"
[build-dependencies] [build-dependencies]
winresource = "0.1.17" winresource = "0.1.17"

View File

@@ -8,6 +8,10 @@
--- ---
**Only legitimate copies of the games are supported. If you don't own the game, please buy it.**
---
## Installation ## Installation
1. Download the game from [Steam](https://store.steampowered.com/) 1. Download the game from [Steam](https://store.steampowered.com/)
@@ -22,6 +26,8 @@
- ```iw4-sp```, ```iw4x```, ```iw5-mod```, ```iw6-mod```, ```s1-mod``` - ```iw4-sp```, ```iw4x```, ```iw5-mod```, ```iw6-mod```, ```s1-mod```
- Skip automatic detection and launch the specified game - Skip automatic detection and launch the specified game
- This should always be the first argument if used - This should always be the first argument if used
- ```--help```
- Print help
- ```--update```, ```-u``` - ```--update```, ```-u```
- Only update the game, don't launch it - Only update the game, don't launch it
- ```--skip-launcher-update``` - ```--skip-launcher-update```
@@ -40,6 +46,10 @@
- Print the launcher version - Print the launcher version
- ```--ignore-required-files``` - ```--ignore-required-files```
- Install client even if required files are missing - Install client even if required files are missing
- ```--skip-redist```
- Skip redistributable installation
- ```--redist```
- (Re-)install redistributables
Example: ```alterware-launcher.exe iw4x --bonus -u --path "C:\Games\IW4x" --pass "-console"``` Example: ```alterware-launcher.exe iw4x --bonus -u --path "C:\Games\IW4x" --pass "-console"```

View File

@@ -37,6 +37,7 @@ pub fn save_value(config_path: PathBuf, key: &str, value: bool) {
"ask_bonus_content" => config.ask_bonus_content = value, "ask_bonus_content" => config.ask_bonus_content = value,
"force_update" => config.force_update = value, "force_update" => config.force_update = value,
"use_https" => config.use_https = value, "use_https" => config.use_https = value,
"skip_redist" => config.skip_redist = value,
_ => (), _ => (),
} }
save(config_path, config); save(config_path, config);

View File

@@ -167,28 +167,6 @@ async fn windows_launcher_install(games: &Vec<Game<'_>>, master_url: &String) {
} }
} }
// fn prompt_client_selection(games: &[Game]) -> String {
// println!(
// "Couldn't detect any games, please select a client to install in the current directory:"
// );
// for (i, g) in games.iter().enumerate() {
// for c in g.client.iter() {
// println!("{}: {}", i, c);
// }
// }
// let input: usize = misc::stdin().parse().unwrap();
// String::from(games[input].client[0])
// }
// async fn manual_install(games: &[Game<'_>]) {
// let selection = prompt_client_selection(games);
// let game = games.iter().find(|&g| g.client[0] == selection).unwrap();
// update(game, &env::current_dir().unwrap(), false, false).await;
// println!("Installation complete. Please run the launcher again or use a shortcut to launch the game.");
// std::io::stdin().read_line(&mut String::new()).unwrap();
// std::process::exit(0);
// }
fn total_download_size(cdn_info: &Vec<CdnFile>, remote_dir: &str) -> u64 { fn total_download_size(cdn_info: &Vec<CdnFile>, remote_dir: &str) -> u64 {
let remote_dir = format!("{}/", remote_dir); let remote_dir = format!("{}/", remote_dir);
let mut size: u64 = 0; let mut size: u64 = 0;
@@ -598,6 +576,8 @@ async fn main() {
println!(" --pass <args>: Pass arguments to the game"); println!(" --pass <args>: Pass arguments to the game");
println!(" --skip-launcher-update: Skip launcher self-update"); println!(" --skip-launcher-update: Skip launcher self-update");
println!(" --ignore-required-files: Skip required files check"); println!(" --ignore-required-files: Skip required files check");
println!(" --skip-redist: Skip redistributable installation");
println!(" --redist: (Re-)Install redistributables");
println!( println!(
"\nExample:\n alterware-launcher.exe iw4x --bonus --pass \"-console -nointro\"" "\nExample:\n alterware-launcher.exe iw4x --bonus --pass \"-console -nointro\""
); );
@@ -679,6 +659,20 @@ async fn main() {
cfg.args = String::default(); cfg.args = String::default();
} }
if arg_bool(&args, "--skip-redist") {
cfg.skip_redist = true;
arg_remove(&mut args, "--skip-redist");
}
#[cfg(windows)]
if arg_bool(&args, "--redist") {
arg_remove(&mut args, "--redist");
misc::install_dependencies(&install_path).await;
println_info!("Redistributables installation finished. Press enter to exit...");
misc::stdin();
std::process::exit(0);
}
let games_json = http_async::get_body_string(format!("{}/games.json", master_url).as_str()) let games_json = http_async::get_body_string(format!("{}/games.json", master_url).as_str())
.await .await
.unwrap(); .unwrap();
@@ -738,6 +732,11 @@ async fn main() {
cfg.args.clone(), cfg.args.clone(),
); );
} }
#[cfg(windows)]
if !cfg.skip_redist {
misc::install_dependencies(&install_path).await;
}
} }
if cfg.engine == "iw4" && !cfg.args.contains("+set logfile 1") { if cfg.engine == "iw4" && !cfg.args.contains("+set logfile 1") {

View File

@@ -85,3 +85,71 @@ macro_rules! println_error {
error!($($arg)*); error!($($arg)*);
}} }}
} }
#[cfg(windows)]
fn install_dependency(path: &Path, args: &[&str]) {
if path.exists() {
match runas::Command::new(path).args(args).status() {
Ok(status) => {
if !status.success() && !matches!(status.code(), Some(1638) | Some(3010)) {
println_error!("Error installing dependency {}, {}", path.display(), status);
} else {
info!("{} installed successfully", path.display());
}
}
Err(e) => {
if let Some(740) = e.raw_os_error() {
println_error!(
"Error: Process requires elevation. Please run the launcher as administrator or install {} manually",
path.display()
);
} else {
println_error!("Error running file {}: {}", path.display(), e);
}
}
}
} else {
println_error!("Installer not found: {}", path.display());
}
}
#[cfg(windows)]
async fn download_and_install_dependency(url: &str, path: &Path, args: &[&str]) {
if !path.exists() {
info!("Downloading {} from {}", path.display(), url);
if let Some(parent) = path.parent() {
match fs::create_dir_all(parent) {
Ok(_) => (),
Err(e) => {
println_error!("Error creating directory {}: {}", parent.display(), e);
return;
}
}
}
match crate::http_async::download_file(url, &PathBuf::from(path)).await {
Ok(_) => info!("Downloaded {}", path.display()),
Err(e) => println_error!("Error downloading {}: {}", path.display(), e),
}
}
install_dependency(path, args);
}
#[cfg(windows)]
pub async fn install_dependencies(install_path: &Path) {
println!("If you run into issues during dependency installation, open alterware-launcher.json and set \"skip_redist\" to true");
let redist_dir = install_path.join("redist\\alterware");
let redists = [
("VC++ 2005", "https://download.microsoft.com/download/8/B/4/8B42259F-5D70-43F4-AC2E-4B208FD8D66A/vcredist_x86.EXE", "vcredist_2005_x86.exe", &["/Q"] as &[&str]),
("VC++ 2008", "https://download.microsoft.com/download/5/D/8/5D8C65CB-C849-4025-8E95-C3966CAFD8AE/vcredist_x86.exe", "vcredist_2008_x86.exe", &["/Q"] as &[&str]),
("VC++ 2010", "https://download.microsoft.com/download/1/6/5/165255E7-1014-4D0A-B094-B6A430A6BFFC/vcredist_x86.exe", "vcredist_2010_x86.exe", &["/Q"] as &[&str]),
("VC++ 2015", "https://download.microsoft.com/download/9/3/F/93FCF1E7-E6A4-478B-96E7-D4B285925B00/vc_redist.x86.exe", "vcredist_2015_x86.exe", &["/install", "/passive", "/norestart"] as &[&str]),
("DirectX End User Runtime", "https://download.microsoft.com/download/1/7/1/1718CCC4-6315-4D8E-9543-8E28A4E18C4C/dxwebsetup.exe", "dxwebsetup.exe", &["/Q"] as &[&str]),
];
for (name, url, file, args) in redists.iter() {
let path = redist_dir.join(file);
println_info!("Installing {}", name);
download_and_install_dependency(url, &path, args).await;
}
}

View File

@@ -43,6 +43,8 @@ pub struct Config {
pub engine: String, pub engine: String,
#[serde(default)] #[serde(default)]
pub use_https: bool, pub use_https: bool,
#[serde(default)]
pub skip_redist: bool,
} }
impl Default for Config { impl Default for Config {
@@ -56,6 +58,7 @@ impl Default for Config {
args: String::default(), args: String::default(),
engine: String::default(), engine: String::default(),
use_https: true, use_https: true,
skip_redist: false,
} }
} }
} }