Add Rust-based Linux memory searcher

This commit is contained in:
Eduardo Alonso 2019-10-25 22:47:59 +02:00
parent 07590ec4c6
commit 5a6a87eb59
No known key found for this signature in database
GPG Key ID: 9DBBF9CBD954F1B1
5 changed files with 475 additions and 29 deletions

View File

@ -4,6 +4,7 @@ import gearth.protocol.HConnection;
import gearth.protocol.memory.habboclient.HabboClient;
import java.io.*;
import java.net.URISyntaxException;
import java.nio.file.Files;
import java.util.*;
@ -149,41 +150,35 @@ public class LinuxHabboClient extends HabboClient {
}
public List<byte[]> getRC4possibilities() {
ArrayList<String> possibleData = new ArrayList<>();
int offset = 4;
List<byte[]> resultSet = new ArrayList<>();
try {
String g_mem = new File(this.getClass().getProtectionDomain().getCodeSource().getLocation().toURI()).getParent() + "/G-Mem";
ProcessBuilder pb = new ProcessBuilder(g_mem, hConnection.getClientHostAndPort().substring(0, hConnection.getClientHostAndPort().indexOf(':')) , Integer.toString(hConnection.getPort()));
for (PotentialHabboProcess process : potentialProcesses) {
PID = process.PID;
maps = process.maps;
List<LinuxMemorySnippet> possibilities = createMemorySnippetListForRC4();
fetchMemory(possibilities);
Process p = pb.start();
BufferedReader reader = new BufferedReader(new InputStreamReader(p.getInputStream()));
for (LinuxMemorySnippet snippet : possibilities) {
if (snippet.getData().length >= 1024 && snippet.getData().length <= 1024+2*offset) {
for (int i = 0; i < (snippet.getData().length - ((256 - 1) * offset)); i+=offset) {
byte[] wannabeRC4data = Arrays.copyOfRange(snippet.getData(), i, 1024 + i);
byte[] data = new byte[256]; // dis is the friggin key
String line;
boolean isvalid = true;
for (int j = 0; j < 1024; j++) {
if (j % 4 != 0 && wannabeRC4data[j] != 0) {
isvalid = false;
break;
}
if (j % 4 == 0) {
data[j/4] = wannabeRC4data[j];
while((line = reader.readLine()) != null) {
if (line.length() > 1) {
System.out.println("[+] " + line);
possibleData.add(line);
}
}
if (isvalid) {
resultSet.add(data);
} catch (URISyntaxException | IOException e) {
e.printStackTrace();
}
}
}
}
}
return resultSet;
List<byte[]> ret = new ArrayList<>();
for (String possibleHexStr : possibleData)
ret.add(hexStringToByteArray(possibleHexStr));
return ret;
}
private List<LinuxMemorySnippet> createMemorySnippetListForRC4() {
@ -283,4 +278,14 @@ public class LinuxHabboClient extends HabboClient {
return result;
}
private static byte[] hexStringToByteArray(String s) {
int len = s.length();
byte[] data = new byte[len / 2];
for (int i = 0; i < len; i += 2) {
data[i / 2] = (byte) ((Character.digit(s.charAt(i), 16) << 4)
+ Character.digit(s.charAt(i+1), 16));
}
return data;
}
}

2
G-Mem/.gitignore vendored Normal file
View File

@ -0,0 +1,2 @@
/target
**/*.rs.bk

250
G-Mem/Cargo.lock generated Normal file
View File

@ -0,0 +1,250 @@
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
[[package]]
name = "G-Mem"
version = "0.1.0"
dependencies = [
"netstat 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)",
"procfs 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)",
"read-process-memory 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "adler32"
version = "1.0.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "autocfg"
version = "0.1.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "bitflags"
version = "1.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "byteorder"
version = "1.3.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "cfg-if"
version = "0.1.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "chrono"
version = "0.4.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"libc 0.2.65 (registry+https://github.com/rust-lang/crates.io-index)",
"num-integer 0.1.41 (registry+https://github.com/rust-lang/crates.io-index)",
"num-traits 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)",
"time 0.1.42 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "crc32fast"
version = "1.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"cfg-if 0.1.10 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "hex"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "kernel32-sys"
version = "0.2.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "lazy_static"
version = "1.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "libc"
version = "0.2.65"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "libflate"
version = "0.1.27"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"adler32 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)",
"crc32fast 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
"rle-decode-fast 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)",
"take_mut 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "log"
version = "0.3.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "log"
version = "0.4.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"cfg-if 0.1.10 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "mach"
version = "0.0.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"libc 0.2.65 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "netstat"
version = "0.7.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"bitflags 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
"libc 0.2.65 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "num-integer"
version = "0.1.41"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"autocfg 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)",
"num-traits 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "num-traits"
version = "0.2.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"autocfg 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "procfs"
version = "0.6.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"bitflags 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
"byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"chrono 0.4.9 (registry+https://github.com/rust-lang/crates.io-index)",
"hex 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
"libc 0.2.65 (registry+https://github.com/rust-lang/crates.io-index)",
"libflate 0.1.27 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "read-process-memory"
version = "0.1.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)",
"libc 0.2.65 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)",
"mach 0.0.5 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "redox_syscall"
version = "0.1.56"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "rle-decode-fast"
version = "1.0.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "take_mut"
version = "0.2.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "time"
version = "0.1.42"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"libc 0.2.65 (registry+https://github.com/rust-lang/crates.io-index)",
"redox_syscall 0.1.56 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "winapi"
version = "0.2.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "winapi"
version = "0.3.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "winapi-build"
version = "0.1.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "winapi-i686-pc-windows-gnu"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "winapi-x86_64-pc-windows-gnu"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
[metadata]
"checksum adler32 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)" = "5d2e7343e7fc9de883d1b0341e0b13970f764c14101234857d2ddafa1cb1cac2"
"checksum autocfg 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)" = "1d49d90015b3c36167a20fe2810c5cd875ad504b39cff3d4eae7977e6b7c1cb2"
"checksum bitflags 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "cf1de2fe8c75bc145a2f577add951f8134889b4795d47466a54a5c846d691693"
"checksum byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)" = "a7c3dd8985a7111efc5c80b44e23ecdd8c007de8ade3b96595387e812b957cf5"
"checksum cfg-if 0.1.10 (registry+https://github.com/rust-lang/crates.io-index)" = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822"
"checksum chrono 0.4.9 (registry+https://github.com/rust-lang/crates.io-index)" = "e8493056968583b0193c1bb04d6f7684586f3726992d6c573261941a895dbd68"
"checksum crc32fast 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ba125de2af0df55319f41944744ad91c71113bf74a4646efff39afe1f6842db1"
"checksum hex 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "023b39be39e3a2da62a94feb433e91e8bcd37676fbc8bea371daf52b7a769a3e"
"checksum kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7507624b29483431c0ba2d82aece8ca6cdba9382bff4ddd0f7490560c056098d"
"checksum lazy_static 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646"
"checksum libc 0.2.65 (registry+https://github.com/rust-lang/crates.io-index)" = "1a31a0627fdf1f6a39ec0dd577e101440b7db22672c0901fe00a9a6fbb5c24e8"
"checksum libflate 0.1.27 (registry+https://github.com/rust-lang/crates.io-index)" = "d9135df43b1f5d0e333385cb6e7897ecd1a43d7d11b91ac003f4d2c2d2401fdd"
"checksum log 0.3.9 (registry+https://github.com/rust-lang/crates.io-index)" = "e19e8d5c34a3e0e2223db8e060f9e8264aeeb5c5fc64a4ee9965c062211c024b"
"checksum log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)" = "14b6052be84e6b71ab17edffc2eeabf5c2c3ae1fdb464aae35ac50c67a44e1f7"
"checksum mach 0.0.5 (registry+https://github.com/rust-lang/crates.io-index)" = "196697f416cf23cf0d3319cf5b2904811b035c82df1dfec2117fb457699bf277"
"checksum netstat 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "48b71f6e2443299ba97e8c834edcd4724be71da3a751b1be75d8b67022801bf3"
"checksum num-integer 0.1.41 (registry+https://github.com/rust-lang/crates.io-index)" = "b85e541ef8255f6cf42bbfe4ef361305c6c135d10919ecc26126c4e5ae94bc09"
"checksum num-traits 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)" = "6ba9a427cfca2be13aa6f6403b0b7e7368fe982bfa16fccc450ce74c46cd9b32"
"checksum procfs 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)" = "911881246ca41baceae6921e32f9f5542c83713e3825b57adedb6afeb48a23a1"
"checksum read-process-memory 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "950b829b2477880c74aaed706d681bc8d50d4e2b15b5e4d98ed33d5d4f93712e"
"checksum redox_syscall 0.1.56 (registry+https://github.com/rust-lang/crates.io-index)" = "2439c63f3f6139d1b57529d16bc3b8bb855230c8efcc5d3a896c8bea7c3b1e84"
"checksum rle-decode-fast 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "cabe4fa914dec5870285fa7f71f602645da47c486e68486d2b4ceb4a343e90ac"
"checksum take_mut 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "f764005d11ee5f36500a149ace24e00e3da98b0158b3e2d53a7495660d3f4d60"
"checksum time 0.1.42 (registry+https://github.com/rust-lang/crates.io-index)" = "db8dcfca086c1143c9270ac42a2bbd8a7ee477b78ac8e45b19abfb0cbede4b6f"
"checksum winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)" = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a"
"checksum winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)" = "8093091eeb260906a183e6ae1abdba2ef5ef2257a21801128899c3fc699229c6"
"checksum winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc"
"checksum winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6"
"checksum winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f"

15
G-Mem/Cargo.toml Normal file
View File

@ -0,0 +1,15 @@
[package]
name = "G-Mem"
version = "0.1.0"
authors = ["G-Earth contributors"]
edition = "2018"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
netstat = "0.7.0"
read-process-memory = "0.1.2"
procfs = "0.6.0"
[profile.dev]
opt-level = 3

174
G-Mem/src/main.rs Normal file
View File

@ -0,0 +1,174 @@
use netstat::*;
use read_process_memory::*;
use std::io;
use std::thread;
use std::sync::mpsc;
use procfs::MemoryMap;
use std::thread::JoinHandle;
fn main() {
// get_rc4_possibilities();
let pid = get_proc_id() as Pid;
get_snippet_list(get_mem_maps(pid), pid);
print!("\n");
}
fn get_mem_maps(pid: Pid) -> Vec<MemoryMap>{
let mut ret: Vec<MemoryMap> = Vec::new();
let habbo_proc = procfs::Process::new(pid as i32).unwrap();
let maps = habbo_proc.maps().unwrap();
for map in maps {
if map.perms == String::from("rw-p") {
ret.push(map);
}
}
return ret;
}
struct MemMap {
start: usize,
len: usize,
mem: Vec<u8>
}
fn get_snippet_list(maps: Vec<MemoryMap>, pid: Pid) {
let (tx, rx) = mpsc::channel();
let mut handles: Vec<JoinHandle<()>> = Vec::new();
for map in maps {
let tx1 = mpsc::Sender::clone(&tx);
let handle = thread::spawn(move || {
let mut n_to_map: [i32; 256] = [-1; 256];
let mut remove_map: [i32; 256] = [-1; 256];
let mut mask_count = 0;
let mut match_start : i64 = -1;
let mut match_end: i64 = -1;
let mem = read_mem(pid, map.address.0 as usize, (map.address.1 - map.address.0) as usize).
unwrap();
for (i, data) in mem.iter().step_by(4).enumerate() {
let offset = 4;
let b = ((*data as u16 + 128) % 256) as u8;
let ind_in_map = (((i) as i64) % 256) as i32;
let deleted_number = remove_map[ind_in_map as usize];
if deleted_number != -1 {
n_to_map[deleted_number as usize] = -1;
mask_count -= 1;
remove_map[ind_in_map as usize] = -1;
}
if n_to_map[b as usize] == -1 {
mask_count += 1;
remove_map[ind_in_map as usize] = b as i32;
n_to_map[b as usize] = ind_in_map;
} else {
remove_map[n_to_map[b as usize] as usize] = -1;
remove_map[ind_in_map as usize] = b as i32;
n_to_map[b as usize] = ind_in_map;
}
if mask_count == 256 {
if match_start == -1 {
match_start = (i * 4 - ((256 - 1) * offset)) as i64;
match_end = (i * 4) as i64;
}
if match_end < (i*4 - (256 - 1) * offset) as i64 {
let m = MemMap {
start: (map.address.0 + match_start as u64) as usize,
len: (match_end - match_start as i64 + 4) as usize,
mem: mem[match_start as usize..(match_end + 4) as usize].to_vec()
};
tx1.send(m).unwrap();
match_start = (i*4 - ((256 - 1) * offset)) as i64;
}
match_end = (i*4) as i64;
}
}
if match_start != -1 {
let m = MemMap {
start: (map.address.0 + match_start as u64) as usize,
len: (match_end - match_start + 4) as usize,
mem: mem[match_start as usize..(match_end + 4) as usize].to_vec()
};
tx1.send(m).unwrap();
}
});
handles.push(handle);
}
thread::spawn(move || {
for handle in handles {
handle.join().unwrap();
}
let tx1 = mpsc::Sender::clone(&tx);
tx1.send(MemMap{
start: 0,
len: 0,
mem: Vec::new()
}).unwrap();
});
for received in rx {
if received.start == 0 { break; }
get_rc4_possibilities(received);
}
}
fn get_rc4_possibilities(snippet: MemMap) {
let offset = 4;
if snippet.len >= 1024 && snippet.len <= 1024 + 2 * offset {
for i in (0..snippet.len - ((256 - 1) * offset)).step_by(4) {
let wannabe_rc4_data = snippet.mem[i..1024 + i].to_vec();
let mut data: [u8; 256] = [0xff; 256];
let mut is_valid = true;
for j in 0..1024 {
if j % 4 != 0 && wannabe_rc4_data[j] != 0 {
is_valid = false;
break;
}
if j % 4 == 0 {
data[j / 4] = wannabe_rc4_data[j];
}
}
if is_valid == true {
for byte in data.iter() {
print!("{:02x}", byte);
}
print!("\n");
}
}
}
}
fn read_mem(pid: Pid, address: usize, size: usize) -> io::Result<Vec<u8>> {
let handle = pid.try_into_process_handle()?;
let _bytes = copy_address(address, size, &handle)?;
Ok(_bytes)
}
fn get_proc_id() -> u32 {
let sockets_info = get_sockets_info(AddressFamilyFlags::IPV4,
ProtocolFlags::TCP).unwrap();
for si in sockets_info {
match si.protocol_socket_info {
ProtocolSocketInfo::Tcp(tcp_si) => {
if tcp_si.remote_port == 30000 {
return si.associated_pids[0];
}
}
ProtocolSocketInfo::Udp(_) => {}
}
}
return 0;
}