modules/nt/notification.cc
/* [<][>][^][v][top][bottom][index][help] */
FUNCTIONS
This source file includes following functions.
- NT_ntfy_filename_generate
- NT_forwd_filename_generate
- NT_cross_filename_generate
- NT_crossntfy_filename_generate
- NT_add_to_ntfy_hash
- NT_add_to_frwd_hash
- NT_add_to_cross_hash
- NT_add_to_ntfy_hash_list
- NT_add_to_frwd_hash_list
- NT_add_to_cross_hash_list
- NT_add_to_ntfy
- NT_add_to_cross
- NT_add_to_ntfy_list
- NT_send_ntfy
- NT_log_ntfy
- NT_delete_ntfy
- nt_gfunc_send
- NT_send_ntfy_list
- nt_gfunc_log
- NT_log_ntfy_list
- nt_gfunc_delete
- NT_delete_ntfy_list
- nt_add_to_list
- NT_unify_list
- NT_gather_ntfy_addresses
- NT_gather_frwd_addresses
- get_overlapping_routes_list
- NT_write_all_ntfs
- NT_write_all_frwds
- NT_send_forw_creation
- NT_forw_create_req
1 /***************************************
2 $Revision: 1.21 $
3
4 NT (Notifications) module
5
6 Status: NOT REVIEWED, NOT TESTED
7
8 Author(s): Engin Gunduz
9
10 ******************/ /******************
11 Modification History:
12 engin (06/07/2000) Created.
13 ******************/ /******************
14 Copyright (c) 2000 RIPE NCC
15
16 All Rights Reserved
17
18 Permission to use, copy, modify, and distribute this software and its
19 documentation for any purpose and without fee is hereby granted,
20 provided that the above copyright notice appear in all copies and that
21 both that copyright notice and this permission notice appear in
22 supporting documentation, and that the name of the author not be
23 used in advertising or publicity pertaining to distribution of the
24 software without specific, written prior permission.
25
26 THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
27 ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS; IN NO EVENT SHALL
28 AUTHOR BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY
29 DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN
30 AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
31 OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
32 ***************************************/
33
34
35
36
37
38
39 #include "notification.h"
40 extern int supress_ack_notif;
41 extern char * defmail;
42 extern int reading_from_mail;
43 extern char * forwlog;
44
45 /* Generates a unique file name and returns the full path of the filename
46 for storing notification message. Creates the file at the same time.
47 May use PID or time or both to ensure uniqueness. */
48
49 char * NT_ntfy_filename_generate( const char * tmpdir, const char * e_mail){
/* [<][>][^][v][top][bottom][index][help] */
50
51 FILE * ntfy_file;
52 char * name;
53 char * replaced_notimailtxt;
54 char * replaced_notinetworktxt;
55
56 /* allocate space for name. 32 should be enough for PID */
57 name = (char*)malloc(strlen(tmpdir) + strlen(e_mail) + strlen("notify") +32 );
58
59 sprintf(name, "%s/%s-%s.%i", tmpdir, "notify", e_mail, getpid());
60
61 /* create the file */
62 if(( ntfy_file = fopen(name, "w")) == NULL){
63 fprintf(stderr, "Can't open notification file for creating, %s", name);
64 }
65
66 fprintf(ntfy_file, "To: %s\nFrom: %s\nSubject: Notification of RIPE Database changes\nReply-To: %s\n\n%s\n", e_mail, humailbox, humailbox, notitxt);
67 if(reading_from_mail){
68 replaced_notimailtxt = UP_replace_globals(notimailtxt);
69 fprintf(ntfy_file, "%s\n\n", replaced_notimailtxt);
70 free(replaced_notimailtxt);
71 }
72
73 if(networkupdate){
74 replaced_notinetworktxt = UP_replace_globals(notinetworktxt);
75 fprintf(ntfy_file, "%s\n\n", replaced_notinetworktxt);
76 free(replaced_notinetworktxt);
77 }
78
79 /* close it */
80 fclose(ntfy_file);
81
82 return name;
83
84 }
85
86
87
88
89
90 /* Generates a unique file name and returns the full path of the filename
91 for storing forwarded message. Creates the file at the same time. */
92 char * NT_forwd_filename_generate( const char * tmpdir, const char * e_mail){
/* [<][>][^][v][top][bottom][index][help] */
93
94 FILE * forwd_file;
95 char * name;
96 char * replaced_fwmailtxt;
97
98 /* allocate space for name. 32 should be enough for PID */
99 name = (char*)malloc(strlen(tmpdir) + strlen(e_mail) + strlen("forwd") +32 );
100
101 sprintf(name, "%s/%s-%s.%i", tmpdir, "forwd", e_mail, getpid());
102 /* create the file */
103 if(( forwd_file = fopen(name, "w")) == NULL){
104 fprintf(stderr, "Can't open forward file, %s", name);
105 }
106
107 fprintf(forwd_file, "To: %s\nFrom: %s\nSubject: Requested RIPE database object changes \nReply-To: %s\n\n%s\n", e_mail, humailbox, humailbox, fwtxt);
108 if(reading_from_mail){
109 replaced_fwmailtxt = UP_replace_globals(fwmailtxt);
110 fprintf(forwd_file, "\n%s\n", replaced_fwmailtxt);
111 free(replaced_fwmailtxt);
112 }
113
114 /* close it */
115 fclose(forwd_file);
116
117 return name;
118
119 }
120
121
122
123
124
125 /* Generates a unique file name and returns the full path of the filename
126 for storing cross notification message. Creates the file at the same time. */
127 char * NT_cross_filename_generate( const char * tmpdir, const char * e_mail, int mode){
/* [<][>][^][v][top][bottom][index][help] */
128
129 FILE * cross_file;
130 char * name;
131
132 /* allocate space for name. 32 should be enough for PID */
133 name = (char*)malloc(strlen(tmpdir) + strlen(e_mail) + strlen("cross") +32 );
134
135 sprintf(name, "%s/%s-%s.%i", tmpdir, "cross", e_mail, getpid());
136 /* create the file */
137 if(( cross_file = fopen(name, "w")) == NULL){
138 fprintf(stderr, "Can't open cross notif file, %s", name);
139 }
140
141 if(mode == ADDITION){
142 fprintf(cross_file, "To: %s\nFrom: %s\n%s\nReply-To: %s\n\n", e_mail, humailbox, cno_subject_add, humailbox);
143 }else{
144 fprintf(cross_file, "To: %s\nFrom: %s\n%s\nReply-To: %s\n\n", e_mail, humailbox, cno_subject_del, humailbox);
145 }
146
147 /* close it */
148 fclose(cross_file);
149
150 return name;
151
152 }
153
154
155
156
157
158
159
160 /* Generates a unique file name and returns the full path of the filename for
161 storing notification message. Creates the file at the same time. */
162 char * NT_crossntfy_filename_generate( const char * tmpdir, const char * e_mail){
/* [<][>][^][v][top][bottom][index][help] */
163 FILE * cross_file;
164 char * name;
165
166 /* allocate space for name. 32 should be enough for PID */
167 name = (char*)malloc(strlen(tmpdir) + strlen(e_mail) + strlen("cross") +32 );
168
169 sprintf(name, "%s/%s-%s.%i", tmpdir, "cross", e_mail, getpid());
170
171 /* create the file */
172 if(( cross_file = fopen(name, "w")) == NULL){
173 fprintf(stderr, "Can't open cross file, %s", name);
174 }
175
176 /* close it */
177 fclose(cross_file);
178
179 return name;
180
181 }
182
183
184
185
186
187 /* Adds the e-mail to the notify hash, generating appropriate temp files */
188 void NT_add_to_ntfy_hash(GHashTable * ntfy_hash, char * e_mail){
/* [<][>][^][v][top][bottom][index][help] */
189
190 if(g_hash_table_lookup(ntfy_hash ,e_mail) == NULL){/* there is no such entry, so create it */
191
192 g_hash_table_insert(ntfy_hash, strdup(e_mail), NT_ntfy_filename_generate(tmpdir, e_mail));
193
194 }
195
196 }
197
198
199
200
201 /* Adds the e-mail to the forw hash, generating appropriate temp files */
202 void NT_add_to_frwd_hash(GHashTable * frwd_hash, char * e_mail){
/* [<][>][^][v][top][bottom][index][help] */
203
204 if(g_hash_table_lookup(frwd_hash ,e_mail) == NULL){/* there is no such entry, so create it */
205 g_hash_table_insert(frwd_hash, strdup(e_mail), NT_forwd_filename_generate(tmpdir, e_mail));
206 }
207
208 }
209
210
211
212
213
214 /* Adds the e-mail to the cross hash, generating appropriate temp files */
215 void NT_add_to_cross_hash(GHashTable * cross_hash, const char * e_mail, int mode){
/* [<][>][^][v][top][bottom][index][help] */
216
217 /* if e-mail is NULL, immediately return */
218 if(e_mail == NULL){
219 return;
220 }
221
222 if(g_hash_table_lookup(cross_hash ,e_mail) == NULL){/* there is no such entry, so create it */
223 g_hash_table_insert(cross_hash, strdup(e_mail), NT_cross_filename_generate(tmpdir, e_mail, mode));
224 }
225
226 }
227
228
229
230
231
232 /* Adds the e-mails in a linked list to the hash */
233 void NT_add_to_ntfy_hash_list(GHashTable * ntfy_hash, GSList * e_mail_list){
/* [<][>][^][v][top][bottom][index][help] */
234
235 GSList * temp = NULL;
236
237 for(temp = e_mail_list; temp != NULL; temp = g_slist_next(temp)){
238 NT_add_to_ntfy_hash(ntfy_hash, (char *)temp->data);
239 }
240
241 }
242
243
244
245
246 /* Adds the e-mails in a linked list to the hash */
247 void NT_add_to_frwd_hash_list(GHashTable * frwd_hash, GSList * e_mail_list){
/* [<][>][^][v][top][bottom][index][help] */
248
249 GSList * temp = NULL;
250
251 for(temp = e_mail_list; temp != NULL; temp = g_slist_next(temp)){
252 NT_add_to_frwd_hash(frwd_hash, (char *)temp->data);
253 }
254
255 }
256
257
258
259 /* Adds the e-mails in a linked list to the hash */
260 void NT_add_to_cross_hash_list(GHashTable * cross_hash, GSList * e_mail_list, int mode){
/* [<][>][^][v][top][bottom][index][help] */
261
262 GSList * temp = NULL;
263
264 for(temp = e_mail_list; temp != NULL; temp = g_slist_next(temp)){
265 NT_add_to_cross_hash(cross_hash, (char *)temp->data, mode);
266 }
267
268 }
269
270
271
272
273
274
275 /* Appends the argument strings to the file. */
276 void NT_add_to_ntfy( char * filename, char * fmt, ... ){
/* [<][>][^][v][top][bottom][index][help] */
277 va_list ap; /* points to each unnamed arg in turn */
278 FILE * ntfy_file;
279
280 if(tracing){
281 printf("TRACING: NT_add_to_ntfy\n");
282 }
283 if(( ntfy_file = fopen(filename, "a")) == NULL){
284 fprintf(stderr, "Can't open notification file for writing, %s\n", filename);
285 return;
286 }
287
288 va_start(ap, fmt);
289 vfprintf(ntfy_file, fmt, ap);
290
291 va_end(ap); /* clean up */
292 fclose(ntfy_file);
293 }
294
295
296
297 /* Appends the argument strings to the file. */
298 void NT_add_to_cross(const char * e_mail, GHashTable * hash, char * fmt, ...){
/* [<][>][^][v][top][bottom][index][help] */
299
300 va_list ap; /* points to each unnamed arg in turn */
301 FILE * cross_file;
302 char * filename;
303
304 /* if e-mail is NULL, immediately return */
305 if(e_mail == NULL){
306 return;
307 }
308
309 if(g_hash_table_lookup(hash, find_email_address(e_mail)) != NULL){
310 filename = (char *)g_hash_table_lookup(hash, find_email_address(e_mail));
311 }else{
312 fprintf(stderr, "Can't find a cross notification file for e-mail %s\n", e_mail);
313 return;
314 }
315
316 if(( cross_file = fopen(filename, "a")) == NULL){
317 fprintf(stderr, "Can't open cross notification file, %s\n", filename);
318 }
319
320
321
322 if(tracing){
323 printf("TRACING: NT_add_to_cross\n");
324 }
325 if(( cross_file = fopen(filename, "a")) == NULL){
326 fprintf(stderr, "Can't open cross notification file for writing, %s\n", filename);
327 }
328
329 va_start(ap, fmt);
330 vfprintf(cross_file, fmt, ap);
331
332 va_end(ap); /* clean up */
333 fclose(cross_file);
334
335
336 }
337
338
339
340
341
342 /* Appends the argument string to the temp notif files in the list */
343 void NT_add_to_ntfy_list(GSList * list, GHashTable * hash, char * arg){
/* [<][>][^][v][top][bottom][index][help] */
344
345 GSList * temp = NULL;
346
347 for(temp = list; temp != NULL; temp = g_slist_next(temp)){
348 NT_add_to_ntfy((char *)g_hash_table_lookup(hash, ((char *)temp->data)), arg);
349 }
350 }
351
352
353
354
355
356
357
358
359 /* Sends the notification message which is stored in the temporary filefilename. */
360 void NT_send_ntfy( const char * filename, const char * to_address, const char * mailercommand){
/* [<][>][^][v][top][bottom][index][help] */
361
362 char * mail_command_line = NULL;
363 char * supress_file = NULL;
364 FILE * notif_file, * supr_file_hdl;
365 char buf[1024];
366
367
368 /* if we are not supressing acks and notifs, send the notif */
369 if(!supress_ack_notif){
370 if(to_address != NULL){
371 mail_command_line = (char *)malloc(strlen(mailercommand) + strlen(filename) + 128);
372 sprintf(mail_command_line, "%s %s < %s", mailercommand, to_address, filename);
373 system(mail_command_line);
374 }
375 /* if we are supressing acks and notifs, send notif to DEFMAIL */
376 }else{
377 supress_file = (char *)malloc(strlen(filename) + strlen(".supress") + 2);
378 sprintf(supress_file, "%s.supress", filename);
379 if(( supr_file_hdl = fopen(supress_file, "w")) == NULL){
380 fprintf(stderr, "Can't open supress notif file, %s", supress_file);
381 }else{
382 fprintf(supr_file_hdl, "From: %s\nTo: %s\nSubject: Supressed notif mail\n\n",
383 humailbox, defmail);
384 if(( notif_file = fopen(filename, "r")) == NULL){
385 fprintf(stderr, "Can't open notif file for reading, %s", filename);
386 }else{
387 while(fgets(buf, 1023, notif_file) != NULL){
388 fprintf(supr_file_hdl, buf);
389 }
390 fclose(notif_file);
391 }
392 }
393 fclose(supr_file_hdl);
394 mail_command_line = (char *)malloc(strlen(mailercommand) + strlen(defmail)
395 + strlen(supress_file) + 128);
396 sprintf(mail_command_line, "%s %s < %s", mailercommand, defmail, supress_file);
397 system(mail_command_line);
398 unlink(supress_file);
399 free(supress_file);
400 }
401
402
403 }
404
405
406
407 /* Adds the notification message which is in the filename into "logfilename.date". */
408 void NT_log_ntfy( const char * filename, const char * logfilename){
/* [<][>][^][v][top][bottom][index][help] */
409
410 FILE * notif_file, * log_file;
411 char * buf;
412 time_t cur_time;
413 char * time_str;
414 char * logfile_date;
415 char * date;
416
417 buf = (char *)malloc(1024);
418 if(( notif_file = fopen(filename, "r")) == NULL){
419 fprintf(stderr, "Can't open notification file for reading, [%s]\n", filename);
420 return;
421 }
422
423 /* construct the "logfilename.date" string */
424 logfile_date = (char *)malloc(strlen(logfilename) + 10);
425 date = UP_get_current_date();
426 snprintf(logfile_date, strlen(logfilename) + 10, "%s.%s", logfilename, date);
427 free(date);
428
429 if(( log_file = fopen(logfile_date, "a")) == NULL){
430 fprintf(stderr, "Can't open log file, %s\n", logfilename);
431 return;
432 }
433
434 /* get time */
435 cur_time = time(NULL);
436 time_str = strdup(ctime(&cur_time));
437 /* cut the '\n' at the end */
438 time_str[strlen(time_str) - 1] = '\0';
439
440 fprintf(log_file, ">>> time: %s NOTIF <<<\n\n", time_str);
441
442
443 while((buf=fgets(buf, 1023, notif_file)) > 0){
444 fprintf(log_file, "%s", buf);
445 }
446 free(buf);
447
448 fclose(notif_file);
449 fclose(log_file);
450
451 }
452
453
454 /* Deletes the temporary notification file. */
455 void NT_delete_ntfy( const char * filename){
/* [<][>][^][v][top][bottom][index][help] */
456
457 unlink(filename);
458
459 }
460
461
462 /* The function required for NT_send_ntfy_list */
463 void nt_gfunc_send(gpointer key, gpointer value, gpointer user_data){
/* [<][>][^][v][top][bottom][index][help] */
464 NT_send_ntfy((char *)value, (char *)key, (char *)user_data);
465 }
466
467
468
469 /* Sends the notification messages whose temp files are stored in filehash. */
470 void NT_send_ntfy_list( GHashTable * filehash, char * mailercommand){
/* [<][>][^][v][top][bottom][index][help] */
471
472 g_hash_table_foreach( filehash, (GHFunc)nt_gfunc_send, mailercommand);
473
474 }
475
476
477
478
479 /* The function required for NT_log_ntfy_list */
480 void nt_gfunc_log(gpointer key, gpointer value, gpointer user_data){
/* [<][>][^][v][top][bottom][index][help] */
481 NT_log_ntfy((char *)value, (char *)user_data);
482 }
483
484
485
486
487 /* Logs the notification whose temp files are in filehash to log_file. */
488 void NT_log_ntfy_list( GHashTable * filehash, char * log_file){
/* [<][>][^][v][top][bottom][index][help] */
489
490 g_hash_table_foreach( filehash, (GHFunc)nt_gfunc_log, log_file);
491
492 }
493
494
495
496 /* The function required for NT_delete_ntfy_list */
497 void nt_gfunc_delete(gpointer key, gpointer value, gpointer user_data){
/* [<][>][^][v][top][bottom][index][help] */
498 NT_delete_ntfy((char *)value);
499 }
500
501
502
503 /* Deletes the temporary notification messages in the filehash. Empties and frees
504 the hash too. */
505 void NT_delete_ntfy_list( GHashTable * filehash){
/* [<][>][^][v][top][bottom][index][help] */
506
507 g_hash_table_foreach(filehash, (GHFunc)nt_gfunc_delete, NULL);
508 g_hash_table_destroy(filehash);
509
510 }
511
512
513 /* to be used with g_hash_table_foreach in NT_unify_list.
514 Adds the 'key' to the list (a GSList) */
515 void nt_add_to_list(char * key, char * value, GSList ** list){
/* [<][>][^][v][top][bottom][index][help] */
516
517 *list = g_slist_append(*list, strdup(value));
518
519
520 }
521
522
523
524 /* "unifies" a list in a case insensitive manner */
525 GSList * NT_unify_list(GSList * in_list){
/* [<][>][^][v][top][bottom][index][help] */
526
527 GHashTable * unification_hash;
528 GSList ** out_list;
529 GSList * temp;
530 char * key, * value;
531
532 /* allocate space for out_list */
533 out_list = (GSList **)malloc(sizeof(GSList *));
534 *out_list = NULL;
535
536 /* initialize the hash to be used for unification process */
537 unification_hash = g_hash_table_new(g_str_hash, g_str_equal);
538
539 /* first put the list elements into a hash, to unify them */
540 for(temp = in_list; temp != NULL; temp = g_slist_next(temp)){
541
542 /* convert the string into lowercase */
543 key = strdup((char *)(temp->data));
544 g_strdown(key);
545 value = strdup((char *)(temp->data));
546
547 if(g_hash_table_lookup(unification_hash, key) == NULL){/* if it is not there */
548
549 g_hash_table_insert(unification_hash, key, value);
550
551 }
552 }
553
554 /* now, get the elements back from the hash into a list */
555 g_hash_table_foreach(unification_hash, (GHFunc)nt_add_to_list, out_list);
556
557 g_slist_free(in_list);
558 g_hash_table_destroy(unification_hash);
559
560 return *out_list;
561
562 }
563
564
565
566
567
568
569
570
571 /* Gathers e-mail boxes to which we will send normal notification messages. It
572 takes old and new objects, looks up maintainers and less specific inetnums/domains/routes
573 when necessary, finds the addresses (in mnt-nfy and notify attributes) and returns
574 a list of them. */
575 GSList * NT_gather_ntfy_addresses( char * old_object, char * new_object){
/* [<][>][^][v][top][bottom][index][help] */
576 GSList * return_list = NULL, * temp = NULL;
577 GSList * mntners = NULL;
578
579 if(old_object != NULL && new_object != NULL){/* it was an update */
580 temp = get_attr_list(old_object, "notify");
581 mntners = get_mntners(old_object);
582 temp = g_slist_concat(temp, get_mntnfy_vector(mntners));
583 }else if(old_object == NULL && new_object != NULL){/* it was a creation */
584 temp = get_attr_list(new_object, "notify");
585 mntners = get_mntners(new_object);
586 temp = g_slist_concat(temp, get_mntnfy_vector(mntners));
587 }else if(old_object != NULL && new_object == NULL){/* it was a deletion */
588 temp = get_attr_list(old_object, "notify");
589 mntners = get_mntners(old_object);
590 temp = g_slist_concat(temp, get_mntnfy_vector(mntners));
591 }
592
593 /* we have to 'unify' the list here! */
594 return_list = NT_unify_list(temp);
595
596 return return_list;
597 }
598
599
600
601 /* Gathers e-mail boxes to which we will forward messages (or rather, objects). It
602 an object, looks up maintainers, finds the addresses (in upd-to attributes) and returns
603 a list of them. */
604 GSList * NT_gather_frwd_addresses(char * object){
/* [<][>][^][v][top][bottom][index][help] */
605 GSList *temp = NULL;
606 GSList * mntners = NULL;
607
608 mntners = get_mntners(object);
609 temp = get_updto_vector(mntners);
610 return temp;
611 }
612
613
614
615
616 /* Accepts a route object as a "* char" and returns a list of overlapping routes */
617 overlap_routes get_overlapping_routes_list(char * object){
/* [<][>][^][v][top][bottom][index][help] */
618
619 char * route_prefix = NULL;
620 GSList * tmp_list;
621 char * result;
622 char * query_string;
623 overlap_routes result_routes;
624 char * origin;
625 bool code;
626
627
628 result_routes.less_spec = NULL;
629 result_routes.exact_match = NULL;
630 result_routes.more_spec = NULL;
631
632 tmp_list = get_attr_list(object, "route");
633
634 if(tmp_list != NULL && tmp_list->data != NULL){
635 route_prefix = strdup((char *)(tmp_list->data));
636 }else{
637 return result_routes; /* then, this wasn't a route object */
638 }
639
640 /* get the less specific route objects */
641 /* form the query string */
642 query_string = (char *)malloc(strlen("-Troute -r -l ") + strlen(route_prefix) + 2);
643 sprintf(query_string, "-Troute -r -l %s", route_prefix);
644
645 /* get the results */
646 result = send_and_get(query_host, query_port, query_string);
647 free(query_string);
648
649 /* and fill in the result field */
650 result_routes.less_spec = take_objects(result);
651
652 /* get the exact match route objects */
653 /* form the query string */
654 query_string = (char *)malloc(strlen("-Troute -r -x ") + strlen(route_prefix) + 2);
655 sprintf(query_string, "-Troute -r -x %s", route_prefix);
656
657 /* get the results */
658 result = send_and_get(query_host, query_port, query_string);
659 free(query_string);
660
661
662 /* filter out the route object itself */
663 result = UP_filter_out_same_origins(result, object);
664
665 /* and fill in the result field */
666 if(result != NULL){
667 result_routes.exact_match = take_objects(result);
668 }
669
670
671 /* get the more specific route objects */
672 /* form the query string */
673 query_string = (char *)malloc(strlen("-Troute -r -M ") + strlen(route_prefix) + 2);
674 sprintf(query_string, "-Troute -r -M %s", route_prefix);
675
676 /* get the results */
677 result = send_and_get(query_host, query_port, query_string);
678 free(query_string);
679
680 /* and fill in the result field */
681 result_routes.more_spec = take_objects(result);
682
683 /* Return the results */
684 return result_routes;
685
686 }
687
688
689
690
691
692 /* Gets old and new versions of the object, and creates temporary notification
693 files when necessary, and then writes appropriate strings into those
694 temporary files. */
695 void NT_write_all_ntfs(char * old_object, char * new_object, char * formatted_object,
/* [<][>][^][v][top][bottom][index][help] */
696 const char * tempdir,
697 GHashTable * ntfy_hash, GHashTable * forwd_hash, GHashTable * cross_hash,
698 char * from_address){
699
700 GSList * e_mail_list = NULL;
701 GSList * temp = NULL;
702 char * e_mail_address;
703 overlap_routes overlapping_routes;
704
705 /* from_address may contain also the name, like "Johnny Bravo <johnny@inter.net>",
706 so extract the e-mail address from it */
707 e_mail_address = find_email_address(from_address);
708
709
710 if(tracing && reading_from_mail){
711 printf("TRACING: NT_write_all_ntfs: from_address=[%s], e_mail_address=[%s]\n", from_address, e_mail_address);
712 }
713 if(old_object != NULL && new_object != NULL){/* it was an update */
714 e_mail_list = NT_gather_ntfy_addresses(old_object, new_object);
715 NT_add_to_ntfy_hash_list(ntfy_hash, e_mail_list);
716 NT_add_to_ntfy_list(e_mail_list, ntfy_hash, "---\nPREVIOUS OBJECT:\n\n");
717 NT_add_to_ntfy_list(e_mail_list, ntfy_hash, old_object);
718 NT_add_to_ntfy_list(e_mail_list, ntfy_hash, "\n\nREPLACED BY:\n\n");
719 NT_add_to_ntfy_list(e_mail_list, ntfy_hash, new_object);
720 NT_add_to_ntfy_list(e_mail_list, ntfy_hash, "\n");
721 }else if(old_object == NULL && new_object != NULL){/* it was a creation */
722 e_mail_list = NT_gather_ntfy_addresses(old_object, new_object);
723 NT_add_to_ntfy_hash_list(ntfy_hash, e_mail_list);
724 NT_add_to_ntfy_list(e_mail_list, ntfy_hash, "---\nOBJECT BELOW CREATED:\n\n");
725 NT_add_to_ntfy_list(e_mail_list, ntfy_hash,
726 formatted_object ? formatted_object : new_object);
727 NT_add_to_ntfy_list(e_mail_list, ntfy_hash, "\n");
728 /* We'll deal with cross notifications only when we create or delete route objects */
729 if(strcmp(get_class_type_char(new_object), "route") == 0){
730 overlapping_routes = get_overlapping_routes_list(new_object);
731 if(overlapping_routes.less_spec != NULL || overlapping_routes.exact_match != NULL ||
732 overlapping_routes.more_spec != NULL ){
733 NT_add_to_cross_hash(cross_hash, e_mail_address, ADDITION);
734 NT_add_to_cross(e_mail_address, cross_hash, "%s\n\n%s\n\n%s\n\n", cno_explain_add, new_object, cno_overlap_add);
735 if(overlapping_routes.less_spec != NULL){
736 NT_add_to_cross(from_address, cross_hash, "LESS SPECIFIC MATCHES\n\n");
737 for(temp = overlapping_routes.less_spec; temp != NULL; temp = g_slist_next(temp)){
738 NT_add_to_cross(from_address, cross_hash, "%s\n\n", (char *)temp->data);
739 }
740 }
741 if(overlapping_routes.exact_match != NULL){
742 NT_add_to_cross(from_address, cross_hash, "EXACT MATCHES\n\n");
743 for(temp = overlapping_routes.exact_match; temp != NULL; temp = g_slist_next(temp)){
744 NT_add_to_cross(from_address, cross_hash, "%s\n\n", (char *)temp->data);
745 }
746 }
747 if(overlapping_routes.more_spec != NULL){
748 NT_add_to_cross(from_address, cross_hash, "MORE SPECIFIC MATCHES\n\n");
749 for(temp = overlapping_routes.more_spec; temp != NULL; temp = g_slist_next(temp)){
750 NT_add_to_cross(from_address, cross_hash, "%s\n\n", (char *)temp->data);
751 }
752 }
753 }
754 }
755 }else if(old_object != NULL && new_object == NULL){/* it was a deletion */
756 old_object = delete_delete_attrib(old_object);
757 e_mail_list = NT_gather_ntfy_addresses(old_object, new_object);
758 NT_add_to_ntfy_hash_list(ntfy_hash, e_mail_list);
759 NT_add_to_ntfy_list(e_mail_list, ntfy_hash, "---\nOBJECT BELOW DELETED:\n\n");
760 NT_add_to_ntfy_list(e_mail_list, ntfy_hash, old_object);
761 NT_add_to_ntfy_list(e_mail_list, ntfy_hash, "\n");
762 /* We'll deal with cross notifications only when we create or delete route objects */
763 if(strcmp(get_class_type_char(old_object), "route") == 0){
764 overlapping_routes = get_overlapping_routes_list(old_object);
765 if(overlapping_routes.less_spec != NULL || overlapping_routes.exact_match != NULL ||
766 overlapping_routes.more_spec != NULL ){
767 NT_add_to_cross_hash(cross_hash, e_mail_address, DELETION);
768 NT_add_to_cross(e_mail_address, cross_hash, "%s\n\n%s\n\n%s\n\n", cno_explain_del, old_object, cno_overlap_del);
769 if(overlapping_routes.less_spec != NULL){
770 NT_add_to_cross(from_address, cross_hash, "LESS SPECIFIC MATCHES\n\n");
771 for(temp = overlapping_routes.less_spec; temp != NULL; temp = g_slist_next(temp)){
772 NT_add_to_cross(from_address, cross_hash, "%s\n\n", (char *)temp->data);
773 }
774 }
775 if(overlapping_routes.exact_match != NULL){
776 NT_add_to_cross(from_address, cross_hash, "EXACT MATCHES\n\n");
777 for(temp = overlapping_routes.exact_match; temp != NULL; temp = g_slist_next(temp)){
778 NT_add_to_cross(from_address, cross_hash, "%s\n\n", (char *)temp->data);
779 }
780 }
781 if(overlapping_routes.more_spec != NULL){
782 NT_add_to_cross(from_address, cross_hash, "MORE SPECIFIC MATCHES\n\n");
783 for(temp = overlapping_routes.more_spec; temp != NULL; temp = g_slist_next(temp)){
784 NT_add_to_cross(from_address, cross_hash, "%s\n\n", (char *)temp->data);
785 }
786 }
787 }
788 }
789 }
790 }
791
792
793
794
795
796 /* Gets old and new versions of the object, and creates temporary notification
797 files when necessary, and then writes appropriate strings into those
798 temporary files. */
799 void NT_write_all_frwds(char * old_object, char * new_object, const char * tempdir,
/* [<][>][^][v][top][bottom][index][help] */
800 GHashTable * ntfy_hash, GHashTable * forwd_hash, GHashTable * cross_hash,
801 const char * from_address){
802
803 GSList * e_mail_list = NULL;
804
805
806 if(tracing){
807 printf("TRACING: NT_write_all_frwds\n");
808 }
809 if(old_object != NULL && new_object != NULL){/* it was an update */
810 e_mail_list = NT_gather_frwd_addresses(old_object);
811 NT_add_to_frwd_hash_list(forwd_hash, e_mail_list);
812 NT_add_to_ntfy_list(e_mail_list, forwd_hash, "----\nUPDATE REQUESTED FOR:\n\n");
813 NT_add_to_ntfy_list(e_mail_list, forwd_hash, new_object);
814 }else if(old_object == NULL && new_object != NULL){/* it was a creation */
815 e_mail_list = NT_gather_frwd_addresses(new_object);
816 NT_add_to_frwd_hash_list(forwd_hash, e_mail_list);
817 NT_add_to_ntfy_list(e_mail_list, forwd_hash, "----\nADDITION REQUESTED FOR:\n\n");
818 NT_add_to_ntfy_list(e_mail_list, forwd_hash, new_object);
819 }else if(old_object != NULL && new_object == NULL){/* it was a deletion */
820 e_mail_list = NT_gather_frwd_addresses(old_object);
821 NT_add_to_frwd_hash_list(forwd_hash, e_mail_list);
822 NT_add_to_ntfy_list(e_mail_list, forwd_hash, "----\nDELETION REQUESTED FOR:\n\n");
823 NT_add_to_ntfy_list(e_mail_list, forwd_hash, old_object);
824 }
825 }
826
827
828
829 /* Sends the creation forward message which is stored in the temporary filefilename. */
830 void NT_send_forw_creation( const char * filename, const char * to_address, const char * mailercommand){
/* [<][>][^][v][top][bottom][index][help] */
831
832 char * mail_command_line = NULL;
833
834
835 if(to_address != NULL){
836 mail_command_line = (char *)malloc(strlen(mailercommand) + strlen(filename) + 128);
837 sprintf(mail_command_line, "%s %s < %s", mailercommand, to_address, filename);
838 system(mail_command_line);
839 free(mail_command_line);
840 }
841
842 }
843
844
845
846
847
848 /* NT_forw_create_req forwards the maintainer and as-block creation requests
849 to <HUMAILBOX> */
850 void NT_forw_create_req(const char * object){
/* [<][>][^][v][top][bottom][index][help] */
851
852 FILE * forw_file;
853 char * filename;
854 char * replaced_mtfwheader;
855 char * replaced_mtfwtxt;
856
857 /* allocate space for name. 32 should be enough for PID */
858 filename = (char*)malloc(strlen(tmpdir) + strlen("creat-forw") +32 );
859
860 sprintf(filename, "%s/%s.%i", tmpdir, "creat-forw", getpid());
861
862 /* create the file */
863 if(( forw_file = fopen(filename, "w")) == NULL){
864 fprintf(stderr, "Can't open creation forward file for creating, %s", filename);
865 }
866
867 replaced_mtfwheader = UP_replace_globals(mtfwheader);
868 replaced_mtfwtxt = UP_replace_globals(mtfwtxt);
869
870 fprintf(forw_file, "%s\n\n", replaced_mtfwheader);
871
872 if(reading_from_mail){
873 fprintf(forw_file, "%s\n\n", replaced_mtfwtxt);
874 }
875
876 /* print the object */
877 fprintf(forw_file, "%s\n\n", object);
878
879 /* close it */
880 fclose(forw_file);
881
882 /* send it */
883 NT_send_forw_creation(filename, humailbox, mailcmd);
884
885 /* log it */
886 NT_log_ntfy(filename, forwlog);
887
888 /* delete it */
889 unlink(filename);
890
891 /* free the mem */
892 free(filename);
893 free(replaced_mtfwheader);
894 free(replaced_mtfwtxt);
895 }