xorp

auth.hh

00001 // -*- c-basic-offset: 4; tab-width: 8; indent-tabs-mode: t -*-
00002 // vim:set sts=4 ts=8:
00003 
00004 // Copyright (c) 2001-2011 XORP, Inc and Others
00005 //
00006 // This program is free software; you can redistribute it and/or modify
00007 // it under the terms of the GNU General Public License, Version 2, June
00008 // 1991 as published by the Free Software Foundation. Redistribution
00009 // and/or modification of this program under the terms of any other
00010 // version of the GNU General Public License is not permitted.
00011 // 
00012 // This program is distributed in the hope that it will be useful, but
00013 // WITHOUT ANY WARRANTY; without even the implied warranty of
00014 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. For more details,
00015 // see the GNU General Public License, Version 2, a copy of which can be
00016 // found in the XORP LICENSE.gpl file.
00017 // 
00018 // XORP Inc, 2953 Bunker Hill Lane, Suite 204, Santa Clara, CA 95054, USA;
00019 // http://xorp.net
00020 
00021 // $XORP: xorp/ospf/auth.hh,v 1.16 2008/11/21 00:07:55 atanu Exp $
00022 
00023 #ifndef __OSPF_AUTH_HH__
00024 #define __OSPF_AUTH_HH__
00025 
00026 #include <openssl/md5.h>
00027 
00028 
00029 
00030 class EventLoop;
00031 
00043 class AuthHandlerBase {
00044  public:
00045     virtual ~AuthHandlerBase();
00046 
00052     virtual const char* effective_name() const = 0;
00053 
00057     virtual void reset() = 0;
00058 
00065     virtual uint32_t additional_payload() const = 0;
00066 
00075     virtual bool authenticate_inbound(const vector<uint8_t>&    packet,
00076                       const IPv4&       src_addr,
00077                       bool          new_peer) = 0;
00078 
00086     virtual bool authenticate_outbound(vector<uint8_t>& packet) = 0;
00087 
00091     const string& error() const;
00092 
00093 protected:
00097     void reset_error();
00098 
00102     void set_error(const string& error_msg);
00103 
00104 private:
00105     string _error;
00106 };
00107 
00112 class NullAuthHandler : public AuthHandlerBase {
00113 public:
00114     static const OspfTypes::AuType AUTH_TYPE = OspfTypes::NULL_AUTHENTICATION;
00115 
00121     const char* effective_name() const;
00122 
00128     static const char* auth_type_name();
00129 
00133     void reset();
00134 
00141     uint32_t additional_payload() const;
00142 
00151     bool authenticate_inbound(const vector<uint8_t>&    packet,
00152                   const IPv4&       src_addr,
00153                   bool          new_peer);
00154 
00162     bool authenticate_outbound(vector<uint8_t>& packet);
00163 };
00164 
00168 class PlaintextAuthHandler : public AuthHandlerBase {
00169  public:
00170     static const OspfTypes::AuType AUTH_TYPE = OspfTypes::SIMPLE_PASSWORD;
00171 
00177     const char* effective_name() const;
00178 
00184     static const char* auth_type_name();
00185 
00189     void reset();
00190 
00197     uint32_t additional_payload() const;
00198 
00207     bool authenticate_inbound(const vector<uint8_t>&    packet,
00208                   const IPv4&       src_addr,
00209                   bool          new_peer);
00210 
00218     bool authenticate_outbound(vector<uint8_t>& packet);
00219 
00225     const string& key() const;
00226 
00232     void set_key(const string& plaintext_key);
00233 
00234  private:
00235     string  _key;
00236     uint8_t _key_data[Packet::AUTH_PAYLOAD_SIZE];
00237 };
00238 
00246 class MD5AuthHandler : public AuthHandlerBase {
00247 public:
00248     static const OspfTypes::AuType AUTH_TYPE =
00249     OspfTypes::CRYPTOGRAPHIC_AUTHENTICATION;
00250 
00254     class MD5Key {
00255     public:
00267     MD5Key(uint8_t      key_id,
00268            const string&    key,
00269            const TimeVal&   start_timeval,
00270            const TimeVal&   end_timeval,
00271            const TimeVal&   max_time_drift,
00272            XorpTimer    start_timer,
00273            XorpTimer    end_timer);
00274 
00278     uint8_t id() const          { return _id; }
00279 
00283     const char* key_data() const    { return _key_data; }
00284 
00288     uint32_t    key_data_bytes() const  { return KEY_BYTES; }
00289 
00293     string      key() const;
00294 
00298     const TimeVal&  start_timeval() const   { return _start_timeval; }
00299 
00303     const TimeVal&  end_timeval() const { return _end_timeval; }
00304 
00308     const TimeVal&  max_time_drift() const  { return _max_time_drift; }
00309 
00313     bool        is_persistent() const   { return _is_persistent; }
00314 
00320     void        set_persistent(bool v)  { _is_persistent = v; }
00321 
00326     bool        id_matches(uint8_t o) const { return _id == o; }
00327 
00333     bool        valid_at(const TimeVal& when) const;
00334 
00338     void        reset();
00339 
00345     void        reset(const IPv4& src_addr);
00346 
00355     bool        packets_received(const IPv4& src_addr) const;
00356 
00365     uint32_t    last_seqno_recv(const IPv4& src_addr) const;
00366 
00374     void        set_last_seqno_recv(const IPv4& src_addr,
00375                         uint32_t seqno);
00376 
00381     uint32_t next_seqno_out()       { return _o_seqno++; }
00382 
00383     protected:
00384     static const uint32_t KEY_BYTES = 16;
00385 
00386     uint8_t     _id;        // Key ID
00387     char        _key_data[KEY_BYTES]; // Key data
00388     TimeVal     _start_timeval; // Start time of the key
00389     TimeVal     _end_timeval;   // End time of the key
00390     TimeVal     _max_time_drift; // Max. time drift among all routers
00391     bool        _is_persistent; // True if key is persistent
00392     map<IPv4, bool> _pkts_recv; // True if packets received
00393     map<IPv4, uint32_t> _lr_seqno;  // Last received seqno
00394     uint32_t    _o_seqno;   // Next outbound sequence number
00395     XorpTimer   _start_timer;   // Key start timer
00396     XorpTimer   _stop_timer;    // Key stop timer
00397 
00398     friend class MD5AuthHandler;
00399     };
00400 
00401     typedef list<MD5Key> KeyChain;
00402 
00403 public:
00409     MD5AuthHandler(EventLoop& eventloop);
00410 
00416     const char* effective_name() const;
00417 
00423     static const char* auth_type_name();
00424 
00428     void reset();
00429 
00436     uint32_t additional_payload() const;
00437 
00446     bool authenticate_inbound(const vector<uint8_t>&    packet,
00447                   const IPv4&       src_addr,
00448                   bool          new_peer);
00449 
00457     bool authenticate_outbound(vector<uint8_t>& packet);
00458 
00473     bool add_key(uint8_t    key_id,
00474          const string&  key,
00475          const TimeVal& start_timeval,
00476          const TimeVal& end_timeval,
00477          const TimeVal& max_time_drift,
00478          string&    error_msg);
00479 
00487     bool remove_key(uint8_t key_id, string& error_msg);
00488 
00494     void key_start_cb(uint8_t key_id);
00495 
00501     void key_stop_cb(uint8_t key_id);
00502 
00512     MD5Key* best_outbound_key(const TimeVal& now);
00513 
00517     void reset_keys();
00518 
00524     const KeyChain& valid_key_chain() const { return _valid_key_chain; }
00525 
00531     const KeyChain& invalid_key_chain() const   { return _invalid_key_chain; }
00532 
00538     bool empty() const;
00539 
00540 protected:
00541     EventLoop&  _eventloop;     // The event loop
00542     KeyChain    _valid_key_chain;   // The set of all valid keys
00543     KeyChain    _invalid_key_chain; // The set of all invalid keys
00544     NullAuthHandler _null_handler;  // Null handler if no valid keys
00545 };
00546 
00551 class Auth {
00552  public:
00553     Auth(EventLoop& eventloop) : _eventloop(eventloop), _auth_handler(NULL)
00554     {
00555     set_method("none");
00556     }
00557 
00558     ~Auth() {
00559     if (_auth_handler != NULL) {
00560         delete _auth_handler;
00561         _auth_handler = NULL;
00562     }
00563     }
00564 
00565     bool set_method(const string& method) {
00566     if (_auth_handler != NULL) {
00567         delete _auth_handler;
00568         _auth_handler = NULL;
00569     }
00570 
00571     if ("none" == method) {
00572         _auth_handler = new NullAuthHandler;
00573         return true;
00574     }
00575 
00576     if ("simple" == method) {
00577         _auth_handler = new PlaintextAuthHandler;
00578         return true;
00579     }
00580 
00581     if ("md5" == method) {
00582         _auth_handler = new MD5AuthHandler(_eventloop);
00583         return true;
00584     }
00585 
00586     // Never allow _auth to be zero.
00587     set_method("none");
00588 
00589     return false;
00590     }
00591 
00595     void generate(vector<uint8_t>& pkt) {
00596     XLOG_ASSERT(_auth_handler != NULL);
00597     _auth_handler->authenticate_outbound(pkt);
00598     }
00599 
00603     bool verify(vector<uint8_t>& pkt, const IPv4& src_addr, bool new_peer) {
00604     XLOG_ASSERT(_auth_handler != NULL);
00605     return _auth_handler->authenticate_inbound(pkt, src_addr, new_peer);
00606     }
00607 
00608     bool verify(vector<uint8_t>& pkt, const IPv6& src_addr, bool new_peer) {
00609     UNUSED(pkt);
00610     UNUSED(src_addr);
00611     UNUSED(new_peer);
00612     return true;
00613     }
00614 
00618     uint32_t additional_payload() const {
00619     XLOG_ASSERT(_auth_handler != NULL);
00620     return _auth_handler->additional_payload();
00621     }
00622 
00623     const string& error() const {
00624     XLOG_ASSERT(_auth_handler != NULL);
00625     return _auth_handler->error();
00626     }
00627 
00631     void reset() {
00632     XLOG_ASSERT(_auth_handler != NULL);
00633     _auth_handler->reset();
00634     }
00635 
00646     bool set_simple_authentication_key(const string& password,
00647                        string& error_msg);
00648 
00658     bool delete_simple_authentication_key(string& error_msg);
00659 
00674     bool set_md5_authentication_key(uint8_t     key_id,
00675                     const string&   password,
00676                     const TimeVal&  start_timeval,
00677                     const TimeVal&  end_timeval,
00678                     const TimeVal&  max_time_drift,
00679                     string&     error_msg);
00680 
00692     bool delete_md5_authentication_key(uint8_t key_id, string& error_msg);
00693 
00694  private:
00695     EventLoop&      _eventloop;     // The event loop
00696     AuthHandlerBase*    _auth_handler;      // The authentication handler
00697 };
00698 
00699 #endif // __OSPF_AUTH_HH__
 All Classes Namespaces Functions Variables Typedefs Enumerations