Subversion Repositories public

Rev

Rev 77 | Only display areas with differences | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 77 Rev 84
1
1
2
/// inotify cron daemon user tables header
2
/// inotify cron daemon user tables header
3
/**
3
/**
4
 * \file usertable.h
4
 * \file usertable.h
5
 *
5
 *
6
 * inotify cron system
6
 * inotify cron system
7
 *
7
 *
8
 * Copyright (C) 2006, 2007 Lukas Jelinek, <lukas@aiken.cz>
8
 * Copyright (C) 2006, 2007 Lukas Jelinek, <lukas@aiken.cz>
9
 *
9
 *
10
 * This program is free software; you can use it, redistribute
10
 * This program is free software; you can use it, redistribute
11
 * it and/or modify it under the terms of the GNU General Public
11
 * it and/or modify it under the terms of the GNU General Public
12
 * License, version 2 (see LICENSE-GPL).
12
 * License, version 2 (see LICENSE-GPL).
13
 *  
13
 *  
14
 */
14
 */
15
15
16
#ifndef _USERTABLE_H_
16
#ifndef _USERTABLE_H_
17
#define _USERTABLE_H_
17
#define _USERTABLE_H_
18
18
19
#include <map>
19
#include <map>
20
#include <deque>
20
#include <deque>
21
#include <sys/poll.h>
21
#include <sys/poll.h>
22
22
23
#include "inotify-cxx.h"
23
#include "inotify-cxx.h"
24
#include "incrontab.h"
24
#include "incrontab.h"
25
25
26
26
27
class UserTable;
27
class UserTable;
28
28
29
/// User name to user table mapping definition
29
/// User name to user table mapping definition
30
typedef std::map<std::string, UserTable*> SUT_MAP;
30
typedef std::map<std::string, UserTable*> SUT_MAP;
31
31
32
/// Callback for calling after a process finishes.
32
/// Callback for calling after a process finishes.
33
typedef void (*proc_done_cb)(InotifyWatch*);
33
typedef void (*proc_done_cb)(InotifyWatch*);
34
34
35
/// Child process data
35
/// Child process data
36
typedef struct
36
typedef struct
37
{
37
{
38
  proc_done_cb onDone;  ///< function called after process finishes
38
  proc_done_cb onDone;  ///< function called after process finishes
39
  InotifyWatch* pWatch; ///< related watch
39
  InotifyWatch* pWatch; ///< related watch
40
} ProcData_t;
40
} ProcData_t;
41
41
42
/// fd-to-usertable mapping
42
/// fd-to-usertable mapping
43
typedef std::map<int, UserTable*> FDUT_MAP;
43
typedef std::map<int, UserTable*> FDUT_MAP;
44
44
45
/// Watch-to-tableentry mapping
45
/// Watch-to-tableentry mapping
46
typedef std::map<InotifyWatch*, IncronTabEntry*> IWCE_MAP;
46
typedef std::map<InotifyWatch*, IncronTabEntry*> IWCE_MAP;
47
47
48
/// Child process list
48
/// Child process list
49
typedef std::map<pid_t, ProcData_t> PROC_MAP;
49
typedef std::map<pid_t, ProcData_t> PROC_MAP;
50
50
51
/// Event dispatcher class.
51
/// Event dispatcher class.
52
/**
52
/**
53
 * This class processes events and distributes them as needed.
53
 * This class processes events and distributes them as needed.
54
 */
54
 */
