Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/srv/net/dnsrsrv/query.c

    r959d2ec r5a324d99  
    3939#include <stdlib.h>
    4040#include <str.h>
    41 
    4241#include "dns_msg.h"
    4342#include "dns_std.h"
     
    4847static uint16_t msg_id;
    4948
    50 int dns_name2host(const char *name, dns_host_info_t **rinfo)
     49static int dns_name_query(const char *name, dns_qtype_t qtype,
     50    dns_host_info_t *info)
    5151{
    52         dns_message_t *msg;
    53         dns_message_t *amsg;
    54         dns_question_t *question;
    55         dns_host_info_t *info;
    56         char *sname, *cname;
    57         size_t eoff;
    58         int rc;
    59 
    60         question = calloc(1, sizeof(dns_question_t));
    61         if (question == NULL)
    62                 return ENOMEM;
    63 
    64         question->qname = (char *)name;
    65         question->qtype = DTYPE_A;
     52        /* Start with the caller-provided name */
     53        char *sname = str_dup(name);
     54        if (sname == NULL)
     55                return ENOMEM;
     56       
     57        char *qname = str_dup(name);
     58        if (qname == NULL) {
     59                free(sname);
     60                return ENOMEM;
     61        }
     62       
     63        dns_question_t *question = calloc(1, sizeof(dns_question_t));
     64        if (question == NULL) {
     65                free(qname);
     66                free(sname);
     67                return ENOMEM;
     68        }
     69       
     70        question->qname = qname;
     71        question->qtype = qtype;
    6672        question->qclass = DC_IN;
    67 
    68         msg = dns_message_new();
    69         if (msg == NULL)
    70                 return ENOMEM;
    71 
    72         list_append(&question->msg, &msg->question);
    73 
     73       
     74        dns_message_t *msg = dns_message_new();
     75        if (msg == NULL) {
     76                free(question);
     77                free(qname);
     78                free(sname);
     79                return ENOMEM;
     80        }
     81       
    7482        msg->id = msg_id++;
    7583        msg->qr = QR_QUERY;
     
    7987        msg->rd = true;
    8088        msg->ra = false;
    81 
    82         rc = dns_request(msg, &amsg);
     89       
     90        list_append(&question->msg, &msg->question);
     91       
     92        dns_message_t *amsg;
     93        int rc = dns_request(msg, &amsg);
    8394        if (rc != EOK) {
     95                dns_message_destroy(msg);
     96                free(sname);
    8497                return rc;
    8598        }
    86 
    87         /* Start with the caller-provided name */
    88         sname = str_dup(name);
    89 
    90         list_foreach(amsg->answer, link) {
    91                 dns_rr_t *rr = list_get_instance(link, dns_rr_t, msg);
    92 
     99       
     100        list_foreach(amsg->answer, msg, dns_rr_t, rr) {
    93101                log_msg(LOG_DEFAULT, LVL_DEBUG, " - '%s' %u/%u, dsize %zu",
    94                         rr->name, rr->rtype, rr->rclass, rr->rdata_size);
    95 
    96                 if (rr->rtype == DTYPE_CNAME && rr->rclass == DC_IN &&
    97                     str_cmp(rr->name, sname) == 0) {
     102                    rr->name, rr->rtype, rr->rclass, rr->rdata_size);
     103               
     104                if ((rr->rtype == DTYPE_CNAME) && (rr->rclass == DC_IN) &&
     105                    (str_cmp(rr->name, sname) == 0)) {
     106                       
    98107                        log_msg(LOG_DEFAULT, LVL_DEBUG, "decode cname (%p, %zu, %zu)",
    99108                            amsg->pdu.data, amsg->pdu.size, rr->roff);
     109                       
     110                        char *cname;
     111                        size_t eoff;
    100112                        rc = dns_name_decode(&amsg->pdu, rr->roff, &cname, &eoff);
    101113                        if (rc != EOK) {
    102                                 log_msg(LOG_DEFAULT, LVL_DEBUG,
    103                                     "error decoding cname");
    104                                 assert(rc == EINVAL || rc == ENOMEM);
     114                                assert((rc == EINVAL) || (rc == ENOMEM));
     115                               
     116                                log_msg(LOG_DEFAULT, LVL_DEBUG, "error decoding cname");
     117                               
    105118                                dns_message_destroy(msg);
    106119                                dns_message_destroy(amsg);
     120                                free(sname);
     121                               
    107122                                return rc;
    108123                        }
    109 
     124                       
    110125                        log_msg(LOG_DEFAULT, LVL_DEBUG, "name = '%s' "
    111126                            "cname = '%s'", sname, cname);
    112 
     127                       
     128                        /* Continue looking for the more canonical name */
    113129                        free(sname);
    114                         /* Continue looking for the more canonical name */
    115130                        sname = cname;
    116131                }
    117 
    118                 if (rr->rtype == DTYPE_A && rr->rclass == DC_IN &&
    119                         rr->rdata_size == sizeof(uint32_t) &&
    120                             str_cmp(rr->name, sname) == 0) {
    121 
    122                         info = calloc(1, sizeof(dns_host_info_t));
    123                         if (info == NULL) {
     132               
     133                if ((qtype == DTYPE_A) && (rr->rtype == DTYPE_A) &&
     134                    (rr->rclass == DC_IN) && (rr->rdata_size == sizeof(addr32_t)) &&
     135                    (str_cmp(rr->name, sname) == 0)) {
     136                       
     137                        info->cname = str_dup(rr->name);
     138                        if (info->cname == NULL) {
    124139                                dns_message_destroy(msg);
    125140                                dns_message_destroy(amsg);
     141                                free(sname);
     142                               
    126143                                return ENOMEM;
    127144                        }
    128 
    129                         info->cname = str_dup(rr->name);
    130                         info->addr.ipv4 = dns_uint32_t_decode(rr->rdata, rr->rdata_size);
    131                         log_msg(LOG_DEFAULT, LVL_DEBUG, "info->name = '%s' "
    132                             "info->addr = %x", info->cname, info->addr.ipv4);
    133 
     145                       
     146                        inet_addr_set(dns_uint32_t_decode(rr->rdata, rr->rdata_size),
     147                            &info->addr);
     148                       
    134149                        dns_message_destroy(msg);
    135150                        dns_message_destroy(amsg);
    136                         *rinfo = info;
     151                        free(sname);
     152                       
    137153                        return EOK;
    138154                }
    139         }
    140 
     155               
     156                if ((qtype == DTYPE_AAAA) && (rr->rtype == DTYPE_AAAA) &&
     157                    (rr->rclass == DC_IN) && (rr->rdata_size == sizeof(addr128_t)) &&
     158                    (str_cmp(rr->name, sname) == 0)) {
     159               
     160                        info->cname = str_dup(rr->name);
     161                        if (info->cname == NULL) {
     162                                dns_message_destroy(msg);
     163                                dns_message_destroy(amsg);
     164                                free(sname);
     165                               
     166                                return ENOMEM;
     167                        }
     168                       
     169                        addr128_t addr;
     170                        dns_addr128_t_decode(rr->rdata, rr->rdata_size, addr);
     171                       
     172                        inet_addr_set6(addr, &info->addr);
     173                       
     174                        dns_message_destroy(msg);
     175                        dns_message_destroy(amsg);
     176                        free(sname);
     177                       
     178                        return EOK;
     179                }
     180        }
     181       
     182        log_msg(LOG_DEFAULT, LVL_DEBUG, "'%s' not resolved, fail", sname);
     183       
    141184        dns_message_destroy(msg);
    142185        dns_message_destroy(amsg);
    143         log_msg(LOG_DEFAULT, LVL_DEBUG, "'%s' not resolved, fail", sname);
    144 
     186        free(sname);
     187       
    145188        return EIO;
     189}
     190
     191int dns_name2host(const char *name, dns_host_info_t **rinfo, ip_ver_t ver)
     192{
     193        dns_host_info_t *info = calloc(1, sizeof(dns_host_info_t));
     194        if (info == NULL)
     195                return ENOMEM;
     196       
     197        int rc;
     198       
     199        switch (ver) {
     200        case ip_any:
     201                rc = dns_name_query(name, DTYPE_AAAA, info);
     202               
     203                if (rc != EOK)
     204                        rc = dns_name_query(name, DTYPE_A, info);
     205               
     206                break;
     207        case ip_v4:
     208                rc = dns_name_query(name, DTYPE_A, info);
     209                break;
     210        case ip_v6:
     211                rc = dns_name_query(name, DTYPE_AAAA, info);
     212                break;
     213        default:
     214                rc = EINVAL;
     215        }
     216       
     217        if (rc == EOK)
     218                *rinfo = info;
     219        else
     220                free(info);
     221       
     222        return rc;
    146223}
    147224
Note: See TracChangeset for help on using the changeset viewer.