00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
#include "util.h"
00046
#include "dns.h"
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061 void _printf_dbg(u_int8_t level,
const char *function,
const char *format,...)
00062 {
00063
char _dbg_output[
MAX_DEBUG_LEN];
00064 va_list argptr;
00065
00066
#ifdef _SPF_DEBUG_LOGFILE
00067
FILE *fp = NULL;
00068
#endif
00069
00070
00071
00072 va_start(argptr, format);
00073 vsnprintf(_dbg_output,
SIZEOF(_dbg_output), format, argptr);
00074 va_end(argptr);
00075
00076
if (
f_bit_set(
confg.
level, level))
00077 {
00078
#ifndef _SPF_DEBUG_LOGFILE
00079
printf(
"%s :: %s", function, _dbg_output);
00080 fflush(stdout);
00081
#else
00082
if ((fp = fopen(
DEBUG_LOG_FILE,
"a")) != NULL)
00083 {
00084 fprintf(fp,
"%s", _dbg_output);
00085 fclose(fp);
00086 }
00087
#endif
00088
00089 }
00090
00091
return;
00092 }
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102
00103
00104
00105
00106 void dummy_debug(
const u_int8_t level,
const char *function,
00107
const char *format,...)
00108 {
00109
return;
00110 }
00111
00112
00113
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124
00125
00126
00127 char *
UTIL_printf(
char *format, ...)
00128 {
00129 va_list arg_ptr;
00130
static char s[1024];
00131
00132 va_start (arg_ptr, format);
00133 vsnprintf (s, 1024, format, arg_ptr);
00134 va_end (arg_ptr);
00135
00136
xvprintf(
"Called with string: %s\n", s);
00137
00138
return(s);
00139 }
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153 char *
UTIL_get_date(
void)
00154 {
00155
struct tm *now;
00156 time_t curtime;
00157
static char my_time[22];
00158
00159 curtime = time(NULL);
00160 now = localtime(&curtime);
00161
00162 strftime(my_time,
sizeof(my_time),
"%Y-%m-%d %H:%M:%S ", now);
00163
00164
return(my_time);
00165 }
00166
00167
00168
00169
00170
00171
00172
00173
00174
00175
00176
00177
00178
00179
00180 void UTIL_log_result(
peer_info_t *peer_info)
00181 {
00182 FILE *fp = NULL;
00183
char buf[
MAX_DEBUG_LEN];
00184
char *date;
00185
00186 date =
UTIL_get_date();
00187 *(date + (strlen(date) - 1)) =
'\0';
00188
00189
if (peer_info->
spf_ver == 0)
00190 {
00191 peer_info->
spf_ver =
SPF_VERSION;
00192 }
00193
00194 sprintf(buf,
"[%s] result: %s :: %s [%s], ver: %i, depth: %i, error: (%s)\n",
00195 date, peer_info->
spf_result[peer_info->
RES].s, peer_info->
from,
00196 peer_info->
r_ip,
spf_rlevel, peer_info->
spf_ver, peer_info->
error);
00197
00198
if ((fp = fopen(
OUTPUT_LOG_FILE,
"a")) != NULL)
00199 {
00200 fprintf(fp,
"%s", buf);
00201 fclose(fp);
00202 }
00203
00204
return;
00205 }
00206
00207
00208
00209
00210
00211
00212
00213
00214
00215
00216
00217
00218
00219
00220
00221 char *
UTIL_strndup(
const char *s,
const size_t n)
00222 {
00223
char *ret_ptr = NULL;
00224
00225
if (s == NULL)
00226 {
00227
xeprintf(
"Passed string is NULL. Abort!.\n");
00228
return(
FALSE);
00229 }
00230
00231 ret_ptr =
xmalloc(n);
00232
xvprintf(
"Allocated %u bytes of memory.\n", n);
00233
00234 memset(ret_ptr,
'\0', n);
00235 memcpy(ret_ptr, s, (n - 1));
00236
00237
xvprintf(
"Returning string: (%s)\n",
00238 ret_ptr);
00239
00240
return(ret_ptr);
00241 }
00242
00243
00244
00245
00246
00247
00248
00249
00250
00251
00252
00253
00254
00255
00256
00257 char *
UTIL_strdup(
const char *s)
00258 {
00259
char *ret_ptr = NULL;
00260
00261
if (s == NULL)
00262 {
00263
xeprintf(
"Passed string is NULL. Abort!.\n");
00264
return(
FALSE);
00265 }
00266
00267
if ((ret_ptr = strdup(s)) == NULL)
00268 {
00269
xeprintf(
"Unable to allocate memory\n");
00270 }
00271
00272
xvprintf(
"Returning string: (%s)\n", ret_ptr);
00273
00274
return(ret_ptr);
00275 }
00276
00277
00278
00279
00280
00281
00282
00283
00284
00285
00286
00287
00288
00289
00290 void *
UTIL_malloc(
const int32_t n,
const char *file, int32_t line,
00291
const char *func)
00292 {
00293
void *x = malloc(n);
00294
00295
if (x == NULL)
00296 {
00297
xvprintf(
"Unable to allocate %i bytes at %s:%i in %s\n",
00298 n, file, line, func);
00299
00300 exit(0);
00301 }
00302
00303
return(x);
00304 }
00305
00306
00307
00308
00309
00310
00311
00312
00313
00314
00315
00316
00317
00318
00319
00320
00321 void *
UTIL_realloc(
void *p,
const int32_t n,
const char *file,
const int32_t
00322 line,
00323
const char *func)
00324 {
00325
void *x = NULL;
00326
00327
if (p == NULL)
00328 {
00329
return(
UTIL_malloc(n, file, line, func));
00330 }
00331
00332 x = realloc(p, n);
00333
if (x == NULL)
00334 {
00335
xvprintf(
"Unable to reallocate %i bytes at %s:%i in %s; " \
00336
"original address 0x%x\n", n, file, line, func, (uintptr_t)p);
00337
00338 exit(0);
00339 }
00340
00341
return(x);
00342 }
00343
00344
00345
00346
00347
00348
00349
00350
00351
00352
00353
00354
00355
00356
00357
00358 void UTIL_free(
void *p,
const char *file,
const int32_t line,
const char *func)
00359 {
00360
if (p == NULL)
00361 {
00362
xvprintf(
"Unable to free() on NULL pointer at %s:%i in %s; " \
00363
"address 0x%x.\n", file, line, func, (uintptr_t)p);
00364
return;
00365 }
00366
00367
xvprintf(
"Free address 0x%x by %s on line %i (%s)\n",
00368 (uintptr_t)p, func, line, file);
00369
00370 free(p);
00371
return;
00372 }
00373
00374
00375
00376
00377
00378
00379
00380
00381
00382
00383
00384
00385
00386
00387 int16_t
UTIL_index(
const char *s,
const char c)
00388 {
00389 int16_t i;
00390
00391
if (s == NULL)
00392 {
00393
xeprintf(
"Passed a NULL string. Abort!\n");
00394
return(0);
00395 }
00396
00397 i = 0;
00398
while (*s)
00399 {
00400
if (*s == c)
00401 {
00402
xvprintf(
"Found search char: (%c); Returning: (%i)\n", *s, i);
00403
00404
return(i);
00405 }
00406 i++;
00407 s++;
00408 }
00409
return(0);
00410 }
00411
00412
00413
00414
00415
00416
00417
00418
00419
00420
00421
00422
00423
00424
00425 char *
UTIL_split_str(
const char *s,
const char c,
const u_int8_t num)
00426 {
00427 u_int8_t i = 0;
00428
00429
char *cp;
00430
char *p;
00431
char *ret;
00432
00433
if (s == NULL)
00434 {
00435
xeprintf(
"Passed a NULL string. Abort!\n");
00436
return(NULL);
00437 }
00438
00439 p = cp =
xstrndup(s, (strlen(s) + 1));
00440
00441
while(*p)
00442 {
00443
if (*p == c)
00444 {
00445 i++;
00446
if (i == num)
00447 {
00448 p++;
00449 ret =
xstrndup(p, (strlen(p) + 1));
00450
xfree(cp);
00451
xvprintf(
"returning: %s\n", ret);
00452
return(ret);
00453 }
00454 }
00455 p++;
00456 }
00457
00458
return(NULL);
00459 }
00460
00461
00462
00463
00464
00465
00466
00467
00468
00469
00470
00471
00472
00473
00474
00475 char *
UTIL_split_strr(
const char *s,
const char c,
const u_int8_t num)
00476 {
00477 u_int8_t i;
00478
00479
char *beg;
00480
char *cp;
00481
char *p;
00482
char *ret;
00483
00484
if (s == NULL)
00485 {
00486
xeprintf(
"Passed a NULL string. Abort!\n");
00487
return(NULL);
00488 }
00489
00490
xvprintf(
"Called with (%s)\n", s);
00491
00492 p = cp =
xstrndup(s, (strlen(s) + 1));
00493 beg = (
char *)&s;
00494
00495
while (*p)
00496 {
00497 p++;
00498 }
00499
00500 i = 0;
00501
while(p != beg)
00502 {
00503
if (*p == c)
00504 {
00505 i++;
00506
if (i == num)
00507 {
00508
if (*p ==
'.')
00509 {
00510 p++;
00511 }
00512 ret =
xstrndup(p, (strlen(p) + 1));
00513
xfree(cp);
00514
xvprintf(
"returning: %s\n", ret);
00515
return(ret);
00516 }
00517 }
00518 p--;
00519 }
00520
00521
xfree(cp);
00522
return(NULL);
00523 }
00524
00525
00526
00527
00528
00529
00530
00531
00532
00533
00534
00535
00536
00537
00538
00539
00540
00541 u_int8_t
UTIL_count_delim(
const char *s,
const char c)
00542 {
00543 u_int8_t i = 0;
00544
00545
if (s == NULL)
00546 {
00547
xeprintf(
"Passed a NULL string. Abort!\n");
00548
return(0);
00549 }
00550
00551
while (*s)
00552 {
00553
if (*s == c)
00554 {
00555 i++;
00556 }
00557 s++;
00558 }
00559
00560
xvprintf(
"returning: %i\n", i);
00561
return(i);
00562 }
00563
00564
00565
00566
00567
00568
00569
00570
00571
00572
00573
00574
00575
00576
00577
00578
00579
00580 size_t
UTIL_guess_whats_in_the_box(
char *s,
const char c,
const u_int16_t num)
00581 {
00582 u_int8_t i = 0;
00583 size_t bytes = 0;
00584
00585
if (s == NULL)
00586 {
00587
xeprintf(
"Passed a NULL string. Abort!\n");
00588
00589
return(0);
00590 }
00591
00592 bytes = strlen(s);
00593
00594
while (*s)
00595 {
00596
if (*s == c)
00597 {
00598 i++;
00599 }
00600
00601
if (i == num)
00602 {
00603 bytes--;
00604 s++;
00605
00606
xvprintf(
"return (%i bytes) (%s)\n", bytes, s);
00607
00608
return(bytes);
00609 }
00610
else
00611 {
00612 bytes--;
00613 s++;
00614 }
00615 }
00616
00617
xvprintf(
"[return (%i bytes) (%s)\n", bytes, s);
00618
00619
return(bytes);
00620 }
00621
00622
00623
00624
00625
00626
00627
00628
00629
00630
00631
00632
00633
00634
00635 SPF_BOOL UTIL_is_spf_delim(
const char c)
00636 {
00637
xvprintf(
"Called with char (%c)\n", c);
00638
00639
if (c ==
'.' || c ==
'-' || c ==
'+' || c ==
','
00640 || c ==
'|' || c ==
'_')
00641 {
00642
return(
TRUE);
00643 }
00644
00645
return(
FALSE);
00646 }
00647
00648
00649
00650
00651
00652
00653
00654
00655
00656
00657
00658
00659
00660
00661 SPF_BOOL UTIL_is_spf_result(
const char c)
00662 {
00663
xvprintf(
"Called with char (%c)\n", c);
00664
00665
if (c ==
'+' || c ==
'-' || c ==
'~' || c ==
'?')
00666 {
00667
return(
TRUE);
00668 }
00669
00670
return(
FALSE);
00671 }
00672
00673
00674
00675
00676
00677
00678
00679
00680
00681
00682
00683
00684
00685
00686
00687 SPF_BOOL UTIL_is_macro(
const char *s)
00688 {
00689
if (s == NULL)
00690 {
00691
xeprintf(
"Passed a NULL string. Abort!\n");
00692
00693
return(
FALSE);
00694 }
00695
00696
xvprintf(
"Called with char (%s)\n", s);
00697
00698
while (*s++)
00699 {
00700
if (*s ==
'%' && *(s + 1) ==
'{')
00701 {
00702
if (strstr(s,
"}"))
00703 {
00704
return(
TRUE);
00705 }
00706 }
00707 }
00708
00709
return(
FALSE);
00710 }
00711
00712
00713
00714
00715
00716
00717
00718
00719
00720
00721
00722
00723
00724
00725
00726
00727
00728 SPF_BOOL UTIL_mx_cmp(
peer_info_t *peer_info,
const char *s,
const int8_t cidr)
00729 {
00730
SPF_BOOL MX_SPF_MATCH =
FALSE;
00731
00732
char *rr_data = NULL;
00733
char *token;
00734
char *token_ptr;
00735
char *peer_ip;
00736
00737 token_ptr = rr_data;
00738
00739
if ((rr_data =
DNS_query(peer_info, s, T_MX, NULL)) == NULL)
00740 {
00741
xeprintf(
"SPF_ERROR parsing DNS Query\n");
00742
return(
FALSE);
00743 }
00744
00745
xvprintf(
"rr_data is: (%s)\n", rr_data);
00746
00747 peer_ip =
xstrndup(inet_ntoa(peer_info->
addr), 16);
00748 token = strtok_r(rr_data,
" ", &token_ptr);
00749
00750
while (token != NULL)
00751 {
00752
xvprintf(
"TOKEN: (%s)\n", token);
00753
00754
if (
UTIL_validate_hostname(peer_info, token, cidr) ==
TRUE)
00755 {
00756
xvprintf(
"%s validated via (%s)\n", peer_info->
from, token);
00757
00758 MX_SPF_MATCH =
TRUE;
00759
UTIL_assoc_prefix(peer_info,
SPF_PASS, NULL);
00760 token = NULL;
00761 }
00762
else
00763 {
00764 token = strtok_r(NULL,
" ", &token_ptr);
00765 }
00766 }
00767
00768
xfree(peer_ip);
00769
xfree(rr_data);
00770
00771
return(MX_SPF_MATCH);
00772 }
00773
00774
00775
00776
00777
00778
00779
00780
00781
00782
00783
00784
00785
00786
00787
00788
00789
00790
00791 SPF_BOOL UTIL_a_cmp(
peer_info_t *peer_info,
const char *s,
const int8_t cidr)
00792 {
00793 int16_t pos;
00794
00795
char *rr_data = NULL;
00796
char *token_ptr;
00797
00798
char *cp;
00799
char *copy;
00800
char **a;
00801
00802 size_t s_len;
00803
00804
struct hostent *host;
00805
00806
policy_addr_t *policy_addr;
00807
00808
if (s == NULL)
00809 {
00810
xeprintf(
"Passed string is NULL. Abort!.\n");
00811
00812
return(
FALSE);
00813 }
00814
00815
xvprintf(
"Called with (%s) and cidr: %i\n", s, cidr);
00816
00817 token_ptr = rr_data;
00818 s_len = strlen(s);
00819
00820
00821
if (s_len > 1 && *(s + 1) ==
':')
00822 {
00823
if (cidr != 32)
00824 {
00825
00826 cp[s_len - 3] =
'\0';
00827 }
00828
00829 cp = copy =
xstrndup(s, (s_len + 1));
00830
00831
if ((pos =
UTIL_index(cp,
':')) <= 0)
00832 {
00833
xeprintf(
"ERROR parsing passed mechanism token\n");
00834
00835
xfree(copy);
00836
return(
FALSE);
00837 }
00838
00839
00840 cp += (pos + 1);
00841 }
00842
else
00843 {
00844 cp = copy =
xstrndup(peer_info->
cur_dom,
00845 (strlen(peer_info->
cur_dom) + 1));
00846 }
00847
00848 policy_addr =
xmalloc(
sizeof(
policy_addr_t));
00849
00850
if ((host = gethostbyname(cp)) != NULL)
00851 {
00852
for (a = host->h_addr_list; *a; a++)
00853 {
00854 memcpy(&policy_addr->
addr.s_addr, *a,
sizeof(
struct in_addr));
00855
00856
xvprintf(
"Checking IP: %lu\n",policy_addr->
addr.s_addr);
00857
00858
00859 policy_addr->
cidr = cidr;
00860
00861
if (
UTIL_cidr_cmp(peer_info, policy_addr, &peer_info->
addr) ==
TRUE)
00862 {
00863 *a = NULL;
00864
xfree(policy_addr);
00865
xfree(copy);
00866
UTIL_assoc_prefix(peer_info,
SPF_PASS, NULL);
00867
return(
TRUE);
00868 }
00869 }
00870
00871
for (a = host->h_aliases; *a; a++)
00872 {
00873 memcpy(&policy_addr->
addr.s_addr, *a,
sizeof(
struct in_addr));
00874
00875
xvprintf(
"Checking ALIAS: %lu\n", policy_addr->
addr.s_addr);
00876
00877
00878 policy_addr->
cidr = cidr;
00879
00880
if (
UTIL_cidr_cmp(peer_info, policy_addr, &peer_info->
addr) ==
TRUE)
00881 {
00882 *a = NULL;
00883
xfree(policy_addr);
00884
xfree(copy);
00885
UTIL_assoc_prefix(peer_info,
SPF_PASS, NULL);
00886
return(
TRUE);
00887 }
00888 }
00889 }
00890
00891
xfree(policy_addr);
00892
xfree(copy);
00893
00894
return(
FALSE);
00895 }
00896
00897
00898
00899
00900
00901
00902
00903
00904
00905
00906
00907
00908
00909
00910
00911
00912
00913
00914
00915
00916
00917
00918
00919
00920
00921
00922
00923 SPF_BOOL UTIL_ptr_cmp(
peer_info_t *peer_info,
const char *s)
00924 {
00925
char *ptr_addr;
00926
char *tmp_ptr;
00927
00928
if (s == NULL)
00929 {
00930
xeprintf(
"Passed string is NULL. Abort!\n");
00931
return(
FALSE);
00932 }
00933
00934
xvprintf(
"Called with (%s)\n", s);
00935
00936
00937 ptr_addr =
UTIL_rev_addr(peer_info->
r_ip);
00938
00939
xvprintf(
"address: %s\n", ptr_addr);
00940
00941
if ((strstr(s,
":")) != NULL)
00942 {
00943 tmp_ptr =
xstrndup(s, (strlen(s) + 1));
00944 }
00945
else
00946 {
00947 tmp_ptr =
xstrndup(peer_info->
cur_dom,
00948 (strlen(peer_info->
cur_dom) + 1));
00949 }
00950
00951
if (
DNS_query(peer_info, ptr_addr, T_PTR, tmp_ptr) != (
char *)
TRUE)
00952 {
00953
xvprintf(
"PTR lookup failed: (%s) (%s)\n", peer_info->
rs, peer_info->
error);
00954
00955
xfree(ptr_addr);
00956
xfree(tmp_ptr);
00957
return(
FALSE);
00958 }
00959
00960
xvprintf(
"PTR lookup succeeded: (%s):(%s)\n", peer_info->
rs,
00961 peer_info->
error);
00962
00963
xfree(ptr_addr);
00964
xfree(tmp_ptr);
00965
return(
TRUE);
00966 }
00967
00968
00969
00970
00971
00972
00973
00974
00975
00976
00977
00978
00979
00980 SPF_MECHANISM UTIL_get_policy_mech(
const char *s)
00981 {
00982
xvprintf(
"Called with: (%s)\n", s);
00983
00984
if (s == NULL || !s)
00985 {
00986
xeprintf(
"Passed a NULL string. Abort!\n");
00987
return(
NO_POLICY);
00988 }
00989
00990
if (strncmp(s,
"v=", 2) == 0)
00991 {
00992
xvprintf(
"Returning %i (VERSION)\n",
VERSION);
00993
return(
VERSION);
00994 }
00995
else if (strncmp(s,
"ip4:", 4) == 0 )
00996 {
00997
xvprintf(
"Returning %i (IP4)\n",
IP4);
00998
return(
IP4);
00999 }
01000
else if (strncmp(s,
"ip6:", 4) == 0)
01001 {
01002
xvprintf(
"Returning %i (IP6)\n",
IP6);
01003
return(
IP6);
01004 }
01005
else if (strncmp(s,
"all", 3) == 0)
01006 {
01007
xvprintf(
"Returning %i (ALL)\n",
ALL);
01008
return(
ALL);
01009 }
01010
else if (strncmp(s,
"mx", 2) == 0)
01011 {
01012
xvprintf(
"Returning %i (MX)\n",
MX);
01013
return(
MX);
01014 }
01015
else if (strncmp(s,
"a:", 2) == 0 || (*s ==
'a' && *(s + 1) ==
'/')
01016 || ((*s ==
'a') && !*(s + 1)))
01017 {
01018
xvprintf(
"Returning %i (A)\n",
A);
01019
return(
A);
01020 }
01021
else if (strncmp(s,
"ptr", 3) == 0)
01022 {
01023
xvprintf(
"Returning %i (PTR)\n",
PTR);
01024
return(
PTR);
01025 }
01026
else if (strncmp(s,
"include", 7) == 0)
01027 {
01028
xvprintf(
"Returning %i (INCLUDE)\n",
INCLUDE);
01029
return(
INCLUDE);
01030 }
01031
else if (strncmp(s,
"exists", 6) == 0)
01032 {
01033
xvprintf(
"Returning %i (EXISTS)\n",
EXISTS);
01034
return(
EXISTS);
01035 }
01036
else if (strncmp(s,
"redirect", 8) == 0)
01037 {
01038
xvprintf(
"Returning %i (REDIRECT)\n",
REDIRECT);
01039
return(
REDIRECT);
01040 }
01041
else if (strncmp(s,
"exp", 3) == 0)
01042 {
01043
xvprintf(
"Returning %i (EXPLAIN)\n",
EXPLAIN);
01044
return(
EXPLAIN);
01045 }
01046
else if (strncmp(s,
"default", 7) == 0)
01047 {
01048
xvprintf(
"Returning %i (DEFAULT)\n",
DEFAULT);
01049
return(
DEFAULT);
01050 }
01051
else if (strstr(s,
":"))
01052 {
01053
xvprintf(
"Returning %i (UNMECH)\n",
UNMECH);
01054
return(
UNMECH);
01055 }
01056
01057
return(
NO_POLICY);
01058 }
01059
01060
01061
01062
01063
01064
01065
01066
01067
01068
01069
01070
01071
01072
01073
01074
01075
01076 SPF_BOOL UTIL_assoc_prefix(
peer_info_t *peer_info, SPF_RESULT p,
const char *s)
01077 {
01078 int16_t pos;
01079
01080
if (s != NULL)
01081 {
01082
xvprintf(
"(QID: %u) :: Entering function (%i) (%s)\n",
spf_rlevel, p, s);
01083
01084
01085
if (strncmp(s,
"default", 7) == 0 && (pos =
UTIL_index(s,
'=')) > 0)
01086 {
01087 s += (pos + 1);
01088
if (strncmp(s,
"deny", 4) == 0)
01089 {
01090
xvprintf(
"(QID: %u) :: Stored SPF_H_FAIL (%i) (%i)\n",
01091
spf_rlevel, p,
SPF_H_FAIL);
01092
01093 peer_info->
RES =
SPF_H_FAIL;
01094 peer_info->
rs = peer_info->
spf_result[
SPF_H_FAIL].
s;
01095
01096 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01097
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01098
01099
return(
TRUE);
01100 }
01101
else if (strncmp(s,
"pass", 4) == 0)
01102 {
01103
xvprintf(
"(QID: %u) :: Stored SPF_PASS (%i) (%i)\n",
01104
spf_rlevel, p,
SPF_PASS);
01105
01106 peer_info->
RES =
SPF_PASS;
01107 peer_info->
rs = peer_info->
spf_result[
SPF_PASS].
s;
01108 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01109
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01110
return(
TRUE);
01111 }
01112
else if (strncmp(s,
"softdeny", 8) == 0)
01113 {
01114
xvprintf(
"(QID: %u) :: Stored SPF_S_FAIL (%i) (%i)\n",
01115
spf_rlevel, p,
SPF_S_FAIL);
01116
01117 peer_info->
RES =
SPF_S_FAIL;
01118 peer_info->
rs = peer_info->
spf_result[
SPF_S_FAIL].
s;
01119 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01120
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01121
return(
TRUE);
01122 }
01123
else if (strncmp(s,
"unknown", 7) == 0)
01124 {
01125
xvprintf(
"(QID: %u) :: Stored SPF_NEUTRAL (%i) (%i)\n",
01126
spf_rlevel, p,
SPF_NEUTRAL);
01127
01128 peer_info->
RES =
SPF_NEUTRAL;
01129 peer_info->
rs = peer_info->
spf_result[
SPF_NEUTRAL].
s;
01130 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01131
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01132
return(
TRUE);
01133 }
01134
else if (strncmp(s,
"include", 7) == 0)
01135 {
01136
xvprintf(
"(QID: %u) :: Stored SPF_UNKNOWN (%i) (%i)\n",
01137
spf_rlevel, p,
SPF_UNKNOWN);
01138
01139 peer_info->
RES =
SPF_UNKNOWN;
01140 peer_info->
rs = peer_info->
spf_result[
SPF_UNKNOWN].
s;
01141 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01142
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01143
return(
TRUE);
01144 }
01145
else
01146 {
01147
xvprintf(
"(QID: %u) :: Stored SPF_ERROR (%i) (%i)\n",
01148
spf_rlevel, p,
SPF_ERROR);
01149
01150 peer_info->
RES =
SPF_UNKNOWN;
01151 peer_info->
rs = peer_info->
spf_result[
SPF_UNKNOWN].
s;
01152 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01153
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01154
return(
FALSE);
01155 }
01156 }
01157 }
01158
01159
switch (p)
01160 {
01161
case SPF_PASS:
01162
xvprintf(
"(QID: %u) :: Stored SPF_PASS (%i) (%i)\n",
01163
spf_rlevel, p,
SPF_PASS);
01164
01165 peer_info->
RES =
SPF_PASS;
01166 peer_info->
rs = peer_info->
spf_result[
SPF_PASS].
s;
01167 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01168
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01169
return(
TRUE);
01170
case SPF_NONE:
01171
xvprintf(
"(QID: %u) :: Stored SPF_NONE (%i) (%i)\n",
01172
spf_rlevel, p,
SPF_NONE);
01173
01174 peer_info->
RES =
SPF_NONE;
01175 peer_info->
rs = peer_info->
spf_result[
SPF_NONE].
s;
01176 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01177
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01178
return(
TRUE);
01179
case SPF_S_FAIL:
01180
xvprintf(
"(QID: %u) :: Stored SPF_S_FAIL (%i) (%i)\n",
01181
spf_rlevel, p,
SPF_S_FAIL);
01182
01183 peer_info->
RES =
SPF_S_FAIL;
01184 peer_info->
rs = peer_info->
spf_result[
SPF_S_FAIL].
s;
01185 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01186
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01187
return(
TRUE);
01188
case SPF_H_FAIL:
01189
xvprintf(
"(QID: %u) :: Stored SPF_H_FAIL (%i) (%i)\n",
01190
spf_rlevel, p,
SPF_H_FAIL);
01191
01192 peer_info->
RES =
SPF_H_FAIL;
01193 peer_info->
rs = peer_info->
spf_result[
SPF_H_FAIL].
s;
01194 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01195
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01196
return(
TRUE);
01197
case SPF_NEUTRAL:
01198
xvprintf(
"(QID: %u) :: Stored SPF_NEUTRAL (%i) (%i)\n",
01199
spf_rlevel, p,
SPF_NEUTRAL);
01200
01201 peer_info->
RES =
SPF_NEUTRAL;
01202 peer_info->
rs = peer_info->
spf_result[
SPF_NEUTRAL].
s;
01203 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01204
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01205
return(
TRUE);
01206
case SPF_UNKNOWN:
01207
xvprintf(
"(QID: %u) :: Stored SPF_UNKNOWN (%i) (%i)\n",
01208
spf_rlevel, p,
SPF_UNKNOWN);
01209
01210 peer_info->
RES =
SPF_UNKNOWN;
01211 peer_info->
rs = peer_info->
spf_result[
SPF_UNKNOWN].
s;
01212 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01213
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01214
return(
TRUE);
01215
case SPF_ERROR:
01216
xvprintf(
"(QID: %u) :: Stored SPF_ERROR (%i) (%i)\n",
01217
spf_rlevel, p,
SPF_ERROR);
01218
01219 peer_info->
RES =
SPF_ERROR;
01220 peer_info->
rs = peer_info->
spf_result[
SPF_ERROR].
s;
01221 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01222
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01223
return(
TRUE);
01224
case SPF_UNMECH:
01225
xvprintf(
"(QID: %u) :: Stored SPF_UNMECH (%i) (%i)\n",
01226
spf_rlevel, p,
SPF_UNMECH);
01227
01228 peer_info->
RES =
SPF_UNMECH;
01229 peer_info->
rs = peer_info->
spf_result[
SPF_UNMECH].
s;
01230 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01231
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01232
return(
TRUE);
01233
01234
default:
01235
xvprintf(
"(QID: %u) :: Stored SPF_PASS (%i) (%i)\n",
01236
spf_rlevel, p,
SPF_PASS);
01237
01238 peer_info->
RES =
SPF_PASS;
01239 peer_info->
rs = peer_info->
spf_result[
SPF_PASS].
s;
01240 snprintf(peer_info->
error,
MAX_ERROR,
"policy result: (%s) from rule " \
01241
"(%s)\n", peer_info->
rs, peer_info->
last_m);
01242
return(
TRUE);
01243 }
01244
01245
return(
FALSE);
01246 }
01247
01248
01249
01250
01251
01252
01253
01254
01255
01256
01257
01258
01259
01260
01261
01262 SPF_RESULT UTIL_get_mech_prefix(
peer_info_t *peer_info,
const char *s)
01263 {
01264 int16_t pos;
01265
01266
if (s == NULL)
01267 {
01268
xeprintf(
"Passed a NULL string. Abort!\n");
01269
return(
SPF_ERROR);
01270 }
01271
01272 snprintf(peer_info->
last_m, (strlen(s) +1),
"%s", s);
01273
01274
switch (*s)
01275 {
01276
case '+':
01277
xvprintf(
"(QID: %u) :: Returning SPF_PASS (%s) %i\n",
01278
spf_rlevel, s,
SPF_PASS);
01279 peer_info->
RES_P =
SPF_PASS;
01280
return(
SPF_PASS);
01281
case '-':
01282
xvprintf(
"(QID: %u) :: Returning SPF_H_FAIL (%s) %i\n",
01283
spf_rlevel, s,
SPF_H_FAIL);
01284 peer_info->
RES_P =
SPF_H_FAIL;
01285
return(
SPF_H_FAIL);
01286
case '?':
01287
xvprintf(
"(QID: %u) :: Returning SPF_NEUTRAL (%s) %i\n",
01288
spf_rlevel, s,
SPF_NEUTRAL);
01289 peer_info->
RES_P =
SPF_NEUTRAL;
01290
return(
SPF_NEUTRAL);
01291
case '~':
01292
xvprintf(
"(QID: %u) :: Returning SPF_S_FAIL (%s) %i\n",
01293
spf_rlevel, s,
SPF_S_FAIL);
01294 peer_info->
RES_P =
SPF_S_FAIL;
01295
return(
SPF_S_FAIL);
01296
default:
01297
if (peer_info->
ALL ==
TRUE)
01298 {
01299
xvprintf(
"(QID: %u) :: Returning (def) SPF_NEUTRAL (%s) %i\n",
01300
spf_rlevel, s,
SPF_NEUTRAL);
01301 peer_info->
RES_P =
SPF_NEUTRAL;
01302 }
01303
else
01304 {
01305
xvprintf(
"(QID: %u) :: Returning (def) SPF_PASS (%s) %i\n",
01306
spf_rlevel, s,
SPF_PASS);
01307 peer_info->
RES_P =
SPF_PASS;
01308 }
01309
return(peer_info->
RES_P);
01310 }
01311
01312
01313
if ((pos =
UTIL_index(s,
'=')) > 0)
01314 {
01315 s += (pos + 1);
01316
01317
if (strncmp(s,
"deny", 4) == 0)
01318 {
01319 peer_info->
RES_P =
SPF_H_FAIL;
01320
return(
SPF_H_FAIL);
01321 }
01322
else if (strncmp(s,
"pass", 4) == 0)
01323 {
01324 peer_info->
RES_P =
SPF_PASS;
01325
return(
SPF_PASS);
01326 }
01327
else if (strncmp(s,
"softdeny", 8) == 0)
01328 {
01329 peer_info->
RES_P =
SPF_S_FAIL;
01330
return(
SPF_S_FAIL);
01331 }
01332
else if (strncmp(s,
"unknown", 7) == 0)
01333 {
01334 peer_info->
RES_P =
SPF_NEUTRAL;
01335
return(
SPF_NEUTRAL);
01336 }
01337
else
01338 {
01339
return(
SPF_NEUTRAL);
01340 }
01341 }
01342
01343
xvprintf(
"Undetermined, returning "
01344
"SPF_PASS (%s)\n", s);
01345
01346
return(
SPF_ERROR);
01347 }
01348
01349
01350
01351
01352
01353
01354
01355
01356
01357
01358
01359
01360
01361
01362
01363
01364
01365 policy_addr_t *
UTIL_expand_ip(
const char *s)
01366 {
01367 size_t len;
01368
const char *token_ptr;
01369 size_t pos;
01370
01371
char *ip;
01372 int8_t cidr = 0;
01373
01374
policy_addr_t *policy_addr;
01375
01376
if (s == NULL)
01377 {
01378
xeprintf(
"Passed a NULL string. Abort!\n");
01379
return(NULL);
01380 }
01381
01382 len = strlen(s);
01383 token_ptr = s;
01384
01385
xvprintf(
"Called with string: (%s)\n", token_ptr);
01386
01387
if ((pos =
UTIL_index(token_ptr,
':')) == 0)
01388 {
01389
xvprintf(
"SPF_ERROR: Unable to get position on token (%s)\n",
01390 token_ptr);
01391
01392
return(NULL);
01393 }
01394
01395
01396 token_ptr += pos + 1;
01397
01398 policy_addr =
xmalloc(
sizeof(
policy_addr_t));
01399
01400
01401
if ((pos =
UTIL_index(token_ptr,
'/')) == 0)
01402 {
01403
xvprintf(
"Unable to get position on token (%s), assuming /32 cidr "
01404
"block\n", token_ptr);
01405
01406 pos = strlen(token_ptr);
01407 cidr = 32;
01408 }
01409
01410
01411 ip =
xstrndup(token_ptr, (pos + 1));
01412
01413
01414
if ((inet_pton(AF_INET, ip, &policy_addr->
addr)) == 0)
01415 {
01416
xvprintf(
"SPF_ERROR: inet_pton unable to convert ip to binary "
01417
"(%s)\n", ip);
01418
01419
xfree(ip);
01420
return(NULL);
01421 }
01422
01423
if (cidr != 32)
01424 {
01425 token_ptr += (pos + 1);
01426 cidr = atoi(token_ptr);
01427 }
01428
01429
xfree(ip);
01430
01431
if (cidr < 0 || cidr > 32)
01432 {
01433
xvprintf(
"SPF_ERROR: cidr violation (%u)\n", cidr);
01434
return(NULL);
01435 }
01436
01437 policy_addr->
cidr = cidr;
01438
01439
xvprintf(
"CIDR: (%i) IP: (%s)\n", policy_addr->
cidr,
01440 inet_ntoa(policy_addr->
addr));
01441
01442
return(policy_addr);
01443 }
01444
01445
01446
01447
01448
01449
01450
01451
01452
01453
01454
01455
01456
01457
01458
01459 SPF_BOOL UTIL_is_ip(
const char *
id)
01460 {
01461 u_int8_t i = 0;
01462
01463
while (*id)
01464 {
01465
if (*
id ==
'.')
01466 {
01467 i++;
01468 }
01469
else if (isdigit(*
id) == 0)
01470 {
01471
return(
FALSE);
01472 }
01473
id++;
01474 }
01475
01476
if (i == 3)
01477 {
01478
return(
TRUE);
01479 }
01480
01481
return(
FALSE);
01482 }
01483
01484
01485
01486
01487
01488
01489
01490
01491
01492
01493
01494
01495
01496
01497
01498 char *
UTIL_rev_addr(
const char *s)
01499 {
01500 u_int8_t i = 0;
01501 u_int16_t len = 0;
01502 u_int8_t tmp[4][1];
01503
01504
char *cp;
01505
char *token;
01506
char *new_addr;
01507
01508
if (s == NULL)
01509 {
01510
xeprintf(
"Passed a null string. Abort!\n");
01511
return(NULL);
01512 }
01513
01514
xvprintf(
"Called with: (%s) len: %i\n", s, strlen(s));
01515
01516 len = (strlen(s) + 1);
01517 cp =
xstrndup(s, len);
01518 token = strtok(cp,
".");
01519
01520
while (token != NULL && i <= 3)
01521 {
01522
xvprintf(
"token : (%s)\n", token);
01523 tmp[i][0] = atoi(token);
01524 token = strtok(NULL,
".");
01525 i++;
01526 }
01527
01528
xfree(cp);
01529
01530
01531 new_addr =
xmalloc(len + 13);
01532
01533 memset(new_addr,
'\0', len);
01534 sprintf(new_addr,
"%u.%u.%u.%u.in-addr.arpa", tmp[3][0], tmp[2][0],
01535 tmp[1][0], tmp[0][0]);
01536
01537
xvprintf(
"Returning reversed ip: %s\n", new_addr);
01538
01539
return(new_addr);
01540 }
01541
01542
01543
01544
01545
01546
01547
01548
01549
01550
01551
01552
01553
01554
01555
01556
01557 char *
UTIL_get_dname(
const char *s)
01558 {
01559 u_int8_t i = 0;
01560
char *buf = NULL;
01561
01562
if (s == NULL)
01563 {
01564
xeprintf(
"Called with NULL. Abort!\n");
01565
01566
return(NULL);
01567 }
01568
01569
xvprintf(
"Called with (%s)\n", s);
01570
01571 i =
UTIL_count_delim(s,
'.');
01572
01573
switch (i)
01574 {
01575
case 0:
01576
return(NULL);
01577
case 1:
01578 buf =
xstrndup(s, (strlen(s) + 1));
01579
return(buf);
01580
default:
01581 buf =
UTIL_split_str(s,
'.', (i - 1));
01582
return(buf);
01583 }
01584
01585
return(NULL);
01586 }
01587
01588
01589
01590
01591
01592
01593
01594
01595
01596
01597
01598
01599
01600
01601
01602
01603
01604 SPF_BOOL UTIL_cidr_cmp(
peer_info_t *peer_info,
const policy_addr_t *policy_addr,
01605
const struct in_addr *peer_addr)
01606 {
01607 u_int32_t a;
01608 u_int32_t b;
01609
01610
char *peer_ip = NULL;
01611
char *policy_ip = NULL;
01612
01613
if ((policy_addr->
addr.s_addr <= 0) &&
01614 (peer_addr->s_addr <= 0))
01615 {
01616
xeprintf(
"Passed with NULL chars. Aborting.\n");
01617
return(
FALSE);
01618 }
01619
01620
xvprintf(
"POL: %lu PEER: %lu CIDR: %i\n", policy_addr->
addr.s_addr,
01621 peer_addr->s_addr, policy_addr->
cidr);
01622
01623 a = ntohl(peer_addr->s_addr);
01624 b = ntohl(policy_addr->
addr.s_addr);
01625
01626
if (policy_addr->
cidr != 32)
01627 {
01628
if ((a&(~0U<<(32-policy_addr->
cidr))) != (b&(~0U<<(32-policy_addr->
cidr))))
01629 {
01630
return(
FALSE);
01631 }
01632 }
01633
else
01634 {
01635
if (peer_addr->s_addr != policy_addr->
addr.s_addr)
01636 {
01637
xvprintf(
"%lu and %lu using 32 cidr do not match\n", peer_addr->s_addr,
01638 policy_addr->
addr.s_addr);
01639
return(
FALSE);
01640 }
01641 }
01642
01643
01644 peer_ip =
xstrndup(inet_ntoa(*peer_addr),
IP_ADDR);
01645 policy_ip =
xstrndup(inet_ntoa(policy_addr->
addr),
IP_ADDR);
01646
01647
xvprintf(
"Peer: (%s) matches address %s with network %i\n", peer_ip,
01648 policy_ip, policy_addr->
cidr);
01649
01650
xfree(peer_ip);
01651
xfree(policy_ip);
01652
01653
return(
TRUE);
01654 }
01655
01656
01657
01658
01659
01660
01661
01662
01663
01664
01665
01666
01667
01668
01669
01670
01671
01672
01673 SPF_BOOL UTIL_validate_ptr(
peer_info_t *peer_info)
01674 {
01675
char *ptr_addr;
01676
char *tmp_ptr;
01677
01678
01679 ptr_addr =
UTIL_rev_addr(peer_info->
r_ip);
01680
xvprintf(
"[address: %s]\n", ptr_addr);
01681
01682 tmp_ptr =
xstrndup(peer_info->
cur_dom, (strlen(peer_info->
cur_dom) + 1));
01683
01684
if (
DNS_query(peer_info, ptr_addr, T_PTR, tmp_ptr) != (
char *)
TRUE)
01685 {
01686
xvprintf(
"PTR lookup failed: (%s) (%s)\n", peer_info->
rs,
01687 peer_info->
error);
01688
01689
xfree(ptr_addr);
01690
xfree(tmp_ptr);
01691
return(
FALSE);
01692 }
01693
01694
xvprintf(
"Peer (%s) successfully validated hostname (%s)\n",
01695 peer_info->
r_ip, peer_info->
r_vhname);
01696
01697
xfree(ptr_addr);
01698
xfree(tmp_ptr);
01699
return(
TRUE);
01700 }
01701
01702
01703
01704
01705
01706
01707
01708
01709
01710
01711
01712
01713
01714
01715
01716
01717
01718
01719 SPF_BOOL UTIL_validate_hostname(
peer_info_t *peer_info,
const char *s,
01720
const int8_t cidr)
01721 {
01722
char **a;
01723
char *val_ip;
01724
01725
struct in_addr addr;
01726
char *ip = NULL;
01727
01728
struct in_addr val_addr;
01729
struct hostent *hp;
01730
01731
policy_addr_t *policy_addr;
01732
01733
if (s == NULL)
01734 {
01735
xeprintf(
"Passed a NULL string.\n");
01736
return(
FALSE);
01737 }
01738
01739
xvprintf(
"Called with: (%lu) and (%s)\n", peer_info->
r_ip, s);
01740
01741
if ((hp = gethostbyname(s)) != NULL)
01742 {
01743
for (a = hp->h_addr_list; *a; a++)
01744 {
01745 memcpy(&addr.s_addr, *a,
sizeof(
struct in_addr));
01746 ip =
xstrndup(inet_ntoa(addr),
IP_ADDR);
01747
01748
xvprintf(
"CLI: %s (%lu) SRV: %s (%lu)\n", ip, addr.s_addr,
01749 peer_info->
r_ip, peer_info->
addr.s_addr);
01750
01751
if (cidr == 32)
01752 {
01753
if (((
struct in_addr *)(*a))->s_addr == peer_info->
addr.s_addr)
01754 {
01755
xvprintf(
"%s (%lu) matches %s (%lu)\n", ip,
01756 ((
struct in_addr *)(*a))->s_addr, peer_info->
r_ip,
01757 peer_info->
addr.s_addr);
01758
01759
xfree(ip);
01760
UTIL_assoc_prefix(peer_info,
SPF_PASS, NULL);
01761
return(
TRUE);
01762 }
01763 }
01764
else if ((cidr < 32) && (cidr >= 8))
01765 {
01766 memcpy(&val_addr.s_addr, hp->h_addr, hp->h_length);
01767 val_ip =
xstrndup(inet_ntoa(val_addr),
IP_ADDR);
01768
01769
xvprintf(
"IP: (%s)\n", val_ip);
01770
01771 policy_addr =
xmalloc(
sizeof(
policy_addr_t));
01772
01773
if ((inet_pton(AF_INET, val_ip, &policy_addr->
addr)) == 0)
01774 {
01775
xeprintf(
"Unable to execute inet_pton()\n");
01776 }
01777
01778 policy_addr->
cidr = cidr;
01779
01780
if ((
UTIL_cidr_cmp(peer_info, policy_addr, &peer_info->
addr)) ==
TRUE)
01781 {
01782
xvprintf(
"(%lu) matches (%lu) with CIDR %u\n",
01783 policy_addr->
addr.s_addr, peer_info->
addr.s_addr, cidr);
01784
01785
xfree(ip);
01786
xfree(policy_addr);
01787
xfree(val_ip);
01788
UTIL_assoc_prefix(peer_info,
SPF_PASS, NULL);
01789
return(
TRUE);
01790 }
01791
else
01792 {
01793
xfree(policy_addr);
01794
xfree(val_ip);
01795 }
01796 }
01797
xfree(ip);
01798 }
01799
01800
for (a = hp->h_aliases; *a; a++)
01801 {
01802 memcpy(&addr.s_addr, *a,
sizeof(
struct in_addr));
01803 ip =
xstrndup(inet_ntoa(addr),
IP_ADDR);
01804
01805
xvprintf(
"CLI: %s (%lu) SRV: %s (%lu)\n", ip, addr.s_addr,
01806 peer_info->
r_ip, peer_info->
addr.s_addr);
01807
01808
if (cidr == 32)
01809 {
01810
if (((
struct in_addr *)(*a))->s_addr == peer_info->
addr.s_addr)
01811 {
01812
xvprintf(
"%s (%lu) SPF_MATCHes %s (%lu)\n", ip,
01813 ((
struct in_addr *)(*a))->s_addr, peer_info->
r_ip,
01814 peer_info->
addr.s_addr);
01815
01816
xfree(ip);
01817
return(
TRUE);
01818 }
01819 }
01820
else if ((cidr < 32) && (cidr >= 8))
01821 {
01822 memcpy(&val_addr.s_addr, hp->h_addr, hp->h_length);
01823 val_ip =
xstrndup(inet_ntoa(val_addr),
IP_ADDR);
01824
01825
xvprintf(
"ALIAS: (%s)\n",
01826 val_ip);
01827
01828 policy_addr =
xmalloc(
sizeof(
policy_addr_t));
01829
01830
if ((inet_pton(AF_INET, val_ip, &policy_addr->
addr)) == 0)
01831 {
01832
xeprintf(
"Unable to execute inet_pton()\n");
01833 }
01834
01835 policy_addr->
cidr = cidr;
01836
01837
if ((
UTIL_cidr_cmp(peer_info, policy_addr, &peer_info->
addr)) ==
TRUE)
01838 {
01839
xvprintf(
"(%lu) matches (%lu) with CIDR %u\n",
01840 policy_addr->
addr.s_addr, peer_info->
addr.s_addr, cidr);
01841
01842
xfree(ip);
01843
xfree(policy_addr);
01844
xfree(val_ip);
01845
UTIL_assoc_prefix(peer_info,
SPF_PASS, NULL);
01846
return(
TRUE);
01847 }
01848
else
01849 {
01850
xfree(policy_addr);
01851
xfree(val_ip);
01852 }
01853 }
01854
xfree(ip);
01855 }
01856 }
01857
else
01858 {
01859
xvprintf(
"Unable to obtain ip address for (%s)\n", s);
01860 }
01861
01862
return(
FALSE);
01863 }
01864
01865
01866
01867
01868
01869
01870
01871
01872
01873
01874
01875
01876
01877
01878
01879
01880
01881 char *
UTIL_url_encode(
const char *s)
01882 {
01883
int len;
01884
char *
new;
01885
char *encoded;
01886
01887
if (s != NULL)
01888 {
01889
01890
01891 len = (strlen(s) * 3);
01892 }
01893
else
01894 {
01895
xeprintf(
"Passed a NULL string. Abort!\n");
01896
return(NULL);
01897 }
01898
01899 encoded =
new =
xmalloc(len);
01900
01901
while (*s !=
'\0')
01902 {
01903
if (
urlchr_test(*s) == 0)
01904 {
01905 *
new++ = *s++;
01906 }
01907
else
01908 {
01909 snprintf(
new, 4,
"%%%x", *s);
01910
new += 3; s++;
01911 }
01912 }
01913
01914 *
new++ =
'\0';
01915
xvprintf(
"[%s] UTIL_url_encode :: Returning (%s)\n", encoded);
01916
01917
return(encoded);
01918 }
01919
01920
01921
01922
01923
01924
01925
01926
01927
01928
01929
01930
01931
01932
01933 char *
UTIL_reverse(
const char *s,
const char delim)
01934 {
01935 size_t len;
01936
01937
split_str_t *master;
01938
split_str_node_t *c_node;
01939
split_str_node_t *kill_node;
01940
01941
char *buf;
01942
char *p;
01943
char *cp;
01944
char *c;
01945
01946
if (s == NULL)
01947 {
01948
xeprintf(
"Passed a NULL string. Abort!\n");
01949
return(NULL);
01950 }
01951
01952
xvprintf(
"Called with (%s) and delim (%c)\n",
01953 s, delim);
01954
01955 len = strlen(s);
01956 cp = c =
xstrndup(s, (len + 1));
01957
01958 master =
xmalloc(
sizeof(
split_str_t));
01959 master->
head = NULL;
01960 master->
tail = NULL;
01961 master->
elements = 0;
01962
01963
01964
01965
01966
01967
01968
01969
01970
01971
01972
01973
01974 buf =
xmalloc(len + 1);
01975 memset(buf,
'\0', (len + 1));
01976
01977
while ((p = strrchr(cp, delim)) != NULL)
01978 {
01979 p++;
01980
UTIL_addnode(master, p,
TRUE);
01981 p--;
01982 *p =
'\0';
01983 }
01984
01985
UTIL_addnode(master, cp,
FALSE);
01986
01987 c_node = master->
head;
01988
while ((kill_node = c_node) != NULL)
01989 {
01990 strncat(buf, kill_node->
s, kill_node->
len);
01991
xfree(kill_node->
s);
01992 c_node = c_node->
next;
01993
xfree(kill_node);
01994 }
01995
01996
xfree(cp);
01997
xfree(master);
01998
01999
xvprintf(
"Returning (%s)\n", buf);
02000
02001
return(buf);
02002 }
02003
02004
02005
02006
02007
02008
02009
02010
02011
02012
02013
02014
02015
02016
02017
02018
02019
02020 SPF_BOOL UTIL_addnode(
split_str_t *master,
const char *s, SPF_BOOL last)
02021 {
02022 size_t len;
02023
02024
split_str_node_t *c_node;
02025
split_str_node_t *new_node;
02026
split_str_node_t *prev_node;
02027
02028
if (s == NULL)
02029 {
02030
xeprintf(
"Passed a NULL string. Abort!\n");
02031
return(
FALSE);
02032 }
02033
02034 len = strlen(s);
02035
02036
if (last ==
TRUE)
02037 {
02038 len += 2;
02039 }
02040
else
02041 {
02042 len++;
02043 }
02044
02045
02046 new_node =
xmalloc(
sizeof(
split_str_node_t));
02047
02048
02049 new_node->
next = NULL;
02050
02051 new_node->
s =
xmalloc(len);
02052 memset(new_node->
s,
'\0', len);
02053
02054
02055
02056
02057
02058
02059
02060
02061
02062 snprintf(new_node->
s, len,
"%s%c", s, last ?
'.' :
'\0');
02063 new_node->
len = (len - 1);
02064
02065 prev_node = NULL;
02066 c_node = master->
head;
02067
02068
02069
while (c_node != NULL)
02070 {
02071 prev_node = c_node;
02072 c_node = c_node->
next;
02073 }
02074
02075
if (prev_node != NULL)
02076 {
02077 new_node->
next = prev_node->
next;
02078 prev_node->
next = new_node;
02079 }
02080
else
02081 {
02082 master->
head = new_node;
02083 }
02084
02085 master->
tail = new_node;
02086 master->
elements++;
02087
02088
return(
TRUE);
02089 }
02090
02091
02092