55
class EventDispatcher
55
class EventDispatcher
56
{
56
{
57
public:
57
public:
58
  /// Constructor.
58
  /// Constructor.
59
  /**
59
  /**
60
   * \param[in] iPipeFd pipe descriptor
60
   * \param[in] iPipeFd pipe descriptor
61
   * \param[in] pIn inotify object for table management
61
   * \param[in] pIn inotify object for table management
62
   * \param[in] pSys watch for system tables
62
   * \param[in] pSys watch for system tables
63
   * \param[in] pUser watch for user tables
63
   * \param[in] pUser watch for user tables
64
   */
64
   */
65
  EventDispatcher(int iPipeFd, Inotify* pIn, InotifyWatch* pSys, InotifyWatch* pUser);
65
  EventDispatcher(int iPipeFd, Inotify* pIn, InotifyWatch* pSys, InotifyWatch* pUser);
66
 
66
 
67
  /// Destructor.
67
  /// Destructor.
68
  ~EventDispatcher();
68
  ~EventDispatcher();
69
69
70
  /// Processes events.
70
  /// Processes events.
71
  /**
71
  /**
72
   * \return pipe event occurred yes/no
72
   * \return pipe event occurred yes/no
73
   */
73
   */
74
  bool ProcessEvents();
74
  bool ProcessEvents();
75
 
75
 
76
  /// Registers an user table.
76
  /// Registers an user table.
77
  /**
77
  /**
78
   * \param[in] pTab user table
78
   * \param[in] pTab user table
79
   */
79
   */
80
  void Register(UserTable* pTab);
80
  void Register(UserTable* pTab);
81
 
81
 
82
  /// Unregisters an user table.
82
  /// Unregisters an user table.
83
  /**
83
  /**
84
   * \param[in] pTab user table
84
   * \param[in] pTab user table
85
   */
85
   */
86
  void Unregister(UserTable* pTab);
86
  void Unregister(UserTable* pTab);
87
 
87
 
88
  /// Returns the poll data size.
88
  /// Returns the poll data size.
89
  /**
89
  /**
90
   * \return poll data size
90
   * \return poll data size
91
   */
91
   */
92
  inline size_t GetSize() const
92
  inline size_t GetSize() const
93
  {
93
  {
94
    return m_size;
94
    return m_size;
95
  }
95
  }
96
 
96
 
97
  /// Returns the poll data.
97
  /// Returns the poll data.
98
  /**
98
  /**
99
   * \return poll data
99
   * \return poll data
100
   */
100
   */
101
  inline struct pollfd* GetPollData()
101
  inline struct pollfd* GetPollData()
102
  {
102
  {
103
    return m_pPoll;
103
    return m_pPoll;
104
  }
104
  }
105
 
105
 
106
  /// Rebuilds the poll array data.
106
  /// Rebuilds the poll array data.
107
  void Rebuild();
107
  void Rebuild();
108
 
108
 
109
  /// Removes all registered user tables.
109
  /// Removes all registered user tables.
110
  /**
110
  /**
111
   * It doesn't cause poll data rebuilding.
111
   * It doesn't cause poll data rebuilding.
112
   */
112
   */
113
  inline void Clear()
113
  inline void Clear()
114
  {
114
  {
115
    m_maps.clear();
115
    m_maps.clear();
116
  }
116
  }
117
 
117
 
118
private:
118
private:
119
  int m_iPipeFd;    ///< pipe file descriptor
119
  int m_iPipeFd;    ///< pipe file descriptor
120
  int m_iMgmtFd;    ///< table management file descriptor
120
  int m_iMgmtFd;    ///< table management file descriptor
121
  Inotify* m_pIn;   ///< table management inotify object 
121
  Inotify* m_pIn;   ///< table management inotify object 
122
  InotifyWatch* m_pSys;   ///< watch for system tables
122
  InotifyWatch* m_pSys;   ///< watch for system tables
123
  InotifyWatch* m_pUser;  ///< watch for user tables 
123
  InotifyWatch* m_pUser;  ///< watch for user tables 
124
  FDUT_MAP m_maps;  ///< watch-to-usertable mapping
124
  FDUT_MAP m_maps;  ///< watch-to-usertable mapping
125
  size_t m_size;    ///< poll data size
125
  size_t m_size;    ///< poll data size
126
  struct pollfd* m_pPoll; ///< poll data array
126
  struct pollfd* m_pPoll; ///< poll data array
127
 
127
 
128
  /// Processes events on the table management inotify object. 
128
  /// Processes events on the table management inotify object. 
129
  void ProcessMgmtEvents();
129
  void ProcessMgmtEvents();
130
};
130
};
131
131
132
132
133
/// User table class.
133
/// User table class.
134
/**
134
/**
135
 * This class processes inotify events for an user. It creates
135
 * This class processes inotify events for an user. It creates
136
 * child processes which do appropriate actions as defined
136
 * child processes which do appropriate actions as defined
137
 * in the user table file.
137
 * in the user table file.
138
 */
