diff --git a/include/arp.h b/include/arp.h index c9aefd4..393118d 100644 --- a/include/arp.h +++ b/include/arp.h @@ -23,15 +23,13 @@ #ifndef TINS_ARP_H #define TINS_ARP_H - -#include #include "pdu.h" -#include "ipaddress.h" #include "endianness.h" #include "hwaddress.h" -#include "network_interface.h" +#include "ipaddress.h" namespace Tins { + class NetworkInterface; /** * \brief Class that represents an ARP PDU. @@ -274,8 +272,8 @@ namespace Tins { /** * \sa PDU::clone_pdu */ - PDU *clone_pdu() const { - return do_clone_pdu(); + ARP *clone_pdu() const { + return new ARP(*this); } private: struct arphdr { diff --git a/include/bootp.h b/include/bootp.h index e5d3170..87d363a 100644 --- a/include/bootp.h +++ b/include/bootp.h @@ -293,8 +293,8 @@ namespace Tins { /** * \sa PDU::clone_pdu */ - PDU *clone_pdu() const { - return do_clone_pdu(); + BootP *clone_pdu() const { + return new BootP(*this); } protected: /** diff --git a/include/dhcp.h b/include/dhcp.h index 72674cc..5642db8 100644 --- a/include/dhcp.h +++ b/include/dhcp.h @@ -27,10 +27,9 @@ #include #include #include "bootp.h" -#include "ipaddress.h" - namespace Tins { + class IPv4Address; /** * \brief Class that represents the DHCP PDU. @@ -385,8 +384,8 @@ namespace Tins { /** * \sa PDU::clone_pdu */ - PDU *clone_pdu() const { - return do_clone_pdu(); + DHCP *clone_pdu() const { + return new DHCP(*this); } private: static const uint32_t MAX_DHCP_SIZE; diff --git a/include/dns.h b/include/dns.h index d02b129..6fc4185 100644 --- a/include/dns.h +++ b/include/dns.h @@ -30,16 +30,24 @@ #include #include "pdu.h" #include "endianness.h" -#include "ipaddress.h" namespace Tins { + class IPv4Address; + + /** + * \class DNS + * \brief Represents a DNS PDU. + */ class DNS : public PDU { public: /** * \brief This PDU's flag. */ static const PDU::PDUType pdu_flag = PDU::DNS; - + + /** + * The DNS type. + */ enum QRType { QUERY = 0, RESPONSE = 1 @@ -475,8 +483,8 @@ namespace Tins { /** * \sa PDU::clone_pdu */ - PDU *clone_pdu() const { - return do_clone_pdu(); + DNS *clone_pdu() const { + return new DNS(*this); } private: struct dnshdr { diff --git a/include/dot11.h b/include/dot11.h index 53b5dfb..04b2b30 100644 --- a/include/dot11.h +++ b/include/dot11.h @@ -25,14 +25,13 @@ #include #include #include -#include #include #include "pdu.h" #include "endianness.h" -#include "network_interface.h" #include "hwaddress.h" #include "small_uint.h" +#include "network_interface.h" namespace Tins { class RSNInformation; diff --git a/include/eapol.h b/include/eapol.h index 463424b..c11a980 100644 --- a/include/eapol.h +++ b/include/eapol.h @@ -22,7 +22,7 @@ #ifndef TINS_EAPOL_H #define TINS_EAPOL_H - +#include #include "pdu.h" #include "small_uint.h" #include "endianness.h" @@ -46,6 +46,9 @@ namespace Tins { */ static const PDU::PDUType pdu_flag = PDU::EAPOL; + /** + * The EAPOL type enum. + */ enum EAPOLTYPE { RC4 = 1, RSN, diff --git a/include/endianness.h b/include/endianness.h index 6bbf105..1b5be3b 100644 --- a/include/endianness.h +++ b/include/endianness.h @@ -26,7 +26,6 @@ #ifndef WIN32 #include #endif -#include "small_uint.h" #define TINS_IS_LITTLE_ENDIAN (__BYTE_ORDER == __LITTLE_ENDIAN) #define TINS_IS_BIG_ENDIAN (__BYTE_ORDER == __BIG_ENDIAN) diff --git a/include/ethernetII.h b/include/ethernetII.h index 65a3ad7..3fdf632 100644 --- a/include/ethernetII.h +++ b/include/ethernetII.h @@ -23,7 +23,6 @@ #define TINS_ETHERNET_II_H #include -#include #include "pdu.h" #include "endianness.h" @@ -42,11 +41,6 @@ namespace Tins { */ typedef HWAddress<6> address_type; - /** - * \brief The hardware address size. - */ - static const size_t ADDR_SIZE; - /** * \brief This PDU's flag. */ @@ -189,8 +183,8 @@ namespace Tins { /** * \sa PDU::clone_pdu */ - PDU *clone_pdu() const { - return do_clone_pdu(); + EthernetII *clone_pdu() const { + return new EthernetII(*this); } private: /** diff --git a/include/icmp.h b/include/icmp.h index 8a1f203..c583d22 100644 --- a/include/icmp.h +++ b/include/icmp.h @@ -305,8 +305,8 @@ namespace Tins { /** * \sa PDU::clone_pdu */ - PDU *clone_pdu() const { - return do_clone_pdu(); + ICMP *clone_pdu() const { + return new ICMP(*this); } private: static uint16_t global_id, global_seq; diff --git a/include/ieee802_3.h b/include/ieee802_3.h index b6b1085..e4e96de 100644 --- a/include/ieee802_3.h +++ b/include/ieee802_3.h @@ -23,7 +23,6 @@ #define TINS_IEEE802_3_H #include -#include #include "pdu.h" #include "endianness.h" @@ -127,13 +126,6 @@ namespace Tins { */ void iface(const NetworkInterface &new_iface_index); - /** - * \brief Setter for the interface. - * - * \param new_iface string reference containing the new interface name. - */ - void iface(const std::string& new_iface) throw (std::runtime_error); - /** * \brief Setter for the length field. * @@ -189,8 +181,8 @@ namespace Tins { /** * \sa PDU::clone_pdu */ - PDU *clone_pdu() const { - return do_clone_pdu(); + IEEE802_3 *clone_pdu() const { + return new IEEE802_3(*this); } private: /** diff --git a/include/ip.h b/include/ip.h index 12ff6e0..e28bff2 100644 --- a/include/ip.h +++ b/include/ip.h @@ -22,16 +22,11 @@ #ifndef TINS_IP_H #define TINS_IP_H -#ifndef WIN32 - #include -#endif -#include -#include #include #include "pdu.h" #include "small_uint.h" -#include "ipaddress.h" #include "endianness.h" +#include "ipaddress.h" namespace Tins { @@ -53,11 +48,6 @@ namespace Tins { * The type used to store addresses. */ typedef IPv4Address address_type; - - /** - * \brief IP address size. - */ - static const uint32_t ADDR_SIZE = 4; /** * \brief Enum indicating the option's class. @@ -103,11 +93,11 @@ namespace Tins { struct IPOption { friend class IP; struct { - #if __BYTE_ORDER == __LITTLE_ENDIAN + #if TINS_IS_LITTLE_ENDIAN unsigned int number:5; unsigned int op_class:2; unsigned int copied:1; - #elif __BYTE_ORDER == __BIG_ENDIAN + #elif TINS_IS_BIG_ENDIAN unsigned int copied:1; unsigned int op_class:2; unsigned int number:5; @@ -398,17 +388,17 @@ namespace Tins { /** * \sa PDU::clone_pdu */ - PDU *clone_pdu() const { - return do_clone_pdu(); + IP *clone_pdu() const { + return new IP(*this); } private: static const uint8_t DEFAULT_TTL; struct iphdr { - #if __BYTE_ORDER == __LITTLE_ENDIAN + #if TINS_IS_LITTLE_ENDIAN unsigned int ihl:4; unsigned int version:4; - #elif __BYTE_ORDER == __BIG_ENDIAN + #elif TINS_IS_BIG_ENDIAN unsigned int version:4; unsigned int ihl:4; #else diff --git a/include/ipaddress.h b/include/ipaddress.h index 3c79ab4..87eb169 100644 --- a/include/ipaddress.h +++ b/include/ipaddress.h @@ -33,6 +33,11 @@ namespace Tins { */ class IPv4Address { public: + /** + * The address size. + */ + static const size_t address_size = sizeof(uint32_t); + /** * \brief Constructor taking a const char*. * diff --git a/include/llc.h b/include/llc.h index c785033..4050574 100644 --- a/include/llc.h +++ b/include/llc.h @@ -23,7 +23,7 @@ #define TINS_IEEE8022_H #include -#include +#include #include #include "pdu.h" #include "endianness.h" @@ -102,16 +102,6 @@ namespace Tins { */ LLC(const uint8_t *buffer, uint32_t total_sz); - /** - * \brief Copy constructor. - */ - LLC(const LLC &other); - - /** - * \brief Copy assignment operator. - */ - LLC &operator= (const LLC &other); - /* Setters */ /** @@ -312,7 +302,9 @@ namespace Tins { * * \sa PDU::clone_pdu */ - PDU *clone_pdu() const; + LLC *clone_pdu() const { + return new LLC(*this); + } private: struct llchdr { uint8_t dsap; @@ -366,6 +358,8 @@ namespace Tins { } __attribute__((__packed__)); #endif + + typedef std::vector field_type; void copy_fields(const LLC *other); void write_serialization(uint8_t *buffer, uint32_t total_sz, const PDU *parent); @@ -379,7 +373,7 @@ namespace Tins { } control_field; Format _type; uint8_t information_field_length; - std::list > information_fields; + std::list information_fields; }; }; diff --git a/include/packetsender.h b/include/packetsender.h index ceb436a..0af4f98 100644 --- a/include/packetsender.h +++ b/include/packetsender.h @@ -27,12 +27,7 @@ #include #include -#ifndef WIN32 - #include - #include -#endif - -#include "pdu.h" +struct timeval; namespace Tins { class PDU; @@ -172,7 +167,7 @@ namespace Tins { int find_type(SocketType type); int timeval_subtract (struct timeval *result, struct timeval *x, struct timeval *y); - PDU *recv_match_loop(int sock, PDU *pdu, struct sockaddr* link_addr, socklen_t addrlen); + PDU *recv_match_loop(int sock, PDU *pdu, struct sockaddr* link_addr, uint32_t addrlen); std::vector _sockets; SocketTypeMap _types; diff --git a/include/pdu.h b/include/pdu.h index 5280b76..a627452 100644 --- a/include/pdu.h +++ b/include/pdu.h @@ -25,7 +25,6 @@ #include #include -#include "packetsender.h" /** \brief The Tins namespace. */ @@ -228,14 +227,14 @@ namespace Tins { * those methods. * \param sender The PacketSender which will send the packet. */ - virtual bool send(PacketSender *sender) { return false; } + virtual bool send(PacketSender *sender); /** \brief Receives a matching response for this packet. * * This method should act as a proxy for PacketSender::recv_lX methods. * \param sender The packet sender which will receive the packet. */ - virtual PDU *recv_response(PacketSender *sender) { return false; } + virtual PDU *recv_response(PacketSender *sender); /** \brief Check wether ptr points to a valid response for this PDU. * diff --git a/include/radiotap.h b/include/radiotap.h index 27cd232..478343a 100644 --- a/include/radiotap.h +++ b/include/radiotap.h @@ -22,7 +22,6 @@ #ifndef TINS_RADIOTAP_H #define TINS_RADIOTAP_H -#include #include "pdu.h" #include "endianness.h" #include "network_interface.h" diff --git a/include/small_uint.h b/include/small_uint.h index b47c556..f50e547 100644 --- a/include/small_uint.h +++ b/include/small_uint.h @@ -1,3 +1,24 @@ +/* + * libtins is a net packet wrapper library for crafting and + * interpreting sniffed packets. + * + * Copyright (C) 2011 Nasel + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + #ifndef TINS_SMALL_UINT_H #define TINS_SMALL_UINT_H diff --git a/include/sniffer.h b/include/sniffer.h index 389ae77..b78ef28 100644 --- a/include/sniffer.h +++ b/include/sniffer.h @@ -26,6 +26,7 @@ #include #include +#include #include #include "pdu.h" #include "ethernetII.h" @@ -138,14 +139,13 @@ namespace Tins { template void Tins::Sniffer::callback_handler(u_char *args, const struct pcap_pkthdr *header, const u_char *packet) { try { - PDU *pdu = 0; + std::auto_ptr pdu; LoopData *data = reinterpret_cast*>(args); if(data->wired) - pdu = new Tins::EthernetII((const uint8_t*)packet, header->caplen); + pdu.reset(new Tins::EthernetII((const uint8_t*)packet, header->caplen)); else - pdu = new Tins::RadioTap((const uint8_t*)packet, header->caplen); - bool ret_val = data->c_handler(pdu); - delete pdu; + pdu.reset(new Tins::RadioTap((const uint8_t*)packet, header->caplen)); + bool ret_val = data->c_handler(pdu.get()); if(!ret_val) pcap_breakloop(data->handle); } diff --git a/include/tcp.h b/include/tcp.h index 0529b82..dd22d1a 100644 --- a/include/tcp.h +++ b/include/tcp.h @@ -26,16 +26,11 @@ #include #include #include -#ifndef WIN32 - #include -#endif #include "pdu.h" -#include "small_uint.h" #include "endianness.h" - +#include "small_uint.h" namespace Tins { - /** * \brief Class that represents an TCP PDU. * @@ -416,7 +411,7 @@ namespace Tins { uint16_t dport; uint32_t seq; uint32_t ack_seq; - #if __BYTE_ORDER == __LITTLE_ENDIAN + #if TINS_IS_LITTLE_ENDIAN uint16_t res1:4, doff:4, fin:1, @@ -427,7 +422,7 @@ namespace Tins { urg:1, ece:1, cwr:1; - #elif __BYTE_ORDER == __BIG_ENDIAN + #elif TINS_IS_BIG_ENDIAN uint16_t doff:4, res1:4, cwr:1, diff --git a/include/tcp_stream.h b/include/tcp_stream.h index d5056b8..8dfabf5 100644 --- a/include/tcp_stream.h +++ b/include/tcp_stream.h @@ -36,52 +36,126 @@ namespace Tins { class Sniffer; class RawPDU; -class TCPSession { +/** + * \class TCPStream + * \brief Represents a TCP stream. + */ +class TCPStream { public: - struct SessionInfo { + /** + * The stream information. + */ + struct StreamInfo { IPv4Address client_addr, server_addr; uint16_t client_port, server_port; - SessionInfo() {} + StreamInfo() {} - SessionInfo(IPv4Address client, IPv4Address server, + StreamInfo(IPv4Address client, IPv4Address server, uint16_t cport, uint16_t sport); - bool operator<(const SessionInfo &rhs) const; + bool operator<(const StreamInfo &rhs) const; }; - + + /** + * The type used to store the payload. + */ typedef std::vector payload_type; - TCPSession(IP *ip, TCP *tcp, uint64_t identifier); - TCPSession(const TCPSession &rhs); - TCPSession& operator=(const TCPSession &rhs); - ~TCPSession(); + /** + * \brief TCPStream constructor. + * \param ip The IP PDU from which to take the initial parameters. + * \param tcp The TCP PDU from which to take the initial parameters. + * \param identifier This stream's identifier number + */ + TCPStream(IP *ip, TCP *tcp, uint64_t identifier); + /** + * Copy constructor. + */ + TCPStream(const TCPStream &rhs); + + /** + * Copy assignment operator. + */ + TCPStream& operator=(const TCPStream &rhs); + + /** + * Destructor. + */ + ~TCPStream(); + + /** + * \brief Retrieves the client payload. + * + * This is the payload that the connection's client has sent so far. + * + * \return const payload_type& containing the payload. + */ const payload_type &client_payload() const { return client_payload_; } + /** + * \brief Retrieves the server payload. + * + * This is the payload that the connection's server has sent so far. + * + * \return const payload_type& containing the payload. + */ const payload_type &server_payload() const { return server_payload_; } - + + /** + * \brief Retrieves this stream's identification number. + * \return uint64_t containing the identification number. + */ uint64_t id() const { return identifier; } - const SessionInfo &session_info() const { + /** + * \brief Retrieves the stream information. + * \return const StreamInfo& containing the stream information. + */ + const StreamInfo &stream_info() const { return info; } - + + /** + * \brief Checks whether this stream is finished. + * + * A stream is considered to be finished, if at least one of the + * peers sends a TCP segment containing the FIN bit on. + * + * \return bool indicating whether the stream is finished. + */ bool is_finished() const { return fin_sent; } + /** + * \brief Updates the stream data. + * + * This may update both the payload and the expected sequence numbers. + * + * \param ip The IP PDU from which to take information. + * \param tcp The TCP PDU from which to take information. + * \return bool indicating whether any changes have been done to + * any of the stored payloads. + */ bool update(IP *ip, TCP *tcp); + + /** + * Clears the client payload. + */ void clear_client_payload(); + + /** + * Clears the server payload. + */ void clear_server_payload(); - - bool operator<(const TCPSession &rhs) const; private: typedef std::map fragments_type; @@ -91,22 +165,43 @@ private: bool generic_process(uint32_t &my_seq, uint32_t &other_seq, payload_type &pload, fragments_type &frags, TCP *tcp, RawPDU *raw); + uint32_t client_seq, server_seq; - SessionInfo info; + StreamInfo info; uint64_t identifier; payload_type client_payload_, server_payload_; fragments_type client_frags, server_frags; bool fin_sent; }; + +/** + * \class TCPStreamFollower + * \brief Follows TCP streams and notifies the user when data is available. + */ class TCPStreamFollower { public: + /** + * \brief Default constructor. + */ TCPStreamFollower(); + /** + * \brief Starts following TCP streams. + * + * The template functors must accept a TCPStream& as argument, which + * will point to the stream which has been modified. + * + * \param sniffer The sniffer which will be used to sniff PDUs. + * \param data_fun The function which will be called whenever one of + * the peers in a connection sends data. + * \param end_fun This function will be called when a stream is + * closed. + */ template void follow_streams(Sniffer &sniffer, DataFunctor data_fun, EndFunctor end_fun); private: - typedef std::map sessions_type; + typedef std::map sessions_type; template struct proxy_caller { @@ -138,7 +233,7 @@ bool TCPStreamFollower::callback(PDU *pdu, const DataFunctor &data_fun, const En IP *ip = pdu->find_pdu(); TCP *tcp = pdu->find_pdu(); if(ip && tcp) { - TCPSession::SessionInfo info = { + TCPStream::StreamInfo info = { ip->src_addr(), ip->dst_addr(), tcp->sport(), tcp->dport() }; @@ -151,7 +246,7 @@ bool TCPStreamFollower::callback(PDU *pdu, const DataFunctor &data_fun, const En sessions.insert( std::make_pair( info, - TCPSession(ip, tcp, last_identifier++) + TCPStream(ip, tcp, last_identifier++) ) ); } diff --git a/include/utils.h b/include/utils.h index b05879a..ffa26b4 100644 --- a/include/utils.h +++ b/include/utils.h @@ -22,11 +22,8 @@ #ifndef TINS_UTILS_H #define TINS_UTILS_H -#include - #ifndef WIN32 #include - #include #endif #include #include @@ -35,12 +32,10 @@ #include "packetsender.h" #include "ipaddress.h" #include "hwaddress.h" -#include "network_interface.h" - -#define TINS_IS_LITTLE_ENDIAN (__BYTE_ORDER == __LITTLE_ENDIAN) -#define TINS_IS_BIG_ENDIAN (__BYTE_ORDER == __BIG_ENDIAN) namespace Tins { + class NetworkInterface; + /** * \brief Network utils namespace. * diff --git a/src/arp.cpp b/src/arp.cpp index 432251d..ef39e79 100644 --- a/src/arp.cpp +++ b/src/arp.cpp @@ -19,7 +19,6 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ -#include #include #include #include @@ -28,9 +27,9 @@ #include "ethernetII.h" #include "rawpdu.h" #include "constants.h" +#include "network_interface.h" -using std::string; using std::runtime_error; namespace Tins { @@ -42,8 +41,8 @@ ARP::ARP(ipaddress_type target_ip, ipaddress_type sender_ip, memset(&_arp, 0, sizeof(arphdr)); hw_addr_format((uint16_t)Constants::ARP::ETHER); prot_addr_format((uint16_t)Constants::Ethernet::IP); - hw_addr_length(EthernetII::ADDR_SIZE); - prot_addr_length(IP::ADDR_SIZE); + hw_addr_length(Tins::EthernetII::address_type::address_size); + prot_addr_length(Tins::IP::address_type::address_size); sender_ip_addr(sender_ip); target_ip_addr(target_ip); sender_hw_addr(sender_hw); diff --git a/src/bootp.cpp b/src/bootp.cpp index 3b6c20a..049f43d 100644 --- a/src/bootp.cpp +++ b/src/bootp.cpp @@ -91,11 +91,13 @@ void BootP::giaddr(ipaddress_type new_giaddr) { } void BootP::sname(const uint8_t *new_sname) { - std::memcpy(_bootp.sname, new_sname, sizeof(_bootp.sname)); + //std::memcpy(_bootp.sname, new_sname, sizeof(_bootp.sname)); + std::copy(new_sname, new_sname + sizeof(_bootp.sname), _bootp.sname); } void BootP::file(const uint8_t *new_file) { - std::memcpy(_bootp.file, new_file, sizeof(_bootp.file)); + //std::memcpy(_bootp.file, new_file, sizeof(_bootp.file)); + std::copy(new_file, new_file + sizeof(_bootp.file), _bootp.file); } void BootP::vend(const vend_type &new_vend) { diff --git a/src/dhcp.cpp b/src/dhcp.cpp index a635db1..4ec05cc 100644 --- a/src/dhcp.cpp +++ b/src/dhcp.cpp @@ -20,11 +20,11 @@ */ #include -#include #include #include "endianness.h" #include "dhcp.h" #include "ethernetII.h" +#include "ipaddress.h" using std::string; using std::list; @@ -37,7 +37,7 @@ const uint32_t DHCP::MAX_DHCP_SIZE = 312; DHCP::DHCP() : _size(sizeof(uint32_t)) { opcode(BOOTREQUEST); htype(1); //ethernet - hlen(EthernetII::ADDR_SIZE); + hlen(EthernetII::address_type::address_size); } DHCP::DHCP(const uint8_t *buffer, uint32_t total_sz) diff --git a/src/dns.cpp b/src/dns.cpp index 3ce4496..c3f40d5 100644 --- a/src/dns.cpp +++ b/src/dns.cpp @@ -24,6 +24,7 @@ #include #include #include "dns.h" +#include "ipaddress.h" using std::string; using std::list; diff --git a/src/dot11.cpp b/src/dot11.cpp index 73ff153..6cbf781 100644 --- a/src/dot11.cpp +++ b/src/dot11.cpp @@ -24,7 +24,6 @@ #include #include #include -#include #ifndef WIN32 #include #include @@ -33,8 +32,8 @@ #include "dot11.h" #include "rawpdu.h" #include "radiotap.h" -#include "sniffer.h" #include "rsn_information.h" +#include "packetsender.h" #include "snap.h" using std::pair; diff --git a/src/ethernetII.cpp b/src/ethernetII.cpp index d5da864..f8b1e41 100644 --- a/src/ethernetII.cpp +++ b/src/ethernetII.cpp @@ -25,16 +25,17 @@ #include #ifndef WIN32 #include + #include #include #endif #include "ethernetII.h" +#include "packetsender.h" #include "rawpdu.h" #include "ip.h" #include "arp.h" namespace Tins { const EthernetII::address_type EthernetII::BROADCAST("ff:ff:ff:ff:ff:ff"); -const size_t EthernetII::ADDR_SIZE(address_type::address_size); EthernetII::EthernetII(const NetworkInterface& iface, const address_type &dst_hw_addr, const address_type &src_hw_addr, @@ -103,9 +104,9 @@ bool EthernetII::send(PacketSender* sender) { addr.sll_family = Endian::host_to_be(PF_PACKET); addr.sll_protocol = Endian::host_to_be(ETH_P_ALL); - addr.sll_halen = ADDR_SIZE; + addr.sll_halen = address_type::address_size; addr.sll_ifindex = _iface.id(); - memcpy(&(addr.sll_addr), _eth.dst_mac, ADDR_SIZE); + memcpy(&(addr.sll_addr), _eth.dst_mac, address_type::address_size); return sender->send_l2(this, (struct sockaddr*)&addr, (uint32_t)sizeof(addr)); } @@ -114,7 +115,7 @@ bool EthernetII::matches_response(uint8_t *ptr, uint32_t total_sz) { if(total_sz < sizeof(ethhdr)) return false; ethhdr *eth_ptr = (ethhdr*)ptr; - if(!memcmp(eth_ptr->dst_mac, _eth.src_mac, ADDR_SIZE)) { + if(!memcmp(eth_ptr->dst_mac, _eth.src_mac, address_type::address_size)) { // chequear broadcast en destino original... return (inner_pdu()) ? inner_pdu()->matches_response(ptr + sizeof(_eth), total_sz - sizeof(_eth)) : true; } @@ -149,9 +150,9 @@ PDU *EthernetII::recv_response(PacketSender *sender) { addr.sll_family = Endian::host_to_be(PF_PACKET); addr.sll_protocol = Endian::host_to_be(ETH_P_ALL); - addr.sll_halen = ADDR_SIZE; + addr.sll_halen = address_type::address_size; addr.sll_ifindex = _iface.id(); - memcpy(&(addr.sll_addr), _eth.dst_mac, ADDR_SIZE); + memcpy(&(addr.sll_addr), _eth.dst_mac, address_type::address_size); return sender->recv_l2(this, (struct sockaddr*)&addr, (uint32_t)sizeof(addr)); } diff --git a/src/ieee802_3.cpp b/src/ieee802_3.cpp index 621988a..5fe0bd6 100644 --- a/src/ieee802_3.cpp +++ b/src/ieee802_3.cpp @@ -25,9 +25,11 @@ #include #ifndef WIN32 #include + #include #include #endif #include "ieee802_3.h" +#include "packetsender.h" #include "llc.h" namespace Tins { @@ -46,17 +48,16 @@ IEEE802_3::IEEE802_3(const NetworkInterface& iface, } -IEEE802_3::IEEE802_3(const uint8_t *buffer, uint32_t total_sz) : PDU(ETHERTYPE_IP) { +IEEE802_3::IEEE802_3(const uint8_t *buffer, uint32_t total_sz) +: PDU(ETHERTYPE_IP) +{ if(total_sz < sizeof(ethhdr)) throw std::runtime_error("Not enough size for an ethernetII header in the buffer."); memcpy(&_eth, buffer, sizeof(ethhdr)); - PDU *next = 0; buffer += sizeof(ethhdr); total_sz -= sizeof(ethhdr); - if(total_sz) { - next = new Tins::LLC(buffer, total_sz); - inner_pdu(next); - } + if(total_sz) + inner_pdu(new Tins::LLC(buffer, total_sz)); } void IEEE802_3::dst_addr(const address_type &new_dst_mac) { diff --git a/src/ip.cpp b/src/ip.cpp index 0507ce5..c253fba 100644 --- a/src/ip.cpp +++ b/src/ip.cpp @@ -35,8 +35,7 @@ #include "utils.h" #include "constants.h" - -using namespace std; +using std::list; namespace Tins { diff --git a/src/llc.cpp b/src/llc.cpp index caa5923..fa4e943 100644 --- a/src/llc.cpp +++ b/src/llc.cpp @@ -22,15 +22,12 @@ #include #include #include -#include -#include #include "pdu.h" #include "llc.h" #include "rawpdu.h" using std::list; -using std::pair; namespace Tins { const uint8_t LLC::GLOBAL_DSAP_ADDR = 0xFF; @@ -81,16 +78,6 @@ LLC::LLC(const uint8_t *buffer, uint32_t total_sz) : PDU(0xff) { inner_pdu(new Tins::RawPDU(buffer, total_sz)); } -LLC::LLC(const LLC &other): PDU(other) { - copy_fields(&other); -} - -LLC &LLC::operator= (const LLC &other) { - copy_fields(&other); - copy_inner_pdu(other); - return *this; -} - void LLC::group(bool value) { if (value) { _header.dsap |= 0x01; @@ -183,17 +170,12 @@ void LLC::modifier_function(LLC::ModifierFunctions mod_func) { } void LLC::add_xid_information(uint8_t xid_id, uint8_t llc_type_class, uint8_t receive_window) { - uint8_t* XID = new uint8_t[3]; - XID[0] = 0; - XID[0] = xid_id; - XID[1] = 0; - XID[1] = llc_type_class; - XID[2] = 0; - XID[2] = receive_window & 0x7F; - - information_field_length += 3; - information_fields.push_back(std::pair(3, XID)); - + field_type xid(3); + xid[0] = xid_id; + xid[1] = llc_type_class; + xid[2] = receive_window; + information_field_length += xid.size(); + information_fields.push_back(xid); } uint32_t LLC::header_size() const { @@ -205,24 +187,6 @@ void LLC::clear_information_fields() { information_fields.clear(); } -Tins::PDU *LLC::clone_pdu() const { - LLC *new_pdu = new LLC(); - new_pdu->copy_fields(this); - return new_pdu; -} - -void LLC::copy_fields(const LLC *other) { - std::memcpy(&_header, &other->_header, sizeof(_header)); - control_field_length = other->control_field_length; - control_field = other->control_field; - information_field_length = other->information_field_length; - for (list >::const_iterator it = other->information_fields.begin(); it != other->information_fields.end(); it++) { - uint8_t* new_info_field = new uint8_t[it->first]; - std::memcpy(new_info_field, it->second, it->first); - information_fields.push_back(pair(it->first, new_info_field)); - } -} - void LLC::write_serialization(uint8_t *buffer, uint32_t total_sz, const Tins::PDU *parent) { assert(total_sz >= header_size()); std::memcpy(buffer, &_header, sizeof(_header)); @@ -242,9 +206,10 @@ void LLC::write_serialization(uint8_t *buffer, uint32_t total_sz, const Tins::PD break; } - for (list >::iterator it = information_fields.begin(); it != information_fields.end(); it++) { - std::memcpy(buffer, it->second, it->first); - buffer += it->first; + for (list::const_iterator it = information_fields.begin(); it != information_fields.end(); it++) { + //std::memcpy(buffer, it->second, it->first); + std::copy(it->begin(), it->end(), buffer); + buffer += it->size(); } } diff --git a/src/network_interface.cpp b/src/network_interface.cpp index f55173c..6594f56 100644 --- a/src/network_interface.cpp +++ b/src/network_interface.cpp @@ -20,11 +20,12 @@ */ #include -#include #include +#include #ifndef WIN32 #include #include + #include #endif #include "network_interface.h" #include "utils.h" diff --git a/src/packetsender.cpp b/src/packetsender.cpp index 0749ba0..1833df2 100644 --- a/src/packetsender.cpp +++ b/src/packetsender.cpp @@ -22,18 +22,20 @@ #ifndef WIN32 #include #include + #include #include #include #include #include #include + #include #endif #include #include #include -#include #include #include "packetsender.h" +#include "pdu.h" const int Tins::PacketSender::INVALID_RAW_SOCKET = -1; @@ -136,7 +138,7 @@ bool Tins::PacketSender::send_l3(PDU *pdu, struct sockaddr* link_addr, uint32_t return ret_val; } -Tins::PDU *Tins::PacketSender::recv_match_loop(int sock, PDU *pdu, struct sockaddr* link_addr, socklen_t addrlen) { +Tins::PDU *Tins::PacketSender::recv_match_loop(int sock, PDU *pdu, struct sockaddr* link_addr, uint32_t addrlen) { fd_set readfds; struct timeval timeout, end_time; int read; diff --git a/src/pdu.cpp b/src/pdu.cpp index 4dbaddc..17318ee 100644 --- a/src/pdu.cpp +++ b/src/pdu.cpp @@ -20,10 +20,9 @@ */ #include -#include -#include "utils.h" #include "pdu.h" #include "rawpdu.h" +#include "packetsender.h" namespace Tins { @@ -61,6 +60,14 @@ uint32_t PDU::size() const { return sz; } +bool PDU::send(PacketSender *) { + return false; +} + +PDU *PDU::recv_response(PacketSender *) { + return false; +} + void PDU::flag(uint32_t new_flag) { _flag = new_flag; } diff --git a/src/radiotap.cpp b/src/radiotap.cpp index ba3bf80..75c427b 100644 --- a/src/radiotap.cpp +++ b/src/radiotap.cpp @@ -21,6 +21,7 @@ #include #include +#include #ifndef WIN32 #include #include diff --git a/src/tcp_stream.cpp b/src/tcp_stream.cpp index 434f36b..a6514db 100644 --- a/src/tcp_stream.cpp +++ b/src/tcp_stream.cpp @@ -19,7 +19,6 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ -#include //borrame #include "rawpdu.h" #include "tcp_stream.h" @@ -31,7 +30,7 @@ TCPStreamFollower::TCPStreamFollower() : last_identifier(0) { -TCPSession::SessionInfo::SessionInfo(IPv4Address client, +TCPStream::StreamInfo::StreamInfo(IPv4Address client, IPv4Address server, uint16_t cport, uint16_t sport) : client_addr(client), server_addr(server), client_port(cport), server_port(sport) @@ -42,18 +41,18 @@ TCPSession::SessionInfo::SessionInfo(IPv4Address client, -TCPSession::TCPSession(IP *ip, TCP *tcp, uint64_t identifier) +TCPStream::TCPStream(IP *ip, TCP *tcp, uint64_t identifier) : client_seq(tcp->seq()), info(ip->src_addr(), ip->dst_addr(), tcp->sport(), tcp->dport()), identifier(identifier), fin_sent(false) { } -TCPSession::TCPSession(const TCPSession &rhs) { +TCPStream::TCPStream(const TCPStream &rhs) { *this = rhs; } -TCPSession& TCPSession::operator=(const TCPSession &rhs) { +TCPStream& TCPStream::operator=(const TCPStream &rhs) { client_seq = rhs.client_seq; server_seq = rhs.server_seq; info = rhs.info; @@ -66,31 +65,31 @@ TCPSession& TCPSession::operator=(const TCPSession &rhs) { return *this; } -TCPSession::~TCPSession() { +TCPStream::~TCPStream() { free_fragments(client_frags); free_fragments(server_frags); } -void TCPSession::free_fragments(fragments_type &frags) { +void TCPStream::free_fragments(fragments_type &frags) { for(fragments_type::iterator it = frags.begin(); it != frags.end(); ++it) delete it->second; } -TCPSession::fragments_type TCPSession::clone_fragments(const fragments_type &frags) { +TCPStream::fragments_type TCPStream::clone_fragments(const fragments_type &frags) { fragments_type new_frags; for(fragments_type::const_iterator it = frags.begin(); it != frags.end(); ++it) new_frags.insert(std::make_pair(it->first, it->second->clone_pdu())); return new_frags; } -bool TCPSession::generic_process(uint32_t &my_seq, uint32_t &other_seq, +bool TCPStream::generic_process(uint32_t &my_seq, uint32_t &other_seq, payload_type &pload, fragments_type &frags, TCP *tcp, RawPDU *raw) { //std::cout << "Entre, my seq: " << std::hex << my_seq << std::endl; bool added_some(false); if(tcp->get_flag(TCP::SYN)) other_seq++; - if(tcp->get_flag(TCP::FIN)) + if(tcp->get_flag(TCP::FIN) || tcp->get_flag(TCP::RST)) fin_sent = true; if(raw) { frags[tcp->seq()] = static_cast(tcp->release_inner_pdu()); @@ -113,7 +112,7 @@ bool TCPSession::generic_process(uint32_t &my_seq, uint32_t &other_seq, return added_some; } -bool TCPSession::update(IP *ip, TCP *tcp) { +bool TCPStream::update(IP *ip, TCP *tcp) { RawPDU *raw = tcp->find_pdu(); if(tcp->get_flag(TCP::SYN) && tcp->get_flag(TCP::ACK)) { server_seq = tcp->seq() + 1; @@ -124,39 +123,11 @@ bool TCPSession::update(IP *ip, TCP *tcp) { return generic_process(server_seq, client_seq, server_payload_, server_frags, tcp, raw); } -void TCPSession::clear_client_payload() { +void TCPStream::clear_client_payload() { client_payload_.clear(); } -void TCPSession::clear_server_payload() { +void TCPStream::clear_server_payload() { server_payload_.clear(); } - -bool TCPSession::SessionInfo::operator<(const SessionInfo &rhs) const { - if(client_addr == rhs.client_addr) { - if(server_addr == rhs.server_addr) { - if(client_port == rhs.client_port) { - return server_port < rhs.server_port; - } - else - return client_port < rhs.client_port; - } - else - return server_addr < rhs.server_addr; - } - else - return client_addr < rhs.client_addr; -} - -bool TCPSession::operator<(const TCPSession &rhs) const { - if(client_seq == rhs.client_seq) { - if(server_seq == rhs.server_seq) { - return info < rhs.info; - } - else - return server_seq < rhs.server_seq; - } - else - return client_seq < rhs.client_seq; -} } diff --git a/src/utils.cpp b/src/utils.cpp index 1e6c9c6..f567d58 100644 --- a/src/utils.cpp +++ b/src/utils.cpp @@ -21,7 +21,6 @@ #include #include -#include #include #include #include @@ -36,6 +35,7 @@ #include "icmp.h" #include "arp.h" #include "endianness.h" +#include "network_interface.h" using namespace std; diff --git a/tests/src/dhcp.cpp b/tests/src/dhcp.cpp index 07253ac..28d22d6 100644 --- a/tests/src/dhcp.cpp +++ b/tests/src/dhcp.cpp @@ -76,7 +76,7 @@ const uint8_t DHCPTest::expected_packet[] = { TEST_F(DHCPTest, DefaultConstructor) { DHCP dhcp; EXPECT_EQ(dhcp.htype(), 1); - EXPECT_EQ(dhcp.hlen(), EthernetII::ADDR_SIZE); + EXPECT_EQ(dhcp.hlen(), (const size_t)EthernetII::address_type::address_size); } TEST_F(DHCPTest, CopyConstructor) { @@ -312,7 +312,7 @@ TEST_F(DHCPTest, ConstructorFromBuffer) { EXPECT_EQ(dhcp1.opcode(), DHCP::DISCOVER); EXPECT_EQ(dhcp1.htype(), 1); - ASSERT_EQ(dhcp1.hlen(), EthernetII::ADDR_SIZE); + ASSERT_EQ(dhcp1.hlen(), (const size_t)EthernetII::address_type::address_size); EXPECT_EQ(dhcp1.hops(), 0x1f); EXPECT_EQ(dhcp1.xid(), 0x3fab23de); EXPECT_EQ(dhcp1.secs(), 0x9f1a);