myph-v2~ rust shellcode loader with evasive capabilities |
| git clone https://github.com/djnnvx/myph-v2.git |
| log | files | refs | archive | README |
env_setup.rs (5845B)
1 //! Environment Setup Module 2 //! 3 //! Handles the initialization and setup of the build environment for generating 4 //! shellcode loaders. This includes verifying prerequisites, creating temporary 5 //! directories, and managing the working directory. 6 //! 7 //! # Workflow 8 //! 9 //! 1. Verify cargo is installed and accessible 10 //! 2. Create a unique temporary directory for the build 11 //! 3. Change the working directory to the temp location 12 //! 13 //! # Safety 14 //! 15 //! Functions that modify the working directory are not thread-safe. Tests that 16 //! use these functions must serialize using `TEST_DIR_MUTEX` to prevent race 17 //! conditions. 18 //! 19 //! # Example 20 //! 21 //! ```no_run 22 //! use myph_v2::env_setup::setup_environment; 23 //! 24 //! let temp_dir = setup_environment().expect("Failed to setup environment"); 25 //! println!("Build directory: {:?}", temp_dir); 26 //! ``` 27 28 use std::env; 29 use std::io; 30 use std::path::PathBuf; 31 use std::process::Command; 32 33 /// Check if cargo is installed on the system 34 /// 35 /// Returns `Ok(())` if cargo is installed and accessible via PATH, 36 /// otherwise returns an error. 37 pub fn check_cargo_installed() -> io::Result<()> { 38 let status = Command::new("cargo") 39 .arg("--version") 40 .stdout(std::process::Stdio::null()) 41 .stderr(std::process::Stdio::null()) 42 .status()?; 43 44 if status.success() { 45 Ok(()) 46 } else { 47 Err(io::Error::new( 48 io::ErrorKind::NotFound, 49 "cargo command failed to execute", 50 )) 51 } 52 } 53 54 /// Create a temporary directory and return its path 55 /// 56 /// Creates a new temporary directory with a unique name in the system temp directory. 57 /// Note: The directory will NOT be automatically cleaned up and must be 58 /// manually removed when no longer needed. 59 /// 60 /// Returns the path to the newly created temporary directory. 61 pub fn create_temp_directory() -> io::Result<PathBuf> { 62 let base_temp_dir = env::temp_dir(); 63 64 let unique_dir = base_temp_dir.join(format!("myph-{}", rand::random::<u32>())); 65 66 std::fs::create_dir_all(&unique_dir)?; 67 68 Ok(unique_dir) 69 } 70 71 /// Change the current working directory to the specified path 72 /// 73 /// # Arguments 74 /// 75 /// * `path` - The path to change to 76 /// 77 /// Returns `Ok(())` if successful, otherwise returns an error. 78 pub fn change_working_directory(path: &PathBuf) -> io::Result<()> { 79 env::set_current_dir(path)?; 80 Ok(()) 81 } 82 83 /// Setup the environment for running the application 84 /// 85 /// This function performs the following steps: 86 /// 1. Checks if cargo is installed 87 /// 2. Creates a temporary directory 88 /// 3. Changes the working directory to the temporary directory 89 /// 90 /// Returns the path to the temporary directory if successful, 91 /// otherwise returns an error describing what went wrong. 92 pub fn setup_environment() -> io::Result<PathBuf> { 93 check_cargo_installed().map_err(|e| { 94 io::Error::new( 95 io::ErrorKind::NotFound, 96 format!("cargo is not installed or not in PATH: {}", e), 97 ) 98 })?; 99 100 let temp_dir = create_temp_directory()?; 101 102 change_working_directory(&temp_dir)?; 103 104 Ok(temp_dir) 105 } 106 107 #[cfg(test)] 108 mod tests { 109 use super::*; 110 use crate::TEST_DIR_MUTEX; 111 use std::env; 112 113 #[test] 114 fn test_check_cargo_installed() { 115 // This test assumes cargo is installed in the test environment 116 let result = check_cargo_installed(); 117 assert!( 118 result.is_ok(), 119 "cargo should be installed in test environment" 120 ); 121 } 122 123 #[test] 124 fn test_create_temp_directory() { 125 let result = create_temp_directory(); 126 assert!(result.is_ok(), "should be able to create temp directory"); 127 128 let temp_path = result.unwrap(); 129 assert!(temp_path.exists(), "temp directory should exist"); 130 assert!(temp_path.is_dir(), "temp path should be a directory"); 131 132 // Clean up 133 let _ = std::fs::remove_dir_all(&temp_path); 134 } 135 136 #[test] 137 fn test_change_working_directory() { 138 let _lock = TEST_DIR_MUTEX.lock().unwrap_or_else(|e| e.into_inner()); 139 140 // Save current directory 141 let original_dir = env::current_dir().unwrap(); 142 143 // Create a temp directory 144 let temp_dir = create_temp_directory().unwrap(); 145 146 // Change to it 147 let result = change_working_directory(&temp_dir); 148 assert!(result.is_ok(), "should be able to change directory"); 149 150 // Verify we're in the new directory 151 let current_dir = env::current_dir().unwrap(); 152 assert_eq!(current_dir, temp_dir, "should be in temp directory"); 153 154 // Clean up - change back to original directory 155 let _ = env::set_current_dir(&original_dir); 156 let _ = std::fs::remove_dir_all(&temp_dir); 157 } 158 159 #[test] 160 fn test_setup_environment() { 161 let _lock = TEST_DIR_MUTEX.lock().unwrap_or_else(|e| e.into_inner()); 162 163 // Save current directory 164 let original_dir = env::current_dir().unwrap(); 165 166 // Run setup 167 let result = setup_environment(); 168 assert!(result.is_ok(), "setup_environment should succeed"); 169 170 let temp_dir = result.unwrap(); 171 assert!(temp_dir.exists(), "temp directory should exist"); 172 173 // Verify we changed to the temp directory 174 let current_dir = env::current_dir().unwrap(); 175 assert_eq!(current_dir, temp_dir, "should be in temp directory"); 176 177 // Clean up 178 let _ = env::set_current_dir(&original_dir); 179 let _ = std::fs::remove_dir_all(&temp_dir); 180 } 181 182 #[test] 183 fn test_change_to_nonexistent_directory() { 184 let nonexistent_path = env::temp_dir().join("definitely-does-not-exist-123456789"); 185 let result = change_working_directory(&nonexistent_path); 186 assert!( 187 result.is_err(), 188 "should fail to change to nonexistent directory" 189 ); 190 } 191 }