diff options
author | Vsevolod Stakhov <vsevolod@highsecure.ru> | 2014-01-27 16:12:27 +0000 |
---|---|---|
committer | Vsevolod Stakhov <vsevolod@highsecure.ru> | 2014-01-27 16:12:27 +0000 |
commit | 9bb4dcceadb7f78efe946946ccf7742a8c6e4f50 (patch) | |
tree | 70c25bfdf8bffbb6ac5eb424a20f9bba871612ee /src/dns_private.h | |
parent | 15b1bddab547189e5fbdcb4441b2d64e4c8f10aa (diff) | |
download | rspamd-9bb4dcceadb7f78efe946946ccf7742a8c6e4f50.tar.gz rspamd-9bb4dcceadb7f78efe946946ccf7742a8c6e4f50.zip |
Rework resolver library.
Diffstat (limited to 'src/dns_private.h')
-rw-r--r-- | src/dns_private.h | 222 |
1 files changed, 222 insertions, 0 deletions
diff --git a/src/dns_private.h b/src/dns_private.h new file mode 100644 index 000000000..46483918e --- /dev/null +++ b/src/dns_private.h @@ -0,0 +1,222 @@ +/* Copyright (c) 2014, Vsevolod Stakhov + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED ''AS IS'' AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef DNS_PRIVATE_H_ +#define DNS_PRIVATE_H_ + +#include "config.h" +#include "chacha_private.h" + +#define MAX_SERVERS 16 +/* Upstream timeouts */ +#define DEFAULT_UPSTREAM_ERROR_TIME 10 +#define DEFAULT_UPSTREAM_DEAD_TIME 300 +#define DEFAULT_UPSTREAM_MAXERRORS 10 + +static const unsigned base = 36; +static const unsigned t_min = 1; +static const unsigned t_max = 26; +static const unsigned skew = 38; +static const unsigned damp = 700; +static const unsigned initial_n = 128; +static const unsigned initial_bias = 72; + +static const gint dns_port = 53; + +#define UDP_PACKET_SIZE 4096 + +#define DNS_COMPRESSION_BITS 0xC0 + +#define DNS_D_MAXLABEL 63 /* + 1 '\0' */ +#define DNS_D_MAXNAME 255 /* + 1 '\0' */ + +#define PERMUTOR_BUF_SIZE 32768 +#define PERMUTOR_KSIZE 32 +#define PERMUTOR_IVSIZE 8 + +#define RESOLV_CONF "/etc/resolv.conf" + +/** + * Represents DNS server + */ +struct rspamd_dns_server { + struct upstream up; /**< upstream structure */ + gchar *name; /**< name of DNS server */ + struct rspamd_dns_io_channel *io_channels; + struct rspamd_dns_io_channel *cur_io_channel; +}; + +/** + * IO channel for a specific DNS server + */ +struct rspamd_dns_io_channel { + struct rspamd_dns_server *srv; + struct rspamd_dns_resolver *resolver; + gint sock; /**< persistent socket */ + struct event ev; + GHashTable *requests; /**< requests in flight */ + struct rspamd_dns_io_channel *prev, *next; +}; + +struct dns_permutor; + +struct rspamd_dns_resolver { + struct rspamd_dns_server servers[MAX_SERVERS]; + gint servers_num; /**< number of DNS servers registered */ + struct dns_permutor *permutor; /**< permutor for randomizing request id */ + guint request_timeout; + guint max_retransmits; + guint max_errors; + GHashTable *io_channels; /**< hash of io chains indexed by socket */ + gboolean throttling; /**< dns servers are busy */ + gboolean is_master_slave; /**< if this is true, then select upstreams as master/slave */ + guint errors; /**< resolver errors */ + struct timeval throttling_time; /**< throttling time */ + struct event throttling_event; /**< throttling event */ + struct event_base *ev_base; /**< base for event ops */ +}; + +struct dns_header; +struct dns_query; + +/* Internal DNS structs */ + +struct dns_header { + guint qid :16; + +#if BYTE_ORDER == BIG_ENDIAN + guint qr:1; + guint opcode:4; + guint aa:1; + guint tc:1; + guint rd:1; + + guint ra:1; + guint unused:3; + guint rcode:4; +#else + guint rd :1; + guint tc :1; + guint aa :1; + guint opcode :4; + guint qr :1; + + guint rcode :4; + guint unused :3; + guint ra :1; +#endif + + guint qdcount :16; + guint ancount :16; + guint nscount :16; + guint arcount :16; +}; + +enum dns_section { + DNS_S_QD = 0x01, +#define DNS_S_QUESTION DNS_S_QD + + DNS_S_AN = 0x02, +#define DNS_S_ANSWER DNS_S_AN + + DNS_S_NS = 0x04, +#define DNS_S_AUTHORITY DNS_S_NS + + DNS_S_AR = 0x08, +#define DNS_S_ADDITIONAL DNS_S_AR + + DNS_S_ALL = 0x0f +}; +/* enum dns_section */ + +enum dns_opcode { + DNS_OP_QUERY = 0, + DNS_OP_IQUERY = 1, + DNS_OP_STATUS = 2, + DNS_OP_NOTIFY = 4, + DNS_OP_UPDATE = 5, +}; +/* dns_opcode */ + +enum dns_class { + DNS_C_IN = 1, + + DNS_C_ANY = 255 +}; +/* enum dns_class */ + +struct dns_query { + gchar *qname; + guint qtype :16; + guint qclass :16; +}; + +enum dns_type { + DNS_T_A = 1, + DNS_T_NS = 2, + DNS_T_CNAME = 5, + DNS_T_SOA = 6, + DNS_T_PTR = 12, + DNS_T_MX = 15, + DNS_T_TXT = 16, + DNS_T_AAAA = 28, + DNS_T_SRV = 33, + DNS_T_OPT = 41, + DNS_T_SSHFP = 44, + DNS_T_SPF = 99, + + DNS_T_ALL = 255 +}; +/* enum dns_type */ + +struct dns_permutor { + chacha_ctx ctx; + guchar perm_buf[PERMUTOR_BUF_SIZE]; + guint pos; +}; + +static const gchar dns_rcodes[16][16] = { + [DNS_RC_NOERROR] = "NOERROR", + [DNS_RC_FORMERR] = "FORMERR", + [DNS_RC_SERVFAIL] = "SERVFAIL", + [DNS_RC_NXDOMAIN] = "NXDOMAIN", + [DNS_RC_NOTIMP] = "NOTIMP", + [DNS_RC_REFUSED] = "REFUSED", + [DNS_RC_YXDOMAIN] = "YXDOMAIN", + [DNS_RC_YXRRSET] = "YXRRSET", + [DNS_RC_NXRRSET] = "NXRRSET", + [DNS_RC_NOTAUTH] = "NOTAUTH", + [DNS_RC_NOTZONE] = "NOTZONE", +}; + +static const gchar dns_types[7][16] = { + [DNS_REQUEST_A] = "A request", + [DNS_REQUEST_PTR] = "PTR request", + [DNS_REQUEST_MX] = "MX request", + [DNS_REQUEST_TXT] = "TXT request", + [DNS_REQUEST_SRV] = "SRV request", + [DNS_REQUEST_SPF] = "SPF request", + [DNS_REQUEST_AAA] = "AAA request" +}; + +#endif /* DNS_PRIVATE_H_ */ |