39#include <arpa/nameser.h>
50#if __BYTE_ORDER == __PDP_ENDIAN
51#define DETERMINED_BYTE_ORDER __LITTLE_ENDIAN
54#if __BYTE_ORDER == __BIG_ENDIAN
55#define DETERMINED_BYTE_ORDER __BIG_ENDIAN
57#if __BYTE_ORDER == __LITTLE_ENDIAN
58#define DETERMINED_BYTE_ORDER __LITTLE_ENDIAN
126#if DETERMINED_BYTE_ORDER == __BIG_ENDIAN
140#if DETERMINED_BYTE_ORDER == __LITTLE_ENDIAN
163 unsigned short class;
166} __attribute__((__packed__));
190 if ((*s & 0xc0) == 0xc0) {
225 if (dns_response ==
NULL || field_size < 0 || remaining_len < field_size) {
229 *dns_response += field_size;
230 remaining_len -= field_size;
232 return remaining_len;
235#ifndef HAVE_RES_NINIT
250static int dns_search_res(
const char *dname,
int rr_class,
int rr_type,
251 unsigned char *dns_response,
int dns_response_len)
258 ret = res_search(dname,
288 unsigned char *dns_response,
int dns_response_len)
292 struct __res_state dns_state;
294 memset(&dns_state, 0,
sizeof(dns_state));
295 res_ninit(&dns_state);
296 ret = res_nsearch(&dns_state,
303#ifdef HAVE_RES_NDESTROY
304 res_ndestroy(&dns_state);
306 res_nclose(&dns_state);
331 int (*callback)(
void *
context,
unsigned char *
answer,
int len,
unsigned char *fullanswer))
333 unsigned char *fullanswer =
answer;
344 for (x = 0; x < ntohs(h->
qdcount); x++) {
357 for (x = 0; x < ntohs(h->
ancount); x++) {
408 int (*response_handler)(
void *
context,
unsigned char *dns_response,
int dns_response_len,
int rcode),
409 int (*record_handler)(
void *
context,
unsigned char *record,
int record_len,
int ttl))
411 unsigned char *dns_response =
answer;
415 int res, x, pos, dns_response_len, ret;
417 dns_response_len = answer_len;
421 response_handler(
context, dns_response, dns_response_len, ntohs(dns_header->rcode));
424 if (answer_len == 0) {
435 for (x = 0; x < ntohs(dns_header->
qdcount); x++) {
448 for (x = 0; x < ntohs(dns_header->
ancount); x++) {
470 if (ntohs(ans->
class) == rr_class && ntohs(ans->
rtype) == rr_type) {
492 const char *dname,
int class,
int type,
493 int (*callback)(
void *
context,
unsigned char *
answer,
int len,
unsigned char *fullanswer))
496 struct __res_state dnsstate;
502 memset(&dnsstate, 0,
sizeof(dnsstate));
503 res_ninit(&dnsstate);
514 }
else if (res == 0) {
515 ast_debug(1,
"No matches found in DNS for %s\n", dname);
521#ifdef HAVE_RES_NDESTROY
522 res_ndestroy(&dnsstate);
524 res_nclose(&dnsstate);
537 int (*response_handler)(
void *
context,
unsigned char *dns_response,
int dns_response_len,
int rcode),
538 int (*record_handler)(
void *
context,
unsigned char *record,
int record_len,
int ttl))
540 int ret, dns_response_len;
541 unsigned char dns_response[
MAX_SIZE];
552 sizeof(dns_response));
554 if (dns_response_len < 0) {
555 ast_debug(1,
"DNS search failed for %s\n", dname);
556 response_handler(
context, (
unsigned char *)
"", 0, NXDOMAIN);
575 ast_debug(1,
"DNS search yielded no results for %s\n", dname);
584 struct __res_state dnsstate;
586 struct __res_state *
state;
596 memset(&dnsstate, 0,
sizeof(dnsstate));
597 res_ninit(&dnsstate);
605 for (i = 0; i <
state->nscount; i++) {
606 char addr[INET6_ADDRSTRLEN];
607 const char *addrp =
NULL;
610 if (
state->nsaddr_list[i].sin_family) {
611 addrp = inet_ntop(AF_INET, &
state->nsaddr_list[i].sin_addr, addr,
sizeof(addr));
612#if defined(HAVE_RES_NINIT) && defined(HAVE_STRUCT___RES_STATE__U__EXT_NSADDRS)
613 }
else if (
state->_u._ext.nsaddrs[i]) {
614 addrp = inet_ntop(AF_INET6, &
state->_u._ext.nsaddrs[i]->sin6_addr, addr,
sizeof(addr));
619 ast_debug(1,
"Discovered nameserver: %s\n", addrp);
625#ifdef HAVE_RES_NDESTROY
626 res_ndestroy(&dnsstate);
628 res_nclose(&dnsstate);
Asterisk main include file. File version handling, generic pbx functions.
@ AO2_ALLOC_OPT_LOCK_NOLOCK
static int answer(void *data)
General Asterisk PBX channel definitions.
#define MAX_SIZE
The maximum size permitted for the answer from the DNS server.
static int dns_search_res(const char *dname, int rr_class, int rr_type, unsigned char *dns_response, int dns_response_len)
Handles the DNS search if the system has RES_NINIT.
enum ast_dns_search_result ast_search_dns_ex(void *context, const char *dname, int rr_class, int rr_type, int(*response_handler)(void *context, unsigned char *dns_response, int dns_response_len, int rcode), int(*record_handler)(void *context, unsigned char *record, int record_len, int ttl))
Extended version of the DNS search function.
static int dns_advance_field(unsigned char **dns_response, int remaining_len, int field_size)
Advances the position of the DNS response pointer by the size of the current field.
struct ao2_container * ast_dns_get_nameservers(void)
Retrieve the configured nameservers of the system.
static int dns_parse_answer_ex(void *context, int rr_class, int rr_type, unsigned char *answer, int answer_len, int(*response_handler)(void *context, unsigned char *dns_response, int dns_response_len, int rcode), int(*record_handler)(void *context, unsigned char *record, int record_len, int ttl))
Extended version of the DNS Parsing function.
static int dns_parse_answer(void *context, int class, int type, unsigned char *answer, int len, int(*callback)(void *context, unsigned char *answer, int len, unsigned char *fullanswer))
Parse DNS lookup result, call callback.
int ast_search_dns(void *context, const char *dname, int class, int type, int(*callback)(void *context, unsigned char *answer, int len, unsigned char *fullanswer))
Lookup record in DNS.
static int skip_name(unsigned char *s, int len)
Tries to find the position of the next field in the DNS response.
DNS support for Asterisk.
ast_dns_search_result
DNS search return values.
@ AST_DNS_SEARCH_NO_RECORDS
Asterisk architecture endianess compatibility definitions.
static int len(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t buflen)
#define ast_debug(level,...)
Log a DEBUG message.
#define ast_mutex_unlock(a)
#define ast_mutex_lock(a)
#define AST_MUTEX_DEFINE_STATIC(mutex)
Wrapper for network related headers, masking differences between various operating systems....
struct ao2_container * ast_str_container_alloc_options(enum ao2_alloc_opts opts, int buckets)
Allocates a hash container for bare strings.
int ast_str_container_add(struct ao2_container *str_container, const char *add)
Adds a string to a string container allocated by ast_str_container_alloc.