1 /*
2     pmacct (Promiscuous mode IP Accounting package)
3     pmacct is Copyright (C) 2003-2020 by Paolo Lucente
4 */
5 
6 /*
7     This program is free software; you can redistribute it and/or modify
8     it under the terms of the GNU General Public License as published by
9     the Free Software Foundation; either version 2 of the License, or
10     (at your option) any later version.
11 
12     This program is distributed in the hope that it will be useful,
13     but WITHOUT ANY WARRANTY; without even the implied warranty of
14     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15     GNU General Public License for more details.
16 
17     You should have received a copy of the GNU General Public License
18     along with this program; if not, write to the Free Software
19     Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
20 */
21 
22 #ifndef _PMACCT_H_
23 #define _PMACCT_H_
24 
25 /* includes */
26 #ifdef HAVE_PCAP_PCAP_H
27 #include <pcap/pcap.h>
28 #endif
29 #ifdef HAVE_PCAP_H
30 #include <pcap.h>
31 #endif
32 
33 #include <inttypes.h>
34 #include <stdio.h>
35 #include <stdlib.h>
36 #include <unistd.h>
37 #include <stdbool.h>
38 #include <string.h>
39 #include <errno.h>
40 #include <assert.h>
41 
42 #ifdef HAVE_GETOPT_H
43 #include <getopt.h>
44 #endif
45 
46 #if defined HAVE_MALLOPT
47 #include <malloc.h>
48 #endif
49 
50 #include <ctype.h>
51 #include <fcntl.h>
52 #include <sys/ioctl.h>
53 #include <time.h>
54 #include <sys/socket.h>
55 #include <sys/un.h>
56 #include <netinet/in.h>
57 #include <net/if.h>
58 #include <arpa/inet.h>
59 #include <sys/types.h>
60 #include <sys/wait.h>
61 #include <sys/stat.h>
62 #include <sys/select.h>
63 #include <signal.h>
64 #include <syslog.h>
65 #include <sys/resource.h>
66 #include <dirent.h>
67 #include <limits.h>
68 #include <pwd.h>
69 #include <grp.h>
70 #include <dlfcn.h>
71 #include <math.h>
72 #include "pmsearch.h"
73 #include "linklist.h"
74 #include "filters/bloom.h"
75 
76 #include <sys/mman.h>
77 #if !defined (MAP_ANONYMOUS)
78 #if defined (MAP_ANON)
79 #define MAP_ANONYMOUS MAP_ANON
80 #else
81 #define MAP_ANONYMOUS 0
82 #define USE_DEVZERO 1
83 #endif
84 #endif
85 
86 #include "pmacct-defines.h"
87 
88 #if defined (WITH_GEOIP)
89 #include <GeoIP.h>
90 #if defined (WITH_GEOIPV2)
91 #error "--enable-geoip and --enable-geoipv2 are mutually exclusive"
92 #endif
93 #endif
94 #if defined (WITH_GEOIPV2)
95 #include <maxminddb.h>
96 #endif
97 
98 #if defined (WITH_NDPI)
99 /* NDPI_LIB_COMPILATION definition appears to be new in 2.5 */
100 #ifndef NDPI_LIB_COMPILATION
101 #define NDPI_LIB_COMPILATION
102 #endif
103 #include <ndpi_main.h>
104 #undef NDPI_LIB_COMPILATION
105 #endif
106 
107 #include "pmacct-build.h"
108 
109 #if !defined ETHER_ADDRSTRLEN
110 #define ETHER_ADDRSTRLEN 18
111 #endif
112 #if !defined INET_ADDRSTRLEN
113 #define INET_ADDRSTRLEN 16
114 #endif
115 #if !defined INET6_ADDRSTRLEN
116 #define INET6_ADDRSTRLEN 46
117 #endif
118 
119 #if (defined SOLARIS) && (defined CPU_sparc)
120 #define htons(x) (x)
121 #define htonl(x) (x)
122 #endif
123 
124 #if (!defined HAVE_U_INT8_T) && (defined HAVE_UINT8_T)
125 #define u_int8_t uint8_t
126 #endif
127 #if (!defined HAVE_U_INT16_T) && (defined HAVE_UINT16_T)
128 #define u_int16_t uint16_t
129 #endif
130 #if (!defined HAVE_U_INT32_T) && (defined HAVE_UINT32_T)
131 #define u_int32_t uint32_t
132 #endif
133 #if (!defined HAVE_U_INT64_T) && (defined HAVE_UINT64_T)
134 #define u_int64_t uint64_t
135 #endif
136 
137 #define MOREBUFSZ 32
138 
139 #ifndef LOCK_UN
140 #define LOCK_UN 8
141 #endif
142 
143 #ifndef LOCK_EX
144 #define LOCK_EX 2
145 #endif
146 
147 #ifdef NOINLINE
148 #define Inline
149 #else
150 #define Inline static inline
151 #endif
152 
153 /* Let work the unaligned copy macros the hard way: byte-per byte copy via
154    u_char pointers. We discard the packed attribute way because it fits just
155    to GNU compiler */
156 #if !defined NEED_ALIGN
157 #define Assign8(a, b) a = b
158 #else
159 #define Assign8(a, b)		\
160 {             			\
161   u_char *ptr = (u_char *)&a;	\
162   *ptr = b;			\
163 }
164 #endif
165 
166 #if !defined NEED_ALIGN
167 #define Assign16(a, b) a = b
168 #else
169 #define Assign16(a, b)		\
170 {      				\
171   u_int16_t c = b;		\
172   u_char *dst = (u_char *)&a;	\
173   u_char *src = (u_char *)&c;	\
174   *(dst + 0) = *(src + 0);	\
175   *(dst + 1) = *(src + 1);	\
176 }
177 #endif
178 
179 #if !defined NEED_ALIGN
180 #define Assign32(a, b) a = b
181 #else
182 #define Assign32(a, b)		\
183 {             			\
184   u_int32_t c = b;		\
185   u_char *dst = (u_char *)&a;	\
186   u_char *src = (u_char *)&c;	\
187   *(dst + 0) = *(src + 0);	\
188   *(dst + 1) = *(src + 1);	\
189   *(dst + 2) = *(src + 2);	\
190   *(dst + 3) = *(src + 3);	\
191 }
192 #endif
193 
194 /* structure to pass requests: probably plugin_requests
195    name outdated at this point .. */
196 
197 struct ptm_complex {
198   int load_ptm_plugin;		/* load_pre_tag_map(): input plugin type ID */
199   int load_ptm_res;		/* load_pre_tag_map(): result */
200   int exec_ptm_dissect;		/* exec_plugins(): TRUE if at least one plugin returned load_ptm_res == TRUE */
201   int exec_ptm_res;		/* exec_plugins(): input to be matched against list->cfg.ptm_complex */
202 };
203 
204 struct plugin_requests {
205   u_int8_t bpf_filter;		/* On-request packet copy for BPF purposes */
206 
207   /* load_id_file() stuff */
208   void *key_value_table;	/* table to be filled in from key-value files */
209   int line_num;			/* line number being processed */
210   int map_entries;		/* number of map entries: wins over global setting */
211   int map_row_len;		/* map row length: wins over global setting */
212   struct ptm_complex ptm_c;	/* flags a map that requires parsing of the records (ie. tee plugin) */
213 };
214 
215 typedef struct {
216   u_char *val;
217   u_int16_t len;
218 } pm_hash_key_t;
219 
220 typedef struct {
221   pm_hash_key_t key;
222   u_int16_t off;
223 } pm_hash_serial_t;
224 
225 #if (defined WITH_JANSSON)
226 #include <jansson.h>
227 #endif
228 
229 #if (defined WITH_AVRO)
230 #include <avro.h>
231 #endif
232 
233 #if (defined WITH_SERDES)
234 #if (!defined WITH_AVRO)
235 #error "--enable-serdes requires --enable-avro"
236 #endif
237 #endif
238 
239 #ifdef WITH_REDIS
240 #include "redis_common.h"
241 #endif
242 
243 #include "network.h"
244 #include "pretag.h"
245 #include "cfg.h"
246 #include "xflow_status.h"
247 #include "log.h"
248 #include "once.h"
249 #include "mpls.h"
250 
251 /*
252  * htonvl(): host to network (byte ordering) variable length
253  * ntohvl(): network to host (byer ordering) variable length
254  */
255 #define htonvl(x) pm_htonll(x)
256 #define ntohvl(x) pm_ntohll(x)
257 #define CACHE_THRESHOLD UINT64T_THRESHOLD
258 
259 /* structures */
260 struct pm_pcap_interface {
261   u_int32_t ifindex;
262   char ifname[IFNAMSIZ];
263   int direction;
264 };
265 
266 struct pm_pcap_interfaces {
267   struct pm_pcap_interface *list;
268   int num;
269 };
270 
271 struct pm_pcap_device {
272   char str[IFNAMSIZ];
273   u_int32_t id;
274   pcap_t *dev_desc;
275   int link_type;
276   int active;
277   int errors; /* error count when reading from a savefile */
278   int fd;
279   struct _devices_struct *data;
280   struct pm_pcap_interface *pcap_if;
281 };
282 
283 struct pm_pcap_devices {
284   struct pm_pcap_device list[PCAP_MAX_INTERFACES];
285   int num;
286 };
287 
288 struct pm_pcap_callback_signals {
289   int is_set;
290   sigset_t set;
291 };
292 
293 struct pm_pcap_callback_data {
294   u_char * f_agent;
295   u_char * bta_table;
296   u_char * bpas_table;
297   u_char * blp_table;
298   u_char * bmed_table;
299   u_char * biss_table;
300   struct pm_pcap_device *device;
301   u_int32_t ifindex_in;
302   u_int32_t ifindex_out;
303   u_int8_t has_tun_prims;
304   struct pm_pcap_callback_signals sig;
305 };
306 
307 struct _protocols_struct {
308   char name[PROTO_LEN];
309   int number;
310 };
311 
312 struct _devices_struct {
313   void (*handler)(const struct pcap_pkthdr *, register struct packet_ptrs *);
314   int link_type;
315 };
316 
317 struct _primitives_matrix_struct {
318   char name[PRIMITIVE_LEN];
319   u_int8_t pmacctd;
320   u_int8_t uacctd;
321   u_int8_t nfacctd;
322   u_int8_t sfacctd;
323   u_int8_t pmtelemetryd;
324   u_int8_t pmbgpd;
325   u_int8_t pmbmpd;
326   char desc[PRIMITIVE_DESC_LEN];
327 };
328 
329 struct largebuf {
330   u_char base[LARGEBUFLEN];
331   u_char *end;
332   u_char *ptr;
333 };
334 
335 struct largebuf_s {
336   char base[LARGEBUFLEN];
337   char *end;
338   char *ptr;
339 };
340 
341 struct child_ctl2 {
342   pid_t *list;
343   u_int16_t active;
344   u_int16_t max;
345   u_int32_t flags;
346 };
347 
348 #define INIT_BUF(x) \
349 	memset(x.base, 0, sizeof(x.base)); \
350 	x.end = x.base+sizeof(x.base); \
351 	x.ptr = x.base;
352 
353 #include "util.h"
354 
355 /* prototypes */
356 void startup_handle_falling_child();
357 void handle_falling_child();
358 void ignore_falling_child();
359 void PM_sigint_handler(int);
360 void PM_sigalrm_noop_handler(int);
361 void reload();
362 void push_stats();
363 void reload_maps();
364 extern void pm_pcap_device_initialize(struct pm_pcap_devices *);
365 extern void pm_pcap_device_copy_all(struct pm_pcap_devices *, struct pm_pcap_devices *);
366 extern void pm_pcap_device_copy_entry(struct pm_pcap_devices *, struct pm_pcap_devices *, int);
367 extern int pm_pcap_device_getindex_byifname(struct pm_pcap_devices *, char *);
368 extern pcap_t *pm_pcap_open(const char *, int, int, int, int, int, char *);
369 extern void pm_pcap_add_filter(struct pm_pcap_device *);
370 extern int pm_pcap_add_interface(struct pm_pcap_device *, char *, struct pm_pcap_interface *, int);
371 
372 extern void null_handler(const struct pcap_pkthdr *, register struct packet_ptrs *);
373 extern void eth_handler(const struct pcap_pkthdr *, register struct packet_ptrs *);
374 extern void fddi_handler(const struct pcap_pkthdr *, register struct packet_ptrs *);
375 extern void tr_handler(const struct pcap_pkthdr *, register struct packet_ptrs *);
376 extern u_int16_t mpls_handler(u_char *, u_int16_t *, u_int16_t *, register struct packet_ptrs *);
377 extern void ppp_handler(const struct pcap_pkthdr *, register struct packet_ptrs *);
378 extern void ieee_802_11_handler(const struct pcap_pkthdr *, register struct packet_ptrs *);
379 extern void sll_handler(const struct pcap_pkthdr *, register struct packet_ptrs *);
380 extern void raw_handler(const struct pcap_pkthdr *, register struct packet_ptrs *);
381 extern u_char *llc_handler(const struct pcap_pkthdr *, u_int, register u_char *, register struct packet_ptrs *);
382 extern void chdlc_handler(const struct pcap_pkthdr *, register struct packet_ptrs *);
383 
384 extern int ip_handler(register struct packet_ptrs *);
385 extern int ip6_handler(register struct packet_ptrs *);
386 extern int gtp_tunnel_func(register struct packet_ptrs *);
387 extern int gtp_tunnel_configurator(struct tunnel_handler *, char *);
388 extern void tunnel_registry_init();
389 extern void pm_pcap_cb(u_char *, const struct pcap_pkthdr *, const u_char *);
390 extern int PM_find_id(struct id_table *, struct packet_ptrs *, pm_id_t *, pm_id_t *);
391 extern void PM_print_stats(time_t);
392 extern void compute_once();
393 extern void reset_index_pkt_ptrs(struct packet_ptrs *);
394 extern void set_index_pkt_ptrs(struct packet_ptrs *);
395 extern ssize_t recvfrom_savefile(struct pm_pcap_device *, void **, struct sockaddr *, struct timeval **, int *, struct packet_ptrs *);
396 extern ssize_t recvfrom_rawip(unsigned char *, size_t, struct sockaddr *, struct packet_ptrs *);
397 
398 #ifndef HAVE_STRLCPY
399 size_t strlcpy(char *, const char *, size_t);
400 #endif
401 
402 void
403 #ifdef __STDC__
404 pm_setproctitle(const char *fmt, ...);
405 #else /* __STDC__ */
406 #error
407 pm_setproctitle(fmt, va_alist);
408 #endif /* __STDC__ */
409 
410 void
411 initsetproctitle(int, char**, char**);
412 
413 /* global variables */
414 extern char sll_mac[2][ETH_ADDR_LEN];
415 extern struct host_addr mcast_groups[MAX_MCAST_GROUPS];
416 extern int reload_map, reload_map_exec_plugins, reload_geoipv2_file;
417 extern int reload_map_bgp_thread, reload_log, reload_log_bgp_thread;
418 extern int reload_map_bmp_thread, reload_log_bmp_thread;
419 extern int reload_map_rpki_thread, reload_log_rpki_thread;
420 extern int reload_map_telemetry_thread, reload_log_telemetry_thread;
421 extern int reload_map_pmacctd;
422 extern int print_stats;
423 extern int reload_log_sf_cnt;
424 extern int data_plugins, tee_plugins;
425 extern int collector_port;
426 extern struct timeval reload_map_tstamp;
427 extern struct child_ctl2 dump_writers;
428 extern int debug;
429 extern struct configuration config; /* global configuration structure */
430 extern struct plugins_list_entry *plugins_list; /* linked list of each plugin configuration */
431 extern pid_t failed_plugins[MAX_N_PLUGINS]; /* plugins failed during startup phase */
432 extern u_char dummy_tlhdr[16], empty_mem_area_256b[SRVBUFLEN];
433 extern struct pm_pcap_device device;
434 extern struct pm_pcap_devices devices, bkp_devices;
435 extern struct pm_pcap_interfaces pm_pcap_if_map, pm_bkp_pcap_if_map;
436 extern struct pcap_stat ps;
437 extern struct sigaction sighandler_action;
438 #endif /* _PMACCT_H_ */
439