author | mickeyl <mickeyl> | 2003-03-28 15:11:52 (UTC) |
---|---|---|
committer | mickeyl <mickeyl> | 2003-03-28 15:11:52 (UTC) |
commit | 11304d02942e9fa493e4e80943a828f9c65f6772 (patch) (side-by-side diff) | |
tree | a0223c10c067e1afc70d15c2b82be3f3c15e41ae /libopie2/opienet | |
parent | b271d575fa05cf570a1a829136517761bd47e69b (diff) | |
download | opie-11304d02942e9fa493e4e80943a828f9c65f6772.zip opie-11304d02942e9fa493e4e80943a828f9c65f6772.tar.gz opie-11304d02942e9fa493e4e80943a828f9c65f6772.tar.bz2 |
skeleton and the start of libopie2, please read README, ROADMAP and STATUS and comment...
-rw-r--r-- | libopie2/opienet/.cvsignore | 6 | ||||
-rw-r--r-- | libopie2/opienet/802_11_user.h | 419 | ||||
-rw-r--r-- | libopie2/opienet/config.in | 7 | ||||
-rw-r--r-- | libopie2/opienet/onetutils.cpp | 101 | ||||
-rw-r--r-- | libopie2/opienet/onetutils.h | 125 | ||||
-rw-r--r-- | libopie2/opienet/onetwork.cpp | 774 | ||||
-rw-r--r-- | libopie2/opienet/onetwork.h | 307 | ||||
-rw-r--r-- | libopie2/opienet/opcap.cpp | 609 | ||||
-rw-r--r-- | libopie2/opienet/opcap.h | 294 | ||||
-rw-r--r-- | libopie2/opienet/opienet.pro | 18 |
10 files changed, 2660 insertions, 0 deletions
diff --git a/libopie2/opienet/.cvsignore b/libopie2/opienet/.cvsignore new file mode 100644 index 0000000..8f7300c --- a/dev/null +++ b/libopie2/opienet/.cvsignore @@ -0,0 +1,6 @@ +Makefile* +moc* +*moc +*.o +~* + diff --git a/libopie2/opienet/802_11_user.h b/libopie2/opienet/802_11_user.h new file mode 100644 index 0000000..0b3f198 --- a/dev/null +++ b/libopie2/opienet/802_11_user.h @@ -0,0 +1,419 @@ +#ifndef IEEE_802_11 +#define IEEE_802_11 + +enum ieee_802_11_link_status_failure_reason { + reserved0, Unspecified=1, Previous_not_valid, + Sender_Quits_ESS_or_IBSS, + Due_Inactivity, AP_Overload, + Class_2_from_NonAuth, + Class_3_from_NonAuth, + Sender_Quits_BSS, + Association_requester_not_authenticated, + Reserved10 +}; + + +#define IEEE_802_11_LINK_STATUS_FAILURE_REASON_STRINGS \ +{ \ + {reserved0, 0xff," Reserved reason "},\ + {Unspecified, 0xff," Unspecified Reason "},\ + {Previous_not_valid, 0xff," Previous Authentication no longer valid "},\ + {Sender_Quits_ESS_or_IBSS,0xff," Deauthenticated because sending station is leaving (has left) IBSS or ESS "},\ + {Due_Inactivity, 0xff," Disassociated due to inactivity "},\ + {AP_Overload, 0xff," Disassociated because AP is unable to handle all currently associated stations "},\ + {Class_2_from_NonAuth, 0xff," Class 2 frame received from non-Authenticated station"},\ + {Class_3_from_NonAuth, 0xff," Class 3 frame received from nonAssociated station"},\ + {Sender_Quits_BSS, 0xff," Disassociated because sending station is leaving (has left) BSS"},\ + {Association_requester_not_authenticated,0xff," Station requesting (Re)Association is not Authenticated with responding station"},\ + {Reserved10, 0xff," Reserved"},\ + {0,0,NULL}\ +}; + + + +struct ieee_802_11_header { + u_int16_t frame_control;// needs to be subtyped + u_int16_t duration; + u_int8_t mac1[6]; + u_int8_t mac2[6]; + u_int8_t mac3[6]; + u_int16_t SeqCtl; + u_int8_t mac4[6]; +// u_int16_t gapLen; +// u_int8_t gap[8]; +}; + + +struct ieee_802_3_header { + + u_int16_t status; + u_int16_t payload_length; + u_int8_t dst_mac[6]; + u_int8_t src_mac[6]; + +}; + +#define P80211_OUI_LEN 3 + +struct ieee_802_11_snap_header { + + u_int8_t dsap; /* always 0xAA */ + u_int8_t ssap; /* always 0xAA */ + u_int8_t ctrl; /* always 0x03 */ + u_int8_t oui[P80211_OUI_LEN]; /* organizational universal id */ + +} __attribute__ ((packed)); + +#define P80211_LLC_OUI_LEN 3 + +struct ieee_802_11_802_1H_header { + + u_int8_t dsap; + u_int8_t ssap; /* always 0xAA */ + u_int8_t ctrl; /* always 0x03 */ + u_int8_t oui[P80211_OUI_LEN]; /* organizational universal id */ + u_int16_t unknown1; /* packet type ID fields */ + u_int16_t unknown2; /* here is something like length in some cases */ +} __attribute__ ((packed)); + +struct ieee_802_11_802_2_header { + + u_int8_t dsap; + u_int8_t ssap; /* always 0xAA */ + u_int8_t ctrl; /* always 0x03 */ + u_int8_t oui[P80211_OUI_LEN]; /* organizational universal id */ + u_int16_t type; /* packet type ID field */ + +} __attribute__ ((packed)); + + + +// following is incoplete and may be incorrect and need reorganization + +#define ieee_802_11_frame_type_Management 0x00 +#define ieee_802_11_frame_type_Control 0x01 +#define ieee_802_11_frame_type_Data 0x10 +#define ieee_802_11_frame_type_Reserved 0x11 + +#define ieee_802_11_frame_subtype_Association_Req 0x0 // Association Request +#define ieee_802_11_frame_subtype_Association_Resp 0x1 // Association Response +#define ieee_802_11_frame_subtype_Reassociation_Req 0x2 // Reassociation Request +#define ieee_802_11_frame_subtype_Reassociation_Resp 0x3 // Reassociation Response +#define ieee_802_11_frame_subtype_Probe_Req 0x4 // Probe Request +#define ieee_802_11_frame_subtype_Probe_Resp 0x5 // Probe Response +#define ieee_802_11_frame_subtype_Beacon 0x8 // Beacon +#define ieee_802_11_frame_subtype_ATIM 0x9 // ATIM +#define ieee_802_11_frame_subtype_Disassociation 0xA // Disassociation +#define ieee_802_11_frame_subtype_Authentication 0xB // Authentication +#define ieee_802_11_frame_subtype_Deauthentication 0xC // Deauthentication +#define ieee_802_11_frame_subtype_PS_Poll 0xA // PS-Poll +#define ieee_802_11_frame_subtype_RTS 0xB // RTS +#define ieee_802_11_frame_subtype_CTS 0xC // CTS +#define ieee_802_11_frame_subtype_ACK 0xD // ACK +#define ieee_802_11_frame_subtype_CFEnd 0xE // CF-End +#define ieee_802_11_frame_subtype_CFEnd_CFAck 0xF // CF-End + CF-Ack +#define ieee_802_11_frame_subtype_Data 0x0 // Data +#define ieee_802_11_frame_subtype_Data_CFAck 0x1 // Data + CF-Ack +#define ieee_802_11_frame_subtype_Data_CF_Poll 0x2 // Data + CF-Poll +#define ieee_802_11_frame_subtype_Data_CF_AckCF_Poll 0x3 // Data + CF-Ack + CF-Poll +#define ieee_802_11_frame_subtype_NullFunction 0x4 // Null Function (no data) +#define ieee_802_11_frame_subtype_CF_Ack 0x5 // CF-Ack (no data) +#define ieee_802_11_frame_subtype_CF_Poll 0x6 // CF-Poll (no data) +#define ieee_802_11_frame_subtype_CF_AckCF_Poll 0x7 // CF-Ack + CF-Poll (no data) + + +#define ieee_802_11_frame_subtype_strings {\ + { ieee_802_11_frame_subtype_Association_Req, 0xF,"f Association Request"},\ + { ieee_802_11_frame_subtype_Association_Resp, 0xF,"1 Association Response"},\ + { ieee_802_11_frame_subtype_Reassociation_Req, 0xF,"2 Reassociation Request"},\ + { ieee_802_11_frame_subtype_Reassociation_Resp, 0xF,"3 Reassociation Response"},\ + { ieee_802_11_frame_subtype_Probe_Req , 0xF,"4 Probe Request"},\ + { ieee_802_11_frame_subtype_Probe_Resp , 0xF,"5 Probe Response"},\ + { ieee_802_11_frame_subtype_Beacon , 0xF,"8 Beacon"},\ + { ieee_802_11_frame_subtype_ATIM , 0xF,"9 ATIM"},\ + { ieee_802_11_frame_subtype_Disassociation, 0xF,"A Disassociation"},\ + { ieee_802_11_frame_subtype_Authentication, 0xF,"B Authentication"},\ + { ieee_802_11_frame_subtype_Deauthentication, 0xF,"C Deauthentication"},\ + { ieee_802_11_frame_subtype_PS_Poll , 0xF,"A PS-Poll"},\ + { ieee_802_11_frame_subtype_RTS , 0xF,"B RTS"},\ + { ieee_802_11_frame_subtype_CTS , 0xF,"C CTS"},\ + { ieee_802_11_frame_subtype_ACK , 0xF,"D ACK"},\ + { ieee_802_11_frame_subtype_CFEnd , 0xF,"E CF-End"},\ + { ieee_802_11_frame_subtype_CFEnd_CFAck , 0xF,"F CF-End + CF-Ack"},\ + { ieee_802_11_frame_subtype_Data , 0xF,"0 Data"},\ + { ieee_802_11_frame_subtype_Data_CFAck , 0xF,"1 Data + CF-Ack"},\ + { ieee_802_11_frame_subtype_Data_CFPoll , 0xF,"2 Data + CF-Poll"},\ + { ieee_802_11_frame_subtype_Data_CFAck_CFPoll, 0xF,"3 Data + CF-Ack + CF-Poll"},\ + { ieee_802_11_frame_subtype_Null_Function , 0xF,"4 Null Function (no data)"},\ + { ieee_802_11_frame_subtype_CFAck , 0xF,"5 CF-Ack (no data)"},\ + { ieee_802_11_frame_subtype_CFPoll , 0xF,"6 CF-Poll (no data)"},\ + { ieee_802_11_frame_subtype_CFAck_CFPoll, 0xF,"y7 CF-Ack + CF-Poll (no data)"},\ + { 0,0,NULL}\ +} +struct ieee_802_11_frame_subtype_class { + u_int8_t subtype; + u_int8_t mask; + u_int8_t klass; + u_int8_t type; +}; +#define ieee_802_11_frame_subtype_classes {\ + { ieee_802_11_frame_subtype_Association_Req, 0xF,2,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_Association_Resp, 0xF,2,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_Reassociation_Req, 0xF,2,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_Reassociation_Resp, 0xF,2,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_Probe_Req , 0xF,1,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_Probe_Resp , 0xF,1,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_Beacon , 0xF,1,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_ATIM , 0xF,1,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_Disassociation, 0xF,2,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_Authentication, 0xF,1,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_Deauthentication, 0xF,3,ieee_802_11_frame_type_Management},\ + { ieee_802_11_frame_subtype_PS-Poll , 0xF,3,ieee_802_11_frame_type_Control},\ + { ieee_802_11_frame_subtype_RTS , 0xF,1,ieee_802_11_frame_type_Control},\ + { ieee_802_11_frame_subtype_CTS , 0xF,1,ieee_802_11_frame_type_Control},\ + { ieee_802_11_frame_subtype_ACK , 0xF,1,ieee_802_11_frame_type_Control},\ + { ieee_802_11_frame_subtype_CFEnd , 0xF,1,ieee_802_11_frame_type_Control},\ + { ieee_802_11_frame_subtype_CFEnd_CFAck , 0xF,1,ieee_802_11_frame_type_Control},\ + { ieee_802_11_frame_subtype_Data , 0xF,3,ieee_802_11_frame_type_Data},\ + { ieee_802_11_frame_subtype_Data_CFAck , 0xF,3,ieee_802_11_frame_type_Data},\ + { ieee_802_11_frame_subtype_Data_CF_Poll 0xF,3,ieee_802_11_frame_type_Data},\ + { ieee_802_11_frame_subtype_Data_CF_AckCF_Poll, 0xF,3,ieee_802_11_frame_type_Data},\ + { ieee_802_11_frame_subtype_NullFunction 0xF,1,ieee_802_11_frame_type_Data},\ + { ieee_802_11_frame_subtype_CF_Ack , 0xF,1,ieee_802_11_frame_type_Data},\ + { ieee_802_11_frame_subtype_CF_Poll , 0xF,1,ieee_802_11_frame_type_Data},\ + { ieee_802_11_frame_subtype_CF_AckCF_Poll, 0xF,1,ieee_802_11_frame_type_Data},\ + { 0,0,NULL}\ +} + +#define IEEE802_11_FC_LEN 2 + +#define T_MGMT 0x0 /* management */ +#define T_CTRL 0x1 /* control */ +#define T_DATA 0x2 /* data */ +#define T_RESV 0x3 /* reserved */ + +#define ST_ASSOC_REQUEST 0x0 +#define ST_ASSOC_RESPONSE 0x1 +#define ST_REASSOC_REQUEST 0x2 +#define ST_REASSOC_RESPONSE 0x3 +#define ST_PROBE_REQUEST 0x4 +#define ST_PROBE_RESPONSE 0x5 +/* RESERVED 0x6 */ +/* RESERVED 0x7 */ +#define ST_BEACON 0x8 +#define ST_ATIM 0x9 +#define ST_DISASSOC 0xA +#define ST_AUTH 0xB +#define ST_DEAUTH 0xC +/* RESERVED 0xD */ +/* RESERVED 0xE */ +/* RESERVED 0xF */ + + +#define CTRL_PS_POLL 0xA +#define CTRL_RTS 0xB +#define CTRL_CTS 0xC +#define CTRL_ACK 0xD +#define CTRL_CF_END 0xE +#define CTRL_END_ACK 0xF + +/* + * Bits in the frame control field. + */ +#define FC_VERSION(fc) ((fc) & 0x3) +#define FC_TYPE(fc) (((fc) >> 2) & 0x3) +#define FC_SUBTYPE(fc) (((fc) >> 4) & 0xF) +#define FC_TO_DS(fc) ((fc) & 0x0100) +#define FC_FROM_DS(fc) ((fc) & 0x0200) +#define FC_MORE_FLAG(fc) ((fc) & 0x0400) +#define FC_RETRY(fc) ((fc) & 0x0800) +#define FC_POWER_MGMT(fc) ((fc) & 0x1000) +#define FC_MORE_DATA(fc) ((fc) & 0x2000) +#define FC_WEP(fc) ((fc) & 0x4000) +#define FC_ORDER(fc) ((fc) & 0x8000) + + +struct ieee_802_11_mgmt_header { + u_int16_t fc; + u_int16_t duration; + u_int8_t da[6]; + u_int8_t sa[6]; + u_int8_t bssid[6]; + u_int16_t seq_ctrl; +}; + + +struct ieee_802_11_data_header { + u_int16_t frame_control; + u_int16_t duration; + u_int8_t mac1[6]; + u_int8_t mac2[6]; + u_int8_t mac3[6]; + u_int16_t SeqCtl; + u_int8_t mac4[6]; +// u_int16_t gapLen; +// u_int8_t gap[8]; +}; + +#define CAPABILITY_ESS(cap) ((cap) & 0x0001) +#define CAPABILITY_IBSS(cap) ((cap) & 0x0002) +#define CAPABILITY_CFP(cap) ((cap) & 0x0004) +#define CAPABILITY_CFP_REQ(cap) ((cap) & 0x0008) +#define CAPABILITY_PRIVACY(cap) ((cap) & 0x0010) + +struct ssid_t { + u_int8_t element_id; + u_int8_t length; + u_char ssid[33]; /* 32 + 1 for null */ +}; + + +struct rates_t { + u_int8_t element_id; + u_int8_t length; + u_int8_t rate[8]; +}; + + +struct challenge_t { + u_int8_t element_id; + u_int8_t length; + u_int8_t text[254]; /* 1-253 + 1 for null */ +}; + + +struct fh_t { + u_int8_t element_id; + u_int8_t length; + u_int16_t dwell_time; + u_int8_t hop_set; + u_int8_t hop_pattern; + u_int8_t hop_index; +}; + + +struct ds_t { + u_int8_t element_id; + u_int8_t length; + u_int8_t channel; +}; + + +struct cf_t { + u_int8_t element_id; + u_int8_t length; + u_int8_t count; + u_int8_t period; + u_int16_t max_duration; + u_int16_t dur_remaing; +}; + + +struct tim_t { + u_int8_t element_id; + u_int8_t length; + u_int8_t count; + u_int8_t period; + u_int8_t bitmap_control; + u_int8_t bitmap[251]; +}; + +#define E_SSID 0 +#define E_RATES 1 +#define E_FH 2 +#define E_DS 3 +#define E_CF 4 +#define E_TIM 5 +#define E_IBSS 6 +#define E_CHALLENGE 16 +#define E_CISCO 133 + + +struct ieee_802_11_mgmt_body { + u_int8_t timestamp[8]; + u_int16_t beacon_interval; +// u_int16_t listen_interval; +// u_int16_t status_code; +// u_int16_t aid; +// u_char ap[6]; +// u_int16_t reason_code; +// u_int16_t auth_alg; +// u_int16_t auth_trans_seq_num; +// struct challenge_t challenge; + u_int16_t capability_info; + struct ssid_t ssid; + struct rates_t rates; + struct ds_t ds; + struct cf_t cf; + struct fh_t fh; + struct tim_t tim; +}; + + +struct ieee_802_11_data_body { +//FIXME +}; + +struct ctrl_rts_t { + u_int16_t fc; + u_int16_t duration; + u_int8_t ra[6]; + u_int8_t ta[6]; + u_int8_t fcs[4]; +}; + +#define CTRL_RTS_LEN (2+2+6+6+4) + +struct ctrl_cts_t { + u_int16_t fc; + u_int16_t duration; + u_int8_t ra[6]; + u_int8_t fcs[4]; +}; + +#define CTRL_CTS_LEN (2+2+6+4) + +struct ctrl_ack_t { + u_int16_t fc; + u_int16_t duration; + u_int8_t ra[6]; + u_int8_t fcs[4]; +}; + +#define CTRL_ACK_LEN (2+2+6+4) + +struct ctrl_ps_poll_t { + u_int16_t fc; + u_int16_t aid; + u_int8_t bssid[6]; + u_int8_t ta[6]; + u_int8_t fcs[4]; +}; + +#define CTRL_PS_POLL_LEN (2+2+6+6+4) + +struct ctrl_end_t { + u_int16_t fc; + u_int16_t duration; + u_int8_t ra[6]; + u_int8_t bssid[6]; + u_int8_t fcs[4]; +}; + +#define CTRL_END_LEN (2+2+6+6+4) + +struct ctrl_end_ack_t { + u_int16_t fc; + u_int16_t duration; + u_int8_t ra[6]; + u_int8_t bssid[6]; + u_int8_t fcs[4]; +}; + +#define CTRL_END_ACK_LEN (2+2+6+6+4) + +#define IV_IV(iv) ((iv) & 0xFFFFFF) +#define IV_PAD(iv) (((iv) >> 24) & 0x3F) +#define IV_KEYID(iv) (((iv) >> 30) & 0x03) + +#endif diff --git a/libopie2/opienet/config.in b/libopie2/opienet/config.in new file mode 100644 index 0000000..5b235da --- a/dev/null +++ b/libopie2/opienet/config.in @@ -0,0 +1,7 @@ + config LIBOPIE2NET + boolean "libopie2net (network and packet capturing related classes)" + default "n" + depends ( LIBQPE || LIBQPE-X11 ) && LIBOPIE2CORE + comment "libopie2net needs a libqpe and libopie2core" + depends !(( LIBQPE || LIBQPE-X11 ) && LIBOPIE2CORE) + diff --git a/libopie2/opienet/onetutils.cpp b/libopie2/opienet/onetutils.cpp new file mode 100644 index 0000000..8006f41 --- a/dev/null +++ b/libopie2/opienet/onetutils.cpp @@ -0,0 +1,101 @@ +/* + This file is part of the Opie Project + + (C) 2003 Michael 'Mickey' Lauer <mickey@tm.informatik.uni-frankfurt.de> + =. + .=l. + .>+-= + _;:, .> :=|. This program is free software; you can +.> <`_, > . <= redistribute it and/or modify it under +:`=1 )Y*s>-.-- : the terms of the GNU Library General Public +.="- .-=="i, .._ License as published by the Free Software + - . .-<_> .<> Foundation; either version 2 of the License, + ._= =} : or (at your option) any later version. + .%`+i> _;_. + .i_,=:_. -<s. 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 +..}^=.= = ; Library General Public License for more +++= -. .` .: details. + : = ...= . :.=- + -. .:....=;==+<; You should have received a copy of the GNU + -_. . . )=. = Library General Public License along with + -- :-=` this library; see the file COPYING.LIB. + If not, write to the Free Software Foundation, + Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + +*/ + +#include <opie2/onetutils.h> + +#include <net/if.h> + +#include <cstdio> +using namespace std; + +/*====================================================================================== + * OMacAddress + *======================================================================================*/ + +// static initializer for broadcast and unknown MAC Adresses +const unsigned char __broadcast[6] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; +const OMacAddress& OMacAddress::broadcast = OMacAddress( __broadcast ); +const unsigned char __unknown[6] = { 0x44, 0x44, 0x44, 0x44, 0x44, 0x44 }; +const OMacAddress& OMacAddress::unknown = OMacAddress( __unknown ); + + +//TODO: Incorporate Ethernet Manufacturer database here! + +OMacAddress::OMacAddress( unsigned char* p ) +{ + memcpy( _bytes, p, 6 ); // D'OH! memcpy in my sources... eeek... +} + + +OMacAddress::OMacAddress( const unsigned char* p ) +{ + memcpy( _bytes, p, 6 ); +} + + +OMacAddress::OMacAddress( struct ifreq& ifr ) +{ + memcpy( _bytes, ifr.ifr_hwaddr.sa_data, 6 ); +} + + +OMacAddress::~OMacAddress() +{ +} + + +QString OMacAddress::toString() const +{ + QString s; + s.sprintf( "%.2X:%.2X:%.2X:%.2X:%.2X:%.2X", + _bytes[0]&0xff, _bytes[1]&0xff, _bytes[2]&0xff, + _bytes[3]&0xff, _bytes[4]&0xff, _bytes[5]&0xff ); + return s; +} + + +bool operator==( const OMacAddress &m1, const OMacAddress &m2 ) +{ + return memcmp( &m1._bytes, &m2._bytes, 6 ) == 0; +} + +void dumpBytes( const unsigned char* data, int num ) +{ + printf( "Dumping %d bytes @ %0x", num, data ); + printf( "-------------------------------------------\n" ); + + for ( int i = 0; i < num; ++i ) + { + printf( "%02x ", data[i] ); + if ( !((i+1) % 32) ) printf( "\n" ); + } + printf( "\n\n" ); +} diff --git a/libopie2/opienet/onetutils.h b/libopie2/opienet/onetutils.h new file mode 100644 index 0000000..0dabe8d --- a/dev/null +++ b/libopie2/opienet/onetutils.h @@ -0,0 +1,125 @@ +/* + This file is part of the Opie Project + + (C) 2003 Michael 'Mickey' Lauer <mickey@tm.informatik.uni-frankfurt.de> + =. + .=l. + .>+-= + _;:, .> :=|. This program is free software; you can +.> <`_, > . <= redistribute it and/or modify it under +:`=1 )Y*s>-.-- : the terms of the GNU Library General Public +.="- .-=="i, .._ License as published by the Free Software + - . .-<_> .<> Foundation; either version 2 of the License, + ._= =} : or (at your option) any later version. + .%`+i> _;_. + .i_,=:_. -<s. 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 +..}^=.= = ; Library General Public License for more +++= -. .` .: details. + : = ...= . :.=- + -. .:....=;==+<; You should have received a copy of the GNU + -_. . . )=. = Library General Public License along with + -- :-=` this library; see the file COPYING.LIB. + If not, write to the Free Software Foundation, + Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + +*/ + +#ifndef ONETUTILS_H +#define ONETUTILS_H + +#include <qdict.h> +#include <qmap.h> +#include <qstring.h> +#include <qhostaddress.h> + +struct ifreq; + +/*====================================================================================== + * OMacAddress + *======================================================================================*/ + +class OMacAddress +{ + public: + OMacAddress( unsigned char* ); + OMacAddress( const unsigned char* ); + OMacAddress( struct ifreq& ); + ~OMacAddress(); + + QString toString() const; + + public: + static const OMacAddress& broadcast; // ff:ff:ff:ff:ff:ff + static const OMacAddress& unknown; // 44:44:44:44:44:44 + + private: + unsigned char _bytes[6]; + + friend bool operator==( const OMacAddress &m1, const OMacAddress &m2 ); + +}; + +bool operator==( const OMacAddress &m1, const OMacAddress &m2 ); + + +/*====================================================================================== + * OHostAddress + *======================================================================================*/ + +class OHostAddress : public QHostAddress +{ + public: + OHostAddress(); + ~OHostAddress(); +}; + + +/*====================================================================================== + * Miscellaneous + *======================================================================================*/ + +/* dump bytes */ + +void dumpBytes( const unsigned char* data, int num ); + +/* Network to host order macros */ + +#ifdef LBL_ALIGN +#define EXTRACT_16BITS(p) \ + ((u_int16_t)((u_int16_t)*((const u_int8_t *)(p) + 0) << 8 | \ + (u_int16_t)*((const u_int8_t *)(p) + 1))) +#define EXTRACT_32BITS(p) \ + ((u_int32_t)((u_int32_t)*((const u_int8_t *)(p) + 0) << 24 | \ + (u_int32_t)*((const u_int8_t *)(p) + 1) << 16 | \ + (u_int32_t)*((const u_int8_t *)(p) + 2) << 8 | \ + (u_int32_t)*((const u_int8_t *)(p) + 3))) +#else +#define EXTRACT_16BITS(p) \ + ((u_int16_t)ntohs(*(const u_int16_t *)(p))) +#define EXTRACT_32BITS(p) \ + ((u_int32_t)ntohl(*(const u_int32_t *)(p))) +#endif + +#define EXTRACT_24BITS(p) \ + ((u_int32_t)((u_int32_t)*((const u_int8_t *)(p) + 0) << 16 | \ + (u_int32_t)*((const u_int8_t *)(p) + 1) << 8 | \ + (u_int32_t)*((const u_int8_t *)(p) + 2))) + +/* Little endian protocol host order macros */ +#define EXTRACT_LE_8BITS(p) (*(p)) +#define EXTRACT_LE_16BITS(p) \ + ((u_int16_t)((u_int16_t)*((const u_int8_t *)(p) + 1) << 8 | \ + (u_int16_t)*((const u_int8_t *)(p) + 0))) +#define EXTRACT_LE_32BITS(p) \ + ((u_int32_t)((u_int32_t)*((const u_int8_t *)(p) + 3) << 24 | \ + (u_int32_t)*((const u_int8_t *)(p) + 2) << 16 | \ + (u_int32_t)*((const u_int8_t *)(p) + 1) << 8 | \ + (u_int32_t)*((const u_int8_t *)(p) + 0))) + +#endif // ONETUTILS_H + diff --git a/libopie2/opienet/onetwork.cpp b/libopie2/opienet/onetwork.cpp new file mode 100644 index 0000000..1d3b9fe --- a/dev/null +++ b/libopie2/opienet/onetwork.cpp @@ -0,0 +1,774 @@ +/* + This file is part of the Opie Project + Copyright (C) 2003 by the Wellenreiter team: + Martin J. Muench <mjm@remote-exploit.org> + Max Moser <mmo@remote-exploit.org + Michael 'Mickey' Lauer <mickey@tm.informatik.uni-frankfurt.de> + =. + .=l. + .>+-= + _;:, .> :=|. This program is free software; you can +.> <`_, > . <= redistribute it and/or modify it under +:`=1 )Y*s>-.-- : the terms of the GNU Library General Public +.="- .-=="i, .._ License as published by the Free Software + - . .-<_> .<> Foundation; either version 2 of the License, + ._= =} : or (at your option) any later version. + .%`+i> _;_. + .i_,=:_. -<s. 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 +..}^=.= = ; Library General Public License for more +++= -. .` .: details. + : = ...= . :.=- + -. .:....=;==+<; You should have received a copy of the GNU + -_. . . )=. = Library General Public License along with + -- :-=` this library; see the file COPYING.LIB. + If not, write to the Free Software Foundation, + Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + +*/ + +/* OPIE */ + +#include <opie2/onetwork.h> + +/* QT */ + +#include <qfile.h> +#include <qtextstream.h> + +/* UNIX */ + +#include <arpa/inet.h> +#include <cerrno> +#include <cstring> +#include <cstdlib> +#include <math.h> +#include <sys/ioctl.h> +#include <sys/socket.h> +#include <sys/types.h> +#include <unistd.h> +#include <linux/wireless.h> + +using namespace std; + +/*====================================================================================== + * ONetwork + *======================================================================================*/ + +ONetwork* ONetwork::_instance = 0; + +ONetwork::ONetwork() +{ + qDebug( "ONetwork::ONetwork()" ); + synchronize(); +} + +void ONetwork::synchronize() +{ + // gather available interfaces by inspecting /proc/net/dev + // we could use SIOCGIFCONF here, but we aren't interested in virtual (e.g. eth0:0) devices + + _interfaces.clear(); + QString str; + QFile f( "/proc/net/dev" ); + bool hasFile = f.open( IO_ReadOnly ); + if ( !hasFile ) + { + qDebug( "ONetwork: /proc/net/dev not existing. No network devices available" ); + return; + } + QTextStream s( &f ); + s.readLine(); + s.readLine(); + while ( !s.atEnd() ) + { + s >> str; + str.truncate( str.find( ':' ) ); + qDebug( "ONetwork: found interface '%s'", (const char*) str ); + ONetworkInterface* iface; + if ( isWirelessInterface( str ) ) + { + iface = new OWirelessNetworkInterface( str ); + qDebug( "ONetwork: interface '%s' has Wireless Extensions", (const char*) str ); + } + else + { + iface = new ONetworkInterface( str ); + } + _interfaces.insert( str, iface ); + s.readLine(); + } +} + + +ONetworkInterface* ONetwork::interface( QString iface ) const +{ + return _interfaces[iface]; +} + + +ONetwork* ONetwork::instance() +{ + if ( !_instance ) _instance = new ONetwork(); + return _instance; +} + + +ONetwork::InterfaceIterator ONetwork::iterator() const +{ + return ONetwork::InterfaceIterator( _interfaces ); +} + + +bool ONetwork::isWirelessInterface( const char* name ) const +{ + int sfd = socket( AF_INET, SOCK_DGRAM, 0 ); + iwreqstruct iwr; + memset( &iwr, 0, sizeof( iwreqstruct ) ); + strcpy( (char*) &iwr.ifr_name, name ); + int result = ::ioctl( sfd, SIOCGIWNAME, &iwr ); + if ( result == -1 ) + qDebug( "ONetwork::ioctl(): SIOCGIWNAME failed: %d (%s)", result, strerror( errno ) ); + else + qDebug( "ONetwork::ioctl(): SIOCGIWNAME ok." ); + return ( result != -1 ); +} + +/*====================================================================================== + * ONetworkInterface + *======================================================================================*/ + +ONetworkInterface::ONetworkInterface( const QString& name ) + :_name( name ), _sfd( socket( AF_INET, SOCK_DGRAM, 0 ) ), _mon( 0 ) +{ + qDebug( "ONetworkInterface::ONetworkInterface()" ); + init(); +} + + +ifreqstruct& ONetworkInterface::ifr() const +{ + return _ifr; +} + + +void ONetworkInterface::init() +{ + qDebug( "ONetworkInterface::init()" ); + + memset( &_ifr, 0, sizeof( struct ifreq ) ); + + if ( _sfd == -1 ) + { + qDebug( "ONetworkInterface::init(): Warning - can't get socket for device '%s'", (const char*) _name ); + return; + } +} + + +bool ONetworkInterface::ioctl( int call, ifreqstruct& ifreq ) const +{ + int result = ::ioctl( _sfd, call, &ifreq ); + if ( result == -1 ) + qDebug( "ONetworkInterface::ioctl(): Call %d - Status: Failed: %d (%s)", call, result, strerror( errno ) ); + else + qDebug( "ONetworkInterface::ioctl(): Call %d - Status: Ok.", call ); + return ( result != -1 ); +} + + +bool ONetworkInterface::ioctl( int call ) const +{ + strcpy( _ifr.ifr_name, (const char*) _name ); + return ioctl( call, _ifr ); +} + + +bool ONetworkInterface::isLoopback() const +{ + ioctl( SIOCGIFFLAGS ); + return _ifr.ifr_flags & IFF_LOOPBACK; +} + + +bool ONetworkInterface::setUp( bool b ) +{ + ioctl( SIOCGIFFLAGS ); + if ( b ) _ifr.ifr_flags |= IFF_UP; + else _ifr.ifr_flags &= (~IFF_UP); + return ioctl( SIOCSIFFLAGS ); +} + + +bool ONetworkInterface::isUp() const +{ + ioctl( SIOCGIFFLAGS ); + return _ifr.ifr_flags & IFF_UP; +} + + +QString ONetworkInterface::ipV4Address() const +{ + if ( ioctl( SIOCGIFADDR ) ) + { + struct sockaddr_in *sa = (struct sockaddr_in *) &_ifr.ifr_addr; + //FIXME: Use QHostAddress here + return QString( inet_ntoa( sa->sin_addr ) ); + } + else + return "<unknown>"; +} + + +OMacAddress ONetworkInterface::macAddress() const +{ + if ( ioctl( SIOCGIFHWADDR ) ) + { + return OMacAddress( _ifr ); + } + else + { + return OMacAddress::unknown; + } +} + + +void ONetworkInterface::setMonitoring( OMonitoringInterface* m ) +{ + _mon = m; + qDebug( "ONetwork::setMonitoring(): Installed monitoring interface '%s'", (const char*) m->name() ); +} + + +OMonitoringInterface* ONetworkInterface::monitoring() const +{ + return _mon; +} + + +const QString& ONetworkInterface::name() const +{ + return _name; +} + + +ONetworkInterface::~ONetworkInterface() +{ + qDebug( "ONetworkInterface::~ONetworkInterface()" ); + if ( _sfd != -1 ) ::close( _sfd ); +} + + +bool ONetworkInterface::setPromiscuousMode( bool b ) +{ + ioctl( SIOCGIFFLAGS ); + if ( b ) _ifr.ifr_flags |= IFF_PROMISC; + else _ifr.ifr_flags &= (~IFF_PROMISC); + return ioctl( SIOCSIFFLAGS ); +} + + +bool ONetworkInterface::promiscuousMode() const +{ + ioctl( SIOCGIFFLAGS ); + return _ifr.ifr_flags & IFF_PROMISC; +} + + +bool ONetworkInterface::isWireless() const +{ + return ioctl( SIOCGIWNAME ); +} + + +/*====================================================================================== + * OChannelHopper + *======================================================================================*/ + +OChannelHopper::OChannelHopper( OWirelessNetworkInterface* iface ) + :QObject( 0, "Mickey's funky hopper" ), + _iface( iface ), _interval( 0 ), _channel( 0 ), _tid( 0 ) +{ +} + + +OChannelHopper::~OChannelHopper() +{ +} + + +void OChannelHopper::timerEvent( QTimerEvent* ) +{ + //FIXME: Get available channels from OWirelessNetworkInterface + if ( --_channel < 0 ) _channel = 13; + _iface->setChannel( _channel ); + qDebug( "OChannelHopper::timerEvent(): set channel %d on interface '%s'", + _channel, (const char*) _iface->name() ); +} + + +void OChannelHopper::setInterval( int interval ) +{ + if ( interval == _interval ) + return; + + if ( _interval ) + killTimer( _tid ); + + _interval = interval; + + if ( _interval ) + { + _tid = startTimer( interval ); + } +} + + +int OChannelHopper::interval() const +{ + return _interval; +} + + +/*====================================================================================== + * OWirelessNetworkInterface + *======================================================================================*/ + +OWirelessNetworkInterface::OWirelessNetworkInterface( const QString& name ) + :ONetworkInterface( name ), _hopper( this ) +{ + qDebug( "OWirelessNetworkInterface::OWirelessNetworkInterface()" ); + init(); +} + + +OWirelessNetworkInterface::~OWirelessNetworkInterface() +{ +} + + +iwreqstruct& OWirelessNetworkInterface::iwr() const +{ + return _iwr; +} + + +void OWirelessNetworkInterface::init() +{ + qDebug( "OWirelessNetworkInterface::init()" ); + + memset( &_iwr, 0, sizeof( struct iwreq ) ); + + // IEEE802.11(b) radio frequency channels + //FIXME: get these directly from the interface + //FIXME: check if these channels are off-by-one + + iwrangestruct range; + _iwr.u.data.pointer = (char*) ⦥ + _iwr.u.data.length = sizeof( iwrangestruct ); + if ( !wioctl( SIOCGIWRANGE ) ) + { + qDebug( "OWirelessNetworkInterface::init(): SIOCGIWRANGE failed (%s)", strerror( errno ) ); + return; + } + + //TODO: Find out what the difference between num_channel and + // num_frequency is about. + + for ( int i = 0; i < range.num_frequency; ++i ) + { + int freq = (int) ( double( range.freq[i].m ) * pow( 10, range.freq[i].e ) / 1000000.0 ); + _channels.insert( freq, i ); + } +} + + +QString OWirelessNetworkInterface::associatedAP() const +{ + //FIXME: use OMacAddress + QString mac; + + if ( ioctl( SIOCGIWAP ) ) + { + mac.sprintf( "%.2X:%.2X:%.2X:%.2X:%.2X:%.2X", + _ifr.ifr_hwaddr.sa_data[0]&0xff, + _ifr.ifr_hwaddr.sa_data[1]&0xff, + _ifr.ifr_hwaddr.sa_data[2]&0xff, + _ifr.ifr_hwaddr.sa_data[3]&0xff, + _ifr.ifr_hwaddr.sa_data[4]&0xff, + _ifr.ifr_hwaddr.sa_data[5]&0xff ); + } + else + { + mac = "<Unknown>"; + } + return mac; +} + + +int OWirelessNetworkInterface::channel() const +{ + if ( !wioctl( SIOCGIWFREQ ) ) + { + return -1; + } + else + { + //FIXME: This is off-by-one !? Why? + return _channels[ static_cast<int>(double( _iwr.u.freq.m ) * pow( 10, _iwr.u.freq.e ) / 1000000) ]; + } +} + + +void OWirelessNetworkInterface::setChannel( int c ) const +{ + if ( !_mon ) + { + memset( &_iwr, 0, sizeof( iwreqstruct ) ); + _iwr.u.freq.m = c; + _iwr.u.freq.e = 0; + wioctl( SIOCSIWFREQ ); + } + else + { + _mon->setChannel( c ); + } +} + + +double OWirelessNetworkInterface::frequency() const +{ + if ( !wioctl( SIOCGIWFREQ ) ) + { + return -1.0; + } + else + { + return double( _iwr.u.freq.m ) * pow( 10, _iwr.u.freq.e ) / 1000000000.0; + } +} + + +int OWirelessNetworkInterface::channels() const +{ + return _channels.count(); +} + + +void OWirelessNetworkInterface::setChannelHopping( int interval ) +{ + _hopper.setInterval( interval ); +} + + +int OWirelessNetworkInterface::channelHopping() const +{ + return _hopper.interval(); +} + + +void OWirelessNetworkInterface::setMonitorMode( bool b ) +{ + if ( _mon ) + _mon->setEnabled( b ); + else + qDebug( "ONetwork(): can't switch monitor mode without installed monitoring interface" ); +} + +bool OWirelessNetworkInterface::monitorMode() const +{ + return _mon ? _mon->enabled() : false; +} + + +QString OWirelessNetworkInterface::nickName() const +{ + char str[IW_ESSID_MAX_SIZE]; + _iwr.u.data.pointer = &str[0]; + _iwr.u.data.length = IW_ESSID_MAX_SIZE; + if ( !wioctl( SIOCGIWNICKN ) ) + { + return "<unknown>"; + } + else + { + str[_iwr.u.data.length] = 0x0; // some drivers (e.g. wlan-ng) don't zero-terminate the string + return str; + } +} + + +QString OWirelessNetworkInterface::SSID() const +{ + char str[IW_ESSID_MAX_SIZE]; + _iwr.u.essid.pointer = &str[0]; + _iwr.u.essid.length = IW_ESSID_MAX_SIZE; + if ( !wioctl( SIOCGIWESSID ) ) + { + return "<unknown>"; + } + else + { + return str; + } +} + + +void OWirelessNetworkInterface::setSSID( const QString& ssid ) +{ + _iwr.u.essid.pointer = const_cast<char*>( (const char*) ssid ); + _iwr.u.essid.length = ssid.length(); + wioctl( SIOCSIWESSID ); +} + + +bool OWirelessNetworkInterface::wioctl( int call, iwreqstruct& iwreq ) const +{ + int result = ::ioctl( _sfd, call, &iwreq ); + if ( result == -1 ) + qDebug( "ONetworkInterface::wioctl(): Call %d - Status: Failed: %d (%s)", call, result, strerror( errno ) ); + else + qDebug( "ONetworkInterface::wioctl(): Call %d - Status: Ok.", call ); + return ( result != -1 ); +} + + +bool OWirelessNetworkInterface::wioctl( int call ) const +{ + strcpy( _iwr.ifr_name, (const char*) _name ); + return wioctl( call, _iwr ); +} + + +/*====================================================================================== + * OMonitoringInterface + *======================================================================================*/ + +OMonitoringInterface::OMonitoringInterface( ONetworkInterface* iface ) + :_enabled( false ), _if( static_cast<OWirelessNetworkInterface*>( iface ) ) +{ +} + + +OMonitoringInterface::~OMonitoringInterface() +{ +} + + +void OMonitoringInterface::setChannel( int c ) +{ + // use standard WE channel switching protocol + memset( &_if->_iwr, 0, sizeof( iwreqstruct ) ); + _if->_iwr.u.freq.m = c; + _if->_iwr.u.freq.e = 0; + _if->wioctl( SIOCSIWFREQ ); +} + + +bool OMonitoringInterface::enabled() const +{ + return _enabled; +} + +void OMonitoringInterface::setEnabled( bool b ) +{ + // open a packet capturer here or leave this to + // the client code? + + /* + + if ( b ) + { + OPacketCapturer* opcap = new OPacketCapturer(); + opcap->open( _if->name() ); + } + */ + + _enabled = b; + +} + +/*====================================================================================== + * OCiscoMonitoringInterface + *======================================================================================*/ + +OCiscoMonitoringInterface::OCiscoMonitoringInterface( ONetworkInterface* iface ) + :OMonitoringInterface( iface ) +{ + iface->setMonitoring( this ); +} + + +OCiscoMonitoringInterface::~OCiscoMonitoringInterface() +{ +} + + +void OCiscoMonitoringInterface::setEnabled( bool b ) +{ + QString fname; + fname.sprintf( "/proc/driver/aironet/%s", (const char*) _if->name() ); + QFile f( fname ); + if ( !f.exists() ) return; + + if ( f.open( IO_WriteOnly ) ) + { + QTextStream s( &f ); + s << "Mode: r"; + s << "Mode: y"; + s << "XmitPower: 1"; + + OMonitoringInterface::setEnabled( b ); + + } + + // flushing and closing will be done automatically when f goes out of scope +} + + +QString OCiscoMonitoringInterface::name() const +{ + return "cisco"; +} + + +void OCiscoMonitoringInterface::setChannel( int ) +{ + // cisco devices automatically switch channels when in monitor mode +} + + +/*====================================================================================== + * OWlanNGMonitoringInterface + *======================================================================================*/ + + +OWlanNGMonitoringInterface::OWlanNGMonitoringInterface( ONetworkInterface* iface ) + :OMonitoringInterface( iface ) +{ + iface->setMonitoring( this ); +} + + +OWlanNGMonitoringInterface::~OWlanNGMonitoringInterface() +{ +} + + +void OWlanNGMonitoringInterface::setEnabled( bool b ) +{ + //FIXME: do nothing if its already in the same mode + + QString enable = b ? "true" : "false"; + QString cmd; + cmd.sprintf( "$(which wlanctl-ng) %s lnxreq_wlansniff channel=%d enable=%s", (const char*) _if->name(), 1, (const char*) enable ); + system( cmd ); + + OMonitoringInterface::setEnabled( b ); +} + + +QString OWlanNGMonitoringInterface::name() const +{ + return "wlan-ng"; +} + + +void OWlanNGMonitoringInterface::setChannel( int ) +{ + // wlan-ng devices automatically switch channels when in monitor mode +} + + +/*====================================================================================== + * OHostAPMonitoringInterface + *======================================================================================*/ + +OHostAPMonitoringInterface::OHostAPMonitoringInterface( ONetworkInterface* iface ) + :OMonitoringInterface( iface ) +{ + iface->setMonitoring( this ); +} + +OHostAPMonitoringInterface::~OHostAPMonitoringInterface() +{ +} + +void OHostAPMonitoringInterface::setEnabled( bool b ) +{ + // IW_MODE_MONITOR was introduced in Wireless Extensions Version 15 + // Wireless Extensions < Version 15 need iwpriv commandos for monitoring + + #if WIRELESS_EXT > 14 + _if->_iwr.u.mode = IW_MODE_MONITOR; + _if->wioctl( SIOCSIWMODE ); + #else + int* args = (int*) &_if._iwr.u.name; + args[0] = 2; + args[1] = 0; + _if->wioctl( SIOCDEVPRIVATE ); + #endif + + OMonitoringInterface::setEnabled( b ); +} + + +QString OHostAPMonitoringInterface::name() const +{ + return "hostap"; +} + + +/*====================================================================================== + * OOrinocoNetworkInterface + *======================================================================================*/ + +OOrinocoMonitoringInterface::OOrinocoMonitoringInterface( ONetworkInterface* iface ) + :OMonitoringInterface( iface ) +{ + iface->setMonitoring( this ); +} + + +OOrinocoMonitoringInterface::~OOrinocoMonitoringInterface() +{ +} + + +void OOrinocoMonitoringInterface::setChannel( int c ) +{ + // call iwpriv <device> monitor 2 <channel> + int* args = (int*) &_if->_iwr.u.name; + args[0] = 2; + args[1] = c; + _if->wioctl( SIOCIWFIRSTPRIV + 0x8 ); +} + + +void OOrinocoMonitoringInterface::setEnabled( bool b ) +{ + if ( b ) + { + setChannel( 1 ); + } + else + { + // call iwpriv <device> monitor 0 0 + int* args = (int*) &_if->_iwr.u.name; + args[0] = 0; + args[1] = 0; + _if->wioctl( SIOCIWFIRSTPRIV + 0x8 ); + } + + OMonitoringInterface::setEnabled( b ); +} + + +QString OOrinocoMonitoringInterface::name() const +{ + return "orinoco"; +} diff --git a/libopie2/opienet/onetwork.h b/libopie2/opienet/onetwork.h new file mode 100644 index 0000000..9a68a74 --- a/dev/null +++ b/libopie2/opienet/onetwork.h @@ -0,0 +1,307 @@ +/* + This file is part of the Opie Project + Copyright (C) 2003 by the Wellenreiter team: + Martin J. Muench <mjm@remote-exploit.org> + Max Moser <mmo@remote-exploit.org + Michael 'Mickey' Lauer <mickey@tm.informatik.uni-frankfurt.de> + =. + .=l. + .>+-= + _;:, .> :=|. This program is free software; you can +.> <`_, > . <= redistribute it and/or modify it under +:`=1 )Y*s>-.-- : the terms of the GNU Library General Public +.="- .-=="i, .._ License as published by the Free Software + - . .-<_> .<> Foundation; either version 2 of the License, + ._= =} : or (at your option) any later version. + .%`+i> _;_. + .i_,=:_. -<s. 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 +..}^=.= = ; Library General Public License for more +++= -. .` .: details. + : = ...= . :.=- + -. .:....=;==+<; You should have received a copy of the GNU + -_. . . )=. = Library General Public License along with + -- :-=` this library; see the file COPYING.LIB. + If not, write to the Free Software Foundation, + Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + +*/ + +#ifndef ONETWORK_H +#define ONETWORK_H + +/* QT */ + +#include <qdict.h> +#include <qmap.h> +#include <qobject.h> +#include <qhostaddress.h> + +/* OPIE */ + +#include <opie2/onetutils.h> + +// ML: Yeah, I hate to include kernel headers, but it's necessary here +// ML: Recent RedHat and MandrakePatches to the Kernel and WE broke something +// ML: #include <net/if.h> e.g. conflicts with #include <linux/wireless.h> +#define IFNAMSIZ 16 +#include <linux/wireless.h> +#include <net/if.h> + +class ONetworkInterface; +class OWirelessNetworkInterface; +class OChannelHopper; +class OMonitoringInterface; + +typedef struct ifreq ifreqstruct; +typedef struct iwreq iwreqstruct; +typedef struct iw_event iweventstruct; +typedef struct iw_freq iwfreqstruct; +typedef struct iw_priv_args iwprivargsstruct; +typedef struct iw_range iwrangestruct; + +/*====================================================================================== + * ONetwork + *======================================================================================*/ + +class ONetwork : public QObject +{ + Q_OBJECT + + public: + typedef QDict<ONetworkInterface> InterfaceMap; + typedef QDictIterator<ONetworkInterface> InterfaceIterator; + + public: + static ONetwork* instance(); + InterfaceIterator iterator() const; + bool isWirelessInterface( const char* ) const; + ONetworkInterface* interface( QString ) const; + + protected: + ONetwork(); + void synchronize(); + + private: + static ONetwork* _instance; + InterfaceMap _interfaces; +}; + + +/*====================================================================================== + * ONetworkInterface + *======================================================================================*/ + +class ONetworkInterface +{ + friend class OMonitoringInterface; + friend class OCiscoMonitoringInterface; + friend class OWlanNGMonitoringInterface; + friend class OHostAPMonitoringInterface; + friend class OOrinocoMonitoringInterface; + + public: + ONetworkInterface( const QString& name ); + virtual ~ONetworkInterface(); + + const QString& name() const; + void setMonitoring( OMonitoringInterface* ); + OMonitoringInterface* monitoring() const; + bool setPromiscuousMode( bool ); + bool promiscuousMode() const; + bool setUp( bool ); + bool isUp() const; + bool isLoopback() const; + bool isWireless() const; + QString ipV4Address() const; + OMacAddress macAddress() const; + + protected: + const QString _name; + const int _sfd; + mutable ifreqstruct _ifr; + OMonitoringInterface* _mon; + + protected: + ifreqstruct& ifr() const; + virtual void init(); + bool ioctl( int call ) const; + bool ioctl( int call, ifreqstruct& ) const; +}; + +/*====================================================================================== + * OChannelHopper + *======================================================================================*/ + +class OChannelHopper : public QObject +{ + public: + OChannelHopper( OWirelessNetworkInterface* ); + virtual ~OChannelHopper(); + virtual void timerEvent( QTimerEvent* ); + void setInterval( int ); + int interval() const; + + private: + OWirelessNetworkInterface* _iface; + int _interval; + int _channel; + int _tid; +}; + + +/*====================================================================================== + * OWirelessNetworkInterface + *======================================================================================*/ + +class OWirelessNetworkInterface : public ONetworkInterface +{ + friend class OMonitoringInterface; + friend class OCiscoMonitoringInterface; + friend class OWlanNGMonitoringInterface; + friend class OHostAPMonitoringInterface; + friend class OOrinocoMonitoringInterface; + + public: + enum Mode { AdHoc, Managed, Monitor }; + + OWirelessNetworkInterface( const QString& name ); + virtual ~OWirelessNetworkInterface(); + + virtual void setChannel( int ) const; + virtual int channel() const; + virtual double frequency() const; + virtual int channels() const; + //virtual double frequency(int) const; + + virtual void setMode( Mode ) {}; + virtual bool mode() const {}; + + virtual void setMonitorMode( bool ); + virtual bool monitorMode() const; + + virtual void setChannelHopping( int interval ); + virtual int channelHopping() const; + + virtual void setNickName( const QString& ) {}; + virtual QString nickName() const; + + virtual bool isAssociated() const {}; + virtual QString associatedAP() const; + + virtual void setSSID( const QString& ); + virtual QString SSID() const; + + protected: + mutable iwreqstruct _iwr; + QMap<int,int> _channels; + + protected: + virtual void init(); + iwreqstruct& iwr() const; + bool wioctl( int call ) const; + bool wioctl( int call, iwreqstruct& ) const; + + private: + OChannelHopper _hopper; +}; + + +/*====================================================================================== + * OMonitoringInterface + *======================================================================================*/ + + +class OMonitoringInterface +{ + public: + OMonitoringInterface(); + OMonitoringInterface( ONetworkInterface* ); + virtual ~OMonitoringInterface(); + + public: + virtual void setEnabled( bool ); + virtual bool enabled() const; + virtual void setChannel( int ); + + virtual QString name() const = 0; + + protected: + bool _enabled; + const OWirelessNetworkInterface* _if; + +}; + + +/*====================================================================================== + * OCiscoMonitoring + *======================================================================================*/ + + +class OCiscoMonitoringInterface : public OMonitoringInterface +{ + public: + OCiscoMonitoringInterface( ONetworkInterface* ); + virtual ~OCiscoMonitoringInterface(); + + virtual void setEnabled( bool ); + virtual QString name() const; + virtual void setChannel( int ); + +}; + +/*====================================================================================== + * OWlanNGMonitoringInterface + *======================================================================================*/ + +class OWlanNGMonitoringInterface : public OMonitoringInterface +{ + public: + OWlanNGMonitoringInterface( ONetworkInterface* ); + virtual ~OWlanNGMonitoringInterface(); + + public: + virtual void setEnabled( bool ); + virtual QString name() const; + virtual void setChannel( int ); + +}; + +/*====================================================================================== + * OHostAPMonitoringInterface + *======================================================================================*/ + +class OHostAPMonitoringInterface : public OMonitoringInterface +{ + public: + OHostAPMonitoringInterface( ONetworkInterface* ); + virtual ~OHostAPMonitoringInterface(); + + public: + virtual void setEnabled( bool ); + virtual QString name() const; + }; + +/*====================================================================================== + * OOrinocoMonitoringInterface + *======================================================================================*/ + +class OOrinocoMonitoringInterface : public OMonitoringInterface +{ + public: + OOrinocoMonitoringInterface( ONetworkInterface* ); + virtual ~OOrinocoMonitoringInterface(); + + public: + virtual void setChannel( int ); + virtual void setEnabled( bool ); + virtual QString name() const; + +}; + +#endif // ONETWORK_H + diff --git a/libopie2/opienet/opcap.cpp b/libopie2/opienet/opcap.cpp new file mode 100644 index 0000000..48f874f --- a/dev/null +++ b/libopie2/opienet/opcap.cpp @@ -0,0 +1,609 @@ +/* + This file is part of the Opie Project + Copyright (C) 2003 by the Wellenreiter team: + Martin J. Muench <mjm@remote-exploit.org> + Max Moser <mmo@remote-exploit.org + Michael 'Mickey' Lauer <mickey@tm.informatik.uni-frankfurt.de> + =. + .=l. + .>+-= + _;:, .> :=|. This program is free software; you can +.> <`_, > . <= redistribute it and/or modify it under +:`=1 )Y*s>-.-- : the terms of the GNU Library General Public +.="- .-=="i, .._ License as published by the Free Software + - . .-<_> .<> Foundation; either version 2 of the License, + ._= =} : or (at your option) any later version. + .%`+i> _;_. + .i_,=:_. -<s. 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 +..}^=.= = ; Library General Public License for more +++= -. .` .: details. + : = ...= . :.=- + -. .:....=;==+<; You should have received a copy of the GNU + -_. . . )=. = Library General Public License along with + -- :-=` this library; see the file COPYING.LIB. + If not, write to the Free Software Foundation, + Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + +*/ + +/* OPIE */ + +#include <opie2/opcap.h> + +/* QT */ + +#include <qapplication.h> // don't use oapplication here (will decrease reusability in other projects) +#include <qsocketnotifier.h> + +/*====================================================================================== + * OPacket + *======================================================================================*/ + +OPacket::OPacket( packetheaderstruct header, const unsigned char* data, QObject* parent ) + :QObject( parent, "Generic" ), _hdr( header ), _data( data ) +{ + qDebug( "OPacket::OPacket(): (Len %d, CapLen %d)" /*, ctime((const time_t*) header.ts.tv_sec)*/, header.len, header.caplen ); + + if ( packetCapturer()->dataLink() == DLT_EN10MB ) + { + qDebug( "OPacket::OPacket(): Received Packet. Datalink = ETHERNET" ); + new OEthernetPacket( (const struct ether_header*) data, this ); + } + else + { + qDebug( "OPacket::OPacket(): Received Packet. Datalink = IEEE802.11" ); + new OWaveLanPacket( (const struct ieee_802_11_header*) data, this ); + } +} + + +OPacket::~OPacket() +{ +} + + +OPacketCapturer* OPacket::packetCapturer() const +{ + return parent()->inherits( "OPacketCapturer" ) ? static_cast<OPacketCapturer*>( parent() ) : 0; +} + + +timevalstruct OPacket::timeval() const +{ + return _hdr.ts; +} + + +int OPacket::caplen() const +{ + return _hdr.caplen; +} + + +void OPacket::dump() const +{ + printf( "OPacket::dump()\n" ); + printf( "----------------\n" ); + + for ( int i = 0; i < _hdr.caplen; ++i ) + { + printf( "%02x ", _data[i] ); + if ( !((i+1) % 32) ) printf( "\n" ); + } + printf( "\n\n" ); +} + + + +int OPacket::len() const +{ + return _hdr.len; +} + +/*====================================================================================== + * OEthernetPacket + *======================================================================================*/ + +OEthernetPacket::OEthernetPacket( const struct ether_header* data, QObject* parent ) + :QObject( parent, "Ethernet" ), _ether( data ) + +{ + + qDebug( "Source = %s", (const char*) sourceAddress().toString() ); + qDebug( "Destination = %s", (const char*) destinationAddress().toString() ); + + if ( sourceAddress() == OMacAddress::broadcast ) + qDebug( "Source is broadcast address" ); + if ( destinationAddress() == OMacAddress::broadcast ) + qDebug( "Destination is broadcast address" ); + + switch ( type() ) + { + case ETHERTYPE_IP: new OIPPacket( (const struct iphdr*) (data+1), this ); break; + case ETHERTYPE_ARP: { qDebug( "OPacket::OPacket(): Received Ethernet Packet : Type = ARP" ); break; } + case ETHERTYPE_REVARP: { qDebug( "OPacket::OPacket(): Received Ethernet Packet : Type = RARP" ); break; } + default: qDebug( "OPacket::OPacket(): Received Ethernet Packet : Type = UNKNOWN" ); + } + +} + + +OEthernetPacket::~OEthernetPacket() +{ +} + + +OMacAddress OEthernetPacket::sourceAddress() const +{ + return OMacAddress( _ether->ether_shost ); +} + + +OMacAddress OEthernetPacket::destinationAddress() const +{ + return OMacAddress( _ether->ether_dhost ); +} + +int OEthernetPacket::type() const +{ + return ntohs( _ether->ether_type ); +} + + +/*====================================================================================== + * OIPPacket + *======================================================================================*/ + + +OIPPacket::OIPPacket( const struct iphdr* data, QObject* parent ) + :QObject( parent, "IP" ), _iphdr( data ) + +{ + qDebug( "OIPPacket::OIPPacket(): decoding IP header..." ); + + //qDebug( "FromAddress: %s", (const char*) inet_ntoa( *src ) ); + //qDebug( " ToAddress: %s", (const char*) inet_ntoa( *dst ) ); + + qDebug( "FromAddress: %s", (const char*) fromIPAddress().toString() ); + qDebug( " toAddress: %s", (const char*) toIPAddress().toString() ); + + switch ( protocol() ) + { + case IPPROTO_UDP: new OUDPPacket( (const struct udphdr*) (data+1), this ); break; + case IPPROTO_TCP: new OTCPPacket( (const struct tcphdr*) (data+1), this ); break; + default: qDebug( "OIPPacket::OIPPacket(): unknown IP protocol type = %d", protocol() ); + } + +} + +OIPPacket::~OIPPacket() +{ +} + + +QHostAddress OIPPacket::fromIPAddress() const +{ + return EXTRACT_32BITS( &_iphdr->saddr ); +} + + +QHostAddress OIPPacket::toIPAddress() const +{ + return EXTRACT_32BITS( &_iphdr->saddr ); +} + + +int OIPPacket::tos() const +{ + return _iphdr->tos; +} + + +int OIPPacket::len() const +{ + return EXTRACT_16BITS( &_iphdr->tot_len ); +} + + +int OIPPacket::id() const +{ + return EXTRACT_16BITS( &_iphdr->id ); +} + + +int OIPPacket::offset() const +{ + return EXTRACT_16BITS( &_iphdr->frag_off ); +} + + +int OIPPacket::ttl() const +{ + return _iphdr->ttl; +} + + +int OIPPacket::protocol() const +{ + return _iphdr->protocol; +} + + +int OIPPacket::checksum() const +{ + return EXTRACT_16BITS( &_iphdr->check ); +} + +/*====================================================================================== + * OUDPPacket + *======================================================================================*/ + + +OUDPPacket::OUDPPacket( const struct udphdr* data, QObject* parent ) + :QObject( parent, "UDP" ), _udphdr( data ) + +{ + qDebug( "OUDPPacket::OUDPPacket(): decoding UDP header..." ); +} + +OUDPPacket::~OUDPPacket() +{ +} + + +/*====================================================================================== + * OTCPPacket + *======================================================================================*/ + + +OTCPPacket::OTCPPacket( const struct tcphdr* data, QObject* parent ) + :QObject( parent, "TCP" ), _tcphdr( data ) + +{ + qDebug( "OTCPPacket::OTCPPacket(): decoding TCP header..." ); +} + +OTCPPacket::~OTCPPacket() +{ +} + + +/*====================================================================================== + * OWaveLanPacket + *======================================================================================*/ + + +OWaveLanPacket::OWaveLanPacket( const struct ieee_802_11_header* data, QObject* parent ) + :QObject( parent, "802.11" ), _wlanhdr( data ) + +{ + qDebug( "OWaveLanPacket::OWaveLanPacket(): decoding IEEE 802.11 header..." ); + qDebug( "type: %0X", type() ); + qDebug( "subType: %0X", subType() ); + qDebug( "duration: %d", duration() ); + qDebug( "powermanagement: %d", usesPowerManagement() ); + qDebug( "wep: %d", usesWep() ); + qDebug( "MAC1: %s", (const char*) macAddress1().toString() ); + qDebug( "MAC2: %s", (const char*) macAddress2().toString() ); + qDebug( "MAC3: %s", (const char*) macAddress3().toString() ); + qDebug( "MAC4: %s", (const char*) macAddress4().toString() ); + + switch ( type() ) + { + case T_MGMT: new OWaveLanManagementPacket( (const struct ieee_802_11_mgmt_header*) data, this ); break; + case T_DATA: new OWaveLanDataPacket( (const struct ieee_802_11_data_header*) data, this ); break; + //case T_CTRL: new OWaveLanControlPacket( (const struct ieee_802_11_ctrl_header*) data, this ); break; + default: qDebug( "OWaveLanPacket::OWaveLanPacket(): Warning: Unknown type!" ); + } +} + +OWaveLanPacket::~OWaveLanPacket() +{ +} + + +int OWaveLanPacket::duration() const +{ + return _wlanhdr->duration; +} + + +OMacAddress OWaveLanPacket::macAddress1() const +{ + return OMacAddress( _wlanhdr->mac1 ); +} + + +OMacAddress OWaveLanPacket::macAddress2() const +{ + return OMacAddress( _wlanhdr->mac2 ); +} + + +OMacAddress OWaveLanPacket::macAddress3() const +{ + return OMacAddress( _wlanhdr->mac3 ); +} + + +OMacAddress OWaveLanPacket::macAddress4() const +{ + return OMacAddress( _wlanhdr->mac4 ); +} + + +int OWaveLanPacket::subType() const +{ + return FC_SUBTYPE( EXTRACT_LE_16BITS( &_wlanhdr->frame_control ) ); +} + + +int OWaveLanPacket::type() const +{ + return FC_TYPE( EXTRACT_LE_16BITS( &_wlanhdr->frame_control ) ); +} + + +int OWaveLanPacket::version() const +{ + return FC_VERSION( EXTRACT_LE_16BITS( &_wlanhdr->frame_control ) ); +} + + +bool OWaveLanPacket::fromDS() const +{ + return FC_FROM_DS( EXTRACT_LE_16BITS( &_wlanhdr->frame_control ) ); +} + + +bool OWaveLanPacket::toDS() const +{ + return FC_TO_DS( EXTRACT_LE_16BITS( &_wlanhdr->frame_control ) ); +} + + +bool OWaveLanPacket::usesPowerManagement() const +{ + return FC_POWER_MGMT( EXTRACT_LE_16BITS( &_wlanhdr->frame_control ) ); +} + + +bool OWaveLanPacket::usesWep() const +{ + return FC_WEP( EXTRACT_LE_16BITS( &_wlanhdr->frame_control ) ); +} + + +/*====================================================================================== + * OWaveLanManagementPacket + *======================================================================================*/ + +OWaveLanManagementPacket::OWaveLanManagementPacket( const struct ieee_802_11_mgmt_header* data, OWaveLanPacket* parent ) + :QObject( parent, "802.11 Management" ), _header( data ), + _body( (const struct ieee_802_11_mgmt_body*) (data+1) ) +{ + qDebug( "OWaveLanManagementPacket::OWaveLanManagementPacket(): decoding frame..." ); + + switch ( ((OWaveLanPacket*) this->parent() )->subType() ) + { + case ST_BEACON: + { + qDebug( "TYPE: BEACON FRAME" ); + qDebug( "ESSID: %s", (const char*) SSID() ); + break; + } + } +} + + +OWaveLanManagementPacket::~OWaveLanManagementPacket() +{ +} + + +QString OWaveLanManagementPacket::SSID() const +{ + int length = _body->ssid.length; + if ( length > 32 ) length = 32; + char essid[length+1]; + memcpy( &essid, _body->ssid.ssid, length ); + essid[length] = 0x0; + return essid; +} + + +/*====================================================================================== + * OWaveLanDataPacket + *======================================================================================*/ + +OWaveLanDataPacket::OWaveLanDataPacket( const struct ieee_802_11_data_header* data, OWaveLanPacket* parent ) + :QObject( parent, "802.11 Data" ), _header( data ) +{ + //qDebug( "size of header = %d", sizeof( struct ieee_802_11_data_header ) ); + //qDebug( "header: %0x", data ); + const unsigned char* payload = (const unsigned char*) data + sizeof( struct ieee_802_11_data_header ); + //qDebug( "payload: %0x", payload ); + + if (!( ( (OWaveLanPacket*) this->parent())->duration() )) payload -= 6; // compensation for missing last address + + new OLLCPacket( (const struct ieee_802_11_802_2_header*) payload, this ); +} + + +OWaveLanDataPacket::~OWaveLanDataPacket() +{ +} + + +/*====================================================================================== + * OLLCPacket + *======================================================================================*/ + +OLLCPacket::OLLCPacket( const struct ieee_802_11_802_2_header* data, QObject* parent ) + :QObject( parent, "802.11 802_2" ), _header( data ) +{ + qDebug( "OLLCPacket::OLLCPacket(): decoding frame..." ); + + if ( !(_header->oui[0] || _header->oui[1] || _header->oui[2]) ) + { + qDebug( "OLLCPacket::OLLCPacket(): contains an encapsulated Ethernet frame (type=%04X)", EXTRACT_16BITS( &_header->type ) ); + + switch ( EXTRACT_16BITS( &_header->type ) ) // defined in linux/if_ether.h + { + case ETH_P_IP: new OIPPacket( (const struct iphdr*) (data+1), this ); break; + default: qDebug( "OLLCPacket::OLLCPacket(): Unknown Encapsulation Type" ); + } + + } +} + + +OLLCPacket::~OLLCPacket() +{ +} + +/*====================================================================================== + * OPacketCapturer + *======================================================================================*/ + +OPacketCapturer::OPacketCapturer( QObject* parent, const char* name ) + :QObject( parent, name ), _name( QString::null ), _open( false ), + _pch( 0 ) +{ +} + + +OPacketCapturer::~OPacketCapturer() +{ + if ( _open ) + { + qDebug( "OPacketCapturer::~OPacketCapturer(): pcap still open, autoclosing." ); + close(); + } +} + + +void OPacketCapturer::setBlocking( bool b ) +{ + if ( pcap_setnonblock( _pch, 1-b, _errbuf ) != -1 ) + { + qDebug( "OPacketCapturer::setBlocking(): blocking mode changed successfully." ); + } + else + { + qDebug( "OPacketCapturer::setBlocking(): can't change blocking mode: %s", _errbuf ); + } +} + + +bool OPacketCapturer::blocking() const +{ + int b = pcap_getnonblock( _pch, _errbuf ); + if ( b == -1 ) + { + qDebug( "OPacketCapturer::blocking(): can't get blocking mode: %s", _errbuf ); + return -1; + } + return !b; +} + + +void OPacketCapturer::close() +{ + if ( _open ) + { + pcap_close( _pch ); + _open = false; + } +} + + +int OPacketCapturer::dataLink() const +{ + return pcap_datalink( _pch ); +} + + +int OPacketCapturer::fileno() const +{ + if ( _open ) + { + return pcap_fileno( _pch ); + } + else + { + return -1; + } +} + + +OPacket* OPacketCapturer::next() +{ + packetheaderstruct header; + const unsigned char* pdata = pcap_next( _pch, &header ); + if ( header.len ) + return new OPacket( header, pdata, this ); + else + return 0; +} + + +bool OPacketCapturer::open( const QString& name ) +{ + if ( _open ) + { + if ( name == _name ) // ignore opening an already openend device + { + return true; + } + else // close the last opened device + { + close(); + } + } + + _name = name; + + pcap_t* handle = pcap_open_live( const_cast<char*>( (const char*) name ), 1024, 0, 0, &_errbuf[0] ); + + if ( handle ) + { + qDebug( "OPacketCapturer::open(): libpcap opened successfully." ); + _pch = handle; + _open = true; + + // in case we have a qapp, create a socket notifier + if ( qApp ) + { + QSocketNotifier* sn = new QSocketNotifier( fileno(), QSocketNotifier::Read, this ); + connect( sn, SIGNAL( activated(int) ), this, SLOT( readyToReceive() ) ); + } + + return true; + } + else + { + qDebug( "OPacketCapturer::open(): can't open libpcap: %s", _errbuf ); + return false; + } + +} + + +bool OPacketCapturer::isOpen() const +{ + return _open; +} + + +void OPacketCapturer::readyToReceive() +{ + qDebug( "OPacketCapturer::readyToReceive(): about to emit 'receivePacket(...)'" ); + emit receivedPacket( next() ); +} + diff --git a/libopie2/opienet/opcap.h b/libopie2/opienet/opcap.h new file mode 100644 index 0000000..65c550c --- a/dev/null +++ b/libopie2/opienet/opcap.h @@ -0,0 +1,294 @@ +/* + This file is part of the Opie Project + Copyright (C) 2003 by the Wellenreiter team: + Martin J. Muench <mjm@remote-exploit.org> + Max Moser <mmo@remote-exploit.org + Michael 'Mickey' Lauer <mickey@tm.informatik.uni-frankfurt.de> + =. + .=l. + .>+-= + _;:, .> :=|. This program is free software; you can +.> <`_, > . <= redistribute it and/or modify it under +:`=1 )Y*s>-.-- : the terms of the GNU Library General Public +.="- .-=="i, .._ License as published by the Free Software + - . .-<_> .<> Foundation; either version 2 of the License, + ._= =} : or (at your option) any later version. + .%`+i> _;_. + .i_,=:_. -<s. 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 +..}^=.= = ; Library General Public License for more +++= -. .` .: details. + : = ...= . :.=- + -. .:....=;==+<; You should have received a copy of the GNU + -_. . . )=. = Library General Public License along with + -- :-=` this library; see the file COPYING.LIB. + If not, write to the Free Software Foundation, + Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. + +*/ + +#ifndef OPCAP_H +#define OPCAP_H + +/* LINUX */ +extern "C" // work around a bpf/pcap conflict in recent headers +{ + #include <pcap.h> +} +#include <netinet/ether.h> +#include <netinet/ip.h> +#include <netinet/udp.h> +#include <netinet/tcp.h> +#include <time.h> + +/* QT */ +#include <qhostaddress.h> +#include <qobject.h> +#include <qstring.h> + +/* OPIE */ +#include <opie2/onetutils.h> +#include "802_11_user.h" + +/* TYPEDEFS */ +typedef struct timeval timevalstruct; +typedef struct pcap_pkthdr packetheaderstruct; + +/* FORWARDS */ +class OPacketCapturer; + +/*====================================================================================== + * OPacket - A frame on the wire + *======================================================================================*/ + +class OPacket : public QObject +{ + Q_OBJECT + + public: + OPacket( packetheaderstruct, const unsigned char*, QObject* parent ); + virtual ~OPacket(); + + timevalstruct timeval() const; + + OPacketCapturer* packetCapturer() const; + + int caplen() const; + int len() const; + void dump() const; + + private: + const packetheaderstruct _hdr; // pcap packet header + const unsigned char* _data; // pcap packet data +}; + +/*====================================================================================== + * OEthernetPacket - DLT_EN10MB frame + *======================================================================================*/ + +class OEthernetPacket : public QObject +{ + Q_OBJECT + + public: + OEthernetPacket( const struct ether_header*, QObject* parent = 0 ); + virtual ~OEthernetPacket(); + + OMacAddress sourceAddress() const; + OMacAddress destinationAddress() const; + int type() const; + + private: + const struct ether_header* _ether; +}; + + +/*====================================================================================== + * OWaveLanPacket - DLT_IEEE802_11 frame + *======================================================================================*/ + +class OWaveLanPacket : public QObject +{ + Q_OBJECT + + public: + OWaveLanPacket( const struct ieee_802_11_header*, QObject* parent = 0 ); + virtual ~OWaveLanPacket(); + + int duration() const; + bool fromDS() const; + bool toDS() const; + virtual OMacAddress macAddress1() const; + virtual OMacAddress macAddress2() const; + virtual OMacAddress macAddress3() const; + virtual OMacAddress macAddress4() const; + bool usesPowerManagement() const; + int type() const; + int subType() const; + int version() const; + bool usesWep() const; + + private: + const struct ieee_802_11_header* _wlanhdr; +}; + + +/*====================================================================================== + * OWaveLanManagementPacket - type: management (T_MGMT) + *======================================================================================*/ + +class OWaveLanManagementPacket : public QObject +{ + Q_OBJECT + + public: + OWaveLanManagementPacket( const struct ieee_802_11_mgmt_header*, OWaveLanPacket* parent = 0 ); + virtual ~OWaveLanManagementPacket(); + + QString SSID() const; + + private: + const struct ieee_802_11_mgmt_header* _header; + const struct ieee_802_11_mgmt_body* _body; +}; + + +/*====================================================================================== + * OWaveLanDataPacket - type: data (T_DATA) + *======================================================================================*/ + +class OWaveLanDataPacket : public QObject +{ + Q_OBJECT + + public: + OWaveLanDataPacket( const struct ieee_802_11_data_header*, OWaveLanPacket* parent = 0 ); + virtual ~OWaveLanDataPacket(); + + private: + const struct ieee_802_11_data_header* _header; +}; + +/*====================================================================================== + * OLLCPacket - IEEE 802.2 Link Level Control + *======================================================================================*/ + +class OLLCPacket : public QObject +{ + Q_OBJECT + + public: + OLLCPacket( const struct ieee_802_11_802_2_header* data, QObject* parent = 0 ); + virtual ~OLLCPacket(); + + private: + const struct ieee_802_11_802_2_header* _header; +}; + +/*====================================================================================== + * OIPPacket + *======================================================================================*/ + +class OIPPacket : public QObject +{ + Q_OBJECT + + public: + OIPPacket( const struct iphdr*, QObject* parent = 0 ); + virtual ~OIPPacket(); + + QHostAddress fromIPAddress() const; + QHostAddress toIPAddress() const; + + int tos() const; + int len() const; + int id() const; + int offset() const; + int ttl() const; + int protocol() const; + int checksum() const; + + private: + const struct iphdr* _iphdr; +}; + +/*====================================================================================== + * OUDPPacket + *======================================================================================*/ + +class OUDPPacket : public QObject +{ + Q_OBJECT + + public: + OUDPPacket( const struct udphdr*, QObject* parent = 0 ); + virtual ~OUDPPacket(); + + int fromPort() const; + int toPort() const; + + private: + const struct udphdr* _udphdr; +}; + +/*====================================================================================== + * OTCPPacket + *======================================================================================*/ + +class OTCPPacket : public QObject +{ + Q_OBJECT + + public: + OTCPPacket( const struct tcphdr*, QObject* parent = 0 ); + virtual ~OTCPPacket(); + + int fromPort() const; + int toPort() const; + + private: + const struct tcphdr* _tcphdr; +}; + + +/*====================================================================================== + * OPacketCapturer + *======================================================================================*/ + +class OPacketCapturer : public QObject +{ + Q_OBJECT + + public: + OPacketCapturer( QObject* parent = 0, const char* name = 0 ); + ~OPacketCapturer(); + + void setBlocking( bool ); + bool blocking() const; + + void close(); + int dataLink() const; + int fileno() const; + OPacket* next(); + bool open( const QString& name ); + bool isOpen() const; + + signals: + void receivedPacket( OPacket* ); + + protected slots: + void readyToReceive(); + + protected: + QString _name; // devicename + bool _open; // check this before doing pcap calls + pcap_t* _pch; // pcap library handle + mutable char _errbuf[PCAP_ERRBUF_SIZE]; +}; + +#endif // OPCAP_H + diff --git a/libopie2/opienet/opienet.pro b/libopie2/opienet/opienet.pro new file mode 100644 index 0000000..e73afbf --- a/dev/null +++ b/libopie2/opienet/opienet.pro @@ -0,0 +1,18 @@ +TEMPLATE = lib +CONFIG += qt warn_on debug +DESTDIR = $(OPIEDIR)/lib +HEADERS = onetutils.cpp onetwork.h opcap.h + +SOURCES = onetutils.cpp onetwork.cpp opcap.cpp +INTERFACES = +TARGET = opienet2 +VERSION = 1.8.1 +INCLUDEPATH += $(OPIEDIR)/include +DEPENDPATH += $(OPIEDIR)/include +LIBS += -lpcap + +MOC_DIR = moc +OBJECTS_DIR = obj + +include ( $(OPIEDIR)/include.pro ) + |