/* doscan - Denial Of Service Capable Auditing of Networks -*- C++ -*- * Copyright (C) 2003 Florian Weimer * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ #ifndef SCAN_TCP_H #define SCAN_TCP_H #include "event_queue.h" #include "ipv4.h" #include class tcp_client_handler : public event_queue::fd_handler { tcp_client_handler(); ipv4_t the_host; unsigned short the_port; public: // Opens a new TCP connection to the specified host/port. // on_activity() is invoked as soon as the connection has been // established, with state == 0. on_activity() should check for // errors (using get_error()) and invoke watch() to react upon the // correct descriptor activity. tcp_client_handler(event_queue&, ipv4_t host, unsigned short port); virtual ~tcp_client_handler(); // Returns information about the connection. ipv4_t host(); unsigned short port(); // Creates non-blocking socket and invoke connect(). Returns -1 on // error. static int make_connection(ipv4_t host, unsigned short port); // Returns the pending error code for fd, or 0 if no error. Might // change errno. It's recommended to invoke this routine // unconditionally after connect() because error signaling is not // portable (e.g. Solaris does not set POLLERR). static int get_error(int fd); // The same, but works on the fd() descriptor. int get_error(); }; class tcp_half_duplex_handler : public tcp_client_handler { tcp_half_duplex_handler(); int next_state; bool next_is_read, stop; std::string data; unsigned offset; // Override routines inherited from fd_handler. virtual bool on_timeout(ticks_t); virtual bool on_activity(activity); bool on_activity_read(activity); bool on_activity_write(activity); public: // Open a half-duplex TCP connection to host:port. When called for // the first time (with state == 0), ready() should check for // pending connect() errors using get_error(). // // If the connect attempt fails, ready() or send_ready() are never // called. tcp_half_duplex_handler(event_queue&, ipv4_t host, unsigned short port); // ready() is called when the requested amount of data has been // received, or a send operation has completed and some data has // been received. // // An implementation in a derived class should call request_data(), // request_more_data() // or send(). If it does not, the // connection is closed. virtual void ready(int state, int error, const std::string& data) = 0; // request_data() should be called by ready() to request more data. // If count bytes are received, ready() is invoked again, with the // given state. (If count is zero, all the data in the TCP socket // buffer is read.) void request_data(int new_state, unsigned count = 0); // request_more_data() is like request_data(), only the data is // appended to the existing buffer. void request_more_data(int new_state, unsigned count = 0); // send() should be called by ready() to send the specified data. // After completion, ready() is invoked with the new state. void send(int new_state, const std::string& data); // Closes the current connection and tries to establish a new one. void reconnect(int new_state, bool first_read); }; // tcp_handler inline ipv4_t tcp_client_handler::host() { return the_host; } inline unsigned short tcp_client_handler::port() { return the_port; } inline int tcp_client_handler::get_error() { return get_error(fd()); } #endif // SCAN_TCP_H // arch-tag: c6944903-dbec-47ef-9435-95d6dc3f0bac