LCOV - code coverage report
Current view: top level - src - Serializer.h (source / functions) Hit Total Coverage
Test: app.info Lines: 28 76 36.8 %
Date: 2010-12-13 Functions: 15 48 31.2 %
Branches: 8 26 30.8 %

           Branch data     Line data    Source code
       1                 :            : // $Id: Serializer.h 6752 2009-06-14 04:24:52Z vern $
       2                 :            : 
       3                 :            : #ifndef SERIALIZER_H
       4                 :            : #define SERIALIZER_H
       5                 :            : 
       6                 :            : #include <map>
       7                 :            : #include <list>
       8                 :            : #include <pcap.h>
       9                 :            : 
      10                 :            : #include "ID.h"
      11                 :            : #include "List.h"
      12                 :            : #include "Expr.h"
      13                 :            : #include "ChunkedIO.h"
      14                 :            : #include "SerializationFormat.h"
      15                 :            : #include "StateAccess.h"
      16                 :            : #include "PriorityQueue.h"
      17                 :            : #include "SerialInfo.h"
      18                 :            : #include "IP.h"
      19                 :            : #include "Timer.h"
      20                 :            : #include "IOSource.h"
      21                 :            : 
      22                 :            : class SerializationCache;
      23                 :            : class SerialInfo;
      24                 :            : 
      25                 :            : class Connection;
      26                 :            : class Timer;
      27                 :            : class Packet;
      28                 :            : 
      29                 :            : class Serializer {
      30                 :            : public:
      31                 :            :         // Currently ID serialization is the only method which may suspend.
      32                 :            :         bool Serialize(SerialInfo* info, const ID& id);
      33                 :            :         bool Serialize(SerialInfo* info, const char* func, val_list* args);
      34                 :            :         bool Serialize(SerialInfo* info, const StateAccess& s);
      35                 :            :         bool Serialize(SerialInfo* info, const Connection& c);
      36                 :            :         bool Serialize(SerialInfo* info, const Timer& t);
      37                 :            :         bool Serialize(SerialInfo* info, const Packet& p);
      38                 :            : 
      39                 :            :         // Access to the current cache.
      40                 :        172 :         SerializationCache* Cache()     { return current_cache; }
      41                 :          3 :         void SetCache(SerializationCache* cache)
      42                 :          3 :                 { current_cache = cache; }
      43                 :            : 
      44                 :            :         // Input/output methods.
      45                 :            : 
      46                 :            : #define DECLARE_READ(type) \
      47                 :            :         bool Read(type* v, const char* tag)     { return format->Read(v, tag); }
      48                 :            : 
      49                 :            : #define DECLARE_WRITE(type) \
      50                 :            :         bool Write(type v, const char* tag)     \
      51                 :            :                 { return format->Write(v, tag); }
      52                 :            : 
      53                 :            : #define DECLARE_IO(type)        \
      54                 :            :         DECLARE_READ(type)      \
      55                 :            :         DECLARE_WRITE(type)
      56                 :            : 
      57                 :        155 :         DECLARE_IO(int)
      58                 :         65 :         DECLARE_IO(uint16)
      59                 :          0 :         DECLARE_IO(uint32)
      60                 :          0 :         DECLARE_IO(int64)
      61                 :        110 :         DECLARE_IO(uint64)
      62                 :         48 :         DECLARE_IO(char)
      63                 :        294 :         DECLARE_IO(bool)
      64                 :          4 :         DECLARE_IO(double)
      65                 :            : 
      66                 :          0 :         bool Read(char** str, int* len, const char* tag)
      67                 :          0 :                 { return format->Read(str, len, tag); }
      68                 :          0 :         bool Read(const char** str, int* len, const char* tag)
      69                 :            :                 // This cast is ok.
      70                 :          0 :                 { return format->Read(const_cast<char**>(str), len, tag); }
      71                 :            : 
      72                 :            :         bool Read(string* s, const char* tag);
      73                 :            : 
      74                 :         42 :         bool Write(const char* s, const char* tag)
      75                 :         42 :                 { return format->Write(s, tag); }
      76                 :          0 :         bool Write(const char* buf, int len, const char* tag)
      77                 :          0 :                 { return format->Write(buf, len, tag); }
      78                 :          0 :         bool Write(const string& s, const char* tag)
      79                 :          0 :                 { return format->Write(s.data(), s.size(), tag); }
      80                 :            : 
      81                 :         85 :         bool WriteOpenTag(const char* tag)
      82                 :         85 :                 { return format->WriteOpenTag(tag); }
      83                 :         84 :         bool WriteCloseTag(const char* tag)
      84                 :         84 :                 { return format->WriteCloseTag(tag); }
      85                 :            : 
      86                 :          1 :         bool WriteSeparator()   { return format->WriteSeparator(); }
      87                 :            : 
      88                 :            :         void Error(const char* msg);
      89                 :            :         void Warning(const char* msg);
      90                 :            : 
      91                 :          2 :         void SetErrorDescr(const char* descr)
      92         [ +  + ]:          2 :                 { delete [] error_descr; error_descr = copy_string(descr); }
      93                 :            : 
      94                 :            : protected:
      95                 :            :         // Format defaults to binary serialization.
      96                 :            :         Serializer(SerializationFormat* format = 0);
      97                 :            :         virtual ~Serializer();
      98                 :            : 
      99                 :            :         // Reads next object.
     100                 :            :         // If 'block' is true, wait until an object can be read.
     101                 :            :         // Returns 0 if no more object available, -1 on error.
     102                 :            :         int Unserialize(UnserialInfo* info, bool block = false);
     103                 :            : 
     104                 :            :         // Callback for error messages.
     105                 :            :         virtual void ReportError(const char* msg) = 0;
     106                 :            : 
     107                 :            :         // Callbacks for unserialized objects.
     108                 :            : 
     109                 :            :         // id points to ID in global scope, val is unserialized value.
     110                 :            :         virtual void GotID(ID* id, Val* val) = 0;
     111                 :            :         virtual void GotEvent(const char* name, double time,
     112                 :            :                                 EventHandlerPtr event, val_list* args) = 0;
     113                 :            :         virtual void GotFunctionCall(const char* name, double time,
     114                 :            :                                 Func* func, val_list* args) = 0;
     115                 :            :         virtual void GotStateAccess(StateAccess* s) = 0;
     116                 :            :         virtual void GotTimer(Timer* t) = 0;
     117                 :            :         virtual void GotConnection(Connection* c) = 0;
     118                 :            :         virtual void GotPacket(Packet* packet) = 0;
     119                 :            : 
     120                 :            :         // Magic to recognize state files.
     121                 :            :         static const uint32 MAGIC = 0x42525354;
     122                 :            : 
     123                 :            :         // This will be increased whenever there is an incompatible change
     124                 :            :         // in the data format.
     125                 :            :         static const uint32 DATA_FORMAT_VERSION = 18;
     126                 :            : 
     127                 :            :         ChunkedIO* io;
     128                 :            : 
     129                 :            : private:
     130                 :            :         bool StartSerialization(SerialInfo* info, const char* descr, char tag);
     131                 :            :         bool EndSerialization(SerialInfo* info);
     132                 :            : 
     133                 :            :         bool UnserializeID(UnserialInfo* info);
     134                 :            :         bool UnserializeCall(UnserialInfo* info);
     135                 :            :         bool UnserializeStateAccess(UnserialInfo* info);
     136                 :            :         bool UnserializeTimer(UnserialInfo* info);
     137                 :            :         bool UnserializeConnection(UnserialInfo* info);
     138                 :            :         bool UnserializePacket(UnserialInfo* info);
     139                 :            : 
     140                 :            :         SerializationFormat* format;
     141                 :            :         SerializationCache* current_cache;
     142                 :            :         const char* error_descr;        // used in error messages
     143                 :            : };
     144                 :            : 
     145                 :            : 
     146                 :            : 
     147                 :            : // We maintain an LRU-cache for some of the objects which have already been
     148                 :            : // serialized. For the cache, we need two types of IDs: TransientIDs (defined
     149                 :            : // in SerialObj.cc) uniquely reference an object during the lifetime of a
     150                 :            : // process.  PermanentIDs uniquely reference an object within a serialization.
     151                 :            : 
     152                 :            : class SerializationCache {
     153                 :            : public:
     154                 :            :         typedef uint64 PermanentID;
     155                 :            :         static const PermanentID NONE = 0;
     156                 :            : 
     157                 :            :         // If max_cache_size is greater than zero, we'll remove old entries
     158                 :            :         // automatically if limit is reached (LRU expiration).
     159                 :            :         SerializationCache(unsigned int max_cache_size = 0);
     160                 :            :         ~SerializationCache();
     161                 :            : 
     162                 :            :         PermanentID Register(const SerialObj* obj, PermanentID pid,
     163                 :            :                                 bool new_cache_strategy);
     164                 :            : 
     165                 :          0 :         const SerialObj* Lookup(PermanentID pid)
     166                 :            :                 {
     167                 :          0 :                 PIDMap::const_iterator i = pid_map.find(pid);
     168         [ #  # ]:          0 :                 if ( i == pid_map.end() )
     169                 :          0 :                         return 0;
     170                 :            : 
     171         [ #  # ]:          0 :                 assert(i->second);
     172                 :          0 :                 MoveEntryToTail(i->second);
     173                 :          0 :                 return i->second->obj.serial;
     174                 :            :                 }
     175                 :            : 
     176                 :        107 :         PermanentID Lookup(const TransientID& tid)
     177                 :            :                 {
     178                 :        107 :                 TIDMap::const_iterator i = tid_map.find(tid.Value());
     179         [ +  + ]:        107 :                 if ( i == tid_map.end() )
     180                 :         65 :                         return 0;
     181                 :            : 
     182                 :         42 :                 uint64 modified = i->second->obj.serial->LastModified();
     183   [ +  -  -  + ]:         42 :                 if ( modified == SerialObj::ALWAYS || modified > i->second->time )
                 [ -  + ]
     184                 :          0 :                         return 0;
     185                 :            : 
     186         [ -  + ]:         42 :                 assert(i->second);
     187                 :         42 :                 MoveEntryToTail(i->second);
     188                 :        107 :                 return i->second->pid;
     189                 :            :                 }
     190                 :            : 
     191                 :          0 :         unsigned int GetMaxCacheSize() const    { return max_cache_size; }
     192                 :          0 :         void SetMaxCacheSize(unsigned int size) { max_cache_size = size; }
     193                 :            : 
     194                 :            :         // These methods have to be called at the start/end of the
     195                 :            :         // serialization of an entity. The cache guarentees that objects
     196                 :            :         // registered after Begin() remain valid until End() is called.
     197                 :            :         // After End(), objects which are not derived from BroObj are
     198                 :            :         // discarded; others *may* remain valid.
     199                 :          2 :         void Begin(bool can_keep_in_cache)      { End(can_keep_in_cache); }
     200                 :            :         void End(bool can_keep_in_cache);
     201                 :            : 
     202                 :            :         void Clear();
     203                 :            : 
     204                 :            : private:
     205                 :            : 
     206                 :            :         struct CacheList;
     207                 :            : 
     208                 :            :         struct CacheEntry {
     209                 :            :                 union {
     210                 :            :                         const SerialObj* serial;
     211                 :            :                         const BroObj* bro;
     212                 :            :                 } obj;
     213                 :            : 
     214                 :            :                 bool is_bro_obj;
     215                 :            :                 PermanentID pid;
     216                 :            :                 TransientID::ID tid;
     217                 :            :                 uint64 time;
     218                 :            :                 struct CacheList* cache;
     219                 :            :                 CacheEntry* prev;
     220                 :            :                 CacheEntry* next;
     221                 :            : 
     222                 :            :                 SerialType stype;       // primarily for debugging
     223                 :            :         };
     224                 :            : 
     225                 :            :         // We maintain two LRU-sorted lists, one for often-changing objects and
     226                 :            :         // one for only rarely changing objects;
     227                 :            :         struct CacheList {
     228                 :            :                 CacheEntry* head;
     229                 :            :                 CacheEntry* tail;
     230                 :            :                 unsigned int size;
     231                 :            :         };
     232                 :            : 
     233                 :            :         void RemoveEntry(CacheEntry* e);
     234                 :            :         void UnlinkEntry(CacheEntry* e);
     235                 :            :         void MoveEntryToTail(CacheEntry* e);
     236                 :            : 
     237                 :            :         unsigned int max_cache_size;
     238                 :            : 
     239                 :            :         typedef map<PermanentID, CacheEntry*> PIDMap;
     240                 :            :         typedef map<TransientID::ID, CacheEntry*> TIDMap;
     241                 :            : 
     242                 :            :         TIDMap tid_map;
     243                 :            :         PIDMap pid_map;
     244                 :            : 
     245                 :            :         CacheList cache_stable;
     246                 :            :         CacheList cache_unstable;
     247                 :            : 
     248                 :            :         // Objects in the cache which aren't derived from BroObj. These are
     249                 :            :         // always stored in the unstable cache.
     250                 :            :         typedef list<CacheEntry*> VolatileList;
     251                 :            :         VolatileList volatiles;
     252                 :            : 
     253                 :            :         PermanentID next_id;
     254                 :            : };
     255                 :            : 
     256                 :            : // A serializer for cloning objects.  Objects can be serialized into
     257                 :            : // the serializer and unserialized into new objects.  An absolutely
     258                 :            : // minimal implementation of Serializer!
     259                 :            : class CloneSerializer : public Serializer {
     260                 :            : public:
     261                 :          0 :         CloneSerializer(SerializationFormat* format = 0) : Serializer(format) { }
     262 [ #  # ][ #  # ]:          0 :         virtual ~CloneSerializer()      { }
     263                 :            : 
     264                 :            : protected:
     265                 :          0 :         virtual void ReportError(const char* msg)       { run_time(msg); }
     266                 :          0 :         virtual void GotID(ID* id, Val* val)    { }
     267                 :            :         virtual void GotEvent(const char* name, double time,
     268                 :          0 :                                 EventHandlerPtr event, val_list* args)  { }
     269                 :            :         virtual void GotFunctionCall(const char* name, double time,
     270                 :          0 :                                 Func* func, val_list* args)     { }
     271         [ #  # ]:          0 :         virtual void GotStateAccess(StateAccess* s)     { delete s; }
     272                 :          0 :         virtual void GotTimer(Timer* t) { }
     273                 :          0 :         virtual void GotConnection(Connection* c)       { }
     274                 :          0 :         virtual void GotPacket(Packet* packet)  { }
     275                 :            : };
     276                 :            : 
     277                 :            : // Write values/events to file or fd.
     278                 :            : class FileSerializer : public Serializer {
     279                 :            : public:
     280                 :            :         FileSerializer(SerializationFormat* format = 0);
     281                 :            :         virtual ~FileSerializer();
     282                 :            : 
     283                 :            :         // Opens the file for serialization.
     284                 :            :         bool Open(const char* file, bool pure = false);
     285                 :            :         bool Close();
     286                 :            : 
     287                 :            :         // Reads the file.
     288                 :            :         bool Read(UnserialInfo* info, const char* file, bool header = true);
     289                 :            : 
     290                 :            : protected:
     291                 :            :         virtual void ReportError(const char* msg);
     292                 :            :         virtual void GotID(ID* id, Val* val);
     293                 :            :         virtual void GotEvent(const char* name, double time,
     294                 :            :                                 EventHandlerPtr event, val_list* args);
     295                 :            :         virtual void GotFunctionCall(const char* name, double time,
     296                 :            :                                 Func* func, val_list* args);
     297                 :            :         virtual void GotStateAccess(StateAccess* s);
     298                 :            :         virtual void GotTimer(Timer* t);
     299                 :            :         virtual void GotConnection(Connection* c);
     300                 :            :         virtual void GotPacket(Packet* packet);
     301                 :            : 
     302                 :            :         bool OpenFile(const char* file, bool readonly, bool should_exist = false);
     303                 :            :         void CloseFile();
     304                 :            :         bool ReadFile(const char* file);
     305                 :            :         bool PrepareForWriting();
     306                 :            :         bool ReadHeader(UnserialInfo* info = 0);
     307                 :            : 
     308                 :            :         SerializationCache cache;
     309                 :            :         const char* file;
     310                 :            :         int fd;
     311                 :            : };
     312                 :            : 
     313                 :            : // Converts from one serialization format into another.
     314                 :            : class ConversionSerializer:public FileSerializer {
     315                 :            : public:
     316                 :            :         ConversionSerializer(SerializationFormat* in, SerializationFormat* out);
     317                 :            :         virtual ~ConversionSerializer();
     318                 :            : 
     319                 :            :         bool Convert(const char* file_in, const char* file_out);
     320                 :            : 
     321                 :            : protected:
     322                 :            :         virtual void GotID(ID* id, Val* val);
     323                 :            :         virtual void GotEvent(const char* name, double time,
     324                 :            :                                 EventHandlerPtr event, val_list* args);
     325                 :            :         virtual void GotFunctionCall(const char* name, double time,
     326                 :            :                                 Func* func, val_list* args);
     327                 :            :         virtual void GotStateAccess(StateAccess* s);
     328                 :            :         virtual void GotPacket(Packet* packet);
     329                 :            : 
     330                 :            :         FileSerializer* serout;
     331                 :            : };
     332                 :            : 
     333                 :            : 
     334                 :            : // Abstract interface class for external sources providing a stream of events.
     335                 :            : class EventSource {
     336                 :            : public:
     337                 :            :         virtual ~EventSource() { }
     338                 :            : 
     339                 :            :         // Returns time of the oldest event (0 if none available).
     340                 :            :         virtual double NextTimestamp(double* local_network_time) = 0;
     341                 :            : 
     342                 :            :         // Dispatches the oldest event and removes it.
     343                 :            :         virtual void DispatchNextEvent() = 0;
     344                 :            : 
     345                 :            :         // Returns true if there are more events to expect from this source.
     346                 :            :         virtual bool IsActive() = 0;
     347                 :            : };
     348                 :            : 
     349                 :            : // Plays a file of events back.
     350                 :            : class EventPlayer : public FileSerializer, public IOSource {
     351                 :            : public:
     352                 :            :         EventPlayer(const char* file);
     353                 :            :         virtual ~EventPlayer();
     354                 :            : 
     355                 :            :         virtual void GetFds(int* read, int* write, int* except);
     356                 :            :         virtual double NextTimestamp(double* local_network_time);
     357                 :            :         virtual void Process();
     358                 :          0 :         virtual const char* Tag()       { return "EventPlayer"; }
     359                 :            : 
     360                 :            : protected:
     361                 :          0 :         virtual void GotID(ID* id, Val* val)    {}
     362                 :            :         virtual void GotEvent(const char* name, double time,
     363                 :            :                                 EventHandlerPtr event, val_list* args);
     364                 :            :         virtual void GotFunctionCall(const char* name, double time,
     365                 :            :                                 Func* func, val_list* args);
     366                 :            : 
     367                 :            :         double stream_time;     // time of first captured event
     368                 :            :         double replay_time;     // network time of replay start
     369                 :            : 
     370                 :            :         // Next event waiting to be dispatched.
     371                 :            :         double ne_time;
     372                 :            :         EventHandlerPtr ne_handler;
     373                 :            :         val_list* ne_args;
     374                 :            : 
     375                 :            : };
     376                 :            : 
     377                 :            : 
     378                 :            : // A link-layer packet.
     379                 :            : //
     380                 :            : // Eventually we should use something like this consistently throughout Bro,
     381                 :            : // replacing the current packet arguments in functions like *::NextPacket().
     382                 :            : // Before doing this, though, we should consider provisioning for packet
     383                 :            : // formats other than just libpcap by designing a more abstract interface.
     384                 :            : //
     385                 :            : // Note that for serialization we don't use much of the support provided by
     386                 :            : // the serialization framework. Serialize/Unserialize do all the work by
     387                 :            : // themselves. In particular, Packets aren't derived from SerialObj. They are
     388                 :            : // completely seperate and self-contained entities, and we don't need any of
     389                 :            : // the sophisticated features like object caching.
     390                 :            : 
     391                 :            : class Packet {
     392                 :            : public:
     393                 :            :         // Argument is whether we should delete associatd memory upon
     394                 :            :         // destruction.
     395                 :          0 :         Packet(TimerMgr::Tag arg_tag, bool arg_free = false)
     396                 :          0 :                 {
     397                 :          0 :                 time = 0.0;
     398                 :          0 :                 hdr = 0;
     399                 :          0 :                 pkt = 0;
     400                 :          0 :                 hdr_size = 0;
     401                 :          0 :                 free = arg_free;
     402                 :          0 :                 tag = arg_tag;
     403                 :          0 :                 }
     404                 :            : 
     405                 :          0 :         ~Packet()
     406                 :            :                 {
     407         [ #  # ]:          0 :                 if ( free )
     408                 :            :                         {
     409                 :          0 :                         delete hdr;
     410         [ #  # ]:          0 :                         delete [] pkt;
     411                 :            :                         }
     412                 :          0 :                 }
     413                 :            : 
     414                 :          0 :         const IP_Hdr IP() const
     415                 :          0 :                 { return IP_Hdr((struct ip *) (pkt + hdr_size)); }
     416                 :            : 
     417                 :            :         void Describe(ODesc* d) const;
     418                 :            : 
     419                 :            :         bool Serialize(SerialInfo* info) const;
     420                 :            :         static Packet* Unserialize(UnserialInfo* info);
     421                 :            : 
     422                 :            :         const struct pcap_pkthdr* hdr;
     423                 :            :         const u_char* pkt;
     424                 :            :         TimerMgr::Tag tag;
     425                 :            :         uint32 link_type;
     426                 :            : 
     427                 :            :         double time;
     428                 :            :         int hdr_size;
     429                 :            : 
     430                 :            : private:
     431                 :            :         bool free;
     432                 :            : };
     433                 :            : 
     434                 :            : extern FileSerializer* event_serializer;
     435                 :            : extern FileSerializer* state_serializer;
     436                 :            : 
     437                 :            : #endif

Generated by: LCOV version 1.8