Skip to content

Instantly share code, notes, and snippets.

@rexim
Last active October 31, 2024 20:32
Show Gist options
  • Select an option

  • Save rexim/38c176fe4669ef83db69aca9909d7b7f to your computer and use it in GitHub Desktop.

Select an option

Save rexim/38c176fe4669ef83db69aca9909d7b7f to your computer and use it in GitHub Desktop.

Revisions

  1. rexim revised this gist Feb 17, 2022. 1 changed file with 3 additions and 0 deletions.
    3 changes: 3 additions & 0 deletions main.rs
    Original file line number Diff line number Diff line change
    @@ -54,6 +54,9 @@ fn read_line_into_buffer(input: &mut impl BufRead, mem: &mut Vec<char>, buf: Ptr

    fn streq(mem: &Vec<char>, mut s1: Ptr, mut s2: Ptr) -> bool {
    while mem[s1] != '\0' && mem[s2] != '\0' {
    if mem[s1] != mem[s2] {
    return false;
    }
    s1 += 1;
    s2 += 1;
    }
  2. rexim created this gist Feb 17, 2022.
    79 changes: 79 additions & 0 deletions main.rs
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,79 @@
    // The Most Memory Safe Buffer Overflow in Rust!
    //
    // Consider all the code below under Public Domain
    //
    // How to build:
    // $ rustc main.rs
    //
    // Wrong password:
    // $ printf "hello\n" | ./main
    //
    // Right password:
    // $ printf "password\n" | ./main
    //
    // Universal password:
    // $ printf "aaaaaaaaaaaaaa\0aaaaaaaaaaaaaa\0" | ./main
    //
    // Support Rust Recovery Foundation: https://rustrecoveryfoundation.neocities.org/

    use std::io::{BufRead, Write};

    const BUF_CAP: usize = 15;

    type Ptr = usize;

    fn alloc_buffer(mem: &mut Vec::<char>, size: usize) -> Ptr {
    let result = mem.len();
    for _ in 0..size {
    mem.push(' ')
    }
    result
    }

    fn alloc_str(mem: &mut Vec<char>, s: &str) -> Ptr {
    let result = mem.len();
    for c in s.chars() {
    mem.push(c)
    }
    mem.push('\0');
    result
    }

    fn read_line_into_buffer(input: &mut impl BufRead, mem: &mut Vec<char>, buf: Ptr) {
    let mut s = String::new();
    let n = input.read_line(&mut s).unwrap();
    for (i, c) in s.chars().enumerate() {
    mem[buf + i] = c;
    }
    if mem[buf + n - 1] == '\n' {
    mem[buf + n - 1] = '\0'
    } else {
    mem[buf + n] = '\0';
    }
    }

    fn streq(mem: &Vec<char>, mut s1: Ptr, mut s2: Ptr) -> bool {
    while mem[s1] != '\0' && mem[s2] != '\0' {
    s1 += 1;
    s2 += 1;
    }

    mem[s1] == '\0' && mem[s2] == '\0'
    }

    fn main() {
    let mut mem = Vec::<char>::new();
    let buffer = alloc_buffer(&mut mem, BUF_CAP);
    let password = alloc_str(&mut mem, "password");
    alloc_buffer(&mut mem, BUF_CAP);

    print!("Password: ");
    std::io::stdout().flush().unwrap();
    read_line_into_buffer(&mut std::io::stdin().lock(), &mut mem, buffer);

    if streq(&mem, buffer, password) {
    println!("Access Granted!")
    } else {
    println!("Access Denied!")
    }
    }