1 #include "ipf.h"
2 #include "ipmon.h"
3
4 static void *file_parse(char **);
5 static void file_destroy(void *);
6 static int file_send(void *, ipmon_msg_t *);
7 static void file_print(void *);
8 static int file_match(void *, void *);
9 static void *file_dup(void *);
10
11 typedef struct file_opts_s {
12 FILE *fp;
13 int raw;
14 char *path;
15 int ref;
16 } file_opts_t;
17
18 ipmon_saver_t filesaver = {
19 "file",
20 file_destroy,
21 file_dup,
22 file_match,
23 file_parse,
24 file_print,
25 file_send
26 };
27
28
29 static void *
file_parse(char ** strings)30 file_parse(char **strings)
31 {
32 file_opts_t *ctx;
33
34 ctx = calloc(1, sizeof(*ctx));
35 if (ctx == NULL)
36 return (NULL);
37
38 if (strings[0] != NULL && strings[0][0] != '\0') {
39 ctx->ref = 1;
40 if (!strncmp(strings[0], "raw://", 6)) {
41 ctx->raw = 1;
42 ctx->path = strdup(strings[0] + 6);
43 ctx->fp = fopen(ctx->path, "ab");
44 } else if (!strncmp(strings[0], "file://", 7)) {
45 ctx->path = strdup(strings[0] + 7);
46 ctx->fp = fopen(ctx->path, "a");
47 } else {
48 free(ctx);
49 ctx = NULL;
50 }
51 } else {
52 free(ctx);
53 ctx = NULL;
54 }
55
56 return (ctx);
57 }
58
59
60 static int
file_match(void * ctx1,void * ctx2)61 file_match(void *ctx1, void *ctx2)
62 {
63 file_opts_t *f1 = ctx1, *f2 = ctx2;
64
65 if (f1->raw != f2->raw)
66 return (1);
67 if (strcmp(f1->path, f2->path))
68 return (1);
69 return (0);
70 }
71
72
73 static void *
file_dup(void * ctx)74 file_dup(void *ctx)
75 {
76 file_opts_t *f = ctx;
77
78 f->ref++;
79 return (f);
80 }
81
82
83 static void
file_print(void * ctx)84 file_print(void *ctx)
85 {
86 file_opts_t *file = ctx;
87
88 if (file->raw)
89 printf("raw://");
90 else
91 printf("file://");
92 printf("%s", file->path);
93 }
94
95
96 static void
file_destroy(void * ctx)97 file_destroy(void *ctx)
98 {
99 file_opts_t *file = ctx;
100
101 file->ref--;
102 if (file->ref > 0)
103 return;
104
105 if (file->path != NULL)
106 free(file->path);
107 free(file);
108 }
109
110
111 static int
file_send(void * ctx,ipmon_msg_t * msg)112 file_send(void *ctx, ipmon_msg_t *msg)
113 {
114 file_opts_t *file = ctx;
115
116 if (file->raw) {
117 fwrite(msg->imm_data, msg->imm_dsize, 1, file->fp);
118 } else {
119 fprintf(file->fp, "%s", msg->imm_msg);
120 }
121 return (0);
122 }
123
124