From 5f203d0f5ba2639043bd5bd1c3687c406d6abac1 Mon Sep 17 00:00:00 2001 From: Noratrieb <48135649+Noratrieb@users.noreply.github.com> Date: Mon, 26 Aug 2024 03:27:16 +0200 Subject: [PATCH] advanced shell --- Cargo.lock | 1 + bin/cluelessh-faked/Cargo.toml | 1 + bin/cluelessh-faked/src/main.rs | 79 +++++++++++++++++++++-------- bin/cluelessh-faked/src/readline.rs | 8 ++- 4 files changed, 67 insertions(+), 22 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index a471047..8b3a013 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -355,6 +355,7 @@ dependencies = [ "eyre", "hex-literal", "rand", + "shlex", "tokio", "tracing", "tracing-subscriber", diff --git a/bin/cluelessh-faked/Cargo.toml b/bin/cluelessh-faked/Cargo.toml index dfc4979..fa2cf85 100644 --- a/bin/cluelessh-faked/Cargo.toml +++ b/bin/cluelessh-faked/Cargo.toml @@ -14,3 +14,4 @@ tokio = { version = "1.39.2", features = ["full"] } tracing-subscriber = { version = "0.3.18", features = ["env-filter", "json"] } tracing.workspace = true +shlex = "1.3.0" diff --git a/bin/cluelessh-faked/src/main.rs b/bin/cluelessh-faked/src/main.rs index afd1870..dafb33b 100644 --- a/bin/cluelessh-faked/src/main.rs +++ b/bin/cluelessh-faked/src/main.rs @@ -261,30 +261,69 @@ fn execute_command(command: &[u8]) -> ProcessOutput { stdout: b"what the hell".to_vec(), }; }; + + // Some hardcoded commands match command.trim() { - "uname -s -v -n -r -m" => ProcessOutput { - status: 0, - stdout: UNAME_SVNRM.to_vec(), - }, - "uname -a" => ProcessOutput { - status: 0, - stdout: UNAME_A.to_vec(), - }, - "cat /proc/cpuinfo|grep name|cut -f2 -d':'|uniq -c ; uname -a" => ProcessOutput { - status: 0, - stdout: CPUINFO_UNAME_A.to_vec(), - }, + "uname -s -v -n -r -m" => { + return ProcessOutput { + status: 0, + stdout: UNAME_SVNRM.to_vec(), + } + } + "uname -a" => { + return ProcessOutput { + status: 0, + stdout: UNAME_A.to_vec(), + } + } + "cat /proc/cpuinfo|grep name|cut -f2 -d':'|uniq -c ; uname -a" => { + return ProcessOutput { + status: 0, + stdout: CPUINFO_UNAME_A.to_vec(), + } + } + _ => {} + } + + // Now, lex the string and do this nicely + let Some(parts) = shlex::split(command) else { + return ProcessOutput { + status: 1, + stdout: b"bash: invalid input\r\n".to_vec(), + }; + }; + + let Some(argv0) = parts.first() else { + return ProcessOutput { + status: 1, + stdout: b"bash: invalid input\r\n".to_vec(), + }; + }; + + match argv0.as_str().trim() { "true" => ProcessOutput { status: 0, stdout: b"".to_vec(), }, - _ => { - let argv0 = command.split_ascii_whitespace().next().unwrap_or(""); - - ProcessOutput { - status: 127, - stdout: format!("bash: line 1: {argv0}: command not found\r\n").into_bytes(), - } - } + "cd" => ProcessOutput { + status: 0, + stdout: b"".to_vec(), + }, + "ls" => ProcessOutput { + status: 0, + stdout: b"hpasswd index.php secrets.php\r\n".to_vec(), + }, + "whoami" => ProcessOutput { + status: 0, + stdout: b"root\r\n".to_vec(), + }, + "id" => ProcessOutput { + status: 0, + stdout: b"uid=0(root) gid=0(root) groups=0(root)\r\n".to_vec(), + }, + _ => ProcessOutput { + status: 127, + stdout: format!("bash: line 1: {argv0}: command not found\r\n").into_bytes(), + }, } } diff --git a/bin/cluelessh-faked/src/readline.rs b/bin/cluelessh-faked/src/readline.rs index f967d28..574aa44 100644 --- a/bin/cluelessh-faked/src/readline.rs +++ b/bin/cluelessh-faked/src/readline.rs @@ -25,10 +25,14 @@ impl InteractiveShell { return; } b'\r' => { - let output = super::execute_command(&self.line_buf); + let output = if !self.line_buf.is_empty() { + super::execute_command(&self.line_buf).stdout + } else { + Vec::new() + }; self.line_buf.clear(); self.write(b"\r\n"); - self.write(&output.stdout); + self.write(&output); self.prompt(); } // ESC