|
IBR-DTNSuite 0.6
|
00001 /* 00002 * SecurityBlock.cpp 00003 * 00004 * Created on: 08.03.2010 00005 * Author: morgenro 00006 */ 00007 00008 #include "ibrdtn/security/SecurityBlock.h" 00009 #include "ibrdtn/security/MutualSerializer.h" 00010 #include "ibrdtn/data/Bundle.h" 00011 #include "ibrdtn/data/PayloadBlock.h" 00012 #include "ibrdtn/data/ExtensionBlock.h" 00013 00014 #include <ibrcommon/Logger.h> 00015 #include <cstdlib> 00016 #include <openssl/rand.h> 00017 #include <openssl/err.h> 00018 #include <openssl/rsa.h> 00019 00020 #ifdef __DEVELOPMENT_ASSERTIONS__ 00021 #include <cassert> 00022 #endif 00023 00024 namespace dtn 00025 { 00026 namespace security 00027 { 00028 const std::string SecurityBlock::TLVList::toString() const 00029 { 00030 std::stringstream ss; 00031 00032 for (std::set<TLV>::const_iterator iter = begin(); iter != end(); iter++) 00033 { 00034 ss << (*iter); 00035 } 00036 00037 return ss.str(); 00038 } 00039 00040 size_t SecurityBlock::TLVList::getLength() const 00041 { 00042 size_t len = getPayloadLength(); 00043 return len; 00044 } 00045 00046 size_t SecurityBlock::TLVList::getPayloadLength() const 00047 { 00048 size_t len = 0; 00049 00050 for (std::set<SecurityBlock::TLV>::const_iterator iter = begin(); iter != end(); iter++) 00051 { 00052 len += (*iter).getLength(); 00053 } 00054 00055 return len; 00056 } 00057 00058 const std::string SecurityBlock::TLVList::get(SecurityBlock::TLV_TYPES type) const 00059 { 00060 for (std::set<SecurityBlock::TLV>::const_iterator iter = begin(); iter != end(); iter++) 00061 { 00062 if ((*iter).getType() == type) 00063 { 00064 return (*iter).getValue(); 00065 } 00066 } 00067 00068 throw ibrcommon::Exception("element not found"); 00069 } 00070 00071 void SecurityBlock::TLVList::get(TLV_TYPES type, unsigned char *value, size_t length) const 00072 { 00073 const std::string data = get(type); 00074 00075 if (length < data.size()) 00076 { 00077 ::memcpy(value, data.c_str(), length); 00078 } 00079 else 00080 { 00081 ::memcpy(value, data.c_str(), data.size()); 00082 } 00083 } 00084 00085 void SecurityBlock::TLVList::set(SecurityBlock::TLV_TYPES type, std::string value) 00086 { 00087 SecurityBlock::TLV tlv(type, value); 00088 00089 erase(tlv); 00090 insert(tlv); 00091 } 00092 00093 void SecurityBlock::TLVList::set(TLV_TYPES type, const unsigned char *value, size_t length) 00094 { 00095 const std::string data(reinterpret_cast<const char *>(value), length); 00096 set(type, data); 00097 } 00098 00099 void SecurityBlock::TLVList::remove(SecurityBlock::TLV_TYPES type) 00100 { 00101 erase(SecurityBlock::TLV(type, "")); 00102 } 00103 00104 const std::string SecurityBlock::TLV::getValue() const 00105 { 00106 return _value; 00107 } 00108 00109 SecurityBlock::TLV_TYPES SecurityBlock::TLV::getType() const 00110 { 00111 return _type; 00112 } 00113 00114 size_t SecurityBlock::TLV::getLength() const 00115 { 00116 return _value.getLength() + sizeof(char); 00117 } 00118 00119 std::ostream& operator<<(std::ostream &stream, const SecurityBlock::TLVList &tlvlist) 00120 { 00121 dtn::data::SDNV length(tlvlist.getPayloadLength()); 00122 stream << length; 00123 00124 for (std::set<SecurityBlock::TLV>::const_iterator iter = tlvlist.begin(); iter != tlvlist.end(); iter++) 00125 { 00126 stream << (*iter); 00127 } 00128 return stream; 00129 } 00130 00131 std::istream& operator>>(std::istream &stream, SecurityBlock::TLVList &tlvlist) 00132 { 00133 dtn::data::SDNV length; 00134 stream >> length; 00135 size_t read_length = 0; 00136 00137 while (read_length < length.getValue()) 00138 { 00139 SecurityBlock::TLV tlv; 00140 stream >> tlv; 00141 tlvlist.insert(tlv); 00142 read_length += tlv.getLength(); 00143 } 00144 00145 return stream; 00146 } 00147 00148 bool SecurityBlock::TLV::operator<(const SecurityBlock::TLV &tlv) const 00149 { 00150 return (_type < tlv._type); 00151 } 00152 00153 bool SecurityBlock::TLV::operator==(const SecurityBlock::TLV &tlv) const 00154 { 00155 return (_type == tlv._type); 00156 } 00157 00158 std::ostream& operator<<(std::ostream &stream, const SecurityBlock::TLV &tlv) 00159 { 00160 stream.put((char)tlv._type); 00161 stream << tlv._value; 00162 return stream; 00163 } 00164 00165 std::istream& operator>>(std::istream &stream, SecurityBlock::TLV &tlv) 00166 { 00167 char tlv_type; 00168 stream.get(tlv_type); tlv._type = SecurityBlock::TLV_TYPES(tlv_type); 00169 stream >> tlv._value; 00170 return stream; 00171 } 00172 00173 SecurityBlock::SecurityBlock(const dtn::security::SecurityBlock::BLOCK_TYPES type, const dtn::security::SecurityBlock::CIPHERSUITE_IDS id) 00174 : Block(type), _ciphersuite_id(id), _ciphersuite_flags(0), _correlator(0) 00175 { 00176 00177 } 00178 00179 SecurityBlock::SecurityBlock(const dtn::security::SecurityBlock::BLOCK_TYPES type) 00180 : Block(type), _ciphersuite_flags(0), _correlator(0) 00181 { 00182 00183 } 00184 00185 SecurityBlock::~SecurityBlock() 00186 { 00187 } 00188 00189 void SecurityBlock::store_security_references() 00190 { 00191 // clear the EID list 00192 _eids.clear(); 00193 00194 // first the security source 00195 if (_security_source == dtn::data::EID()) 00196 { 00197 _ciphersuite_flags &= ~(SecurityBlock::CONTAINS_SECURITY_SOURCE); 00198 } 00199 else 00200 { 00201 _ciphersuite_flags |= SecurityBlock::CONTAINS_SECURITY_SOURCE; 00202 _eids.push_back(_security_source); 00203 } 00204 00205 // then the destination 00206 if (_security_destination == dtn::data::EID()) 00207 { 00208 _ciphersuite_flags &= ~(SecurityBlock::CONTAINS_SECURITY_DESTINATION); 00209 } 00210 else 00211 { 00212 _ciphersuite_flags |= SecurityBlock::CONTAINS_SECURITY_DESTINATION; 00213 _eids.push_back(_security_destination); 00214 } 00215 00216 if (_eids.size() > 0) 00217 { 00218 set(Block::BLOCK_CONTAINS_EIDS, true); 00219 } 00220 else 00221 { 00222 set(Block::BLOCK_CONTAINS_EIDS, false); 00223 } 00224 } 00225 00226 const dtn::data::EID SecurityBlock::getSecuritySource() const 00227 { 00228 return _security_source; 00229 } 00230 00231 const dtn::data::EID SecurityBlock::getSecurityDestination() const 00232 { 00233 return _security_destination; 00234 } 00235 00236 void SecurityBlock::setSecuritySource(const dtn::data::EID &source) 00237 { 00238 _security_source = source; 00239 store_security_references(); 00240 } 00241 00242 void SecurityBlock::setSecurityDestination(const dtn::data::EID &destination) 00243 { 00244 _security_destination = destination; 00245 store_security_references(); 00246 } 00247 00248 void SecurityBlock::setCiphersuiteId(const CIPHERSUITE_IDS id) 00249 { 00250 _ciphersuite_id = static_cast<u_int64_t>(id); 00251 } 00252 00253 void SecurityBlock::setCorrelator(const u_int64_t corr) 00254 { 00255 _correlator = corr; 00256 _ciphersuite_flags |= SecurityBlock::CONTAINS_CORRELATOR; 00257 } 00258 00259 bool SecurityBlock::isCorrelatorPresent(const dtn::data::Bundle& bundle, const u_int64_t correlator) 00260 { 00261 std::list<const dtn::data::Block *> blocks = bundle.getBlocks(); 00262 bool return_val = false; 00263 for (std::list<const dtn::data::Block *>::const_iterator it = blocks.begin(); it != blocks.end() && !return_val; it++) 00264 { 00265 char type = (*it)->getType(); 00266 if (type == BUNDLE_AUTHENTICATION_BLOCK 00267 || type == PAYLOAD_INTEGRITY_BLOCK 00268 || type == PAYLOAD_CONFIDENTIAL_BLOCK 00269 || type == EXTENSION_SECURITY_BLOCK) 00270 return_val = static_cast<const SecurityBlock*>(*it)->_correlator == correlator; 00271 } 00272 return return_val; 00273 } 00274 00275 u_int64_t SecurityBlock::createCorrelatorValue(const dtn::data::Bundle& bundle) 00276 { 00277 u_int64_t corr = random(); 00278 while (isCorrelatorPresent(bundle, corr)) 00279 corr = random(); 00280 return corr; 00281 } 00282 00283 size_t SecurityBlock::getLength() const 00284 { 00285 size_t length = dtn::data::SDNV::getLength(_ciphersuite_id) 00286 + dtn::data::SDNV::getLength(_ciphersuite_flags); 00287 00288 if (_ciphersuite_flags & CONTAINS_CORRELATOR) 00289 { 00290 length += dtn::data::SDNV::getLength(_correlator); 00291 } 00292 00293 if (_ciphersuite_flags & CONTAINS_CIPHERSUITE_PARAMS) 00294 { 00295 const dtn::data::SDNV size(_ciphersuite_params.getLength()); 00296 length += size.getLength() + size.getValue(); 00297 } 00298 00299 if (_ciphersuite_flags & CONTAINS_SECURITY_RESULT) 00300 { 00301 const dtn::data::SDNV size(getSecurityResultSize()); 00302 length += size.getLength() + size.getValue(); 00303 } 00304 00305 return length; 00306 } 00307 00308 size_t SecurityBlock::getLength_mutable() const 00309 { 00310 // ciphersuite_id 00311 size_t length = MutualSerializer::sdnv_size; 00312 00313 // ciphersuite_flags 00314 length += MutualSerializer::sdnv_size; 00315 00316 // correlator 00317 if (_ciphersuite_flags & CONTAINS_CORRELATOR) 00318 { 00319 length += MutualSerializer::sdnv_size; 00320 } 00321 00322 // ciphersuite parameters 00323 if (_ciphersuite_flags & CONTAINS_CIPHERSUITE_PARAMS) 00324 { 00325 length += MutualSerializer::sdnv_size; 00326 length += _ciphersuite_params.getLength(); 00327 } 00328 // security result 00329 if (_ciphersuite_flags & CONTAINS_SECURITY_RESULT) 00330 { 00331 length += MutualSerializer::sdnv_size + getSecurityResultSize(); 00332 } 00333 00334 return length; 00335 } 00336 00337 std::ostream& SecurityBlock::serialize(std::ostream &stream, size_t &length) const 00338 { 00339 stream << dtn::data::SDNV(_ciphersuite_id) << dtn::data::SDNV(_ciphersuite_flags); 00340 00341 if (_ciphersuite_flags & CONTAINS_CORRELATOR) 00342 { 00343 stream << dtn::data::SDNV(_correlator); 00344 } 00345 00346 if (_ciphersuite_flags & CONTAINS_CIPHERSUITE_PARAMS) 00347 { 00348 stream << _ciphersuite_params; 00349 } 00350 00351 if (_ciphersuite_flags & CONTAINS_SECURITY_RESULT) 00352 { 00353 stream << _security_result; 00354 } 00355 00356 return stream; 00357 } 00358 00359 std::ostream& SecurityBlock::serialize_strict(std::ostream &stream, size_t &length) const 00360 { 00361 stream << dtn::data::SDNV(_ciphersuite_id) << dtn::data::SDNV(_ciphersuite_flags); 00362 00363 if (_ciphersuite_flags & CONTAINS_CORRELATOR) 00364 { 00365 stream << dtn::data::SDNV(_correlator); 00366 } 00367 00368 if (_ciphersuite_flags & CONTAINS_CIPHERSUITE_PARAMS) 00369 { 00370 stream << _ciphersuite_params; 00371 } 00372 00373 if (_ciphersuite_flags & CONTAINS_SECURITY_RESULT) 00374 { 00375 stream << dtn::data::SDNV(getSecurityResultSize()); 00376 } 00377 00378 return stream; 00379 } 00380 00381 std::istream& SecurityBlock::deserialize(std::istream &stream, const size_t length) 00382 { 00383 #ifdef __DEVELOPMENT_ASSERTIONS__ 00384 // recheck blocktype. if blocktype is set wrong, this will be a huge fail 00385 assert(_blocktype == BUNDLE_AUTHENTICATION_BLOCK || _blocktype == PAYLOAD_INTEGRITY_BLOCK || _blocktype == PAYLOAD_CONFIDENTIAL_BLOCK || _blocktype == EXTENSION_SECURITY_BLOCK); 00386 #endif 00387 00388 dtn::data::SDNV ciphersuite_id, ciphersuite_flags; 00389 stream >> ciphersuite_id >> ciphersuite_flags; 00390 _ciphersuite_id = ciphersuite_id.getValue(); 00391 _ciphersuite_flags = ciphersuite_flags.getValue(); 00392 00393 #ifdef __DEVELOPMENT_ASSERTIONS__ 00394 // recheck ciphersuite_id 00395 assert(_ciphersuite_id == BAB_HMAC || _ciphersuite_id == PIB_RSA_SHA256 || _ciphersuite_id == PCB_RSA_AES128_PAYLOAD_PIB_PCB || _ciphersuite_id == ESB_RSA_AES128_EXT); 00396 // recheck ciphersuite_flags, could be more exhaustive 00397 assert(_ciphersuite_flags < 32); 00398 #endif 00399 00400 // copy security source and destination 00401 if (_ciphersuite_flags & SecurityBlock::CONTAINS_SECURITY_SOURCE) 00402 { 00403 if (_eids.size() == 0) 00404 throw dtn::SerializationFailedException("ciphersuite flags indicate a security source, but it is not present"); 00405 00406 _security_source = _eids.front(); 00407 } 00408 00409 if (_ciphersuite_flags & SecurityBlock::CONTAINS_SECURITY_DESTINATION) 00410 { 00411 if (_ciphersuite_flags & SecurityBlock::CONTAINS_SECURITY_SOURCE) 00412 { 00413 if (_eids.size() < 2) 00414 throw dtn::SerializationFailedException("ciphersuite flags indicate a security destination, but it is not present"); 00415 00416 _security_destination = (*(_eids.begin())++); 00417 } 00418 else 00419 { 00420 if (_eids.size() == 0) 00421 throw dtn::SerializationFailedException("ciphersuite flags indicate a security destination, but it is not present"); 00422 00423 _security_destination = _eids.front(); 00424 } 00425 } 00426 00427 if (_ciphersuite_flags & CONTAINS_CORRELATOR) 00428 { 00429 dtn::data::SDNV correlator; 00430 stream >> correlator; 00431 _correlator = correlator.getValue(); 00432 } 00433 if (_ciphersuite_flags & CONTAINS_CIPHERSUITE_PARAMS) 00434 { 00435 stream >> _ciphersuite_params; 00436 #ifdef __DEVELOPMENT_ASSERTIONS__ 00437 assert(_ciphersuite_params.getLength() > 0); 00438 #endif 00439 } 00440 00441 if (_ciphersuite_flags & CONTAINS_SECURITY_RESULT) 00442 { 00443 stream >> _security_result; 00444 #ifdef __DEVELOPMENT_ASSERTIONS__ 00445 assert(_security_result.getLength() > 0); 00446 #endif 00447 } 00448 00449 return stream; 00450 } 00451 00452 dtn::security::MutualSerializer& SecurityBlock::serialize_mutable(dtn::security::MutualSerializer &serializer) const 00453 { 00454 serializer << dtn::data::SDNV(_ciphersuite_id); 00455 serializer << dtn::data::SDNV(_ciphersuite_flags); 00456 00457 if (_ciphersuite_flags & CONTAINS_CORRELATOR) 00458 serializer << dtn::data::SDNV(_ciphersuite_flags); 00459 00460 if (_ciphersuite_flags & CONTAINS_CIPHERSUITE_PARAMS) 00461 { 00462 serializer << _ciphersuite_params; 00463 } 00464 00465 if (_ciphersuite_flags & CONTAINS_SECURITY_RESULT) 00466 { 00467 serializer << _security_result; 00468 } 00469 00470 return serializer; 00471 } 00472 00473 dtn::security::MutualSerializer& SecurityBlock::serialize_mutable_without_security_result(dtn::security::MutualSerializer &serializer) const 00474 { 00475 serializer << dtn::data::SDNV(_ciphersuite_id); 00476 serializer << dtn::data::SDNV(_ciphersuite_flags); 00477 00478 if (_ciphersuite_flags & CONTAINS_CORRELATOR) 00479 serializer << dtn::data::SDNV(_ciphersuite_flags); 00480 00481 if (_ciphersuite_flags & CONTAINS_CIPHERSUITE_PARAMS) 00482 { 00483 serializer << _ciphersuite_params; 00484 } 00485 00486 if (_ciphersuite_flags & CONTAINS_SECURITY_RESULT) 00487 { 00488 serializer << dtn::data::SDNV(getSecurityResultSize()); 00489 } 00490 00491 return serializer; 00492 } 00493 00494 size_t SecurityBlock::getSecurityResultSize() const 00495 { 00496 #ifdef __DEVELOPMENT_ASSERTIONS__ 00497 assert(_security_result.getLength() != 0); 00498 #endif 00499 return _security_result.getLength(); 00500 } 00501 00502 void SecurityBlock::createSaltAndKey(u_int32_t& salt, unsigned char* key, size_t key_size) 00503 { 00504 00505 if (!RAND_bytes(reinterpret_cast<unsigned char *>(&salt), sizeof(u_int32_t))) 00506 { 00507 IBRCOMMON_LOGGER_ex(critical) << "failed to generate salt. maybe /dev/urandom is missing for seeding the PRNG" << IBRCOMMON_LOGGER_ENDL; 00508 ERR_print_errors_fp(stderr); 00509 } 00510 if (!RAND_bytes(key, key_size)) 00511 { 00512 IBRCOMMON_LOGGER_ex(critical) << "failed to generate key. maybe /dev/urandom is missing for seeding the PRNG" << IBRCOMMON_LOGGER_ENDL; 00513 ERR_print_errors_fp(stderr); 00514 } 00515 } 00516 00517 void SecurityBlock::addKey(TLVList& security_parameter, unsigned char const * const key, size_t key_size, RSA * rsa) 00518 { 00519 // encrypt the ephemeral key and place it in _ciphersuite_params 00520 #ifdef __DEVELOPMENT_ASSERTIONS__ 00521 assert(key_size < RSA_size(rsa)-41); 00522 #endif 00523 unsigned char encrypted_key[RSA_size(rsa)]; 00524 int encrypted_key_len = RSA_public_encrypt(key_size, key, encrypted_key, rsa, RSA_PKCS1_OAEP_PADDING); 00525 if (encrypted_key_len == -1) 00526 { 00527 IBRCOMMON_LOGGER_ex(critical) << "failed to encrypt the symmetric AES key" << IBRCOMMON_LOGGER_ENDL; 00528 ERR_print_errors_fp(stderr); 00529 } 00530 security_parameter.set(SecurityBlock::key_information, std::string(reinterpret_cast<char *>(encrypted_key), encrypted_key_len)); 00531 } 00532 00533 bool SecurityBlock::getKey(const TLVList& security_parameter, unsigned char * key, size_t key_size, RSA * rsa) 00534 { 00535 std::string key_string = security_parameter.get(SecurityBlock::key_information); 00536 // get key, convert with reinterpret_cast 00537 unsigned char const * encrypted_key = reinterpret_cast<const unsigned char*>(key_string.c_str()); 00538 unsigned char the_key[RSA_size(rsa)]; 00539 RSA_blinding_on(rsa, NULL); 00540 int plaintext_key_len = RSA_private_decrypt(key_string.size(), encrypted_key, the_key, rsa, RSA_PKCS1_OAEP_PADDING); 00541 RSA_blinding_off(rsa); 00542 if (plaintext_key_len == -1) 00543 { 00544 IBRCOMMON_LOGGER_ex(critical) << "failed to decrypt the symmetric AES key" << IBRCOMMON_LOGGER_ENDL; 00545 ERR_print_errors_fp(stderr); 00546 return false; 00547 } 00548 #ifdef __DEVELOPMENT_ASSERTIONS__ 00549 assert(plaintext_key_len == key_size); 00550 #endif 00551 std::copy(the_key, the_key+key_size, key); 00552 return true; 00553 } 00554 00555 void SecurityBlock::copyEID(const Block& from, Block& to, size_t skip) 00556 { 00557 // take eid list, getEIDList() is broken 00558 std::list<dtn::data::EID> their_eids = from.getEIDList(); 00559 std::list<dtn::data::EID>::iterator it = their_eids.begin(); 00560 00561 while (it != their_eids.end() && skip > 0) 00562 { 00563 skip--; 00564 it++; 00565 } 00566 00567 for (; it != their_eids.end(); it++) 00568 to.addEID(*it); 00569 } 00570 00571 void SecurityBlock::addSalt(TLVList& security_parameters, u_int32_t salt) 00572 { 00573 std::stringstream salt_stream; 00574 salt_stream << salt; 00575 security_parameters.set(SecurityBlock::salt, salt_stream.str()); 00576 } 00577 00578 u_int32_t SecurityBlock::getSalt(const TLVList& security_parameters) 00579 { 00580 // get salt, convert with stringstream 00581 std::string salt_string = security_parameters.get(SecurityBlock::salt); 00582 std::stringstream salt_stream; 00583 salt_stream << salt_string; 00584 u_int32_t salt; 00585 salt_stream >> salt; 00586 return salt; 00587 } 00588 00589 void SecurityBlock::decryptBlock(dtn::data::Bundle& bundle, const dtn::security::SecurityBlock &block, u_int32_t salt, const unsigned char key[ibrcommon::AES128Stream::key_size_in_bytes]) 00590 { 00591 // the array for the extracted tag 00592 unsigned char tag[ibrcommon::AES128Stream::tag_len]; 00593 00594 // the array for the extracted iv 00595 unsigned char iv[ibrcommon::AES128Stream::iv_len]; 00596 00597 // get iv, convert with reinterpret_cast 00598 block._ciphersuite_params.get(SecurityBlock::initialization_vector, iv, ibrcommon::AES128Stream::iv_len); 00599 00600 // get data and tag, the last tag_len bytes are the tag. cut them of and reinterpret_cast 00601 std::string block_data = block._security_result.get(SecurityBlock::encapsulated_block); 00602 00603 // create a pointer to the tag begin 00604 const char *tag_p = block_data.c_str() + (block_data.size() - ibrcommon::AES128Stream::tag_len); 00605 00606 // copy the tag 00607 ::memcpy(tag, tag_p, ibrcommon::AES128Stream::tag_len); 00608 00609 // strip off the tag from block data 00610 block_data.resize(block_data.size() - ibrcommon::AES128Stream::tag_len); 00611 00612 // decrypt block 00613 std::stringstream plaintext; 00614 ibrcommon::AES128Stream decrypt(ibrcommon::CipherStream::CIPHER_DECRYPT, plaintext, key, salt, iv); 00615 decrypt << block_data << std::flush; 00616 00617 // verify the decrypt tag 00618 if (!decrypt.verify(tag)) 00619 { 00620 throw ibrcommon::Exception("decryption of block failed - tag is bad"); 00621 } 00622 00623 // deserialize block 00624 dtn::data::DefaultDeserializer ddser(plaintext); 00625 00626 // peek the block type 00627 char block_type = plaintext.peek(); 00628 00629 if (block_type == dtn::data::PayloadBlock::BLOCK_TYPE) 00630 { 00631 dtn::data::PayloadBlock &plaintext_block = bundle.insert<dtn::data::PayloadBlock>(block); 00632 ddser >> plaintext_block; 00633 } 00634 else 00635 { 00636 try { 00637 dtn::data::ExtensionBlock::Factory &f = dtn::data::ExtensionBlock::Factory::get(block_type); 00638 dtn::data::Block &plaintext_block = bundle.insert(f, block); 00639 ddser >> plaintext_block; 00640 00641 plaintext_block.getEIDList().clear(); 00642 00643 // copy eids 00644 // remove security_source and destination 00645 size_t skip = 0; 00646 if (block._ciphersuite_flags & SecurityBlock::CONTAINS_SECURITY_DESTINATION) 00647 skip++; 00648 if (block._ciphersuite_flags & SecurityBlock::CONTAINS_SECURITY_SOURCE) 00649 skip++; 00650 copyEID(plaintext_block, plaintext_block, skip); 00651 00652 } catch (const ibrcommon::Exception &ex) { 00653 dtn::data::ExtensionBlock &plaintext_block = bundle.insert<dtn::data::ExtensionBlock>(block); 00654 ddser >> plaintext_block; 00655 00656 plaintext_block.getEIDList().clear(); 00657 00658 // copy eids 00659 // remove security_source and destination 00660 size_t skip = 0; 00661 if (block._ciphersuite_flags & SecurityBlock::CONTAINS_SECURITY_DESTINATION) 00662 skip++; 00663 if (block._ciphersuite_flags & SecurityBlock::CONTAINS_SECURITY_SOURCE) 00664 skip++; 00665 copyEID(plaintext_block, plaintext_block, skip); 00666 } 00667 } 00668 00669 bundle.remove(block); 00670 } 00671 00672 void SecurityBlock::addFragmentRange(TLVList& ciphersuite_params, size_t fragmentoffset, size_t payload_length) 00673 { 00674 dtn::data::SDNV offset(fragmentoffset); 00675 dtn::data::SDNV range_sdnv(payload_length); 00676 00677 std::stringstream ss; 00678 ss << offset << range_sdnv; 00679 00680 ciphersuite_params.set(SecurityBlock::fragment_range, ss.str()); 00681 } 00682 00683 bool SecurityBlock::isSecuritySource(const dtn::data::Bundle& bundle, const dtn::data::EID& eid) const 00684 { 00685 IBRCOMMON_LOGGER_DEBUG(30) << "check security source: " << getSecuritySource(bundle).getString() << " == " << eid.getNode().getString() << IBRCOMMON_LOGGER_ENDL; 00686 return getSecuritySource(bundle) == eid.getNode(); 00687 } 00688 00689 bool SecurityBlock::isSecurityDestination(const dtn::data::Bundle& bundle, const dtn::data::EID& eid) const 00690 { 00691 IBRCOMMON_LOGGER_DEBUG(30) << "check security destination: " << getSecurityDestination(bundle).getString() << " == " << eid.getNode().getString() << IBRCOMMON_LOGGER_ENDL; 00692 return getSecurityDestination(bundle) == eid.getNode(); 00693 } 00694 00695 const dtn::data::EID SecurityBlock::getSecuritySource(const dtn::data::Bundle& bundle) const 00696 { 00697 dtn::data::EID source = getSecuritySource(); 00698 if (source == dtn::data::EID()) 00699 source = bundle._source.getNode(); 00700 return source; 00701 } 00702 00703 const dtn::data::EID SecurityBlock::getSecurityDestination(const dtn::data::Bundle& bundle) const 00704 { 00705 dtn::data::EID destination = getSecurityDestination(); 00706 if (destination == dtn::data::EID()) 00707 destination = bundle._destination.getNode(); 00708 return destination; 00709 } 00710 } 00711 }