Branch data Line data Source code
1 : : // $Id: PersistenceSerializer.h 2698 2006-04-03 05:50:52Z vern $
2 : : //
3 : : // Implements persistance for Bro's data structures.
4 : :
5 : : #ifndef persistence_serializer_h
6 : : #define persistence_serializer_h
7 : :
8 : : #include "Serializer.h"
9 : : #include "List.h"
10 : :
11 : : class StateAccess;
12 : :
13 : : class PersistenceSerializer : public FileSerializer {
14 : : public:
15 : : PersistenceSerializer();
16 : : virtual ~PersistenceSerializer();
17 : :
18 : : // Define the directory where to store the data.
19 : 1 : void SetDir(const char* arg_dir) { dir = copy_string(arg_dir); }
20 : :
21 : : // Register/unregister the ID/connection to be saved by WriteAll().
22 : : void Register(ID* id);
23 : : void Unregister(ID* id);
24 : : void Register(Connection* conn);
25 : : void Unregister(Connection* conn);
26 : :
27 : : // Read all data that has been changed since last scan of directory.
28 : : // is_init should be true for the first read upon start-up. All existing
29 : : // state will be cleared. If delete_files is true, file which have been
30 : : // read are removed (even if the read was unsuccessful!).
31 : : bool ReadAll(bool is_init, bool delete_files);
32 : :
33 : : // Each of the following four methods may suspend operation.
34 : : // If they do, they install a Timer which resumes after some
35 : : // amount of time. If a function is called again before it
36 : : // has completely finished its task, it will do nothing and
37 : : // return false.
38 : :
39 : : bool WriteState(bool may_suspend);
40 : :
41 : : // Writes Bro's configuration (w/o dynamic state).
42 : : bool WriteConfig(bool may_suspend);
43 : :
44 : : // Sends all registered state to remote host
45 : : // (by leveraging the remote_serializer).
46 : : bool SendState(SourceID peer, bool may_suspend);
47 : :
48 : : // Sends Bro's config to remote host
49 : : // (by leveraging the remote_serializer).
50 : : bool SendConfig(SourceID peer, bool may_suspend);
51 : :
52 : : // Returns true if a serialization is currently running.
53 : 14 : bool IsSerializationRunning() const { return running.length(); }
54 : :
55 : : // Tells the serializer that this access was performed. If a
56 : : // serialization is going on, it may store it. (Need only be called if
57 : : // IsSerializationRunning() returns true.)
58 : : bool LogAccess(const StateAccess& s);
59 : :
60 : : protected:
61 : : friend class RemoteSerializer;
62 : : friend class IncrementalWriteTimer;
63 : :
64 : : virtual void GotID(ID* id, Val* val);
65 : : virtual void GotEvent(const char* name, double time,
66 : : EventHandlerPtr event, val_list* args);
67 : : virtual void GotFunctionCall(const char* name, double time,
68 : : Func* func, val_list* args) ;
69 : : virtual void GotStateAccess(StateAccess* s);
70 : : virtual void GotTimer(Timer* t);
71 : : virtual void GotConnection(Connection* c);
72 : : virtual void GotPacket(Packet* packet);
73 : :
74 : : // If file has changed since last check, read it.
75 : : bool CheckForFile(UnserialInfo* info, const char* file,
76 : : bool delete_file);
77 : :
78 : : // Returns true if it's a regular file and has a more recent timestamp
79 : : // than last time we checked it.
80 : : bool CheckTimestamp(const char* file);
81 : :
82 : : // Move file from <dir>/tmp/<file> to <dir>/<file>. Afterwards, call
83 : : // CheckTimestamp() with <dir>/<file>.
84 : : bool MoveFileUp(const char* dir, const char* file);
85 : :
86 : : // Generates an error message, terminates current serialization,
87 : : // and returns false.
88 : : bool SerialError(const char* msg);
89 : :
90 : : // Start a new serialization.
91 : : struct SerialStatus;
92 : : bool RunSerialization(SerialStatus* status);
93 : :
94 : : // Helpers for RunSerialization.
95 : : bool DoIDSerialization(SerialStatus* status, ID* id);
96 : : bool DoConnSerialization(SerialStatus* status, Connection* conn);
97 : : bool DoAccessSerialization(SerialStatus* status, StateAccess* access);
98 : :
99 : : typedef PDict(ID) id_map;
100 : :
101 [ - + ][ # # ]: 5 : declare(PDict, Connection);
102 : : typedef PDict(Connection) conn_map;
103 : :
104 : 1 : struct SerialStatus {
105 : : enum Type {
106 : : WritingState, WritingConfig,
107 : : SendingState, SendingConfig,
108 : : };
109 : :
110 : 1 : SerialStatus(Serializer* s, Type arg_type) : info(s)
111 : : {
112 : 1 : type = arg_type;
113 : 1 : ids = 0;
114 : 1 : id_cookie = 0;
115 : 1 : conns = 0;
116 : 1 : conn_cookie = 0;
117 : 1 : peer = SOURCE_LOCAL;
118 : 1 : };
119 : :
120 : : Type type;
121 : : SerialInfo info;
122 : :
123 : : // IDs to serialize.
124 : : id_map* ids;
125 : : IterCookie* id_cookie;
126 : :
127 : : // Connections to serialize.
128 : : conn_map* conns;
129 : : IterCookie* conn_cookie;
130 : :
131 : : // Accesses performed while we're serializing.
132 : 2 : declare(PList,StateAccess);
133 : : typedef PList(StateAccess) state_access_list;
134 : : state_access_list accesses;
135 : :
136 : : // The ID/Conn we're currently serializing.
137 : : union {
138 : : ID* id;
139 : : Connection* conn;
140 : : } current;
141 : :
142 : : // Only set if type is Writing{State,Config}.
143 : : const char* filename;
144 : :
145 : : // Only set if type is Sending{State,Config}.
146 : : SourceID peer;
147 : : };
148 : :
149 : : const char* dir;
150 : :
151 : 7 : declare(PList, SerialStatus);
152 : : PList(SerialStatus) running;
153 : :
154 : : id_map persistent_ids;
155 : : conn_map persistent_conns;
156 : :
157 : : // To keep track of files' modification times.
158 [ - + ][ # # ]: 7 : declare(PDict, time_t);
159 : : typedef PDict(time_t) file_map;
160 : : file_map files;
161 : : };
162 : :
163 : : extern PersistenceSerializer* persistence_serializer;
164 : :
165 : : #endif
|