From: Jean-Marc Pigeon (Delson) Date: Thu, 15 Aug 2024 16:34:16 +0000 (-0400) Subject: work in progess on unidns.c X-Git-Tag: tag-0.4.2-end~28 X-Git-Url: https://jmp-git.ovh.safe.ca/?a=commitdiff_plain;h=f9852ca7ac69b7a2487332778f7af919740d71cf;p=jmp%2Fmailleur work in progess on unidns.c --- diff --git a/app/chkdns.c b/app/chkdns.c index c4b63df..5326d88 100644 --- a/app/chkdns.c +++ b/app/chkdns.c @@ -28,11 +28,13 @@ int main(int argc,char *argv[]) { int status; +int try; char *curname; int phase; _Bool proceed; status=0; +try=0; if ((curname=strrchr(argv[0],'/'))==(char *)0) curname=argv[0]; else @@ -59,7 +61,7 @@ while (proceed==true) { if (argv[1]!=(char *)0) { //always SPFENU spf; - spf=dns_get_spf_status(argv[1],argv[2]); + spf=dns_get_spf_status(&try,argv[1],argv[2]); (void) rou_alert(0,"%s %s ==> %s",argv[1],argv[2],dns_spfASCII(spf)); } break; diff --git a/lib/subrou.c b/lib/subrou.c index 31f6d15..7d767ef 100644 --- a/lib/subrou.c +++ b/lib/subrou.c @@ -21,7 +21,7 @@ //version definition #define VERSION "0.4.2" -#define RELEASE "7" +#define RELEASE "8" //Public variables PUBLIC int debug=0; //debug level diff --git a/lib/unidns.c b/lib/unidns.c index 4693183..34c2983 100644 --- a/lib/unidns.c +++ b/lib/unidns.c @@ -17,15 +17,30 @@ #include "subrou.h" #include "unidns.h" +#define MXDNS 10 //maximun number of DNS acess + //spf1 marker within DNS record #define SPF1 "v=spf1 " -#define B64K 65536 /*according US Cert VU#738331 */ +#define B64K 65536 //according US Cert VU#738331 typedef union { - HEADER hdr; /*defined in resolv.h */ - u_char buf[B64K]; /*according US Cert VU#738331 */ + HEADER hdr; //defined in resolv.h + u_char buf[B64K]; //according US Cert VU#738331 }RSPTYP; +typedef enum { //mechanism definition + mch_all, //"all" + mch_a, //'a' + mch_exists, //"existe" + mch_include, //"include" + mch_ip4, //"ip4" + mch_ip6, //"ip6" + mch_mx, //"mx" + mch_ptr, //"mx" + mch_redirect, //"redirect" + mch_unknown //unknown mechanism + }MCHTYP; + static _Bool modopen; //module open/close status /* @@ -35,16 +50,12 @@ static _Bool modopen; //module open/close status /* Procedure to display SPF debug information */ /* */ /********************************************************/ -static void dbgspf(int dbg,AFNTYP *afnnum,char *seq,SPFENU status) +static void dbgspf(int dbg,char *peerip,char *seq,SPFENU status) { if (debug>-dbg) { - char *strip; - - strip=afn_stripnum(afnnum); (void) rou_alert(dbg,"Current SPF Value <%s>\n\tIP=[%s]\n\tSPF=<%s>", - dns_spfASCII(status),strip,seq); - strip=rou_freestr(strip); + dns_spfASCII(status),peerip,seq); } } /* @@ -52,6 +63,47 @@ if (debug>-dbg) { */ /********************************************************/ /* */ +/* Procedure to parse mechanisme string */ +/* */ +/********************************************************/ +static MCHTYP tellmechanism(char *seq) + +{ +//MUST be set in the MCHTYP order +static char *voc[]= + { + "all", //allways match + "a", //addresss + "exists", //allways match + "include", //include sub domain + "ip4", //IPV4 address format + "ip6", //IPV5 address format + "mx", //MX definition + "ptr", //PTR definition + "redirect", //PTR definition + (char *)0 + }; + +MCHTYP mch; + +mch=mch_unknown; +for (int i=0;voc[i]!=(char *)0;i++) { + register int taille; + + taille=strlen(voc[i]); + if (strncmp(voc[i],seq,taille)!=0) + continue; + (void) memmove(seq,seq+taille,strlen(seq+taille)+1); + mch=(MCHTYP)i; + break; + } +return mch; +} +/* + +*/ +/********************************************************/ +/* */ /* Procedure to get the next SPF component */ /* return a dynamic char pointer with the isolated */ /* SPF sequence. */ @@ -113,7 +165,7 @@ return seq; /* sequence contents */ /* */ /********************************************************/ -static SPFENU checkseq(char *seq,AFNTYP *afnum,SPFENU spf) +static SPFENU checkseq(int *try,char *seq,char *peerip,SPFENU spf) { #define OPEP "unidns.c:checkseq" @@ -141,7 +193,7 @@ while (proceed==true) { spf=spf_fail; break; default : - (void) rou_alert(0,"%s <%s> is not an expected SPF Mechanisms (Bug?)", + (void) rou_alert(0,"%s <%s> is not an expected SPF Prefix (Bug?)", OPEP,seq); break; } @@ -149,6 +201,27 @@ while (proceed==true) { } break; case 1 : //check directive + switch (tellmechanism(seq)) { + case mch_include : //include sub domain + (void) printf("JMPDBG should include <%s>\n",seq+1); + if (seq[0]==':') { + (*try)++; + spf=dns_get_spf_status(try,seq+1,peerip); + } + else { + (void) rou_alert(0,"%s wrong SPF include seq <%s> (SPF format?)", + OPEP,seq); + spf=spf_permerr; + } + break; + default : //trouble + break; + case mch_unknown : //trouble + (void) rou_alert(0,"%s unknown mechanism <%s> (bug?, config?)", + OPEP,seq); + spf=spf_permerr; + break; + } break; default : //SAFE guard proceed=false; @@ -408,26 +481,20 @@ return infspf; /* spf allowed IP */ /* */ /********************************************************/ -static SPFENU is_peerip_ok(char *peerip,char *spfrec) +static SPFENU is_peerip_ok(int *try,char *peerip,char *spfrec) { #define OPEP "unidns.c:is_peerip_ok" SPFENU spf; -AFNTYP *afnnum; int phase; _Bool proceed; spf=spf_permerr; -afnnum=(AFNTYP *)0; phase=0; proceed=true; while (proceed==true) { switch (phase) { case 0 : //Converting the IP number - if ((afnnum=afn_getipnum(peerip))==(AFNTYP *)0) { - (void) rou_alert(0,"%s Unable to convert ip <%s> (bug?)",OPEP,peerip); - phase=999; - } if (spfrec==(char *)0) { (void) rou_alert(0,"%s SPF record is NULL (bug?)",OPEP); phase=999; @@ -441,14 +508,14 @@ while (proceed==true) { break; case 2 : //making sure spfrec is an SPF1 spfrec+=strlen(SPF1); - (void) dbgspf(2,afnnum,spfrec,spf); + (void) dbgspf(2,peerip,spfrec,spf); if (strlen(spfrec)>0) { char *seq; while ((seq=getspfseq(spfrec))!=(char *)0) { spfrec=strstr(spfrec,seq); spfrec+=strlen(seq); - spf=checkseq(seq,afnnum,spf); + spf=checkseq(try,seq,peerip,spf); seq=rou_freestr(seq); } } @@ -518,7 +585,7 @@ return ascii; /* domain name and and an IP. */ /* */ /********************************************************/ -PUBLIC SPFENU dns_get_spf_status(char *domain,char *peerip) +PUBLIC SPFENU dns_get_spf_status(int *try,char *domain,char *peerip) { #define OPEP "unidns.c:dns_get_spf_status" @@ -528,6 +595,7 @@ char **list; int phase; _Bool proceed; +(*try)++; spf=spf_permerr; list=(char **)0; phase=0; @@ -540,20 +608,26 @@ while (proceed==true) { phase=999; //trouble trouble } break; - case 1 : //get the spf LIST related to SPF + case 1 : //check the number of DNS access + if ((*try)>MXDNS) { + (void) rou_alert(0,"%s SPF record scan is too deep (aborting)",OPEP); + phase=999; //trouble trouble + } + break; + case 2 : //get the spf LIST related to SPF if ((list=getspf(domain))==(char **)0) phase=999; //trouble trouble break; - case 2 : //check if we have onlye ONE SPF entry + case 3 : //check if we have only ONE SPF entry if (rou_nbrlist((void **)list)>1) { (void) rou_alert(0,"%s more than 1 SPF record for domain <%s>", OPEP,domain); phase=999; //trouble trouble } break; - case 3 : //gett the spf LIST related to SPF + case 4 : //gett the spf LIST related to SPF (void) printf("JMPDBG peerip=<%s>, spf=<%s>\n",peerip,list[0]); - spf=is_peerip_ok(peerip,list[0]); + spf=is_peerip_ok(try,peerip,list[0]); list=(char **)rou_freelist((void **)list,(freehandler_t)rou_freestr); break; default : //SAFE guard diff --git a/lib/unidns.h b/lib/unidns.h index 53fafa6..ed3d677 100644 --- a/lib/unidns.h +++ b/lib/unidns.h @@ -23,7 +23,7 @@ typedef enum { extern const char *dns_spfASCII(SPFENU spf); //get the SPF status for a specific domain and a remote peer IP -extern SPFENU dns_get_spf_status(char *domain,char *peerip); +extern SPFENU dns_get_spf_status(int *try,char *domain,char *peerip); //homework to be done before starting/stopping module. extern int dns_modeunidns(_Bool mode);