ze-filter  (ze-filter-0.8.0-develop-180218)
ze-makemap.c
Go to the documentation of this file.
1 
2 /*
3  *
4  * ze-filter - Mail Server Filter for sendmail
5  *
6  * Copyright (c) 2001-2018 - Jose-Marcio Martins da Cruz
7  *
8  * Auteur : Jose Marcio Martins da Cruz
9  * jose.marcio.mc@gmail.org
10  *
11  * Historique :
12  * Creation : janvier 2002
13  *
14  * This program is free software, but with restricted license :
15  *
16  *
17  * This program is distributed in the hope that it will be useful,
18  * but WITHOUT ANY WARRANTY; without even the implied warranty of
19  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
20  *
21  * More details about ze-filter license can be found at ze-filter
22  * web site : http://foss.jose-marcio.org
23  */
24 
25 #include <ze-sys.h>
26 
27 #include "ze-filter.h"
28 
29 
30 
31 static void usage();
32 
33 static ZEDB_T zdbh = ZEDB_INITIALIZER;
34 
35 #define MDB_NONE 0
36 #define MDB_UPDATE 1
37 #define MDB_SKIP 2
38 #define MDB_ERASE 4
39 
40 static int db_updt_mode = MDB_NONE;
41 static int add_db_rec(void *, void *);
42 
43 static long nb_ok, nb_ko, nb_t;
44 
45 static bool lk = TRUE, lv = TRUE;
46 
47 
48 int
49 main(argc, argv)
50  int argc;
51  char **argv;
52 {
53  const char *args = "h12b:rvdfk:t:m:cw:eC:X";
54  int c;
55  int verbose = 0;
56  char *dbname = NULL;
57  int dbattrnb = 2;
58  bool dbreverse = FALSE;
59  bool dbdump = FALSE;
60  bool dbtext = FALSE;
61  bool dbcount = FALSE;
62 
63  bool dbtype = TRUE;
64 
65  char *dbstartkey = NULL;
66 
67  int kw = 40;
68  bool dbexport = TRUE;
69 
70 #ifndef USE_BerkeleyDB
71  fprintf(stderr, " -> ze-filter wasn't compiled with BerkeleyDB...\n");
72  fprintf(stderr, " -> Can't use dabatases without BerkeleyDB !\n");
73  exit(1);
74 #endif
75 
77 
78  while ((c = getopt(argc, argv, args)) != -1) {
79  switch (c) {
80  case 'f':
81  dbtext = TRUE;
82  break;
83  case 'h':
84  usage();
85  exit(0);
86  break;
87  case '1':
88  dbattrnb = 1;
89  break;
90  case '2':
91  dbattrnb = 2;
92  break;
93  case 't':
94  switch (tolower(*optarg)) {
95  case 'b':
96  dbtype = TRUE;
97  break;
98  case 'h':
99  dbtype = FALSE;
100  break;
101  default:
102  ZE_MessageInfo(0, "Error : optarg ...");
103  usage();
104  exit(1);
105  break;
106  }
107  break;
108  case 'w':
109  {
110  int w = atoi(optarg);
111 
112  if (w > 0)
113  kw = w;
114  }
115  break;
116  case 'e':
117  dbexport = !dbexport;
118  break;
119  case 'm':
120  switch (tolower(*optarg)) {
121  case 'e':
122  db_updt_mode |= MDB_ERASE;
123  break;
124  case 'u':
125  db_updt_mode |= MDB_UPDATE;
126  break;
127  case 's':
128  db_updt_mode |= MDB_SKIP;
129  break;
130  default:
131  ZE_MessageInfo(0, "Error : optarg ...");
132  usage();
133  exit(1);
134  }
135  break;
136  case 'b':
137  if (optarg == NULL || *optarg == '\0') {
138  fprintf(stderr, "Error %s\n", optarg ? optarg : "");
139  exit(1);
140  }
141  if (dbname != NULL) {
142  fprintf(stderr, "Error : only one -b option allowed\n");
143  exit(1);
144  }
145  if ((dbname = strdup(optarg)) == NULL) {
146  fprintf(stderr, "FATAL ERROR - memory allocation dbname\n");
147  exit(1);
148  }
149  break;
150  case 'c':
151  dbcount = TRUE;
152  dbdump = TRUE;
153  break;
154  case 'r':
155  dbreverse = TRUE;
156  break;
157  case 'v':
158  verbose = 1;
159  break;
160  case 'd':
161  dbdump = TRUE;
162  break;
163  case 'k':
164  if (optarg == NULL || *optarg == '\0') {
165  fprintf(stderr, "Error %s\n", optarg ? optarg : "");
166  exit(1);
167  }
168  FREE(dbstartkey);
169  if ((dbstartkey = strdup(optarg)) == NULL) {
170  fprintf(stderr, "FATAL ERROR - memory allocation dbname\n");
171  exit(1);
172  }
173  break;
174  case 'C':
175  if (optarg != NULL) {
176  char *p;
177 
178  for (p = optarg; *p != '\0'; p++) {
179  switch (*p) {
180  case 'k':
181  break;
182  case 'K':
183  break;
184  case 'v':
185  break;
186  case 'V':
187  break;
188  }
189  }
190  }
191  break;
192  default:
193  fprintf(stderr, "\nInvalid option\n");
194  usage();
195  exit(1);
196  }
197  }
198 
199  if (db_updt_mode == MDB_NONE)
200  db_updt_mode = MDB_ERASE | MDB_SKIP;
201 
202  if ((db_updt_mode & MDB_UPDATE) != 0 && (db_updt_mode & MDB_SKIP) != 0) {
203  fprintf(stderr, "\n Can't set both SKIP and UPDATE modes\n");
204  usage();
205  exit(EX_SOFTWARE);
206  }
207 
208  if ((db_updt_mode & (MDB_UPDATE | MDB_SKIP)) == 0)
209  db_updt_mode |= MDB_SKIP;
210 
211  ze_logLevel = 8;
212  dbstartkey = STRNULL(dbstartkey, "");
213 
214  nb_t = nb_ok = nb_ko = 0;
215 
216  if (dbtext) {
217  zm_RdTextFile(NULL, dbattrnb, dbreverse, "", NULL);
218  exit(0);
219  }
220 
221  if (dbname == NULL) {
222  usage();
223  fprintf(stderr, "Missing -b option\n");
224  exit(1);
225  }
226 
227  if (*dbname == '-') {
228  usage();
229  fprintf(stderr, "dbname not valid : %s\n", dbname);
230  exit(1);
231  }
232 
233 
234  /*
235  * #### #### # # # # #####
236  * # # # # # # ## # #
237  * # # # # # # # # #
238  * # # # # # # # # #
239  * # # # # # # # ## #
240  * #### #### #### # # #
241  */
242  if (dbcount) {
243  if (zeDb_Open(&zdbh, NULL, dbname, 0444, TRUE, dbtype, 0)) {
244  long nb = 0;
245 
246  ZEDB_STAT_T *st;
247 
248  if (!zeDb_Stat(&zdbh, &st))
249  exit(1);
250  printf(" ** %7ld records found\n", (long int ) st->st.btree_st.bt_ndata);
251  FREE(st);
252  zeDb_Close(&zdbh);
253  }
254  exit(0);
255  }
256 
257  /*
258  * ##### # # # # #####
259  * # # # # ## ## # #
260  * # # # # # ## # # #
261  * # # # # # # #####
262  * # # # # # # #
263  * ##### #### # # #
264  */
265  if (dbdump) {
266  if (zeDb_Open(&zdbh, NULL, dbname, 0444, TRUE, dbtype, 0)) {
267  long nb = 0;
268 
269  if (zeDb_CursorOpen(&zdbh, TRUE)) {
270  char key[256], data[256];
271  int j;
272  time_t now;
273 
274  memset(key, 0, sizeof (key));
275  memset(data, 0, sizeof (data));
276 
277  snprintf(key, sizeof (key), "%s", dbstartkey);
278 
279  now = time(NULL);
280 
281  snprintf(key, sizeof (key), "%s", dbstartkey);
282 
283  if (zeDb_CursorGetFirst(&zdbh, key, sizeof (key), data, sizeof (data))) {
285  do {
286  char format[64];
287 
288  DB_BTREE_SEQ_CHECK(key, zdbh.database);
289 
290  if (strncmp(key, dbstartkey, strlen(dbstartkey)) != 0)
291  break;
292  if (!dbcount) {
293  if (!dbexport)
294  snprintf(format, sizeof (format),
295  " ** KEY : %%-%ds - DATA : %%s\n", kw);
296  else
297  snprintf(format, sizeof (format), "%%-%ds %%s\n", kw);
298  printf(format, key, data);
299  }
300  nb++;
301  } while (zeDb_CursorGetNext(&zdbh, key, sizeof (key), data, sizeof (data)));
302 
304  }
305 
306  (void) zeDb_CursorClose(&zdbh);
307  }
308  zeDb_Close(&zdbh);
309 
310  if (!dbexport || dbcount)
311  printf(" ** %7ld records found\n", nb);
312  }
313 
314  exit(0);
315  }
316 
317  /*
318  * # # ##### ##### ## ##### ######
319  * # # # # # # # # # #
320  * # # # # # # # # # #####
321  * # # ##### # # ###### # #
322  * # # # # # # # # #
323  * #### # ##### # # # ######
324  */
325  {
326  if (zeDb_Open(&zdbh, NULL, dbname, 0644, FALSE, dbtype, 0)) {
327 
328  if ((db_updt_mode & MDB_ERASE) != 0)
329  (void) zeDb_Empty(&zdbh);
330 
331  (void) zm_RdTextFile(NULL, dbattrnb, dbreverse, "", add_db_rec);
332 
333  zeDb_Close(&zdbh);
334  }
335  printf("* Total : %6ld records read\n", nb_t);
336  printf(" %6ld records added\n", nb_ok);
337  printf(" %6ld errors\n", nb_ko);
338  }
339 
340  return 0;
341 }
342 
343 
344 /* ***************************************************************************
345  * *
346  * *
347  *****************************************************************************/
348 #define BFSZ 1024
349 
350 static int
351 add_db_rec(vk, vv)
352  void *vk;
353  void *vv;
354 {
355  char *k = (char *) vk;
356  char *v = (char *) vv;
357  bool res = TRUE;
358 
359  nb_t++;
360 
361  if (k == NULL || strlen(k) == 0)
362  res = FALSE;
363 
364  if (res) {
365  if (v == NULL)
366  v = "";
367 
368  (void) zeStr2Lower(k);
369  (void) zeStr2Lower(v);
370 
371  if ((db_updt_mode & MDB_SKIP) != 0) {
372  char buf[BFSZ];
373 
374  if (zeDb_GetRec(&zdbh, k, buf, sizeof (buf)))
375  return 1;
376  }
377 
378  res = zeDb_AddRec(&zdbh, k, v, strlen(v) + 1);
379  }
380 
381  if (res)
382  nb_ok++;
383  else
384  nb_ko++;
385 
386  return (res ? 1 : 0);
387 }
388 
389 /* ****************************************************************************
390  * *
391  * *
392  **************************************************************************** */
393 static void
394 usage()
395 {
396  printf("Usage : ze-makemap options\n"
397  " %s\n"
398  " Compiled on %s %s\n" " -b table : specifies table name\n"
399  " -d : dump instead of update\n"
400  " -c : count records on database\n"
401  " -k key : matching key\n"
402  " -w NN : column width when dumping database\n"
403  " -t : database type\n"
404  " btree\n"
405  " hash\n"
406  " -m mode : how to insert records\n"
407  " e - clear database before update\n"
408  " s - skip existent records\n"
409  " u - new records update existent records\n"
410  " - can be defined multiple times\n"
411  " - default mode : erase and skim\n"
412  " -r : reverse key/value order (value/key)\n"
413  " -1 : single column (key only)\n"
414  " -2 : two columns (key / value) - default\n"
415  " -h : help (print this and exits)\n"
416  " default mode : erase and skim\n"
417  "\n%s - %s\n\n",
418  PACKAGE, __DATE__, __TIME__, PACKAGE,COPYRIGHT);
419 }
#define MDB_ERASE
Definition: ze-makemap.c:38
void ZEDB_STAT_T
Definition: zeDb.h:100
bool zeDb_Stat(ZEDB_T *h, ZEDB_STAT_T **)
Definition: zeDb.c:1263
bool zeDb_AddRec(ZEDB_T *h, char *, void *, size_t)
Definition: zeDb.c:750
#define FREE(x)
Definition: macros.h:37
#define COPYRIGHT
Definition: version.h:31
bool zeDb_Empty(ZEDB_T *h)
Definition: zeDb.c:696
int ze_logLevel
Definition: zeSyslog.c:34
#define STRNULL(x, r)
Definition: macros.h:81
Definition: zeDb.h:47
void zeLog_SetOutput(bool, bool)
Definition: zeSyslog.c:490
#define FALSE
Definition: macros.h:160
#define DB_BTREE_SEQ_START()
Definition: zeDb.h:176
#define MDB_NONE
Definition: ze-makemap.c:35
bool zeDb_CursorGetFirst(ZEDB_T *h, char *, size_t, void *, size_t)
Definition: zeDb.c:1041
#define MDB_UPDATE
Definition: ze-makemap.c:36
#define BFSZ
Definition: ze-makemap.c:348
bool zeDb_Open(ZEDB_T *h, ZEDB_ENV_T *, char *, int, bool, bool, size_t)
Definition: zeDb.c:462
bool zeDb_Close(ZEDB_T *h)
Definition: zeDb.c:667
#define DB_BTREE_SEQ_END()
Definition: zeDb.h:196
int zm_RdTextFile(char *, int, int, char *, int(*)(void *, void *))
#define ZE_MessageInfo(level,...)
Definition: zeSyslog.h:90
char * database
Definition: zeDb.h:50
int nb
Definition: ze-connopen.c:61
bool zeDb_GetRec(ZEDB_T *h, char *, void *, size_t)
Definition: zeDb.c:791
#define TRUE
Definition: macros.h:157
bool zeDb_CursorOpen(ZEDB_T *h, bool)
Definition: zeDb.c:936
void usage(char *arg)
int main(int argc, char **argv)
Definition: ze-makemap.c:49
#define MDB_SKIP
Definition: ze-makemap.c:37
#define DB_BTREE_SEQ_CHECK(key, dbname)
Definition: zeDb.h:182
char * zeStr2Lower(char *)
Definition: zeStrings.c:295
#define PACKAGE
Definition: version.h:28
bool zeDb_CursorClose(ZEDB_T *h)
Definition: zeDb.c:991
#define ZEDB_INITIALIZER
Definition: zeDb.h:111
bool zeDb_CursorGetNext(ZEDB_T *h, char *, size_t, void *, size_t)
Definition: zeDb.c:1116