4. The check_host() Function (La funzione check_host())
4. The check_host() Function (La funzione check_host())
Questa descrizione non è una definizione dell'interfaccia di programmazione dell'applicazione, ma una descrizione di funzione per illustrare l'algoritmo. Le implementazioni SPF conformi devono produrre risultati semanticamente equivalenti a questa descrizione.
La funzione check_host() recupera i record SPF, li analizza e li valuta per determinare se un particolare host è autorizzato o non autorizzato a inviare posta con una determinata identità. L'ADMD ricevente che esegue questo controllo deve valutare correttamente la funzione check_host() come descritto qui.
Le implementazioni possono utilizzare un algoritmo diverso dall'algoritmo canonico definito qui, purché i risultati siano identici in tutti i casi.
4.1 Arguments (Argomenti)
La funzione check_host() accetta i seguenti argomenti:
<ip> - L'indirizzo IP del client SMTP che invia la posta, sia IPv4 che IPv6.
<domain> - Il dominio che fornisce le informazioni di autorizzazione ricercate; inizialmente la parte dominio dell'identità "MAIL FROM" o "HELO".
<sender> - L'identità "MAIL FROM" o "HELO".
Per valutazioni ricorsive, la parte dominio di <sender> può differire dall'argomento <domain> quando check_host() viene valutato per la prima volta. Nella maggior parte degli altri casi, sarà lo stesso (vedere sezione 5.2 sotto). Il limite globale di query DNS per i termini SPF descritto nella sezione 4.6.4 deve essere tracciato come un singolo limite globale su tutte le valutazioni, non solo per una singola istanza di valutazione ricorsiva.
Si noti che l'argomento <domain> potrebbe non essere un nome di dominio ben formato. Ad esempio, se il percorso inverso è vuoto, viene utilizzato il dominio EHLO/HELO con i suoi problemi associati (vedere sezione 2.3). In questi casi, check_host() è definito nella sezione 4.3 per restituire un risultato "none".
4.2 Results (Risultati)
La funzione check_host() può restituire uno dei diversi risultati descritti nella sezione 2.6. L'azione da intraprendere in base al risultato è determinata dalla politica locale del destinatario. Questo è discusso nella sezione 8.
4.3 Initial Processing (Elaborazione iniziale)
Se <domain> è formattato in modo errato (ad esempio, lunghezza dell'etichetta superiore a 63 caratteri, etichette di lunghezza zero non terminali, ecc.) o non è un nome di dominio multi-etichetta, o se la query DNS restituisce "Name Error" (RCODE 3, noto anche come "NXDOMAIN" [RFC2308]), check_host() restituisce immediatamente il risultato "none". Gli RCODE DNS sono definiti in [RFC1035]. Un dominio ben formato è un nome di dominio completamente qualificato come definito in [RFC1983]. Cioè, nel DNS, sono implicitamente qualificati rispetto alla radice (vedere sezione 3.1 di [RFC1034]). I nomi di dominio internazionalizzati devono essere codificati come A-label, come descritto nella sezione 2.3 di [RFC5890].
Se <sender> non ha una local-part, sostituire la local-part con la stringa "postmaster".
4.4 Record Lookup (Ricerca del record)
A seconda di come viene pubblicato il record (vedere sezione 3 sopra), è necessaria una query DNS per il nome <domain>, solo per il tipo TXT.
Se la query DNS restituisce un guasto del server (RCODE 2) o un altro errore (RCODE né 0 né 3), o se la query scade, check_host() termina immediatamente con il risultato "temperror".
4.5 Selecting Records (Selezione dei record)
I record iniziano con una parte versione:
record = version terms *SP
version = "v=spf1"
Partendo dall'insieme di record restituito dalla query, scartare i record che non iniziano con una parte versione di esattamente "v=spf1". Si noti che la parte versione è terminata da un carattere SP o dalla fine del record. Ad esempio, un record con una parte versione "v=spf10" non corrisponde e viene scartato.
Se l'insieme di record risultante non contiene record, check_host() produce un risultato "none". Se l'insieme di record risultante contiene più record, check_host() produce un risultato "permerror".
4.6 Record Evaluation (Valutazione del record)
La funzione check_host() analizza e interpreta il record SPF per trovare un risultato per il test corrente. Innanzitutto, la sintassi del record viene convalidata e, se sono presenti errori di sintassi in qualsiasi punto del record, check_host() restituisce immediatamente il risultato "permerror" senza ulteriore interpretazione o valutazione.
4.6.1 Term Evaluation (Valutazione dei termini)
Esistono due tipi di termini: meccanismi (definiti nella sezione 5) e modificatori (definiti nella sezione 6). I record contengono un elenco ordinato di questi, come specificato nella seguente notazione di forma di Backus-Naur aumentata (ABNF).
terms = *( 1*SP ( directive / modifier ) )
directive = [ qualifier ] mechanism
qualifier = "+" / "-" / "?" / "~"
mechanism = ( all / include
/ a / mx / ptr / ip4 / ip6 / exists )
modifier = redirect / explanation / unknown-modifier
unknown-modifier = name "=" macro-string
; where name is not any known modifier
name = ALPHA *( ALPHA / DIGIT / "-" / "_" / "." )
La maggior parte dei meccanismi consente un carattere ":" o "/" dopo il nome.
I modificatori contengono sempre un carattere uguale ('=') immediatamente dopo il nome e prima di qualsiasi carattere ":" o "/" che potrebbe far parte di un macro-string.
Un termine che non contiene nessuno dei caratteri "=", ":" o "/" è un meccanismo, come definito nella sezione 5.
Secondo la notazione ABNF come definita in [RFC5234], i nomi di meccanismi e modificatori non fanno distinzione tra maiuscole e minuscole.
4.6.2 Mechanisms (Meccanismi)
Ogni meccanismo viene considerato in ordine da sinistra a destra. Se non ci sono più meccanismi, il risultato è il risultato predefinito descritto nella sezione 4.7.
Quando viene valutato un meccanismo, possono verificarsi tre cose: può corrispondere, non corrispondere o restituire un'eccezione.
Se corrisponde, l'elaborazione termina e il valore del qualificatore viene restituito come risultato per questo record. Se non corrisponde, l'elaborazione continua con il meccanismo successivo. Se restituisce un'eccezione, l'elaborazione del meccanismo termina e il valore dell'eccezione viene restituito.
I possibili qualificatori e i risultati che causano per check_host() sono i seguenti:
"+" pass
"-" fail
"~" softfail
"?" neutral
Il qualificatore è opzionale e il valore predefinito è "+".
Quando il meccanismo corrisponde e il qualificatore è "-", viene restituito un risultato "fail" e la stringa di spiegazione viene calcolata come descritto nella sezione 6.2.
La sezione 5 descrive i meccanismi specifici.
4.6.3 Modifiers (Modificatori)
I modificatori non sono meccanismi. Non restituiscono corrispondenza o non corrispondenza. Invece, forniscono informazioni aggiuntive. Sebbene i modificatori non influenzino direttamente la valutazione del record, il modificatore "redirect" ha un impatto dopo la valutazione di tutti i meccanismi.
4.6.4 DNS Lookup Limits (Limiti di ricerca DNS)
Alcuni meccanismi e modificatori (collettivamente chiamati "termini") causano query DNS durante la valutazione, mentre altri no. I seguenti termini causano query DNS: i meccanismi "include", "a", "mx", "ptr" e "exists", nonché il modificatore "redirect". Le implementazioni SPF devono limitare il numero totale di questi termini a 10 durante una valutazione SPF, per evitare un carico irragionevole sul DNS. Se questo limite viene superato, l'implementazione deve restituire "permerror". Altri termini -- i meccanismi "all", "ip4" e "ip6", nonché il modificatore "exp" -- non causano query DNS durante la valutazione SPF (il modificatore "exp" causa una query solo in un momento successivo), e il loro utilizzo non è soggetto a questo limite.
Durante la valutazione del meccanismo "mx", il numero di record di risorse "MX" interrogati è incluso nel limite globale sopra di 10 meccanismi/modificatori che causano query DNS. Oltre a questo limite, la valutazione di ciascun record "MX" non deve assolutamente comportare l'interrogazione di più di 10 record di indirizzi -- record di risorse "A" o "AAAA". Se questo limite viene superato, il meccanismo "mx" deve produrre un risultato "permerror".
Durante la valutazione del meccanismo "ptr" o della macro %\{p}, il numero di record di risorse "PTR" interrogati è incluso nel limite globale sopra di 10 meccanismi/modificatori che causano query DNS. Oltre a questo limite, la valutazione di ciascun record "PTR" non deve assolutamente comportare l'interrogazione di più di 10 record di indirizzi -- record di risorse "A" o "AAAA". Se questo limite viene superato, tutti i record tranne i primi 10 devono essere ignorati.
Il motivo della differenza è che l'insieme e il contenuto dei record MX sono sotto il controllo dell'ADMD di pubblicazione, mentre l'insieme e il contenuto dei record PTR sono sotto il controllo del proprietario dell'indirizzo IP che stabilisce effettivamente la connessione.
Questi limiti sono per meccanismo o macro in un record e si aggiungono ai limiti di query specificati sopra.
Un MTA o un altro processore dovrebbe imporre un limite di tempo trascorso massimo per la valutazione di check_host(). Tale limite dovrebbe consentire almeno 20 secondi. Se tale limite viene superato, il risultato di autorizzazione dovrebbe essere "temperror".
Come menzionato alla fine della sezione 11.1, in alcuni casi può essere utile limitare il numero di "termini" che restituiscono query DNS che restituiscono una risposta positiva (RCODE 0) con un conteggio delle risposte di 0, o una risposta "Name Error" (RCODE 3). Questi sono talvolta collettivamente chiamati "void lookups". Le implementazioni SPF dovrebbero limitare i "void lookups" a due. Le implementazioni possono scegliere di rendere tale limite configurabile. In questo caso, si raccomanda che il valore predefinito sia due. Il superamento del limite produce un risultato "permerror".
4.7 Default Result (Risultato predefinito)
Se nessuno dei meccanismi corrisponde e non c'è un modificatore "redirect", check_host() restituisce il risultato "neutral", come se "?all" fosse specificato come ultima direttiva. Se è presente un modificatore "redirect", check_host() continua come definito nella sezione 6.1.
È preferibile utilizzare un modificatore "redirect" o un meccanismo "all" per terminare esplicitamente l'elaborazione. Sebbene ci sia un "?all" implicito alla fine di ogni record che non termina esplicitamente, aiuta gli sforzi di debug quando viene fornito esplicitamente.
Esempio:
v=spf1 +mx -all
Oppure
v=spf1 +mx redirect=_spf.example.com
4.8 Domain Specification (Specifica del dominio)
Diversi di questi meccanismi e modificatori hanno una parte <domain-spec>. La stringa è sottoposta a espansione di macro (vedere sezione 7). La stringa risultante è la rappresentazione abituale di un nome DNS completamente qualificato: una sequenza di etichette separate da punti. Questo dominio è chiamato <target-name> nel resto di questo documento.
Nota: Il risultato dell'espansione della macro non è soggetto ad alcun ulteriore escaping. Pertanto, questo strumento non può produrre tutti i caratteri legali nelle etichette DNS (ad esempio, caratteri di controllo). Tuttavia, questo strumento è sufficientemente potente per esprimere nomi host legali ed etichette di utilità comuni utilizzate nel DNS (ad esempio, "_spf").
Per diversi meccanismi, <domain-spec> è opzionale. Se non viene fornito, il <domain> dagli argomenti check_host() (vedere sezione 4.1) viene utilizzato come <target-name>. "domain" e <target-name> sono sintatticamente identici dopo l'espansione delle macro. "domain" è il valore di input per check_host(), mentre <target-name> è calcolato da check_host().
La valutazione di check_host() con un dominio sintatticamente non valido è indefinita.
Nota: Questo documento e il suo predecessore non contengono alcuna disposizione per la gestione corretta di <domain-spec> sintatticamente non validi (possibilmente il risultato di un'espansione di macro) secondo [RFC1035]. Gli esempi includono nomi con etichette vuote come "foo..example.com" ed etichette con una lunghezza superiore a 63 caratteri. Alcune implementazioni scelgono di trattare tali errori come non corrispondenza e quindi ignorano tali nomi, mentre altre implementazioni restituiscono un'eccezione "permerror".