source: logging.c @ 3c7d086a

barnowl_perlaimdebianowlrelease-1.4release-1.5release-1.6release-1.7release-1.8release-1.9
Last change on this file since 3c7d086a was 3c7d086a, checked in by Erik Nygren <nygren@mit.edu>, 15 years ago
Fix for BZ 90: crash when sending/logging outgoing AIM message and not logged in Also made the message log deal with getting passed a NULL message.
  • Property mode set to 100644
File size: 13.1 KB
Line 
1#include "owl.h"
2#include <stdlib.h>
3#include <string.h>
4#include <ctype.h>
5#include <sys/param.h>
6
7static const char fileIdent[] = "$Id$";
8
9/* This is now the one function that should be called to log a
10 * message.  It will do all the work necessary by calling the other
11 * functions in this file as necessary.
12 */
13void owl_log_message(owl_message *m) {
14  owl_function_debugmsg("owl_log_message: entering");
15
16  if (m == NULL) {
17    owl_function_debugmsg("owl_log_message: passed null message");
18    return;
19  }
20
21  /* should we be logging this message? */
22  if (!owl_log_shouldlog_message(m)) {
23    owl_function_debugmsg("owl_log_message: not logging message");
24    return;
25  }
26
27  /* handle incmoing messages */
28  if (owl_message_is_direction_in(m)) {
29    owl_log_incoming(m);
30    owl_function_debugmsg("owl_log_message: leaving");
31    return;
32  }
33
34  /* handle outgoing messages */
35  if (owl_message_is_type_aim(m)) {
36    owl_log_outgoing_aim(m);
37  } else if (owl_message_is_type_zephyr(m)) {
38    owl_log_outgoing_zephyr(m);
39  } else if (owl_message_is_type_loopback(m)) {
40    owl_log_outgoing_loopback(m);
41  } else {
42    owl_function_error("Unknown message type for logging");
43  }
44  owl_function_debugmsg("owl_log_message: leaving");
45}
46
47/* Return 1 if we should log the given message, otherwise return 0 */
48int owl_log_shouldlog_message(owl_message *m) {
49  owl_filter *f;
50
51  /* If there's a logfilter and this message matches it, log */
52  f=owl_global_get_filter(&g, owl_global_get_logfilter(&g));
53  if (f && owl_filter_message_match(f, m)) return(1);
54
55  /* otherwise we do things based on the logging variables */
56
57  /* skip login/logout messages if appropriate */
58  if (!owl_global_is_loglogins(&g) && owl_message_is_loginout(m)) return(0);
59     
60  /* check for nolog */
61  if (!strcasecmp(owl_message_get_opcode(m), "nolog") || !strcasecmp(owl_message_get_instance(m), "nolog")) return(0);
62
63  /* check direction */
64  if ((owl_global_get_loggingdirection(&g)==OWL_LOGGING_DIRECTION_IN) && owl_message_is_direction_out(m)) {
65    return(0);
66  }
67  if ((owl_global_get_loggingdirection(&g)==OWL_LOGGING_DIRECTION_OUT) && owl_message_is_direction_in(m)) {
68    return(0);
69  }
70
71  if (owl_message_is_type_zephyr(m)) {
72    if (owl_message_is_personal(m) && !owl_global_is_logging(&g)) return(0);
73    if (!owl_message_is_personal(m) && !owl_global_is_classlogging(&g)) return(0);
74  } else {
75    if (owl_message_is_private(m) || owl_message_is_loginout(m)) {
76      if (!owl_global_is_logging(&g)) return(0);
77    } else {
78      if (!owl_global_is_classlogging(&g)) return(0);
79    }
80  }
81  return(1);
82}
83
84void owl_log_outgoing_zephyr(owl_message *m)
85{
86  FILE *file;
87  char filename[MAXPATHLEN], *logpath;
88  char *to, *text;
89
90  /* strip local realm */
91  to=short_zuser(owl_message_get_recipient(m));
92
93  /* expand ~ in path names */
94  logpath=owl_text_substitute(owl_global_get_logpath(&g), "~", owl_global_get_homedir(&g));
95
96  text=owl_message_get_body(m);
97
98  snprintf(filename, MAXPATHLEN, "%s/%s", logpath, to);
99  file=fopen(filename, "a");
100  if (!file) {
101    owl_function_error("Unable to open file for outgoing logging");
102    owl_free(logpath);
103    owl_free(to);
104    return;
105  }
106  fprintf(file, "OUTGOING (owl): %s\n%s\n", to, text);
107  if (text[strlen(text)-1]!='\n') {
108    fprintf(file, "\n");
109  }
110  fclose(file);
111
112  snprintf(filename, MAXPATHLEN, "%s/all", logpath);
113  owl_free(logpath);
114  file=fopen(filename, "a");
115  if (!file) {
116    owl_function_error("Unable to open file for outgoing logging");
117    owl_free(to);
118    return;
119  }
120  fprintf(file, "OUTGOING (owl): %s\n%s\n", to, text);
121  if (text[strlen(text)-1]!='\n') {
122    fprintf(file, "\n");
123  }
124  fclose(file);
125
126  owl_free(to);
127}
128
129void owl_log_outgoing_zephyr_error(char *to, char *text)
130{
131  FILE *file;
132  char filename[MAXPATHLEN], *logpath;
133  char *tobuff, *zwriteline;
134  owl_message *m;
135
136  /* create a present message so we can pass it to
137   * owl_log_shouldlog_message()
138   */
139  zwriteline=owl_sprintf("zwrite %s", to);
140  m=owl_function_make_outgoing_zephyr(text, zwriteline, "");
141  owl_free(zwriteline);
142  if (!owl_log_shouldlog_message(m)) {
143    owl_message_free(m);
144    return;
145  }
146  owl_message_free(m);
147
148  /* chop off a local realm */
149  tobuff=short_zuser(to);
150
151  /* expand ~ in path names */
152  logpath = owl_text_substitute(owl_global_get_logpath(&g), "~", owl_global_get_homedir(&g));
153
154  snprintf(filename, MAXPATHLEN, "%s/%s", logpath, tobuff);
155  file=fopen(filename, "a");
156  if (!file) {
157    owl_function_error("Unable to open file for outgoing logging");
158    owl_free(logpath);
159    owl_free(tobuff);
160    return;
161  }
162  fprintf(file, "ERROR (owl): %s\n%s\n", tobuff, text);
163  if (text[strlen(text)-1]!='\n') {
164    fprintf(file, "\n");
165  }
166  fclose(file);
167
168  snprintf(filename, MAXPATHLEN, "%s/all", logpath);
169  owl_free(logpath);
170  file=fopen(filename, "a");
171  if (!file) {
172    owl_function_error("Unable to open file for outgoing logging");
173    owl_free(tobuff);
174    return;
175  }
176  fprintf(file, "ERROR (owl): %s\n%s\n", tobuff, text);
177  if (text[strlen(text)-1]!='\n') {
178    fprintf(file, "\n");
179  }
180  fclose(file);
181
182  owl_free(tobuff);
183}
184
185void owl_log_outgoing_aim(owl_message *m)
186{
187  FILE *file;
188  char filename[MAXPATHLEN], *logpath;
189  char *tobuff, *normalto, *text;
190
191  owl_function_debugmsg("owl_log_outgoing_aim: entering");
192
193  /* normalize and downcase the screenname */
194  normalto=owl_aim_normalize_screenname(owl_message_get_recipient(m));
195  downstr(normalto);
196  tobuff=owl_sprintf("aim:%s", normalto);
197  owl_free(normalto);
198
199  /* expand ~ in path names */
200  logpath = owl_text_substitute(owl_global_get_logpath(&g), "~", owl_global_get_homedir(&g));
201
202  text=owl_message_get_body(m);
203 
204  snprintf(filename, MAXPATHLEN, "%s/%s", logpath, tobuff);
205  file=fopen(filename, "a");
206  if (!file) {
207    owl_function_error("Unable to open file for outgoing logging");
208    owl_free(logpath);
209    owl_free(tobuff);
210    return;
211  }
212  fprintf(file, "OUTGOING (owl): %s\n%s\n", tobuff, text);
213  if (text[strlen(text)-1]!='\n') {
214    fprintf(file, "\n");
215  }
216  fclose(file);
217
218  snprintf(filename, MAXPATHLEN, "%s/all", logpath);
219  owl_free(logpath);
220  file=fopen(filename, "a");
221  if (!file) {
222    owl_function_error("Unable to open file for outgoing logging");
223    owl_free(tobuff);
224    return;
225  }
226  fprintf(file, "OUTGOING (owl): %s\n%s\n", tobuff, text);
227  if (text[strlen(text)-1]!='\n') {
228    fprintf(file, "\n");
229  }
230  fclose(file);
231
232  owl_free(tobuff);
233}
234
235void owl_log_outgoing_loopback(owl_message *m)
236{
237  FILE *file;
238  char filename[MAXPATHLEN], *logpath;
239  char *tobuff, *text;
240
241  tobuff=owl_sprintf("loopback");
242
243  /* expand ~ in path names */
244  logpath = owl_text_substitute(owl_global_get_logpath(&g), "~", owl_global_get_homedir(&g));
245
246  text=owl_message_get_body(m);
247
248  snprintf(filename, MAXPATHLEN, "%s/%s", logpath, tobuff);
249  file=fopen(filename, "a");
250  if (!file) {
251    owl_function_error("Unable to open file for outgoing logging");
252    owl_free(logpath);
253    owl_free(tobuff);
254    return;
255  }
256  fprintf(file, "OUTGOING (owl): %s\n%s\n", tobuff, text);
257  if (text[strlen(text)-1]!='\n') {
258    fprintf(file, "\n");
259  }
260  fclose(file);
261
262  snprintf(filename, MAXPATHLEN, "%s/all", logpath);
263  owl_free(logpath);
264  file=fopen(filename, "a");
265  if (!file) {
266    owl_function_error("Unable to open file for outgoing logging");
267    owl_free(tobuff);
268    return;
269  }
270  fprintf(file, "OUTGOING (owl): %s\n%s\n", tobuff, text);
271  if (text[strlen(text)-1]!='\n') {
272    fprintf(file, "\n");
273  }
274  fclose(file);
275
276  owl_free(tobuff);
277}
278
279void owl_log_incoming(owl_message *m)
280{
281  FILE *file, *allfile;
282  char filename[MAXPATHLEN], allfilename[MAXPATHLEN], *logpath;
283  char *frombuff=NULL, *from=NULL, *buff=NULL, *ptr;
284  int len, ch, i, personal;
285
286  /* figure out if it's a "personal" message or not */
287  if (owl_message_is_type_zephyr(m)) {
288    if (owl_message_is_personal(m)) {
289      personal=1;
290    } else {
291      personal=0;
292    }
293  } else {
294    if (owl_message_is_private(m) || owl_message_is_loginout(m)) {
295      personal=1;
296    } else {
297      personal=0;
298    }
299  }
300
301  if (owl_message_is_type_zephyr(m)) {
302    if (personal) {
303      if (owl_message_is_type_zephyr(m)) {
304        from=frombuff=short_zuser(owl_message_get_sender(m));
305      }
306    } else {
307      from=frombuff=owl_strdup(owl_message_get_class(m));
308    }
309  } else if (owl_message_is_type_aim(m)) {
310    /* we do not yet handle chat rooms */
311    char *normalto;
312    normalto=owl_aim_normalize_screenname(owl_message_get_sender(m));
313    downstr(normalto);
314    from=frombuff=owl_sprintf("aim:%s", normalto);
315    owl_free(normalto);
316  } else if (owl_message_is_type_loopback(m)) {
317    from=frombuff=owl_strdup("loopback");
318  } else {
319    from=frombuff=owl_strdup("unknown");
320  }
321 
322  /* check for malicious sender formats */
323  len=strlen(frombuff);
324  if (len<1 || len>35) from="weird";
325  if (strchr(frombuff, '/')) from="weird";
326
327  ch=frombuff[0];
328  if (!isalnum(ch)) from="weird";
329
330  for (i=0; i<len; i++) {
331    if (frombuff[i]<'!' || frombuff[i]>='~') from="weird";
332  }
333
334  if (!strcmp(frombuff, ".") || !strcasecmp(frombuff, "..")) from="weird";
335
336  if (!personal) {
337    if (strcmp(from, "weird")) downstr(from);
338  }
339
340  /* create the filename (expanding ~ in path names) */
341  if (personal) {
342    logpath = owl_text_substitute(owl_global_get_logpath(&g), "~", owl_global_get_homedir(&g));
343    snprintf(filename, MAXPATHLEN, "%s/%s", logpath, from);
344    snprintf(allfilename, MAXPATHLEN, "%s/all", logpath);
345
346  } else {
347    logpath = owl_text_substitute(owl_global_get_classlogpath(&g), "~", owl_global_get_homedir(&g));
348    snprintf(filename, MAXPATHLEN, "%s/%s", logpath, from);
349  }
350  owl_free(logpath);
351 
352  file=fopen(filename, "a");
353  if (!file) {
354    owl_function_error("Unable to open file for incoming logging");
355    owl_free(frombuff);
356    return;
357  }
358
359  allfile=NULL;
360  if (personal) {
361    allfile=fopen(allfilename, "a");
362    if (!allfile) {
363      owl_function_error("Unable to open file for incoming logging");
364      owl_free(frombuff);
365      fclose(file);
366      return;
367    }
368  }
369
370  /* write to the main file */
371  if (owl_message_is_type_zephyr(m)) {
372    char *tmp;
373   
374    tmp=short_zuser(owl_message_get_sender(m));
375    fprintf(file, "Class: %s Instance: %s", owl_message_get_class(m), owl_message_get_instance(m));
376    if (strcmp(owl_message_get_opcode(m), "")) fprintf(file, " Opcode: %s", owl_message_get_opcode(m));
377    fprintf(file, "\n");
378    fprintf(file, "Time: %s Host: %s\n", owl_message_get_timestr(m), owl_message_get_hostname(m));
379    ptr=owl_zephyr_get_zsig(owl_message_get_notice(m), &i);
380    buff=owl_malloc(i+10);
381    memcpy(buff, ptr, i);
382    buff[i]='\0';
383    fprintf(file, "From: %s <%s>\n\n", buff, tmp);
384    fprintf(file, "%s\n\n", owl_message_get_body(m));
385    owl_free(tmp);
386  } else if (owl_message_is_type_aim(m) && !owl_message_is_loginout(m)) {
387    fprintf(file, "From: <%s> To: <%s>\n", owl_message_get_sender(m), owl_message_get_recipient(m));
388    fprintf(file, "Time: %s\n\n", owl_message_get_timestr(m));
389    fprintf(file, "%s\n\n", owl_message_get_body(m));
390  } else if (owl_message_is_type_aim(m) && owl_message_is_loginout(m)) {
391    fprintf(file, "From: <%s> To: <%s>\n", owl_message_get_sender(m), owl_message_get_recipient(m));
392    fprintf(file, "Time: %s\n\n", owl_message_get_timestr(m));
393    if (owl_message_is_login(m)) fprintf(file, "LOGIN\n\n");
394    if (owl_message_is_logout(m)) fprintf(file, "LOGOUT\n\n");
395  } else {
396    fprintf(file, "From: <%s> To: <%s>\n", owl_message_get_sender(m), owl_message_get_recipient(m));
397    fprintf(file, "Time: %s\n\n", owl_message_get_timestr(m));
398    fprintf(file, "%s\n\n", owl_message_get_body(m));
399  }
400
401  fclose(file);
402
403  /* if it's a personal message, also write to the 'all' file */
404  if (personal) {
405    if (owl_message_is_type_zephyr(m)) {
406      char *tmp;
407
408      tmp=short_zuser(owl_message_get_sender(m));
409      fprintf(allfile, "Class: %s Instance: %s", owl_message_get_class(m), owl_message_get_instance(m));
410      if (strcmp(owl_message_get_opcode(m), "")) fprintf(allfile, " Opcode: %s", owl_message_get_opcode(m));
411      fprintf(allfile, "\n");
412      fprintf(allfile, "Time: %s Host: %s\n", owl_message_get_timestr(m), owl_message_get_hostname(m));
413      fprintf(allfile, "From: %s <%s>\n\n", buff, tmp);
414      fprintf(allfile, "%s\n\n", owl_message_get_body(m));
415      owl_free(tmp);
416    } else if (owl_message_is_type_aim(m) && !owl_message_is_loginout(m)) {
417      fprintf(allfile, "From: <%s> To: <%s>\n", owl_message_get_sender(m), owl_message_get_recipient(m));
418      fprintf(allfile, "Time: %s\n\n", owl_message_get_timestr(m));
419      fprintf(allfile, "%s\n\n", owl_message_get_body(m));
420    } else if (owl_message_is_type_aim(m) && owl_message_is_loginout(m)) {
421      fprintf(allfile, "From: <%s> To: <%s>\n", owl_message_get_sender(m), owl_message_get_recipient(m));
422      fprintf(allfile, "Time: %s\n\n", owl_message_get_timestr(m));
423      if (owl_message_is_login(m)) fprintf(allfile, "LOGIN\n\n");
424      if (owl_message_is_logout(m)) fprintf(allfile, "LOGOUT\n\n");
425    } else {
426      fprintf(allfile, "From: <%s> To: <%s>\n", owl_message_get_sender(m), owl_message_get_recipient(m));
427      fprintf(allfile, "Time: %s\n\n", owl_message_get_timestr(m));
428      fprintf(allfile, "%s\n\n", owl_message_get_body(m));
429    }
430    fclose(allfile);
431  }
432
433  if (owl_message_is_type_zephyr(m)) {
434    owl_free(buff);
435  }
436  owl_free(frombuff);
437}
Note: See TracBrowser for help on using the repository browser.