138
 */
139
class UserTable
139
class UserTable
140
{
140
{
141
public:
141
public:
142
  /// Constructor.
142
  /// Constructor.
143
  /**
143
  /**
144
   * \param[in] pEd event dispatcher
144
   * \param[in] pEd event dispatcher
145
   * \param[in] rUser user name
145
   * \param[in] rUser user name
146
   * \param[in] fSysTable system table yes/no
146
   * \param[in] fSysTable system table yes/no
147
   */
147
   */
148
        UserTable(EventDispatcher* pEd, const std::string& rUser, bool fSysTable);
148
        UserTable(EventDispatcher* pEd, const std::string& rUser, bool fSysTable);
149
 
149
 
150
  /// Destructor.
150
  /// Destructor.
151
        virtual ~UserTable();
151
        virtual ~UserTable();
152
 
152
 
153
  /// Loads the table.
153
  /// Loads the table.
154
  /**
154
  /**
155
   * All loaded entries have their inotify watches and are
155
   * All loaded entries have their inotify watches and are
156
   * registered for event dispatching.
156
   * registered for event dispatching.
157
   * If loading fails the table remains empty.
157
   * If loading fails the table remains empty.
158
   */
158
   */
159
  void Load();
159
  void Load();
160
 
160
 
161
  /// Removes all entries from the table.
161
  /// Removes all entries from the table.
162
  /**
162
  /**
163
   * All entries are unregistered from the event dispatcher and
163
   * All entries are unregistered from the event dispatcher and
164
   * their watches are destroyed.
164
   * their watches are destroyed.
165
   */
165
   */
166
  void Dispose();
166
  void Dispose();
167
 
167
 
168
  /// Processes an inotify event.
168
  /// Processes an inotify event.
169
  /**
169
  /**
170
   * \param[in] rEvt inotify event
170
   * \param[in] rEvt inotify event
171
   */
171
   */
172
  void OnEvent(InotifyEvent& rEvt);
172
  void OnEvent(InotifyEvent& rEvt);
173
 
173
 
174
  /// Cleans-up all zombie child processes and enables disabled watches.
174
  /// Cleans-up all zombie child processes and enables disabled watches.
175
  /**
175
  /**
176
   * \attention This method must be called AFTER processing all events
176
   * \attention This method must be called AFTER processing all events
177
   *            which has been caused by the processes.
177
   *            which has been caused by the processes.
178
   */
178
   */
179
  static void FinishDone();
179
  static void FinishDone();
180
 
180
 
181
  /// Checks whether the user may access a file.
181
  /// Checks whether the user may access a file.
182
  /**
182
  /**
183
   * Any access right (RWX) is sufficient.
183
   * Any access right (RWX) is sufficient.
184
   *
184
   *
185
   * \param[in] rPath absolute file path
185
   * \param[in] rPath absolute file path
186
   * \param[in] fNoFollow don't follow a symbolic link
186
   * \param[in] fNoFollow don't follow a symbolic link
187
   * \return true = access granted, false = otherwise
187
   * \return true = access granted, false = otherwise
188
   */
188
   */
189
  bool MayAccess(const std::string& rPath, bool fNoFollow) const;
189
  bool MayAccess(const std::string& rPath, bool fNoFollow) const;
190
 
190
 
191
  /// Checks whether it is a system table.
191
  /// Checks whether it is a system table.
192
  /**
192
  /**
193
   * \return true = system table, false = user table
193
   * \return true = system table, false = user table
194
   */
194
   */
195
  bool IsSystem() const;
195
  bool IsSystem() const;
196
 
196
 
197
  /// Returns the related inotify object.
197
  /// Returns the related inotify object.
198
  /**
198
  /**
199
   * \return related inotify object
199
   * \return related inotify object
200
   */
200
   */
201
  Inotify* GetInotify()
201
  Inotify* GetInotify()
202
  {
202
  {
203
    return &m_in;
203
    return &m_in;
204
  }
204
  }
205
 
205
 
206
  /// Checks whether an user exists and has permission to use incron.
206
  /// Checks whether an user exists and has permission to use incron.
207
  /**
207
  /**
208
   * It searches for the given user name in the user database.
208
   * It searches for the given user name in the user database.
209
   * If it failes it returns 'false'. Otherwise it checks
209
   * If it failes it returns 'false'. Otherwise it checks
210
   * permission files for this user (see InCronTab::CheckUser()).
210
   * permission files for this user (see InCronTab::CheckUser()).
211
   *
211
   *
212
   * \param[in] user user name
212
   * \param[in] user user name
213
   * \return true = user has permission to use incron, false = otherwise
213
   * \return true = user has permission to use incron, false = otherwise
214
   *
214
   *
215
   * \sa InCronTab::CheckUser()
215
   * \sa InCronTab::CheckUser()
216
   */
216
   */
217
  inline static bool CheckUser(const char* user)
217
  inline static bool CheckUser(const char* user)
218
  {
218
  {
219
    struct passwd* pw = getpwnam(user);
219
    struct passwd* pw = getpwnam(user);
220
    if (pw == NULL)
220
    if (pw == NULL)
221
      return false;
221
      return false;
222
     
222
     
223
    return IncronTab::CheckUser(user);
223
    return IncronTab::CheckUser(user);
224
  }
224
  }
225
 
225
 
226
  /// Runs a program as the table's user.
226
  /// Runs a program as the table's user.
227
  /**
227
  /**
228
   * \attention Don't call from the main process (before forking)!
228
   * \attention Don't call from the main process (before forking)!
229
   */
229
   */
230
  void RunAsUser(char* const* argv) const;
230
  void RunAsUser(char* const* argv) const;
231
 
231
 
232
private:
232
private:
233
  Inotify m_in;           ///< inotify object
233
  Inotify m_in;           ///< inotify object
234
  EventDispatcher* m_pEd; ///< event dispatcher
234
  EventDispatcher* m_pEd; ///< event dispatcher
235
  std::string m_user;     ///< user name
235
  std::string m_user;     ///< user name
236
  bool m_fSysTable;       ///< system table yes/no
236
  bool m_fSysTable;       ///< system table yes/no
237
  IncronTab m_tab;        ///< incron table
237
  IncronTab m_tab;        ///< incron table
238
  IWCE_MAP m_map;         ///< watch-to-entry mapping
238
  IWCE_MAP m_map;         ///< watch-to-entry mapping
239
239
240
  static PROC_MAP s_procMap;  ///< child process mapping
240
  static PROC_MAP s_procMap;  ///< child process mapping
241
 
241
 
242
  /// Finds an entry for a watch.
242
  /// Finds an entry for a watch.
243
  /**
243
  /**
244
   * \param[in] pWatch inotify watch
244
   * \param[in] pWatch inotify watch
245
   * \return pointer to the appropriate entry; NULL if no such entry exists
245
   * \return pointer to the appropriate entry; NULL if no such entry exists
246
   */
246
   */
247
  IncronTabEntry* FindEntry(InotifyWatch* pWatch);
247
  IncronTabEntry* FindEntry(InotifyWatch* pWatch);
248
 
248
 
249
  /// Prepares arguments for creating a child process.
249
  /// Prepares arguments for creating a child process.
250
  /**
250
  /**
251
   * \param[in] rCmd command string
251
   * \param[in] rCmd command string
252
   * \param[out] argc argument count
252
   * \param[out] argc argument count
253
   * \param[out] argv argument array
253
   * \param[out] argv argument array
254
   * \return true = success, false = failure
254
   * \return true = success, false = failure
255
   */
255
   */
256
  bool PrepareArgs(const std::string& rCmd, int& argc, char**& argv);
256
  bool PrepareArgs(const std::string& rCmd, int& argc, char**& argv);
257
 
257
 
258
  /// Frees memory allocated for arguments.
258
  /// Frees memory allocated for arguments.
259
  /**
259
  /**
260
   * \param[in] argc argument count
260
   * \param[in] argc argument count
261
   * \param[in] argv argument array
261
   * \param[in] argv argument array
262
   */
262
   */
263
  void CleanupArgs(int argc, char** argv);
263
  void CleanupArgs(int argc, char** argv);
264
 
264
 
265
};
265
};
266
266
267
#endif //_USERTABLE_H_
267
#endif //_USERTABLE_H_
268
 
268