Mio : TcpStream::Connect sends RST

Hello,

I'm quite new to Rust. I'm working a networking app and I need to connect through TCP to a remote host. However, connection never succeeds. I am aware to subject Mio : TcpStream::Connect always return success. Here is my code :

fn connect_network(listen : &str, remote : &str){

let socket = &listen.parse().unwrap();
//
// // Setup the server socket
let server = match TcpListener::bind(socket) {
    Err(err) => panic!("Could not bind to {}: {}", listen, err),
    Ok(s) => s
};

// Create a poll instance
let poll = match Poll::new(){
    Err(err) => panic!("Could not poll to {}: {}", socket, err),
    Ok(p) => p
};

// Start listening for incoming connections
poll.register(&server, SERVER, Ready::readable(), PollOpt::level()).unwrap();

let mut events = Events::with_capacity(1024);
let id = 0;


match TcpStream::connect(&remote.parse().unwrap()) {
    Ok(stream) => {
        poll.register(&stream, Token(0), Ready::readable() | Ready::writable(), PollOpt::level()).unwrap();
        println!("Trying to connect from {:?} to {}", stream.local_addr(), remote);
        // match (stream.local_addr(), stream.peer_addr()) {
        //     (Ok(local), Ok(peer)) => {
        //         println!("{}:New Connection {} -- {}", id, local, peer);
        //         // Some(Connection{id : id, status : RefCell::new(ConnectionStatus::Disconnected), stream : RefCell::new(stream), logger : logger})
        //     },
        //     (Ok(local), Err(e)) => {
        //         println!("{}:Error 1 while connecting from {} to {}:{}", id, local, remote, e);
        //         // None
        //     },
        //     (Err(e), Ok(peer))=> {
        //         println!("{}:Error 2 while connecting to {} {} {}", id, remote, peer, e);
        //         // None
        //     },
        //     (Err(e1), Err(e2))=> {
        //         println!("{}:Error 3 while connecting to {}\n{}\n{}", id, remote, e1, e2);
        //         // None
        //     },
        // }
    },
    Err(e) => {
        println!("{}:Error 4 while connecting to {} : {}", id, remote, e);
        // None
    }
};

loop {
    match poll.poll(&mut events, None) {
        Err(e) => println!("Error during poll(): {}", e),
        Ok(_) => {}
    }

    for event in events.iter() {
        println!("event={:?}", event);
        match event.token() {
            SERVER => {
                // Accept and drop the socket immediately, this will close
                // the socket and notify the client of the EOF.

                let (stream, _client_addr) = match server.accept() {
                    Ok((stream, client_addr)) => {
                        println!("0\tAccepting connection... {:?} from {:?}", stream, client_addr);
                        (stream, client_addr)
                    },
                    Err(e) => panic!("got an error when accepting a connection: {}", e),
                };

                // do some stuff
            }
            Token(c) => {
                let r = event.readiness();

                if r.is_readable() {
                    println!("Client {} received bytes",c);
                }
                if r.is_writable() {
                    println!("Client {} might write",c);
                }
            }
        }
    }
}

}

When I run it, i use wireshark to sniff the network. I can see that my program opens a connection to the remote host and sends a SYN. The remote host answers with a SYN+ACK message, and right after I see a RST message. I do not understand.

This problem does not occur when the remote host is 127.0.0.1.
Do you have any clue about this ?

What platform are you on? I think rust just delegates to system calls that handle the actual setting up of the connection etc.

On linux / ubuntu.
When I use netcat, I dot not have the problem of RST...

I'm not an expert with networking so take what I say with a pinch of salt.

Have you tried strace to see what syscalls are being made?

It looks like you're dropping the TcpStream after connect succeeds? So it's quite expected that the connection gets closed again...

Actually, it is the same behavior if I store the TCPStream in a local variable: stream.peer_addr() returns an error with code 107 : Transport endpoint is not connected (os error 107)

Well, then I second @derekdreery 's suggestion to check what syscalls are being made. strace -e network should be a good starting point.

It seems that calling stream.peer_addr() in the loop upon reception of an event is OK. I guess I call it to early.