mirror of
https://github.com/mfontanini/libtins
synced 2026-01-27 04:11:35 +01:00
Added small_uint class.
This commit is contained in:
@@ -104,43 +104,43 @@ const Dot11::Dot11Option *Dot11::search_option(TaggedOption opt) const {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void Dot11::protocol(uint8_t new_proto) {
|
||||
void Dot11::protocol(small_uint<2> new_proto) {
|
||||
this->_header.control.protocol = new_proto;
|
||||
}
|
||||
|
||||
void Dot11::type(uint8_t new_type) {
|
||||
void Dot11::type(small_uint<2> new_type) {
|
||||
this->_header.control.type = new_type;
|
||||
}
|
||||
|
||||
void Dot11::subtype(uint8_t new_subtype) {
|
||||
void Dot11::subtype(small_uint<4> new_subtype) {
|
||||
this->_header.control.subtype = new_subtype;
|
||||
}
|
||||
|
||||
void Dot11::to_ds(bool new_value) {
|
||||
void Dot11::to_ds(small_uint<1> new_value) {
|
||||
this->_header.control.to_ds = (new_value)? 1 : 0;
|
||||
}
|
||||
|
||||
void Dot11::from_ds(bool new_value) {
|
||||
void Dot11::from_ds(small_uint<1> new_value) {
|
||||
this->_header.control.from_ds = (new_value)? 1 : 0;
|
||||
}
|
||||
|
||||
void Dot11::more_frag(bool new_value) {
|
||||
void Dot11::more_frag(small_uint<1> new_value) {
|
||||
this->_header.control.more_frag = (new_value)? 1 : 0;
|
||||
}
|
||||
|
||||
void Dot11::retry(bool new_value) {
|
||||
void Dot11::retry(small_uint<1> new_value) {
|
||||
this->_header.control.retry = (new_value)? 1 : 0;
|
||||
}
|
||||
|
||||
void Dot11::power_mgmt(bool new_value) {
|
||||
void Dot11::power_mgmt(small_uint<1> new_value) {
|
||||
this->_header.control.power_mgmt = (new_value)? 1 : 0;
|
||||
}
|
||||
|
||||
void Dot11::wep(bool new_value) {
|
||||
void Dot11::wep(small_uint<1> new_value) {
|
||||
this->_header.control.wep = (new_value)? 1 : 0;
|
||||
}
|
||||
|
||||
void Dot11::order(bool new_value) {
|
||||
void Dot11::order(small_uint<1> new_value) {
|
||||
this->_header.control.order = (new_value)? 1 : 0;
|
||||
}
|
||||
|
||||
@@ -338,10 +338,8 @@ void Dot11ManagementFrame::ssid(const std::string &new_ssid) {
|
||||
}
|
||||
|
||||
void Dot11ManagementFrame::rsn_information(const RSNInformation& info) {
|
||||
uint32_t size;
|
||||
uint8_t *buffer = info.serialize(size);
|
||||
add_tagged_option(RSN, size, buffer);
|
||||
delete[] buffer;
|
||||
RSNInformation::serialization_type buffer = info.serialize();
|
||||
add_tagged_option(RSN, buffer.size(), &buffer[0]);
|
||||
}
|
||||
|
||||
uint8_t *Dot11ManagementFrame::serialize_rates(const rates_type &rates) {
|
||||
@@ -570,45 +568,47 @@ void Dot11ManagementFrame::challenge_text(const std::string &text) {
|
||||
|
||||
// Getters
|
||||
|
||||
bool Dot11ManagementFrame::rsn_information(RSNInformation *rsn) {
|
||||
RSNInformation Dot11ManagementFrame::rsn_information() {
|
||||
const char *err_msg = "Malformed RSN information option";
|
||||
const Dot11::Dot11Option *option = search_option(RSN);
|
||||
if(!option || option->data_size() < (sizeof(uint16_t) << 1) + sizeof(uint32_t))
|
||||
return false;
|
||||
throw std::runtime_error("RSN information not set");
|
||||
RSNInformation rsn;
|
||||
const uint8_t *buffer = option->data_ptr();
|
||||
uint32_t bytes_left = option->data_size();
|
||||
rsn->version(*(uint16_t*)buffer);
|
||||
rsn.version(*(uint16_t*)buffer);
|
||||
buffer += sizeof(uint16_t);
|
||||
rsn->group_suite((RSNInformation::CypherSuites)*(uint32_t*)buffer);
|
||||
rsn.group_suite((RSNInformation::CypherSuites)*(uint32_t*)buffer);
|
||||
buffer += sizeof(uint32_t);
|
||||
|
||||
bytes_left -= (sizeof(uint16_t) << 1) + sizeof(uint32_t);
|
||||
if(bytes_left < sizeof(uint16_t))
|
||||
return false;
|
||||
throw std::runtime_error(err_msg);
|
||||
uint16_t count = *(uint16_t*)buffer;
|
||||
buffer += sizeof(uint16_t);
|
||||
if(count * sizeof(uint32_t) > bytes_left)
|
||||
return false;
|
||||
throw std::runtime_error(err_msg);
|
||||
bytes_left -= count * sizeof(uint32_t);
|
||||
while(count--) {
|
||||
rsn->add_pairwise_cypher((RSNInformation::CypherSuites)*(uint32_t*)buffer);
|
||||
rsn.add_pairwise_cypher((RSNInformation::CypherSuites)*(uint32_t*)buffer);
|
||||
buffer += sizeof(uint32_t);
|
||||
}
|
||||
if(bytes_left < sizeof(uint16_t))
|
||||
return false;
|
||||
throw std::runtime_error(err_msg);
|
||||
count = *(uint16_t*)buffer;
|
||||
buffer += sizeof(uint16_t);
|
||||
bytes_left -= sizeof(uint16_t);
|
||||
if(count * sizeof(uint32_t) > bytes_left)
|
||||
return false;
|
||||
throw std::runtime_error(err_msg);
|
||||
bytes_left -= count * sizeof(uint32_t);
|
||||
while(count--) {
|
||||
rsn->add_akm_cypher((RSNInformation::AKMSuites)*(uint32_t*)buffer);
|
||||
rsn.add_akm_cypher((RSNInformation::AKMSuites)*(uint32_t*)buffer);
|
||||
buffer += sizeof(uint32_t);
|
||||
}
|
||||
if(bytes_left < sizeof(uint16_t))
|
||||
return false;
|
||||
rsn->capabilities(*(uint16_t*)buffer);
|
||||
return true;
|
||||
throw std::runtime_error(err_msg);
|
||||
rsn.capabilities(*(uint16_t*)buffer);
|
||||
return rsn;
|
||||
}
|
||||
|
||||
string Dot11ManagementFrame::ssid() const {
|
||||
@@ -1587,32 +1587,33 @@ void RSNInformation::group_suite(CypherSuites group) {
|
||||
}
|
||||
|
||||
void RSNInformation::version(uint16_t ver) {
|
||||
_version = ver;
|
||||
_version = Utils::host_to_le(ver);
|
||||
}
|
||||
|
||||
void RSNInformation::capabilities(uint16_t cap) {
|
||||
_capabilities = cap;
|
||||
_capabilities = Utils::host_to_le(cap);
|
||||
}
|
||||
|
||||
uint8_t *RSNInformation::serialize(uint32_t &size) const {
|
||||
size = sizeof(_version) + sizeof(_capabilities) + sizeof(uint32_t);
|
||||
RSNInformation::serialization_type RSNInformation::serialize() const {
|
||||
uint32_t size = sizeof(_version) + sizeof(_capabilities) + sizeof(uint32_t);
|
||||
size += (sizeof(uint16_t) << 1); // 2 lists count.
|
||||
size += sizeof(uint32_t) * (_akm_cyphers.size() + _pairwise_cyphers.size());
|
||||
|
||||
uint8_t *buffer = new uint8_t[size], *ptr = buffer;
|
||||
|
||||
serialization_type buffer(size);
|
||||
serialization_type::value_type *ptr = &buffer[0];
|
||||
*(uint16_t*)ptr = _version;
|
||||
ptr += sizeof(_version);
|
||||
*(uint32_t*)ptr = _group_suite;
|
||||
ptr += sizeof(uint32_t);
|
||||
*(uint16_t*)ptr = _pairwise_cyphers.size();
|
||||
ptr += sizeof(uint16_t);
|
||||
for(std::list<CypherSuites>::const_iterator it = _pairwise_cyphers.begin(); it != _pairwise_cyphers.end(); ++it) {
|
||||
for(cyphers_type::const_iterator it = _pairwise_cyphers.begin(); it != _pairwise_cyphers.end(); ++it) {
|
||||
*(uint32_t*)ptr = *it;
|
||||
ptr += sizeof(uint32_t);
|
||||
}
|
||||
*(uint16_t*)ptr = _akm_cyphers.size();
|
||||
ptr += sizeof(uint16_t);
|
||||
for(std::list<AKMSuites>::const_iterator it = _akm_cyphers.begin(); it != _akm_cyphers.end(); ++it) {
|
||||
for(akm_type::const_iterator it = _akm_cyphers.begin(); it != _akm_cyphers.end(); ++it) {
|
||||
*(uint32_t*)ptr = *it;
|
||||
ptr += sizeof(uint32_t);
|
||||
}
|
||||
|
||||
205
src/eapol.cpp
205
src/eapol.cpp
@@ -26,24 +26,25 @@
|
||||
#include "dot11.h"
|
||||
|
||||
|
||||
Tins::EAPOL::EAPOL(uint8_t packet_type, EAPOLTYPE type) : PDU(0xff) {
|
||||
namespace Tins {
|
||||
EAPOL::EAPOL(uint8_t packet_type, EAPOLTYPE type) : PDU(0xff) {
|
||||
std::memset(&_header, 0, sizeof(_header));
|
||||
_header.version = 1;
|
||||
_header.packet_type = packet_type;
|
||||
_header.type = (uint8_t)type;
|
||||
}
|
||||
|
||||
Tins::EAPOL::EAPOL(const uint8_t *buffer, uint32_t total_sz) : PDU(0xff) {
|
||||
EAPOL::EAPOL(const uint8_t *buffer, uint32_t total_sz) : PDU(0xff) {
|
||||
if(total_sz < sizeof(_header))
|
||||
throw std::runtime_error("Not enough size for an EAPOL header in the buffer.");
|
||||
std::memcpy(&_header, buffer, sizeof(_header));
|
||||
}
|
||||
|
||||
Tins::EAPOL::EAPOL(const EAPOL &other) : PDU(other) {
|
||||
EAPOL::EAPOL(const EAPOL &other) : PDU(other) {
|
||||
copy_eapol_fields(&other);
|
||||
}
|
||||
|
||||
Tins::EAPOL *Tins::EAPOL::from_bytes(const uint8_t *buffer, uint32_t total_sz) {
|
||||
EAPOL *EAPOL::from_bytes(const uint8_t *buffer, uint32_t total_sz) {
|
||||
if(total_sz < sizeof(eapolhdr))
|
||||
throw std::runtime_error("Not enough size for an EAPOL header in the buffer.");
|
||||
const eapolhdr *ptr = (const eapolhdr*)buffer;
|
||||
@@ -59,23 +60,23 @@ Tins::EAPOL *Tins::EAPOL::from_bytes(const uint8_t *buffer, uint32_t total_sz) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void Tins::EAPOL::version(uint8_t new_version) {
|
||||
void EAPOL::version(uint8_t new_version) {
|
||||
_header.version = new_version;
|
||||
}
|
||||
|
||||
void Tins::EAPOL::packet_type(uint8_t new_ptype) {
|
||||
void EAPOL::packet_type(uint8_t new_ptype) {
|
||||
_header.packet_type = new_ptype;
|
||||
}
|
||||
|
||||
void Tins::EAPOL::length(uint16_t new_length) {
|
||||
void EAPOL::length(uint16_t new_length) {
|
||||
_header.length = new_length;
|
||||
}
|
||||
|
||||
void Tins::EAPOL::type(uint8_t new_type) {
|
||||
void EAPOL::type(uint8_t new_type) {
|
||||
_header.type = new_type;
|
||||
}
|
||||
|
||||
void Tins::EAPOL::write_serialization(uint8_t *buffer, uint32_t total_sz, const PDU *) {
|
||||
void EAPOL::write_serialization(uint8_t *buffer, uint32_t total_sz, const PDU *) {
|
||||
uint32_t sz = header_size();
|
||||
assert(total_sz >= sz);
|
||||
if(!_header.length)
|
||||
@@ -84,18 +85,22 @@ void Tins::EAPOL::write_serialization(uint8_t *buffer, uint32_t total_sz, const
|
||||
write_body(buffer + sizeof(_header), total_sz - sizeof(_header));
|
||||
}
|
||||
|
||||
void Tins::EAPOL::copy_eapol_fields(const EAPOL *other) {
|
||||
void EAPOL::copy_eapol_fields(const EAPOL *other) {
|
||||
std::memcpy(&_header, &other->_header, sizeof(_header));
|
||||
|
||||
}
|
||||
|
||||
/* RC4EAPOL */
|
||||
|
||||
Tins::RC4EAPOL::RC4EAPOL() : EAPOL(0x03, RC4), _key(0), _key_size(0) {
|
||||
RC4EAPOL::RC4EAPOL()
|
||||
: EAPOL(0x03, RC4)
|
||||
{
|
||||
std::memset(&_header, 0, sizeof(_header));
|
||||
}
|
||||
|
||||
Tins::RC4EAPOL::RC4EAPOL(const uint8_t *buffer, uint32_t total_sz) : EAPOL(buffer, total_sz), _key_size(0) {
|
||||
RC4EAPOL::RC4EAPOL(const uint8_t *buffer, uint32_t total_sz)
|
||||
: EAPOL(buffer, total_sz)
|
||||
{
|
||||
buffer += sizeof(eapolhdr);
|
||||
total_sz -= sizeof(eapolhdr);
|
||||
if(total_sz < sizeof(_header))
|
||||
@@ -103,101 +108,64 @@ Tins::RC4EAPOL::RC4EAPOL(const uint8_t *buffer, uint32_t total_sz) : EAPOL(buffe
|
||||
std::memcpy(&_header, buffer, sizeof(_header));
|
||||
buffer += sizeof(_header);
|
||||
total_sz -= sizeof(_header);
|
||||
if(total_sz == key_length()) {
|
||||
_key = new uint8_t[total_sz];
|
||||
_key_size = total_sz;
|
||||
std::memcpy(_key, buffer, total_sz);
|
||||
}
|
||||
else
|
||||
_key = 0;
|
||||
if(total_sz == key_length())
|
||||
_key.assign(buffer, buffer + total_sz);
|
||||
}
|
||||
|
||||
Tins::RC4EAPOL::RC4EAPOL(const RC4EAPOL &other) : EAPOL(other) {
|
||||
copy_fields(&other);
|
||||
}
|
||||
|
||||
Tins::RC4EAPOL &Tins::RC4EAPOL::operator= (const RC4EAPOL &other) {
|
||||
copy_fields(&other);
|
||||
copy_inner_pdu(other);
|
||||
return *this;
|
||||
}
|
||||
|
||||
Tins::RC4EAPOL::~RC4EAPOL() {
|
||||
delete[] _key;
|
||||
}
|
||||
|
||||
void Tins::RC4EAPOL::key_length(uint16_t new_key_length) {
|
||||
void RC4EAPOL::key_length(uint16_t new_key_length) {
|
||||
_header.key_length = Utils::host_to_be(new_key_length);
|
||||
}
|
||||
|
||||
void Tins::RC4EAPOL::replay_counter(uint16_t new_replay_counter) {
|
||||
void RC4EAPOL::replay_counter(uint16_t new_replay_counter) {
|
||||
_header.replay_counter = Utils::host_to_be(new_replay_counter);
|
||||
}
|
||||
|
||||
void Tins::RC4EAPOL::key_iv(const uint8_t *new_key_iv) {
|
||||
void RC4EAPOL::key_iv(const uint8_t *new_key_iv) {
|
||||
std::memcpy(_header.key_iv, new_key_iv, sizeof(_header.key_iv));
|
||||
}
|
||||
|
||||
void Tins::RC4EAPOL::key_flag(bool new_key_flag) {
|
||||
void RC4EAPOL::key_flag(small_uint<1> new_key_flag) {
|
||||
_header.key_flag = new_key_flag;
|
||||
}
|
||||
|
||||
void Tins::RC4EAPOL::key_index(uint8_t new_key_index) {
|
||||
void RC4EAPOL::key_index(small_uint<7> new_key_index) {
|
||||
_header.key_index = new_key_index;
|
||||
}
|
||||
|
||||
void Tins::RC4EAPOL::key_sign(const uint8_t *new_key_sign) {
|
||||
void RC4EAPOL::key_sign(const uint8_t *new_key_sign) {
|
||||
std::memcpy(_header.key_sign, new_key_sign, sizeof(_header.key_sign));
|
||||
}
|
||||
|
||||
void Tins::RC4EAPOL::key(const uint8_t *new_key, uint32_t sz) {
|
||||
delete[] _key;
|
||||
_key = new uint8_t[sz];
|
||||
_key_size = sz;
|
||||
std::memcpy(_key, new_key, sz);
|
||||
void RC4EAPOL::key(const key_type &new_key) {
|
||||
_key = new_key;
|
||||
}
|
||||
|
||||
uint32_t Tins::RC4EAPOL::header_size() const {
|
||||
return sizeof(eapolhdr) + sizeof(_header) + _key_size;
|
||||
uint32_t RC4EAPOL::header_size() const {
|
||||
return sizeof(eapolhdr) + sizeof(_header) + _key.size();
|
||||
}
|
||||
|
||||
void Tins::RC4EAPOL::write_body(uint8_t *buffer, uint32_t total_sz) {
|
||||
uint32_t sz = sizeof(_header) + _key_size;
|
||||
void RC4EAPOL::write_body(uint8_t *buffer, uint32_t total_sz) {
|
||||
uint32_t sz = sizeof(_header) + _key.size();
|
||||
assert(total_sz >= sz);
|
||||
if(_key)
|
||||
_header.key_length = Utils::host_to_be(_key_size);
|
||||
if(_key.size())
|
||||
_header.key_length = Utils::host_to_be(_key.size());
|
||||
std::memcpy(buffer, &_header, sizeof(_header));
|
||||
buffer += sizeof(_header);
|
||||
if(_key)
|
||||
std::memcpy(buffer, _key, _key_size);
|
||||
}
|
||||
|
||||
Tins::PDU *Tins::RC4EAPOL::clone_pdu() const {
|
||||
RC4EAPOL *new_pdu = new RC4EAPOL();
|
||||
new_pdu->copy_fields(this);
|
||||
return new_pdu;
|
||||
}
|
||||
|
||||
void Tins::RC4EAPOL::copy_fields(const RC4EAPOL *other) {
|
||||
copy_eapol_fields(other);
|
||||
std::memcpy(&_header, &other->_header, sizeof(_header));
|
||||
_key_size = other->_key_size;
|
||||
if(_key_size) {
|
||||
_key = new uint8_t[_key_size];
|
||||
std::memcpy(_key, other->_key, _key_size);
|
||||
}
|
||||
else
|
||||
_key = 0;
|
||||
std::copy(_key.begin(), _key.end(), buffer);
|
||||
}
|
||||
|
||||
/* RSNEAPOL */
|
||||
|
||||
|
||||
Tins::RSNEAPOL::RSNEAPOL() : EAPOL(0x03, RSN), _key(0), _key_size(0) {
|
||||
RSNEAPOL::RSNEAPOL()
|
||||
: EAPOL(0x03, RSN)
|
||||
{
|
||||
std::memset(&_header, 0, sizeof(_header));
|
||||
}
|
||||
|
||||
Tins::RSNEAPOL::RSNEAPOL(const uint8_t *buffer, uint32_t total_sz) : EAPOL(0x03, RSN), _key_size(0) {
|
||||
RSNEAPOL::RSNEAPOL(const uint8_t *buffer, uint32_t total_sz)
|
||||
: EAPOL(0x03, RSN)
|
||||
{
|
||||
buffer += sizeof(eapolhdr);
|
||||
total_sz -= sizeof(eapolhdr);
|
||||
if(total_sz < sizeof(_header))
|
||||
@@ -205,109 +173,68 @@ Tins::RSNEAPOL::RSNEAPOL(const uint8_t *buffer, uint32_t total_sz) : EAPOL(0x03,
|
||||
std::memcpy(&_header, buffer, sizeof(_header));
|
||||
buffer += sizeof(_header);
|
||||
total_sz -= sizeof(_header);
|
||||
if(total_sz == wpa_length()) {
|
||||
_key = new uint8_t[total_sz];
|
||||
_key_size = total_sz;
|
||||
std::memcpy(_key, buffer, total_sz);
|
||||
}
|
||||
else
|
||||
_key = 0;
|
||||
if(total_sz == wpa_length())
|
||||
_key.assign(buffer, buffer + total_sz);
|
||||
}
|
||||
|
||||
Tins::RSNEAPOL::RSNEAPOL(const RSNEAPOL &other) : EAPOL(other) {
|
||||
copy_fields(&other);
|
||||
}
|
||||
|
||||
Tins::RSNEAPOL &Tins::RSNEAPOL::operator= (const RSNEAPOL &other) {
|
||||
copy_fields(&other);
|
||||
copy_inner_pdu(other);
|
||||
return *this;
|
||||
}
|
||||
|
||||
Tins::RSNEAPOL::~RSNEAPOL() {
|
||||
delete[] _key;
|
||||
}
|
||||
|
||||
void Tins::RSNEAPOL::RSNEAPOL::nonce(const uint8_t *new_nonce) {
|
||||
void RSNEAPOL::RSNEAPOL::nonce(const uint8_t *new_nonce) {
|
||||
std::memcpy(_header.nonce, new_nonce, sizeof(_header.nonce));
|
||||
}
|
||||
|
||||
void Tins::RSNEAPOL::rsc(uint64_t new_rsc) {
|
||||
void RSNEAPOL::rsc(uint64_t new_rsc) {
|
||||
_header.rsc = Utils::host_to_be(new_rsc);
|
||||
}
|
||||
|
||||
void Tins::RSNEAPOL::id(uint64_t new_id) {
|
||||
void RSNEAPOL::id(uint64_t new_id) {
|
||||
_header.id = Utils::host_to_be(new_id);
|
||||
}
|
||||
|
||||
void Tins::RSNEAPOL::mic(const uint8_t *new_mic) {
|
||||
void RSNEAPOL::mic(const uint8_t *new_mic) {
|
||||
std::memcpy(_header.mic, new_mic, sizeof(_header.mic));
|
||||
}
|
||||
|
||||
void Tins::RSNEAPOL::wpa_length(uint16_t new_wpa_length) {
|
||||
void RSNEAPOL::wpa_length(uint16_t new_wpa_length) {
|
||||
_header.wpa_length = Utils::host_to_be(new_wpa_length);
|
||||
}
|
||||
|
||||
void Tins::RSNEAPOL::key(const uint8_t *new_key, uint32_t sz) {
|
||||
delete[] _key;
|
||||
_key = new uint8_t[sz];
|
||||
_key_size = sz;
|
||||
_header.key_type = 0;
|
||||
std::memcpy(_key, new_key, sz);
|
||||
void RSNEAPOL::key(const key_type &new_key) {
|
||||
_key = new_key;
|
||||
_header.key_t = 0;
|
||||
}
|
||||
|
||||
void Tins::RSNEAPOL::rsn_information(const RSNInformation &rsn) {
|
||||
_key = rsn.serialize(_key_size);
|
||||
_header.key_type = 1;
|
||||
void RSNEAPOL::rsn_information(const RSNInformation &rsn) {
|
||||
_key = rsn.serialize();
|
||||
_header.key_t = 1;
|
||||
}
|
||||
|
||||
uint32_t Tins::RSNEAPOL::header_size() const {
|
||||
uint32_t RSNEAPOL::header_size() const {
|
||||
uint32_t padding(0);
|
||||
if(_header.key_type && _key_size)
|
||||
if(_header.key_t && _key.size())
|
||||
padding = 2;
|
||||
return sizeof(eapolhdr) + sizeof(_header) + _key_size + padding;
|
||||
return sizeof(eapolhdr) + sizeof(_header) + _key.size() + padding;
|
||||
}
|
||||
|
||||
void Tins::RSNEAPOL::write_body(uint8_t *buffer, uint32_t total_sz) {
|
||||
void RSNEAPOL::write_body(uint8_t *buffer, uint32_t total_sz) {
|
||||
uint32_t sz = header_size() - sizeof(eapolhdr);
|
||||
assert(total_sz >= sz);
|
||||
if(_key) {
|
||||
if(!_header.key_type) {
|
||||
if(_key.size()) {
|
||||
if(!_header.key_t) {
|
||||
_header.key_length = Utils::host_to_be<uint16_t>(32);
|
||||
wpa_length(_key_size);
|
||||
wpa_length(_key.size());
|
||||
}
|
||||
else if(_key_size) {
|
||||
else if(_key.size()) {
|
||||
_header.key_length = 0;
|
||||
wpa_length(_key_size + 2);
|
||||
wpa_length(_key.size() + 2);
|
||||
}
|
||||
else
|
||||
wpa_length(0);
|
||||
}
|
||||
std::memcpy(buffer, &_header, sizeof(_header));
|
||||
buffer += sizeof(_header);
|
||||
if(_key) {
|
||||
if(_header.key_type && _key_size) {
|
||||
*(buffer++) = Dot11::RSN;
|
||||
*(buffer++) = _key_size;
|
||||
}
|
||||
std::memcpy(buffer, _key, _key_size);
|
||||
if(_header.key_t && _key.size()) {
|
||||
*(buffer++) = Dot11::RSN;
|
||||
*(buffer++) = _key.size();
|
||||
}
|
||||
std::copy(_key.begin(), _key.end(), buffer);
|
||||
}
|
||||
|
||||
void Tins::RSNEAPOL::copy_fields(const RSNEAPOL *other) {
|
||||
copy_eapol_fields(other);
|
||||
std::memcpy(&_header, &other->_header, sizeof(_header));
|
||||
_key_size = other->_key_size;
|
||||
if(_key_size) {
|
||||
_key = new uint8_t[_key_size];
|
||||
std::memcpy(_key, other->_key, _key_size);
|
||||
}
|
||||
else
|
||||
_key = 0;
|
||||
}
|
||||
|
||||
Tins::PDU *Tins::RSNEAPOL::clone_pdu() const {
|
||||
RSNEAPOL *new_pdu = new RSNEAPOL();
|
||||
new_pdu->copy_fields(this);
|
||||
return new_pdu;
|
||||
}
|
||||
|
||||
61
src/ip.cpp
61
src/ip.cpp
@@ -38,9 +38,11 @@
|
||||
|
||||
using namespace std;
|
||||
|
||||
const uint8_t Tins::IP::DEFAULT_TTL = 128;
|
||||
namespace Tins {
|
||||
|
||||
Tins::IP::IP(address_type ip_dst, address_type ip_src, PDU *child)
|
||||
const uint8_t IP::DEFAULT_TTL = 128;
|
||||
|
||||
IP::IP(address_type ip_dst, address_type ip_src, PDU *child)
|
||||
: PDU(Constants::IP::PROTO_IP, child)
|
||||
{
|
||||
init_ip_fields();
|
||||
@@ -48,7 +50,7 @@ Tins::IP::IP(address_type ip_dst, address_type ip_src, PDU *child)
|
||||
this->src_addr(ip_src);
|
||||
}
|
||||
|
||||
Tins::IP::IP(const uint8_t *buffer, uint32_t total_sz)
|
||||
IP::IP(const uint8_t *buffer, uint32_t total_sz)
|
||||
: PDU(Constants::IP::PROTO_IP)
|
||||
{
|
||||
static const char *msg("Not enough size for an IP header in the buffer.");
|
||||
@@ -128,7 +130,7 @@ Tins::IP::IP(const uint8_t *buffer, uint32_t total_sz)
|
||||
}
|
||||
}
|
||||
|
||||
void Tins::IP::init_ip_fields() {
|
||||
void IP::init_ip_fields() {
|
||||
memset(&_ip, 0, sizeof(iphdr));
|
||||
this->_ip.version = 4;
|
||||
this->ttl(DEFAULT_TTL);
|
||||
@@ -139,65 +141,65 @@ void Tins::IP::init_ip_fields() {
|
||||
|
||||
/* Setters */
|
||||
|
||||
void Tins::IP::tos(uint8_t new_tos) {
|
||||
void IP::tos(uint8_t new_tos) {
|
||||
_ip.tos = new_tos;
|
||||
}
|
||||
|
||||
void Tins::IP::tot_len(uint16_t new_tot_len) {
|
||||
void IP::tot_len(uint16_t new_tot_len) {
|
||||
_ip.tot_len = Utils::host_to_be(new_tot_len);
|
||||
}
|
||||
|
||||
void Tins::IP::id(uint16_t new_id) {
|
||||
void IP::id(uint16_t new_id) {
|
||||
_ip.id = Utils::host_to_be(new_id);
|
||||
}
|
||||
|
||||
void Tins::IP::frag_off(uint16_t new_frag_off) {
|
||||
void IP::frag_off(uint16_t new_frag_off) {
|
||||
_ip.frag_off = Utils::host_to_be(new_frag_off);
|
||||
}
|
||||
|
||||
void Tins::IP::ttl(uint8_t new_ttl) {
|
||||
void IP::ttl(uint8_t new_ttl) {
|
||||
_ip.ttl = new_ttl;
|
||||
}
|
||||
|
||||
void Tins::IP::protocol(uint8_t new_protocol) {
|
||||
void IP::protocol(uint8_t new_protocol) {
|
||||
_ip.protocol = new_protocol;
|
||||
}
|
||||
|
||||
void Tins::IP::check(uint16_t new_check) {
|
||||
void IP::check(uint16_t new_check) {
|
||||
_ip.check = Utils::host_to_be(new_check);
|
||||
}
|
||||
|
||||
|
||||
void Tins::IP::src_addr(address_type ip) {
|
||||
void IP::src_addr(address_type ip) {
|
||||
_ip.saddr = ip;
|
||||
}
|
||||
|
||||
|
||||
void Tins::IP::dst_addr(address_type ip) {
|
||||
void IP::dst_addr(address_type ip) {
|
||||
_ip.daddr = ip;
|
||||
}
|
||||
|
||||
void Tins::IP::head_len(uint8_t new_head_len) {
|
||||
void IP::head_len(small_uint<4> new_head_len) {
|
||||
_ip.ihl = new_head_len;
|
||||
}
|
||||
|
||||
void Tins::IP::version(uint8_t ver) {
|
||||
void IP::version(small_uint<4> ver) {
|
||||
_ip.version = ver;
|
||||
}
|
||||
|
||||
void Tins::IP::set_eol_option() {
|
||||
void IP::set_eol_option() {
|
||||
this->set_option(0, IP::CONTROL, IP::END);
|
||||
}
|
||||
|
||||
void Tins::IP::set_noop_option() {
|
||||
void IP::set_noop_option() {
|
||||
this->set_option(0, IP::CONTROL, IP::NOOP);
|
||||
}
|
||||
|
||||
void Tins::IP::set_sec_option(const uint8_t* data, uint32_t data_len) {
|
||||
void IP::set_sec_option(const uint8_t* data, uint32_t data_len) {
|
||||
this->set_option(1, IP::CONTROL, IP::SEC, data, data_len);
|
||||
}
|
||||
|
||||
void Tins::IP::set_option(uint8_t copied,
|
||||
void IP::set_option(uint8_t copied,
|
||||
OptionClass op_class,
|
||||
Option number,
|
||||
const uint8_t* data,
|
||||
@@ -220,7 +222,7 @@ void Tins::IP::set_option(uint8_t copied,
|
||||
_padded_options_size = padding ? (_options_size - padding + 4) : _options_size;
|
||||
}
|
||||
|
||||
const Tins::IP::IPOption *Tins::IP::search_option(OptionClass opt_class, Option opt_number) const {
|
||||
const IP::IPOption *IP::search_option(OptionClass opt_class, Option opt_number) const {
|
||||
for(std::list<IPOption>::const_iterator it = _ip_options.begin(); it != _ip_options.end(); ++it) {
|
||||
if(it->type.op_class == (uint8_t)opt_class && it->type.number == (uint8_t)opt_number)
|
||||
return &(*it);
|
||||
@@ -228,7 +230,7 @@ const Tins::IP::IPOption *Tins::IP::search_option(OptionClass opt_class, Option
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint8_t* Tins::IP::IPOption::write(uint8_t* buffer) {
|
||||
uint8_t* IP::IPOption::write(uint8_t* buffer) {
|
||||
memcpy(buffer, &type, 1);
|
||||
buffer += 1;
|
||||
if (!optional_data.empty()) {
|
||||
@@ -238,21 +240,21 @@ uint8_t* Tins::IP::IPOption::write(uint8_t* buffer) {
|
||||
return buffer;
|
||||
}
|
||||
|
||||
const uint8_t* Tins::IP::IPOption::data_ptr() const {
|
||||
const uint8_t* IP::IPOption::data_ptr() const {
|
||||
return !optional_data.empty() ? (&optional_data[1]) : 0;
|
||||
}
|
||||
|
||||
uint8_t Tins::IP::IPOption::data_size() const {
|
||||
uint8_t IP::IPOption::data_size() const {
|
||||
return !optional_data.empty() ? (optional_data.size() - 1) : 0;
|
||||
}
|
||||
|
||||
/* Virtual method overriding. */
|
||||
|
||||
uint32_t Tins::IP::header_size() const {
|
||||
uint32_t IP::header_size() const {
|
||||
return sizeof(iphdr) + _padded_options_size;
|
||||
}
|
||||
|
||||
bool Tins::IP::send(PacketSender* sender) {
|
||||
bool IP::send(PacketSender* sender) {
|
||||
struct sockaddr_in link_addr;
|
||||
PacketSender::SocketType type = PacketSender::IP_SOCKET;
|
||||
link_addr.sin_family = AF_INET;
|
||||
@@ -264,7 +266,7 @@ bool Tins::IP::send(PacketSender* sender) {
|
||||
return sender->send_l3(this, (struct sockaddr*)&link_addr, sizeof(link_addr), type);
|
||||
}
|
||||
|
||||
Tins::PDU *Tins::IP::recv_response(PacketSender *sender) {
|
||||
PDU *IP::recv_response(PacketSender *sender) {
|
||||
struct sockaddr_in link_addr;
|
||||
PacketSender::SocketType type = PacketSender::IP_SOCKET;
|
||||
link_addr.sin_family = AF_INET;
|
||||
@@ -276,7 +278,7 @@ Tins::PDU *Tins::IP::recv_response(PacketSender *sender) {
|
||||
return sender->recv_l3(this, (struct sockaddr*)&link_addr, sizeof(link_addr), type);
|
||||
}
|
||||
|
||||
void Tins::IP::write_serialization(uint8_t *buffer, uint32_t total_sz, const PDU* parent) {
|
||||
void IP::write_serialization(uint8_t *buffer, uint32_t total_sz, const PDU* parent) {
|
||||
uint32_t my_sz = header_size();
|
||||
assert(total_sz >= my_sz);
|
||||
if(inner_pdu()) {
|
||||
@@ -308,7 +310,7 @@ void Tins::IP::write_serialization(uint8_t *buffer, uint32_t total_sz, const PDU
|
||||
}
|
||||
}
|
||||
|
||||
bool Tins::IP::matches_response(uint8_t *ptr, uint32_t total_sz) {
|
||||
bool IP::matches_response(uint8_t *ptr, uint32_t total_sz) {
|
||||
if(total_sz < sizeof(iphdr))
|
||||
return false;
|
||||
iphdr *ip_ptr = (iphdr*)ptr;
|
||||
@@ -319,7 +321,7 @@ bool Tins::IP::matches_response(uint8_t *ptr, uint32_t total_sz) {
|
||||
return false;
|
||||
}
|
||||
|
||||
Tins::PDU *Tins::IP::clone_packet(const uint8_t *ptr, uint32_t total_sz) {
|
||||
PDU *IP::clone_packet(const uint8_t *ptr, uint32_t total_sz) {
|
||||
if(total_sz < sizeof(iphdr))
|
||||
return 0;
|
||||
const iphdr *ip_ptr = (iphdr*)ptr;
|
||||
@@ -335,3 +337,4 @@ Tins::PDU *Tins::IP::clone_packet(const uint8_t *ptr, uint32_t total_sz) {
|
||||
cloned->inner_pdu(child);
|
||||
return cloned;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,30 +20,27 @@
|
||||
*/
|
||||
|
||||
#include <cassert>
|
||||
#include <cstring>
|
||||
#include <algorithm>
|
||||
#include "rawpdu.h"
|
||||
|
||||
|
||||
Tins::RawPDU::RawPDU(const uint8_t *pload, uint32_t size) : PDU(255), _payload_size(size), _owns_payload(true) {
|
||||
_payload = new uint8_t[size];
|
||||
std::memcpy(_payload, pload, size);
|
||||
}
|
||||
|
||||
Tins::RawPDU::RawPDU(uint8_t *pload, uint32_t size) : PDU(255), _payload(pload), _payload_size(size), _owns_payload(false) {
|
||||
namespace Tins {
|
||||
RawPDU::RawPDU(const uint8_t *pload, uint32_t size)
|
||||
: PDU(255), _payload(pload, pload + size)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
Tins::RawPDU::~RawPDU() {
|
||||
if(_owns_payload)
|
||||
delete[] _payload;
|
||||
uint32_t RawPDU::header_size() const {
|
||||
return _payload.size();
|
||||
}
|
||||
|
||||
uint32_t Tins::RawPDU::header_size() const {
|
||||
return _payload_size;
|
||||
void RawPDU::write_serialization(uint8_t *buffer, uint32_t total_sz, const PDU *) {
|
||||
assert(total_sz >= _payload.size());
|
||||
std::copy(_payload.begin(), _payload.end(), buffer);
|
||||
}
|
||||
|
||||
void Tins::RawPDU::write_serialization(uint8_t *buffer, uint32_t total_sz, const PDU *) {
|
||||
assert(total_sz >= _payload_size);
|
||||
std::memcpy(buffer, _payload, _payload_size);
|
||||
void RawPDU::payload(const payload_type &pload) {
|
||||
_payload = pload;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -120,7 +120,7 @@ void TCP::payload(uint8_t *new_payload, uint32_t new_payload_size) {
|
||||
inner_pdu(new RawPDU(new_payload, new_payload_size));
|
||||
}
|
||||
|
||||
void TCP::data_offset(uint8_t new_doff) {
|
||||
void TCP::data_offset(small_uint<4> new_doff) {
|
||||
this->_tcp.doff = new_doff;
|
||||
}
|
||||
|
||||
@@ -201,7 +201,7 @@ bool TCP::search_altchecksum_option(uint8_t *value) {
|
||||
return generic_search(ALTCHK, value);
|
||||
}
|
||||
|
||||
uint8_t TCP::get_flag(Flags tcp_flag) {
|
||||
small_uint<1> TCP::get_flag(Flags tcp_flag) {
|
||||
switch(tcp_flag) {
|
||||
case FIN:
|
||||
return _tcp.fin;
|
||||
@@ -233,7 +233,7 @@ uint8_t TCP::get_flag(Flags tcp_flag) {
|
||||
};
|
||||
}
|
||||
|
||||
void TCP::set_flag(Flags tcp_flag, uint8_t value) {
|
||||
void TCP::set_flag(Flags tcp_flag, small_uint<1> value) {
|
||||
switch(tcp_flag) {
|
||||
case FIN:
|
||||
_tcp.fin = value;
|
||||
|
||||
@@ -122,7 +122,7 @@ bool Utils::resolve_hwaddr(const NetworkInterface &iface, IPv4Address ip,
|
||||
std::auto_ptr<PDU> packet(ARP::make_arp_request(iface, ip, info.ip_addr, info.hw_addr));
|
||||
std::auto_ptr<PDU> response(sender->send_recv(packet.get()));
|
||||
if(response.get()) {
|
||||
ARP *arp_resp = response->find_inner_pdu<ARP>();
|
||||
ARP *arp_resp = response->find_pdu<ARP>();
|
||||
if(arp_resp)
|
||||
*address = arp_resp->sender_hw_addr();
|
||||
return arp_resp;
|
||||
|
||||
Reference in New Issue
Block a user