suricata
util-host-os-info.c
Go to the documentation of this file.
1 /* Copyright (C) 2007-2010 Open Information Security Foundation
2  *
3  * You can copy, redistribute or modify this Program under the terms of
4  * the GNU General Public License version 2 as published by the Free
5  * Software Foundation.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * version 2 along with this program; if not, write to the Free Software
14  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
15  * 02110-1301, USA.
16  */
17 
18 /**
19  * \file
20  *
21  * \author Anoop Saldanha <anoopsaldanha@gmail.com>
22  *
23  * Host info utility functions
24  */
25 
26 #include "suricata-common.h"
27 #include "util-host-os-info.h"
28 #include "util-error.h"
29 #include "util-debug.h"
30 #include "util-ip.h"
31 #include "util-radix-tree.h"
32 #include "stream-tcp-private.h"
33 #include "stream-tcp-reassemble.h"
34 
35 #include "conf.h"
36 #include "conf-yaml-loader.h"
37 
38 #include "util-enum.h"
39 #include "util-unittest.h"
40 
41 /** Enum map for the various OS flavours */
43  { "none", OS_POLICY_NONE },
44  { "bsd", OS_POLICY_BSD },
45  { "bsd-right", OS_POLICY_BSD_RIGHT },
46  { "old-linux", OS_POLICY_OLD_LINUX },
47  { "linux", OS_POLICY_LINUX },
48  { "old-solaris", OS_POLICY_OLD_SOLARIS },
49  { "solaris", OS_POLICY_SOLARIS },
50  { "hpux10", OS_POLICY_HPUX10 },
51  { "hpux11", OS_POLICY_HPUX11 },
52  { "irix", OS_POLICY_IRIX },
53  { "macos", OS_POLICY_MACOS },
54  { "windows", OS_POLICY_WINDOWS },
55  { "vista", OS_POLICY_VISTA },
56  { "windows2k3", OS_POLICY_WINDOWS2K3 },
57  { NULL, -1 },
58 };
59 
60 /** Radix tree that holds the host OS information */
61 static SCRadixTree *sc_hinfo_tree = NULL;
62 
63 
64 /**
65  * \brief Allocates the host_os flavour wrapped in user_data variable to be sent
66  * along with the key to the radix tree
67  *
68  * \param host_os Pointer to a character string containing the host_os flavour
69  *
70  * \retval user_data On success, pointer to the user_data that has to be sent
71  * along with the key, to be added to the Radix tree; NULL on
72  * failure
73  * \initonly
74  */
75 static void *SCHInfoAllocUserDataOSPolicy(const char *host_os)
76 {
77  int *user_data = NULL;
78 
79  if ( (user_data = SCMalloc(sizeof(int))) == NULL) {
80  SCLogError(SC_ERR_FATAL, "Error allocating memory. Exiting");
81  exit(EXIT_FAILURE);
82  }
83 
84  /* the host os flavour that has to be sent as user data */
85  if ( (*user_data = SCMapEnumNameToValue(host_os, sc_hinfo_os_policy_map)) == -1) {
86  SCLogError(SC_ERR_INVALID_ENUM_MAP, "Invalid enum map inside "
87  "SCHInfoAddHostOSInfo()");
88  SCFree(user_data);
89  return NULL;
90  }
91 
92  return (void *)user_data;
93 }
94 
95 /**
96  * \brief Used to free the user data that is allocated by host_os_info API
97  *
98  * \param Pointer to the data that has to be freed
99  */
100 static void SCHInfoFreeUserDataOSPolicy(void *data)
101 {
102  if (data != NULL)
103  SCFree(data);
104 
105  return;
106 }
107 
108 /**
109  * \brief Used to add the host-os-info data obtained from the conf
110  *
111  * \param host_os The host_os name/flavour from the conf file
112  * \param host_os_ip_range Pointer to a char string holding the ip/ip_netblock
113  * for the host_os specified in the first argument
114  * \param is_ipv4 Indicates if the ip address to be considered for the
115  * default configuration is IPV4; if not it is IPV6.
116  * Specified using SC_HINFO_IS_IPV6 or SC_HINFO_IS_IPV4
117  *
118  * \retval 0 On successfully adding the host os info to the Radix tree
119  * \retval -1 On failure
120  * \initonly (only specified from config, at the startup)
121  */
122 int SCHInfoAddHostOSInfo(const char *host_os, const char *host_os_ip_range, int is_ipv4)
123 {
124  char *ip_str = NULL;
125  char *ip_str_rem = NULL;
126  struct in_addr *ipv4_addr = NULL;
127  struct in6_addr *ipv6_addr = NULL;
128  char *netmask_str = NULL;
129  int netmask_value = 0;
130  int *user_data = NULL;
131  char recursive = FALSE;
132 
133  if (host_os == NULL || host_os_ip_range == NULL ||
134  strlen(host_os_ip_range) == 0) {
135  SCLogError(SC_ERR_INVALID_ARGUMENT, "Invalid arguments");
136  return -1;
137  }
138 
139  /* create the radix tree that would hold all the host os info */
140  if (sc_hinfo_tree == NULL)
141  sc_hinfo_tree = SCRadixCreateRadixTree(SCHInfoFreeUserDataOSPolicy, NULL);
142 
143  /* the host os flavour that has to be sent as user data */
144  if ( (user_data = SCHInfoAllocUserDataOSPolicy(host_os)) == NULL) {
145  SCLogError(SC_ERR_INVALID_ENUM_MAP, "Invalid enum map inside");
146  return -1;
147  }
148 
149  /* if we have a default configuration set the appropriate values for the
150  * netblocks */
151  if ( (strcasecmp(host_os_ip_range, "default")) == 0) {
152  if (is_ipv4)
153  host_os_ip_range = "0.0.0.0/0";
154  else
155  host_os_ip_range = "::/0";
156  }
157 
158  if ( (ip_str = SCStrdup(host_os_ip_range)) == NULL) {
159  SCLogError(SC_ERR_MEM_ALLOC, "Error allocating memory");
160  exit(EXIT_FAILURE);
161  }
162 
163  /* check if we have more addresses in the host_os_ip_range */
164  if ((ip_str_rem = strchr(ip_str, ',')) != NULL) {
165  ip_str_rem[0] = '\0';
166  ip_str_rem++;
167  recursive = TRUE;
168  }
169 
170  /* check if we have received a netblock */
171  if ( (netmask_str = strchr(ip_str, '/')) != NULL) {
172  netmask_str[0] = '\0';
173  netmask_str++;
174  }
175 
176  if (strchr(ip_str, ':') == NULL) {
177  /* if we are here, we have an IPV4 address */
178  if ( (ipv4_addr = ValidateIPV4Address(ip_str)) == NULL) {
179  SCLogError(SC_ERR_INVALID_IPV4_ADDR, "Invalid IPV4 address");
180  SCHInfoFreeUserDataOSPolicy(user_data);
181  SCFree(ip_str);
182  return -1;
183  }
184 
185  if (netmask_str == NULL) {
186  SCRadixAddKeyIPV4((uint8_t *)ipv4_addr, sc_hinfo_tree,
187  (void *)user_data);
188  } else {
189  netmask_value = atoi(netmask_str);
190  if (netmask_value < 0 || netmask_value > 32) {
191  SCLogError(SC_ERR_INVALID_IP_NETBLOCK, "Invalid IPV4 Netblock");
192  SCHInfoFreeUserDataOSPolicy(user_data);
193  SCFree(ipv4_addr);
194  SCFree(ip_str);
195  return -1;
196  }
197 
198  MaskIPNetblock((uint8_t *)ipv4_addr, netmask_value, 32);
199  SCRadixAddKeyIPV4Netblock((uint8_t *)ipv4_addr, sc_hinfo_tree,
200  (void *)user_data, netmask_value);
201  }
202  } else {
203  /* if we are here, we have an IPV6 address */
204  if ( (ipv6_addr = ValidateIPV6Address(ip_str)) == NULL) {
205  SCLogError(SC_ERR_INVALID_IPV6_ADDR, "Invalid IPV6 address inside");
206  SCHInfoFreeUserDataOSPolicy(user_data);
207  SCFree(ip_str);
208  return -1;
209  }
210 
211  if (netmask_str == NULL) {
212  SCRadixAddKeyIPV6((uint8_t *)ipv6_addr, sc_hinfo_tree,
213  (void *)user_data);
214  } else {
215  netmask_value = atoi(netmask_str);
216  if (netmask_value < 0 || netmask_value > 128) {
217  SCLogError(SC_ERR_INVALID_IP_NETBLOCK, "Invalid IPV6 Netblock");
218  SCHInfoFreeUserDataOSPolicy(user_data);
219  SCFree(ipv6_addr);
220  SCFree(ip_str);
221  return -1;
222  }
223 
224  MaskIPNetblock((uint8_t *)ipv6_addr, netmask_value, 128);
225  SCRadixAddKeyIPV6Netblock((uint8_t *)ipv6_addr, sc_hinfo_tree,
226  (void *)user_data, netmask_value);
227  }
228  }
229 
230  if (recursive == TRUE) {
231  SCHInfoAddHostOSInfo(host_os, ip_str_rem, is_ipv4);
232  }
233 
234  SCFree(ip_str);
235  if (ipv4_addr != NULL)
236  SCFree(ipv4_addr);
237  if (ipv6_addr != NULL)
238  SCFree(ipv6_addr);
239  return *user_data;
240 }
241 
242 /**
243  * \brief Retrieves the host os flavour, given an ipv4/ipv6 address as a string.
244  *
245  * \param Pointer to a string containing an IP address
246  *
247  * \retval The OS flavour on success; -1 on failure, or on not finding the key
248  */
249 int SCHInfoGetHostOSFlavour(const char *ip_addr_str)
250 {
251  struct in_addr *ipv4_addr = NULL;
252  struct in6_addr *ipv6_addr = NULL;
253  void *user_data = NULL;
254 
255  if (ip_addr_str == NULL || strchr(ip_addr_str, '/') != NULL)
256  return -1;
257 
258  if (strchr(ip_addr_str, ':') != NULL) {
259  if ( (ipv6_addr = ValidateIPV6Address(ip_addr_str)) == NULL) {
260  SCLogError(SC_ERR_INVALID_IPV4_ADDR, "Invalid IPV4 address");
261  return -1;
262  }
263 
264  (void)SCRadixFindKeyIPV6BestMatch((uint8_t *)ipv6_addr, sc_hinfo_tree, &user_data);
265  SCFree(ipv6_addr);
266  if (user_data == NULL)
267  return -1;
268  else
269  return *((int *)user_data);
270  } else {
271  if ( (ipv4_addr = ValidateIPV4Address(ip_addr_str)) == NULL) {
272  SCLogError(SC_ERR_INVALID_IPV4_ADDR, "Invalid IPV4 address");
273  return -1;
274  }
275 
276  (void)SCRadixFindKeyIPV4BestMatch((uint8_t *)ipv4_addr, sc_hinfo_tree, &user_data);
277  SCFree(ipv4_addr);
278  if (user_data == NULL)
279  return -1;
280  else
281  return *((int *)user_data);
282  }
283 }
284 
285 /**
286  * \brief Retrieves the host os flavour, given an ipv4 address in the raw
287  * address format.
288  *
289  * \param Pointer to a raw ipv4 address.
290  *
291  * \retval The OS flavour on success; -1 on failure, or on not finding the key
292  */
293 int SCHInfoGetIPv4HostOSFlavour(uint8_t *ipv4_addr)
294 {
295  void *user_data = NULL;
296  (void)SCRadixFindKeyIPV4BestMatch(ipv4_addr, sc_hinfo_tree, &user_data);
297  if (user_data == NULL)
298  return -1;
299  else
300  return *((int *)user_data);
301 }
302 
303 /**
304  * \brief Retrieves the host os flavour, given an ipv6 address in the raw
305  * address format.
306  *
307  * \param Pointer to a raw ipv6 address.
308  *
309  * \retval The OS flavour on success; -1 on failure, or on not finding the key
310  */
311 int SCHInfoGetIPv6HostOSFlavour(uint8_t *ipv6_addr)
312 {
313  void *user_data = NULL;
314  (void)SCRadixFindKeyIPV6BestMatch(ipv6_addr, sc_hinfo_tree, &user_data);
315  if (user_data == NULL)
316  return -1;
317  else
318  return *((int *)user_data);
319 }
320 
322 {
323  if (sc_hinfo_tree != NULL) {
324  SCRadixReleaseRadixTree(sc_hinfo_tree);
325  sc_hinfo_tree = NULL;
326  }
327 
328  return;
329 }
330 
331 /**
332  * \brief Load the host os policy information from the configuration.
333  *
334  * \initonly (A mem alloc error should cause an exit failure)
335  */
337 {
338  ConfNode *root = ConfGetNode("host-os-policy");
339  if (root == NULL)
340  return;
341 
342  ConfNode *policy;
343  TAILQ_FOREACH(policy, &root->head, next) {
344  ConfNode *host;
345  TAILQ_FOREACH(host, &policy->head, next) {
346  int is_ipv4 = 1;
347  if (host->val != NULL && strchr(host->val, ':') != NULL)
348  is_ipv4 = 0;
349  if (SCHInfoAddHostOSInfo(policy->name, host->val, is_ipv4) == -1) {
351  "Failed to add host \"%s\" with policy \"%s\" to host "
352  "info database", host->val, policy->name);
353  exit(EXIT_FAILURE);
354  }
355  }
356  }
357 }
358 
359 /*------------------------------------Unit_Tests------------------------------*/
360 
361 #ifdef UNITTESTS
362 static SCRadixTree *sc_hinfo_tree_backup = NULL;
363 
364 static void SCHInfoCreateContextBackup(void)
365 {
366  sc_hinfo_tree_backup = sc_hinfo_tree;
367  sc_hinfo_tree = NULL;
368 
369  return;
370 }
371 
372 static void SCHInfoRestoreContextBackup(void)
373 {
374  sc_hinfo_tree = sc_hinfo_tree_backup;
375  sc_hinfo_tree_backup = NULL;
376 
377  return;
378 }
379 
380 /**
381  * \test Check if we the IPs with the right OS flavours are added to the host OS
382  * radix tree, and the IPS with invalid flavours returns an error(-1)
383  */
384 static int SCHInfoTestInvalidOSFlavour01(void)
385 {
386  SCHInfoCreateContextBackup();
387 
388  int result = 0;
389 
390  if (SCHInfoAddHostOSInfo("bamboo", "192.168.1.1", SC_HINFO_IS_IPV4) != -1) {
391  goto end;
392  }
393  if (SCHInfoAddHostOSInfo("linux", "192.168.1.1", SC_HINFO_IS_IPV4) !=
394  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
395  goto end;
396  }
397  if (SCHInfoAddHostOSInfo("windows", "192.168.1.1", SC_HINFO_IS_IPV4) !=
398  SCMapEnumNameToValue("windows", sc_hinfo_os_policy_map)) {
399  goto end;
400  }
401  if (SCHInfoAddHostOSInfo("solaris", "192.168.1.1", SC_HINFO_IS_IPV4) !=
402  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
403  goto end;
404  }
405  if (SCHInfoAddHostOSInfo("hpux10", "192.168.1.1", SC_HINFO_IS_IPV4) !=
406  SCMapEnumNameToValue("hpux10", sc_hinfo_os_policy_map)) {
407  goto end;
408  }
409  if (SCHInfoAddHostOSInfo("hpux11", "192.168.1.1", SC_HINFO_IS_IPV4) !=
410  SCMapEnumNameToValue("hpux11", sc_hinfo_os_policy_map)) {
411  goto end;
412  }
413  if (SCHInfoAddHostOSInfo("irix", "192.168.1.1", SC_HINFO_IS_IPV4) !=
414  SCMapEnumNameToValue("irix", sc_hinfo_os_policy_map)) {
415  goto end;
416  }
417  if (SCHInfoAddHostOSInfo("bsd", "192.168.1.1", SC_HINFO_IS_IPV4) !=
418  SCMapEnumNameToValue("bsd", sc_hinfo_os_policy_map)) {
419  goto end;
420  }
421  if (SCHInfoAddHostOSInfo("old_linux", "192.168.1.1", SC_HINFO_IS_IPV4) !=
422  SCMapEnumNameToValue("old_linux", sc_hinfo_os_policy_map)) {
423  goto end;
424  }
425  if (SCHInfoAddHostOSInfo("macos", "192.168.1.1", SC_HINFO_IS_IPV4) !=
426  SCMapEnumNameToValue("macos", sc_hinfo_os_policy_map)) {
427  goto end;
428  }
429  if (SCHInfoAddHostOSInfo("vista", "192.168.1.1", SC_HINFO_IS_IPV4) !=
430  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
431  goto end;
432  }
433  if (SCHInfoAddHostOSInfo("windows2k3", "192.168.1.1", SC_HINFO_IS_IPV4) !=
434  SCMapEnumNameToValue("windows2k3", sc_hinfo_os_policy_map)) {
435  goto end;
436  }
437 
438  result = 1;
439 
440  end:
442  SCHInfoRestoreContextBackup();
443 
444  return result;
445 }
446 
447 /**
448  * \test Check that invalid ipv4 addresses and ipv4 netblocks are rejected by
449  * the host os info API
450  */
451 static int SCHInfoTestInvalidIPV4Address02(void)
452 {
453  SCHInfoCreateContextBackup();
454 
455  int result = 0;
456 
457  if (SCHInfoAddHostOSInfo("linux", "192.168.1.566", SC_HINFO_IS_IPV4) != -1) {
458  goto end;
459  }
460  if (SCHInfoAddHostOSInfo("linux", "192.168.1", SC_HINFO_IS_IPV4) != -1) {
461  goto end;
462  }
463  if (SCHInfoAddHostOSInfo("linux", "192.", SC_HINFO_IS_IPV4) != -1) {
464  goto end;
465  }
466  if (SCHInfoAddHostOSInfo("linux", "192.168", SC_HINFO_IS_IPV4) != -1) {
467  goto end;
468  }
469  if (SCHInfoAddHostOSInfo("linux", "", SC_HINFO_IS_IPV4) != -1) {
470  goto end;
471  }
472  if (SCHInfoAddHostOSInfo("linux", "192.168.1.1/33", SC_HINFO_IS_IPV4) != -1) {
473  goto end;
474  }
475 
476  result = 1;
477 
478  end:
480  SCHInfoRestoreContextBackup();
481 
482  return result;
483 }
484 
485 /**
486  * \test Check that invalid ipv4 addresses and ipv4 netblocks are rejected by
487  * the host os info API
488  */
489 static int SCHInfoTestInvalidIPV6Address03(void)
490 {
491  SCHInfoCreateContextBackup();
492 
493  int result = 0;
494 
495  if (SCHInfoAddHostOSInfo("linux", "2362:7322", SC_HINFO_IS_IPV6) != -1) {
496  goto end;
497  }
498  if (SCHInfoAddHostOSInfo("linux", "19YW:", SC_HINFO_IS_IPV6) != -1) {
499  goto end;
500  }
501  if (SCHInfoAddHostOSInfo("linux", "1235", SC_HINFO_IS_IPV6) != -1) {
502  goto end;
503  }
504  if (SCHInfoAddHostOSInfo("linux", "1922:236115:", SC_HINFO_IS_IPV6) != -1) {
505  goto end;
506  }
507  if (SCHInfoAddHostOSInfo("linux", "", SC_HINFO_IS_IPV6) != -1) {
508  goto end;
509  }
510  if (SCHInfoAddHostOSInfo("linux",
511  "1921.6311:6241:6422:7352:ABBB:DDDD:EEEE/129",
512  SC_HINFO_IS_IPV6) != -1) {
513  goto end;
514  }
515 
516  result = 1;
517 
518  end:
520  SCHInfoRestoreContextBackup();
521 
522  return result;
523 }
524 
525 /**
526  * \test Check that valid ipv4 addresses are inserted into the host os radix
527  * tree, and the host os api retrieves the right value for the host os
528  * flavour, on supplying as arg an ipv4 addresses that has been added to
529  * the host os radix tree.
530  */
531 static int SCHInfoTestValidIPV4Address04(void)
532 {
533  SCHInfoCreateContextBackup();
534 
535  int result = 0;
536 
537  if (SCHInfoAddHostOSInfo("linux", "192.168.1.1", SC_HINFO_IS_IPV4) == -1) {
538  goto end;
539  }
540  if (SCHInfoAddHostOSInfo("windows", "192.192.1.2", SC_HINFO_IS_IPV4) == -1) {
541  goto end;
542  }
543  if (SCHInfoAddHostOSInfo("solaris", "192.168.1.100", SC_HINFO_IS_IPV4) == -1) {
544  goto end;
545  }
546  if (SCHInfoAddHostOSInfo("hpux10", "192.168.2.4", SC_HINFO_IS_IPV4) == -1) {
547  goto end;
548  }
549  if (SCHInfoAddHostOSInfo("linux", "192.192.1.5", SC_HINFO_IS_IPV4) == -1) {
550  goto end;
551  }
552  if (SCHInfoAddHostOSInfo("vista", "192.168.10.20", SC_HINFO_IS_IPV4) == -1) {
553  goto end;
554  }
555  if (SCHInfoAddHostOSInfo("solaris", "111.163.151.62", SC_HINFO_IS_IPV4) == -1) {
556  goto end;
557  }
558  if (SCHInfoAddHostOSInfo("solaris", "11.1.120.210", SC_HINFO_IS_IPV4) == -1) {
559  goto end;
560  }
561  if (SCHInfoAddHostOSInfo("linux", "19.18.110.210", SC_HINFO_IS_IPV4) == -1) {
562  goto end;
563  }
564  if (SCHInfoAddHostOSInfo("windows", "19.18.120.110", SC_HINFO_IS_IPV4) == -1) {
565  goto end;
566  }
567  if (SCHInfoAddHostOSInfo("hpux11", "191.168.11.128", SC_HINFO_IS_IPV4) == -1) {
568  goto end;
569  }
570  if (SCHInfoAddHostOSInfo("vista", "191.168.11.192", SC_HINFO_IS_IPV4) == -1) {
571  goto end;
572  }
573 
574  if (SCHInfoGetHostOSFlavour("192.168.1.1") !=
575  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
576  goto end;
577  }
578  if (SCHInfoGetHostOSFlavour("192.168.1.2") != -1) {
579  goto end;
580  }
581  if (SCHInfoGetHostOSFlavour("192.168.1.100") !=
582  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
583  goto end;
584  }
585  if (SCHInfoGetHostOSFlavour("192.192.2.4") != -1) {
586  goto end;
587  }
588  if (SCHInfoGetHostOSFlavour("192.168.2.4") !=
589  SCMapEnumNameToValue("hpux10", sc_hinfo_os_policy_map)) {
590  goto end;
591  }
592  if (SCHInfoGetHostOSFlavour("192.192.1.5") !=
593  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
594  goto end;
595  }
596  if (SCHInfoGetHostOSFlavour("192.168.10.20") !=
597  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
598  goto end;
599  }
600  if (SCHInfoGetHostOSFlavour("111.163.151.62") !=
601  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
602  goto end;
603  }
604  if (SCHInfoGetHostOSFlavour("11.1.120.210") !=
605  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
606  goto end;
607  }
608  if (SCHInfoGetHostOSFlavour("19.18.110.210") !=
609  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
610  goto end;
611  }
612  if (SCHInfoGetHostOSFlavour("19.18.120.110") !=
613  SCMapEnumNameToValue("windows", sc_hinfo_os_policy_map)) {
614  goto end;
615  }
616  if (SCHInfoGetHostOSFlavour("191.168.11.128") !=
617  SCMapEnumNameToValue("hpux11", sc_hinfo_os_policy_map)) {
618  goto end;
619  }
620  if (SCHInfoGetHostOSFlavour("191.168.11.192") !=
621  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
622  goto end;
623  }
624  if (SCHInfoGetHostOSFlavour("191.168.11.224") != -1) {
625  goto end;
626  }
627 
628  result = 1;
629 
630  end:
632  SCHInfoRestoreContextBackup();
633 
634  return result;
635 }
636 
637 /**
638  * \test Check that valid ipv4 addresses/netblocks are inserted into the host os
639  * radix tree, and the host os api retrieves the right value for the host
640  * os flavour, on supplying as arg an ipv4 addresses that has been added
641  * to the host os radix tree.
642  */
643 static int SCHInfoTestValidIPV4Address05(void)
644 {
645  SCHInfoCreateContextBackup();
646 
647  struct in_addr in;
648  int result = 0;
649 
650  if (SCHInfoAddHostOSInfo("linux", "192.168.1.1", SC_HINFO_IS_IPV4) == -1) {
651  goto end;
652  }
653  if (SCHInfoAddHostOSInfo("windows", "192.192.1.2", SC_HINFO_IS_IPV4) == -1) {
654  goto end;
655  }
656  if (SCHInfoAddHostOSInfo("solaris", "192.168.1.100", SC_HINFO_IS_IPV4) == -1) {
657  goto end;
658  }
659  if (SCHInfoAddHostOSInfo("hpux10", "192.168.2.4", SC_HINFO_IS_IPV4) == -1) {
660  goto end;
661  }
662  if (SCHInfoAddHostOSInfo("linux", "192.192.1.5", SC_HINFO_IS_IPV4) == -1) {
663  goto end;
664  }
665  if (SCHInfoAddHostOSInfo("vista", "192.168.10.20", SC_HINFO_IS_IPV4) == -1) {
666  goto end;
667  }
668  if (SCHInfoAddHostOSInfo("solaris", "111.163.151.62", SC_HINFO_IS_IPV4) == -1) {
669  goto end;
670  }
671  if (SCHInfoAddHostOSInfo("hpux11", "111.162.208.124/20", SC_HINFO_IS_IPV4) == -1) {
672  goto end;
673  }
674  if (SCHInfoAddHostOSInfo("windows", "111.162.240.1", SC_HINFO_IS_IPV4) == -1) {
675  goto end;
676  }
677  if (SCHInfoAddHostOSInfo("solaris", "111.162.214.100", SC_HINFO_IS_IPV4) == -1) {
678  goto end;
679  }
680  if (SCHInfoAddHostOSInfo("vista", "111.162.208.100", SC_HINFO_IS_IPV4) == -1) {
681  goto end;
682  }
683  if (SCHInfoAddHostOSInfo("linux", "111.162.194.112", SC_HINFO_IS_IPV4) == -1) {
684  goto end;
685  }
686 
687  if (SCHInfoGetHostOSFlavour("192.168.1.1") !=
688  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
689  goto end;
690  }
691  if (SCHInfoGetHostOSFlavour("192.168.1.2") != -1) {
692  goto end;
693  }
694  if (SCHInfoGetHostOSFlavour("192.168.1.100") !=
695  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
696  goto end;
697  }
698  if (SCHInfoGetHostOSFlavour("192.192.2.4") != -1) {
699  goto end;
700  }
701  if (SCHInfoGetHostOSFlavour("192.168.2.4") !=
702  SCMapEnumNameToValue("hpux10", sc_hinfo_os_policy_map)) {
703  goto end;
704  }
705  if (SCHInfoGetHostOSFlavour("192.192.1.5") !=
706  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
707  goto end;
708  }
709  if (SCHInfoGetHostOSFlavour("192.168.10.20") !=
710  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
711  goto end;
712  }
713  if (SCHInfoGetHostOSFlavour("111.163.151.62") !=
714  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
715  goto end;
716  }
717  if (SCHInfoGetHostOSFlavour("111.162.208.0") !=
718  SCMapEnumNameToValue("hpux11", sc_hinfo_os_policy_map)) {
719  goto end;
720  }
721  if (SCHInfoGetHostOSFlavour("111.162.210.1") !=
722  SCMapEnumNameToValue("hpux11", sc_hinfo_os_policy_map)) {
723  goto end;
724  }
725  if (SCHInfoGetHostOSFlavour("111.162.214.1") !=
726  SCMapEnumNameToValue("hpux11", sc_hinfo_os_policy_map)) {
727  goto end;
728  }
729  if (SCHInfoGetHostOSFlavour("111.162.0.0") != -1) {
730  goto end;
731  }
732  if (SCHInfoGetHostOSFlavour("111.162.240.112") != -1) {
733  goto end;
734  }
735  if (SCHInfoGetHostOSFlavour("111.162.240.1") !=
736  SCMapEnumNameToValue("windows", sc_hinfo_os_policy_map)) {
737  goto end;
738  }
739  if (SCHInfoGetHostOSFlavour("111.162.214.100") !=
740  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
741  goto end;
742  }
743  if (inet_pton(AF_INET, "111.162.208.100", &in) < 0) {
744  goto end;
745  }
746  if (SCHInfoGetIPv4HostOSFlavour((uint8_t *)&in) !=
747  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
748  goto end;
749  }
750  if (SCHInfoGetHostOSFlavour("111.162.194.112") !=
751  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
752  goto end;
753  }
754  if (SCHInfoGetHostOSFlavour("111.162.208.200") !=
755  SCMapEnumNameToValue("hpux11", sc_hinfo_os_policy_map)) {
756  goto end;
757  }
758  if (inet_pton(AF_INET, "111.162.208.200", &in) < 0) {
759  goto end;
760  }
761  if (SCHInfoGetIPv4HostOSFlavour((uint8_t *)&in) !=
762  SCMapEnumNameToValue("hpux11", sc_hinfo_os_policy_map)) {
763  goto end;
764  }
765  if (SCHInfoGetHostOSFlavour("111.162.200.201") != -1) {
766  goto end;
767  }
768 
769  result = 1;
770 
771  end:
773  SCHInfoRestoreContextBackup();
774 
775  return result;
776 }
777 
778 /**
779  * \test Check that valid ipv6 addresses are inserted into the host os radix
780  * tree, and the host os api retrieves the right value for the host os
781  * flavour, on supplying as arg an ipv6 address that has been added to
782  * the host os radix tree.
783  */
784 static int SCHInfoTestValidIPV6Address06(void)
785 {
786  SCHInfoCreateContextBackup();
787 
788  int result = 0;
789 
790  if (SCHInfoAddHostOSInfo("linux",
791  "2351:2512:6211:6246:235A:6242:2352:62AD",
792  SC_HINFO_IS_IPV6) == -1) {
793  goto end;
794  }
795  if (SCHInfoAddHostOSInfo("windows",
796  "6961:6121:2132:6241:423A:2135:2461:621D",
797  SC_HINFO_IS_IPV6) == -1) {
798  goto end;
799  }
800  if (SCHInfoAddHostOSInfo("solaris",
801  "DD13:613D:F312:62DD:6213:421A:6212:2652",
802  SC_HINFO_IS_IPV6) == -1) {
803  goto end;
804  }
805  if (SCHInfoAddHostOSInfo("hpux10",
806  "9891:2131:2151:6426:1342:674D:622F:2342",
807  SC_HINFO_IS_IPV6) == -1) {
808  goto end;
809  }
810  if (SCHInfoAddHostOSInfo("linux",
811  "3525:2351:4223:6211:2311:2667:6242:2154",
812  SC_HINFO_IS_IPV6) == -1) {
813  goto end;
814  }
815  if (SCHInfoAddHostOSInfo("vista",
816  "1511:6211:6726:7777:1212:2333:6222:7722",
817  SC_HINFO_IS_IPV6) == -1) {
818  goto end;
819  }
820  if (SCHInfoAddHostOSInfo("solaris",
821  "2666:6222:7222:2335:6223:7722:3425:2362",
822  SC_HINFO_IS_IPV6) == -1) {
823  goto end;
824  }
825  if (SCHInfoAddHostOSInfo("solaris",
826  "8762:2352:6241:7245:EE23:21AD:2312:622C",
827  SC_HINFO_IS_IPV6) == -1) {
828  goto end;
829  }
830  if (SCHInfoAddHostOSInfo("linux",
831  "6422:EE1A:2621:34AD:2462:432D:642E:E13A",
832  SC_HINFO_IS_IPV6) == -1) {
833  goto end;
834  }
835  if (SCHInfoAddHostOSInfo("windows",
836  "3521:7622:6241:6242:7277:1234:2352:6234",
837  SC_HINFO_IS_IPV6) == -1) {
838  goto end;
839  }
840  if (SCHInfoAddHostOSInfo("hpux11",
841  "2141:6232:6252:2223:7734:2345:6245:6222",
842  SC_HINFO_IS_IPV6) == -1) {
843  goto end;
844  }
845  if (SCHInfoAddHostOSInfo("vista",
846  "5222:6432:6432:2322:6662:3423:4322:3245",
847  SC_HINFO_IS_IPV6) == -1) {
848  goto end;
849  }
850 
851  if (SCHInfoGetHostOSFlavour("2351:2512:6211:6246:235A:6242:2352:62AD") !=
852  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
853  goto end;
854  }
855  if (SCHInfoGetHostOSFlavour("2351:2512:6211:6246:235A:6242:2352:6FFFE") != -1) {
856  goto end;
857  }
858  if (SCHInfoGetHostOSFlavour("DD13:613D:F312:62DD:6213:421A:6212:2652") !=
859  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
860  goto end;
861  }
862  if (SCHInfoGetHostOSFlavour("DD13:613D:F312:62DD:6213:421A:6212:2222") != -1) {
863  goto end;
864  }
865  if (SCHInfoGetHostOSFlavour("9891:2131:2151:6426:1342:674D:622F:2342") !=
866  SCMapEnumNameToValue("hpux10", sc_hinfo_os_policy_map)) {
867  goto end;
868  }
869  if (SCHInfoGetHostOSFlavour("3525:2351:4223:6211:2311:2667:6242:2154") !=
870  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
871  goto end;
872  }
873  if (SCHInfoGetHostOSFlavour("1511:6211:6726:7777:1212:2333:6222:7722") !=
874  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
875  goto end;
876  }
877  if (SCHInfoGetHostOSFlavour("2666:6222:7222:2335:6223:7722:3425:2362") !=
878  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
879  goto end;
880  }
881  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2312:622C") !=
882  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
883  goto end;
884  }
885  if (SCHInfoGetHostOSFlavour("6422:EE1A:2621:34AD:2462:432D:642E:E13A") !=
886  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
887  goto end;
888  }
889  if (SCHInfoGetHostOSFlavour("3521:7622:6241:6242:7277:1234:2352:6234") !=
890  SCMapEnumNameToValue("windows", sc_hinfo_os_policy_map)) {
891  goto end;
892  }
893  if (SCHInfoGetHostOSFlavour("2141:6232:6252:2223:7734:2345:6245:6222") !=
894  SCMapEnumNameToValue("hpux11", sc_hinfo_os_policy_map)) {
895  goto end;
896  }
897  if (SCHInfoGetHostOSFlavour("5222:6432:6432:2322:6662:3423:4322:3245") !=
898  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
899  goto end;
900  }
901  if (SCHInfoGetHostOSFlavour("5222:6432:6432:2322:6662:3423:4322:DDDD") != -1) {
902  goto end;
903  }
904 
905  result = 1;
906 
907  end:
909  SCHInfoRestoreContextBackup();
910 
911  return result;
912 }
913 
914 /**
915  * \test Check that valid ipv6 addresses/netblocks are inserted into the host os
916  * radix tree, and the host os api retrieves the right value for the host
917  * os flavour, on supplying as arg an ipv6 address that has been added to
918  * the host os radix tree.
919  */
920 static int SCHInfoTestValidIPV6Address07(void)
921 {
922  SCHInfoCreateContextBackup();
923 
924  int result = 0;
925 
926  if (SCHInfoAddHostOSInfo("linux",
927  "2351:2512:6211:6246:235A:6242:2352:62AD",
928  SC_HINFO_IS_IPV6) == -1) {
929  goto end;
930  }
931  if (SCHInfoAddHostOSInfo("windows",
932  "6961:6121:2132:6241:423A:2135:2461:621D",
933  SC_HINFO_IS_IPV6) == -1) {
934  goto end;
935  }
936  if (SCHInfoAddHostOSInfo("solaris",
937  "DD13:613D:F312:62DD:6213:421A:6212:2652",
938  SC_HINFO_IS_IPV6) == -1) {
939  goto end;
940  }
941  if (SCHInfoAddHostOSInfo("hpux10",
942  "9891:2131:2151:6426:1342:674D:622F:2342",
943  SC_HINFO_IS_IPV6) == -1) {
944  goto end;
945  }
946  if (SCHInfoAddHostOSInfo("linux",
947  "3525:2351:4223:6211:2311:2667:6242:2154",
948  SC_HINFO_IS_IPV6) == -1) {
949  goto end;
950  }
951  if (SCHInfoAddHostOSInfo("vista",
952  "1511:6211:6726:7777:1212:2333:6222:7722",
953  SC_HINFO_IS_IPV6) == -1) {
954  goto end;
955  }
956  if (SCHInfoAddHostOSInfo("solaris",
957  "2666:6222:7222:2335:6223:7722:3425:2362",
958  SC_HINFO_IS_IPV6) == -1) {
959  goto end;
960  }
961  if (SCHInfoAddHostOSInfo("solaris",
962  "8762:2352:6241:7245:EE23:21AD:2312:622C/68",
963  SC_HINFO_IS_IPV6) == -1) {
964  goto end;
965  }
966  if (SCHInfoAddHostOSInfo("linux",
967  "8762:2352:6241:7245:EE23:21AD:2412:622C",
968  SC_HINFO_IS_IPV6) == -1) {
969  goto end;
970  }
971  if (SCHInfoAddHostOSInfo("windows",
972  "8762:2352:6241:7245:EE23:21AD:FFFF:622C",
973  SC_HINFO_IS_IPV6) == -1) {
974  goto end;
975  }
976  if (SCHInfoAddHostOSInfo("hpux11",
977  "8762:2352:6241:7245:EE23:21AD:2312:62FF",
978  SC_HINFO_IS_IPV6) == -1) {
979  goto end;
980  }
981  if (SCHInfoAddHostOSInfo("vista",
982  "8762:2352:6241:7245:EE23:21AD:2121:1212",
983  SC_HINFO_IS_IPV6) == -1) {
984  goto end;
985  }
986 
987  if (SCHInfoGetHostOSFlavour("2351:2512:6211:6246:235A:6242:2352:62AD") !=
988  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
989  goto end;
990  }
991  if (SCHInfoGetHostOSFlavour("2351:2512:6211:6246:235A:6242:2352:6FFFE") != -1) {
992  goto end;
993  }
994  if (SCHInfoGetHostOSFlavour("DD13:613D:F312:62DD:6213:421A:6212:2652") !=
995  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
996  goto end;
997  }
998  if (SCHInfoGetHostOSFlavour("DD13:613D:F312:62DD:6213:421A:6212:2222") != -1) {
999  goto end;
1000  }
1001  if (SCHInfoGetHostOSFlavour("9891:2131:2151:6426:1342:674D:622F:2342") !=
1002  SCMapEnumNameToValue("hpux10", sc_hinfo_os_policy_map)) {
1003  goto end;
1004  }
1005  if (SCHInfoGetHostOSFlavour("3525:2351:4223:6211:2311:2667:6242:2154") !=
1006  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
1007  goto end;
1008  }
1009  if (SCHInfoGetHostOSFlavour("1511:6211:6726:7777:1212:2333:6222:7722") !=
1010  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
1011  goto end;
1012  }
1013  if (SCHInfoGetHostOSFlavour("2666:6222:7222:2335:6223:7722:3425:2362") !=
1014  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1015  goto end;
1016  }
1017  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2312:622C") !=
1018  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1019  goto end;
1020  }
1021  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2412:622C") !=
1022  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
1023  goto end;
1024  }
1025  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:FFFF:622C") !=
1026  SCMapEnumNameToValue("windows", sc_hinfo_os_policy_map)) {
1027  goto end;
1028  }
1029  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2312:62FF") !=
1030  SCMapEnumNameToValue("hpux11", sc_hinfo_os_policy_map)) {
1031  goto end;
1032  }
1033  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2121:1212") !=
1034  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
1035  goto end;
1036  }
1037  if (SCHInfoGetHostOSFlavour("5222:6432:6432:2322:6662:3423:4322:DDDD") != -1) {
1038  goto end;
1039  }
1040  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2121:1DDD") !=
1041  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1042  goto end;
1043  }
1044  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:FFFF:2121:1DDD") !=
1045  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1046  goto end;
1047  }
1048  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2312:622C") !=
1049  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1050  goto end;
1051  }
1052  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE00:0000:0000:0000") !=
1053  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1054  goto end;
1055  }
1056  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:E000:0000:0000:0000") !=
1057  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1058  goto end;
1059  }
1060 
1061  result = 1;
1062 
1063  end:
1065  SCHInfoRestoreContextBackup();
1066 
1067  return result;
1068 }
1069 
1070 /**
1071  * \test Check that valid ipv6 addresses/netblocks are inserted into the host os
1072  * radix tree, and the host os api retrieves the right value for the host
1073  * os flavour, on supplying as arg an ipv6 address that has been added to
1074  * the host os radix tree.
1075  */
1076 static int SCHInfoTestValidIPV6Address08(void)
1077 {
1078  SCHInfoCreateContextBackup();
1079 
1080  struct in6_addr in6;
1081  int result = 0;
1082 
1083  if (SCHInfoAddHostOSInfo("linux",
1084  "2351:2512:6211:6246:235A:6242:2352:62AD",
1085  SC_HINFO_IS_IPV6) == -1) {
1086  goto end;
1087  }
1088  if (SCHInfoAddHostOSInfo("windows",
1089  "6961:6121:2132:6241:423A:2135:2461:621D",
1090  SC_HINFO_IS_IPV6) == -1) {
1091  goto end;
1092  }
1093  if (SCHInfoAddHostOSInfo("solaris",
1094  "DD13:613D:F312:62DD:6213:421A:6212:2652",
1095  SC_HINFO_IS_IPV6) == -1) {
1096  goto end;
1097  }
1098  if (SCHInfoAddHostOSInfo("hpux10",
1099  "9891:2131:2151:6426:1342:674D:622F:2342",
1100  SC_HINFO_IS_IPV6) == -1) {
1101  goto end;
1102  }
1103  if (SCHInfoAddHostOSInfo("linux",
1104  "3525:2351:4223:6211:2311:2667:6242:2154",
1105  SC_HINFO_IS_IPV6) == -1) {
1106  goto end;
1107  }
1108  if (SCHInfoAddHostOSInfo("vista",
1109  "1511:6211:6726:7777:1212:2333:6222:7722",
1110  SC_HINFO_IS_IPV6) == -1) {
1111  goto end;
1112  }
1113  if (SCHInfoAddHostOSInfo("solaris",
1114  "2666:6222:7222:2335:6223:7722:3425:2362",
1115  SC_HINFO_IS_IPV6) == -1) {
1116  goto end;
1117  }
1118  if (SCHInfoAddHostOSInfo("solaris",
1119  "8762:2352:6241:7245:EE23:21AD:2312:622C/68",
1120  SC_HINFO_IS_IPV6) == -1) {
1121  goto end;
1122  }
1123  if (SCHInfoAddHostOSInfo("linux",
1124  "8762:2352:6241:7245:EE23:21AD:2412:622C",
1125  SC_HINFO_IS_IPV6) == -1) {
1126  goto end;
1127  }
1128  if (SCHInfoAddHostOSInfo("windows",
1129  "8762:2352:6241:7245:EE23:21AD:FFFF:622C",
1130  SC_HINFO_IS_IPV6) == -1) {
1131  goto end;
1132  }
1133  if (SCHInfoAddHostOSInfo("hpux11",
1134  "8762:2352:6241:7245:EE23:21AD:2312:62FF",
1135  SC_HINFO_IS_IPV6) == -1) {
1136  goto end;
1137  }
1138  if (SCHInfoAddHostOSInfo("vista",
1139  "8762:2352:6241:7245:EE23:21AD:2121:1212",
1140  SC_HINFO_IS_IPV6) == -1) {
1141  goto end;
1142  }
1143  if (SCHInfoAddHostOSInfo("irix", "default", SC_HINFO_IS_IPV6) == -1) {
1144  goto end;
1145  }
1146 
1147  if (SCHInfoGetHostOSFlavour("2351:2512:6211:6246:235A:6242:2352:62AD") !=
1148  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
1149  goto end;
1150  }
1151  if (SCHInfoGetHostOSFlavour("2351:2512:6211:6246:235A:6242:2352:6FFF") !=
1152  SCMapEnumNameToValue("irix", sc_hinfo_os_policy_map)) {
1153  goto end;
1154  }
1155  if (SCHInfoGetHostOSFlavour("DD13:613D:F312:62DD:6213:421A:6212:2652") !=
1156  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1157  goto end;
1158  }
1159  if (SCHInfoGetHostOSFlavour("DD13:613D:F312:62DD:6213:421A:6212:2222") !=
1160  SCMapEnumNameToValue("irix", sc_hinfo_os_policy_map)) {
1161  goto end;
1162  }
1163  if (SCHInfoGetHostOSFlavour("9891:2131:2151:6426:1342:674D:622F:2342") !=
1164  SCMapEnumNameToValue("hpux10", sc_hinfo_os_policy_map)) {
1165  goto end;
1166  }
1167  if (SCHInfoGetHostOSFlavour("3525:2351:4223:6211:2311:2667:6242:2154") !=
1168  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
1169  goto end;
1170  }
1171  if (SCHInfoGetHostOSFlavour("1511:6211:6726:7777:1212:2333:6222:7722") !=
1172  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
1173  goto end;
1174  }
1175  if (SCHInfoGetHostOSFlavour("2666:6222:7222:2335:6223:7722:3425:2362") !=
1176  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1177  goto end;
1178  }
1179  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2312:622C") !=
1180  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1181  goto end;
1182  }
1183  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2412:622C") !=
1184  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
1185  goto end;
1186  }
1187  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:FFFF:622C") !=
1188  SCMapEnumNameToValue("windows", sc_hinfo_os_policy_map)) {
1189  goto end;
1190  }
1191  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2312:62FF") !=
1192  SCMapEnumNameToValue("hpux11", sc_hinfo_os_policy_map)) {
1193  goto end;
1194  }
1195  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2121:1212") !=
1196  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
1197  goto end;
1198  }
1199  if (SCHInfoGetHostOSFlavour("5222:6432:6432:2322:6662:3423:4322:DDDD") !=
1200  SCMapEnumNameToValue("irix", sc_hinfo_os_policy_map)) {
1201  goto end;
1202  }
1203  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2121:1DDD") !=
1204  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1205  goto end;
1206  }
1207  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:FFFF:2121:1DDD") !=
1208  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1209  goto end;
1210  }
1211  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE23:21AD:2312:622C") !=
1212  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1213  goto end;
1214  }
1215  if (SCHInfoGetHostOSFlavour("8762:2352:6241:7245:EE00:0000:0000:0000") !=
1216  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1217  goto end;
1218  }
1219  if (inet_pton(AF_INET6, "8762:2352:6241:7245:E000:0000:0000:0000", &in6) < 0) {
1220  goto end;
1221  }
1222  if (SCHInfoGetIPv6HostOSFlavour((uint8_t *)&in6) !=
1223  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1224  goto end;
1225  }
1226  if (inet_pton(AF_INET6, "AD23:2DDA:6D1D:A223:E235:0232:1241:1666", &in6) < 0) {
1227  goto end;
1228  }
1229  if (SCHInfoGetIPv6HostOSFlavour((uint8_t *)&in6) !=
1230  SCMapEnumNameToValue("irix", sc_hinfo_os_policy_map)) {
1231  goto end;
1232  }
1233 
1234  result = 1;
1235 
1236  end:
1238  SCHInfoRestoreContextBackup();
1239 
1240  return result;
1241 }
1242 
1243 /**
1244  * \test Check that valid ipv4 addresses are inserted into the host os radix
1245  * tree, and the host os api retrieves the right value for the host os
1246  * flavour, on supplying as arg an ipv4 addresses that has been added to
1247  * the host os radix tree.
1248  */
1249 static int SCHInfoTestValidIPV4Address09(void)
1250 {
1251  SCHInfoCreateContextBackup();
1252 
1253  int result = 0;
1254 
1255  if (SCHInfoAddHostOSInfo("linux", "192.168.1.0", SC_HINFO_IS_IPV4) == -1) {
1256  goto end;
1257  }
1258  if (SCHInfoAddHostOSInfo("windows", "192.192.1.2", SC_HINFO_IS_IPV4) == -1) {
1259  goto end;
1260  }
1261  if (SCHInfoGetHostOSFlavour("192.168.1.0") !=
1262  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
1263  goto end;
1264  }
1265  if (SCHInfoAddHostOSInfo("solaris", "192.168.1.0/16", SC_HINFO_IS_IPV4) == -1) {
1266  goto end;
1267  }
1268  if (SCHInfoAddHostOSInfo("macos", "192.168.1.0/20", SC_HINFO_IS_IPV4) == -1) {
1269  goto end;
1270  }
1271  if (SCHInfoGetHostOSFlavour("192.168.1.0") !=
1272  SCMapEnumNameToValue("linux", sc_hinfo_os_policy_map)) {
1273  goto end;
1274  }
1275  if (SCHInfoAddHostOSInfo("vista", "192.168.50.128/25", SC_HINFO_IS_IPV4) == -1) {
1276  goto end;
1277  }
1278  if (SCHInfoGetHostOSFlavour("192.168.50.128") !=
1279  SCMapEnumNameToValue("vista", sc_hinfo_os_policy_map)) {
1280  goto end;
1281  }
1282  if (SCHInfoAddHostOSInfo("irix", "192.168.50.128", SC_HINFO_IS_IPV4) == -1) {
1283  goto end;
1284  }
1285  if (SCHInfoGetHostOSFlavour("192.168.50.128") !=
1286  SCMapEnumNameToValue("irix", sc_hinfo_os_policy_map)) {
1287  goto end;
1288  }
1289 
1290  if (SCHInfoGetHostOSFlavour("192.168.1.100") !=
1291  SCMapEnumNameToValue("macos", sc_hinfo_os_policy_map)) {
1292  goto end;
1293  }
1294 
1295  struct sockaddr_in servaddr;
1296  memset(&servaddr, 0, sizeof(servaddr));
1297  if (inet_pton(AF_INET, "192.168.0.0", &servaddr.sin_addr) <= 0) {
1298  goto end;
1299  }
1300 
1301  SCRadixRemoveKeyIPV4Netblock((uint8_t *)&servaddr.sin_addr, sc_hinfo_tree, 16);
1302 
1303  if (SCHInfoGetHostOSFlavour("192.168.1.100") !=
1304  SCMapEnumNameToValue("macos", sc_hinfo_os_policy_map)) {
1305  goto end;
1306  }
1307 
1308  memset(&servaddr, 0, sizeof(servaddr));
1309  if (inet_pton(AF_INET, "192.168.0.0", &servaddr.sin_addr) <= 0) {
1310  goto end;
1311  }
1312  SCRadixRemoveKeyIPV4Netblock((uint8_t *)&servaddr.sin_addr, sc_hinfo_tree, 20);
1313 
1314  if (SCHInfoGetHostOSFlavour("192.168.1.100") != -1) {
1315  goto end;
1316  }
1317  if (SCHInfoAddHostOSInfo("solaris", "192.168.1.0/16", SC_HINFO_IS_IPV4) == -1) {
1318  goto end;
1319  }
1320  if (SCHInfoAddHostOSInfo("macos", "192.168.1.0/20", SC_HINFO_IS_IPV4) == -1) {
1321  goto end;
1322  }
1323 
1324  /* 192.168.1.100 should match "macos" as its more specific than
1325  * "solaris". */
1326  if (SCHInfoGetHostOSFlavour("192.168.1.100") !=
1327  SCMapEnumNameToValue("macos", sc_hinfo_os_policy_map)) {
1328  goto end;
1329  }
1330 
1331  /* Remove the 192.168.1.0/20 -> macos entry. */
1332  memset(&servaddr, 0, sizeof(servaddr));
1333  if (inet_pton(AF_INET, "192.168.0.0", &servaddr.sin_addr) <= 0) {
1334  goto end;
1335  }
1336  SCRadixRemoveKeyIPV4Netblock((uint8_t *)&servaddr.sin_addr, sc_hinfo_tree, 20);
1337 
1338  if (SCHInfoGetHostOSFlavour("192.168.1.100") !=
1339  SCMapEnumNameToValue("solaris", sc_hinfo_os_policy_map)) {
1340  goto end;
1341  }
1342 
1343  /* Remove the 192.168.1.0/16 -> solaris entry. */
1344  memset(&servaddr, 0, sizeof(servaddr));
1345  if (inet_pton(AF_INET, "192.168.0.0", &servaddr.sin_addr) <= 0) {
1346  goto end;
1347  }
1348  SCRadixRemoveKeyIPV4Netblock((uint8_t *)&servaddr.sin_addr, sc_hinfo_tree, 16);
1349 
1350  if (SCHInfoGetHostOSFlavour("192.168.1.100") != -1) {
1351  goto end;
1352  }
1353 
1354  result = 1;
1355 
1356  end:
1358  SCHInfoRestoreContextBackup();
1359 
1360  return result;
1361 }
1362 
1363 /**
1364  * \test Check the loading of host info from a configuration file.
1365  */
1366 static int SCHInfoTestLoadFromConfig01(void)
1367 {
1368  char config[] = "\
1369 %YAML 1.1\n\
1370 ---\n\
1371 host-os-policy:\n\
1372  bsd: [0.0.0.0/0]\n\
1373  windows: [10.0.0.0/8, 192.168.1.0/24]\n\
1374  linux: [10.0.0.5/32]\n\
1375 \n";
1376 
1377  int result = 0;
1378 
1379  SCHInfoCreateContextBackup();
1380 
1382  ConfInit();
1383  ConfYamlLoadString(config, strlen(config));
1384 
1386  if (SCHInfoGetHostOSFlavour("10.0.0.4") != OS_POLICY_WINDOWS)
1387  goto end;
1388  if (SCHInfoGetHostOSFlavour("10.0.0.5") != OS_POLICY_LINUX)
1389  goto end;
1390  if (SCHInfoGetHostOSFlavour("192.168.1.1") != OS_POLICY_WINDOWS)
1391  goto end;
1392  if (SCHInfoGetHostOSFlavour("172.168.1.1") != OS_POLICY_BSD)
1393  goto end;
1394 
1395  result = 1;
1396 
1397  end:
1398  ConfDeInit();
1400 
1401  SCHInfoRestoreContextBackup();
1402 
1403  return result;
1404 }
1405 
1406 /**
1407  * \test Check the loading of host info from a configuration file.
1408  */
1409 static int SCHInfoTestLoadFromConfig02(void)
1410 {
1411  char config[] = "\
1412 %YAML 1.1\n\
1413 ---\n\
1414 host-os-policy:\n\
1415  one-two: [0.0.0.0/0]\n\
1416  one-two-three:\n\
1417  four_five:\n\
1418  six-seven_eight: [10.0.0.0/8, 192.168.1.0/24]\n\
1419  nine_ten_eleven: [10.0.0.5/32]\n\
1420 \n";
1421 
1422  int result = 0;
1423 
1424  SCHInfoCreateContextBackup();
1425 
1427  ConfInit();
1428  ConfYamlLoadString(config, strlen(config));
1429 
1430  ConfNode *root = ConfGetNode("host-os-policy");
1431  if (root == NULL)
1432  goto end;
1433 
1434  int count = 0;
1435 
1436  ConfNode *policy;
1437  TAILQ_FOREACH(policy, &root->head, next) {
1438  switch (count) {
1439  case 0:
1440  if (strcmp("one-two", policy->name) != 0)
1441  goto end;
1442  break;
1443  case 1:
1444  if (strcmp("one-two-three", policy->name) != 0)
1445  goto end;
1446  break;
1447  case 2:
1448  if (strcmp("four-five", policy->name) != 0)
1449  goto end;
1450  break;
1451  case 3:
1452  if (strcmp("six-seven-eight", policy->name) != 0)
1453  goto end;
1454  break;
1455  case 4:
1456  if (strcmp("nine-ten-eleven", policy->name) != 0)
1457  goto end;
1458  break;
1459  }
1460  count++;
1461  }
1462 
1463  result = 1;
1464 
1465  end:
1466  ConfDeInit();
1468 
1469  SCHInfoRestoreContextBackup();
1470 
1471  return result;
1472 }
1473 
1474 /**
1475  * \test Check the loading of host info from a configuration file.
1476  */
1477 static int SCHInfoTestLoadFromConfig03(void)
1478 {
1479  char config[] = "\
1480 %YAML 1.1\n\
1481 ---\n\
1482 host-os-policy:\n\
1483  bsd-right: [0.0.0.1]\n\
1484  old-linux: [0.0.0.2]\n\
1485  old-solaris: [0.0.0.3]\n\
1486  windows: [0.0.0.4]\n\
1487  vista: [0.0.0.5]\n\
1488 \n";
1489 
1490  int result = 0;
1491 
1492  SCHInfoCreateContextBackup();
1493 
1495  ConfInit();
1496  ConfYamlLoadString(config, strlen(config));
1497 
1498  ConfNode *root = ConfGetNode("host-os-policy");
1499  if (root == NULL)
1500  goto end;
1501 
1502  ConfNode *policy;
1503  TAILQ_FOREACH(policy, &root->head, next) {
1504  if (SCMapEnumNameToValue(policy->name, sc_hinfo_os_policy_map) == -1) {
1505  printf("Invalid enum map inside\n");
1506  goto end;
1507  }
1508  }
1509 
1510  result = 1;
1511 
1512  end:
1513  ConfDeInit();
1515 
1516  SCHInfoRestoreContextBackup();
1517  return result;
1518 }
1519 
1520 /**
1521  * \test Check the loading of host info from a configuration file.
1522  */
1523 static int SCHInfoTestLoadFromConfig04(void)
1524 {
1525  char config[] = "\
1526 %YAML 1.1\n\
1527 ---\n\
1528 host-os-policy:\n\
1529  bsd_right: [0.0.0.1]\n\
1530  old_linux: [0.0.0.2]\n\
1531  old_solaris: [0.0.0.3]\n\
1532  windows: [0.0.0.4]\n\
1533  vista: [0.0.0.5]\n\
1534 \n";
1535 
1536  int result = 0;
1537 
1538  SCHInfoCreateContextBackup();
1539 
1541  ConfInit();
1542  ConfYamlLoadString(config, strlen(config));
1543 
1544  ConfNode *root = ConfGetNode("host-os-policy");
1545  if (root == NULL)
1546  goto end;
1547 
1548  ConfNode *policy;
1549  TAILQ_FOREACH(policy, &root->head, next) {
1550  if (SCMapEnumNameToValue(policy->name, sc_hinfo_os_policy_map) == -1) {
1551  printf("Invalid enum map inside\n");
1552  goto end;
1553  }
1554  }
1555 
1556  result = 1;
1557 
1558  end:
1559  ConfDeInit();
1561 
1562  SCHInfoRestoreContextBackup();
1563  return result;
1564 }
1565 
1566 /**
1567  * \test Check the loading of host info from a configuration file.
1568  */
1569 static int SCHInfoTestLoadFromConfig05(void)
1570 {
1571  char config[] = "\
1572 %YAML 1.1\n\
1573 ---\n\
1574 host-os-policy:\n\
1575  bsd_right: [0.0.0.1]\n\
1576  old_linux: [0.0.0.2]\n\
1577  old-solaris: [0.0.0.3]\n\
1578  windows: [0.0.0.4]\n\
1579  linux: [0.0.0.5]\n\
1580 \n";
1581 
1582  SCHInfoCreateContextBackup();
1583 
1585  ConfInit();
1586  ConfYamlLoadString(config, strlen(config));
1588 
1594  FAIL_IF (SCHInfoGetHostOSFlavour("0.0.0.0") != -1);
1595  FAIL_IF (SCHInfoGetHostOSFlavour("0.0.0.6") != -1);
1596 
1597  ConfDeInit();
1599  SCHInfoRestoreContextBackup();
1600  PASS;
1601 }
1602 
1603 #endif /* UNITTESTS */
1604 
1606 {
1607 
1608 #ifdef UNITTESTS
1609 
1610  UtRegisterTest("SCHInfoTesInvalidOSFlavour01",
1611  SCHInfoTestInvalidOSFlavour01);
1612  UtRegisterTest("SCHInfoTestInvalidIPV4Address02",
1613  SCHInfoTestInvalidIPV4Address02);
1614  UtRegisterTest("SCHInfoTestInvalidIPV6Address03",
1615  SCHInfoTestInvalidIPV6Address03);
1616  UtRegisterTest("SCHInfoTestValidIPV4Address04",
1617  SCHInfoTestValidIPV4Address04);
1618  UtRegisterTest("SCHInfoTestValidIPV4Address05",
1619  SCHInfoTestValidIPV4Address05);
1620  UtRegisterTest("SCHInfoTestValidIPV6Address06",
1621  SCHInfoTestValidIPV6Address06);
1622  UtRegisterTest("SCHInfoTestValidIPV6Address07",
1623  SCHInfoTestValidIPV6Address07);
1624  UtRegisterTest("SCHInfoTestValidIPV6Address08",
1625  SCHInfoTestValidIPV6Address08);
1626  UtRegisterTest("SCHInfoTestValidIPV4Address09",
1627  SCHInfoTestValidIPV4Address09);
1628 
1629  UtRegisterTest("SCHInfoTestLoadFromConfig01", SCHInfoTestLoadFromConfig01);
1630  UtRegisterTest("SCHInfoTestLoadFromConfig02", SCHInfoTestLoadFromConfig02);
1631  UtRegisterTest("SCHInfoTestLoadFromConfig03", SCHInfoTestLoadFromConfig03);
1632  UtRegisterTest("SCHInfoTestLoadFromConfig04", SCHInfoTestLoadFromConfig04);
1633  UtRegisterTest("SCHInfoTestLoadFromConfig05", SCHInfoTestLoadFromConfig05);
1634 #endif /* UNITTESTS */
1635 
1636 }
#define TAILQ_FOREACH(var, head, field)
Definition: queue.h:350
void SCHInfoRegisterTests(void)
struct HtpBodyChunk_ * next
#define FALSE
void MaskIPNetblock(uint8_t *stream, int netmask, int key_bitlen)
Culls the non-netmask portion of the IP address. For example an IP address 192.168.240.1 would be chopped to 192.168.224.0 against a netmask value of 19.
Definition: util-ip.c:187
void ConfDeInit(void)
De-initializes the configuration system.
Definition: conf.c:722
#define PASS
Pass the test.
int SCHInfoGetIPv4HostOSFlavour(uint8_t *ipv4_addr)
Retrieves the host os flavour, given an ipv4 address in the raw address format.
int ConfYamlLoadString(const char *string, size_t len)
Load configuration from a YAML string.
#define FAIL_IF(expr)
Fail a test if expression evaluates to false.
Definition: util-unittest.h:71
SCRadixNode * SCRadixFindKeyIPV6BestMatch(uint8_t *key_stream, SCRadixTree *tree, void **user_data_result)
Checks if an IPV6 address is present in the tree under a netblock.
SCRadixTree * SCRadixCreateRadixTree(void(*Free)(void *), void(*PrintData)(void *))
Creates a new Radix tree.
int SCMapEnumNameToValue(const char *enum_name, SCEnumCharMap *table)
Maps a string name to an enum value from the supplied table. Please specify the last element of any m...
Definition: util-enum.c:41
char * val
Definition: conf.h:34
#define TRUE
void SCHInfoLoadFromConfig(void)
Load the host os policy information from the configuration.
SCRadixNode * SCRadixAddKeyIPV4Netblock(uint8_t *key_stream, SCRadixTree *tree, void *user, uint8_t netmask)
Adds a new IPV4 netblock to the Radix tree.
void SCRadixReleaseRadixTree(SCRadixTree *tree)
Frees a Radix tree and all its nodes.
void ConfCreateContextBackup(void)
Creates a backup of the conf_hash hash_table used by the conf API.
Definition: conf.c:699
SCRadixNode * SCRadixAddKeyIPV4(uint8_t *key_stream, SCRadixTree *tree, void *user)
Adds a new IPV4 address to the Radix tree.
int SCHInfoAddHostOSInfo(const char *host_os, const char *host_os_ip_range, int is_ipv4)
Used to add the host-os-info data obtained from the conf.
#define SCLogError(err_code,...)
Macro used to log ERROR messages.
Definition: util-debug.h:294
void SCHInfoCleanResources(void)
void ConfInit(void)
Initialize the configuration system.
Definition: conf.c:113
void UtRegisterTest(const char *name, int(*TestFn)(void))
Register unit test.
struct in_addr * ValidateIPV4Address(const char *addr_str)
Validates an IPV4 address and returns the network endian arranged version of the IPV4 address...
Definition: util-ip.c:128
void ConfRestoreContextBackup(void)
Restores the backup of the hash_table present in backup_conf_hash back to conf_hash.
Definition: conf.c:711
#define SC_HINFO_IS_IPV6
SCRadixNode * SCRadixFindKeyIPV4BestMatch(uint8_t *key_stream, SCRadixTree *tree, void **user_data_result)
Checks if an IPV4 address is present in the tree under a netblock.
Definition: conf.h:32
int SCHInfoGetHostOSFlavour(const char *ip_addr_str)
Retrieves the host os flavour, given an ipv4/ipv6 address as a string.
#define SCMalloc(a)
Definition: util-mem.h:222
#define SCFree(a)
Definition: util-mem.h:322
struct in6_addr * ValidateIPV6Address(const char *addr_str)
Validates an IPV6 address and returns the network endian arranged version of the IPV6 addresss...
Definition: util-ip.c:158
char * name
Definition: conf.h:33
ConfNode * ConfGetNode(const char *name)
Get a ConfNode by name.
Definition: conf.c:176
#define SCStrdup(a)
Definition: util-mem.h:268
int SCHInfoGetIPv6HostOSFlavour(uint8_t *ipv6_addr)
Retrieves the host os flavour, given an ipv6 address in the raw address format.
SCRadixNode * SCRadixAddKeyIPV6Netblock(uint8_t *key_stream, SCRadixTree *tree, void *user, uint8_t netmask)
Adds a new IPV6 netblock to the Radix tree.
SCRadixNode * SCRadixAddKeyIPV6(uint8_t *key_stream, SCRadixTree *tree, void *user)
Adds a new IPV6 address to the Radix tree.
void SCRadixRemoveKeyIPV4Netblock(uint8_t *key_stream, SCRadixTree *tree, uint8_t netmask)
Removes an IPV4 address netblock key from the Radix tree.
SCEnumCharMap sc_hinfo_os_policy_map[]
Structure for the radix tree.
#define SC_HINFO_IS_IPV4