Post

IronScan - My Rust(y) Network Scanning Tool

IronScan - My Rust(y) Network Scanning Tool

I’ve written a NetScan in Rust, Just for Fun!

Hi!

Last week, I decided to try something new: I wanted to create my version of NMap!

For those who don’t know, NMap is a network scanning tool, used in a vast pool of situations (such as cybersecurity analysis, network setup etc.). This is very interesting, but you know me, I wanted to do it my way.

Fist Version

The first thing I thought was: How?????. I had no idea where to start.

I knew it was necessary to read users’ input, so I decided to create my input parser:

1
2
3
4
5
6
7
8
9
#[derive(Parser)]
struct Args {
    /// Target IP address
    target: String,
    /// Start port
    start_port: u16,
    /// End port
    end_port: u16,
}

As you might notice, I used clap::Parser for this.

After that, I was able to read inputs made like ADDRESS START_PORT END_PORT. Amazing!

The core of the first version is the following:

1
2
3
4
5
6
7
8
9
fn scan_port(addr: &str, port: u16) -> bool {
    let socket = format!("{}:{}", addr, port);
    let timeout = std::time::Duration::from_millis(300);

    match TcpStream::connect_timeout(&socket.to_socket_addrs().unwrap().next().unwrap(), timeout) {
        Ok(_) => true,
        Err(_) => false,
    }
}

Let’s break it down a bit!

The scan_port function checks if a specific port on a given address is open.

  1. Socket Creation:

    1
    
    let socket = format!("{}:{}", addr, port);
    

    This line formats the address and port into a socket string.

  2. Timeout Setting:

    1
    
    let timeout = std::time::Duration::from_millis(300);
    

    A timeout duration of 300 milliseconds is set for the connection attempt.

  3. Connection Attempt:

    1
    2
    3
    4
    
    match TcpStream::connect_timeout(&socket.to_socket_addrs().unwrap().next().unwrap(), timeout) {
        Ok(_) => true,
        Err(_) => false,
    }
    

    The function attempts to connect to the socket with the specified timeout. If the connection is successful, it returns true; otherwise, it returns false.

In the main function I just call this and I am done!

Second Version

The second version is still under development, some of the things I’m adding are:

  • Parallel scan
  • Ping and ICMP messages
  • UDP Scanning: Similar to TCP but with std::net::UdpSocket.
  • Service Detection: Implement banner grabbing on open ports.

Conclusion

For now it ends here! I am learning a lot of new things about Rust and how to use it in real world scenarios!

Thanks for passing by,

See you soon!

Federico

This post is licensed under CC BY 4.0 by the author.