"Fossies" - the Fresh Open Source Software Archive

Member "libspf2-1.2.10/src/libspf2/spf_dns_rr.c" (28 Jan 2012, 5378 Bytes) of package /linux/privat/libspf2-1.2.10.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "spf_dns_rr.c" see the Fossies "Dox" file reference documentation.

    1 /* 
    2  * This program is free software; you can redistribute it and/or modify
    3  * it under the terms of either:
    4  * 
    5  *   a) The GNU Lesser General Public License as published by the Free
    6  *      Software Foundation; either version 2.1, or (at your option) any
    7  *      later version, 
    8  * 
    9  *   OR
   10  * 
   11  *   b) The two-clause BSD license.
   12  *
   13  * These licenses can be found with the distribution in the file LICENSES
   14  */
   15 
   16 
   17 #include "spf_sys_config.h"
   18 
   19 #ifdef STDC_HEADERS
   20 # include <stdio.h>        /* stdin / stdout */
   21 # include <stdlib.h>       /* malloc / free */
   22 #endif
   23 
   24 #ifdef HAVE_STRING_H
   25 # include <string.h>       /* strstr / strdup */
   26 #else
   27 # ifdef HAVE_STRINGS_H
   28 #  include <strings.h>       /* strstr / strdup */
   29 # endif
   30 #endif
   31 
   32 #ifdef HAVE_NETDB_H
   33 #include <netdb.h>
   34 #endif
   35 
   36 #ifdef HAVE_ARPA_NAMESER_H
   37 #include <arpa/nameser.h>
   38 #endif
   39 
   40 
   41 #include "spf.h"
   42 #include "spf_dns.h"
   43 #include "spf_internal.h"
   44 #include "spf_dns_internal.h"
   45 #include "spf_dns_rr.h"
   46 
   47 /**
   48  * @file
   49  * Audited, 2008-09-13, Shevek.
   50  */
   51 
   52 SPF_dns_rr_t *
   53 SPF_dns_rr_new_nxdomain(SPF_dns_server_t *spf_dns_server,
   54                 const char *domain)
   55 {
   56     return SPF_dns_rr_new_init(spf_dns_server,
   57                     domain, ns_t_any, 0, HOST_NOT_FOUND);
   58 }
   59 
   60 SPF_dns_rr_t *
   61 SPF_dns_rr_new_init(SPF_dns_server_t *spf_dns_server,
   62                 const char *domain,
   63                 ns_type rr_type, int ttl,
   64                 SPF_dns_stat_t herrno)
   65 {
   66     SPF_dns_rr_t    *spfrr;
   67 
   68     spfrr = SPF_dns_rr_new();
   69     if (spfrr == NULL)
   70         return spfrr;
   71 
   72     spfrr->source = spf_dns_server;
   73     if (domain && (domain[0] != '\0')) {
   74         spfrr->domain = strdup(domain);
   75         if (spfrr->domain == NULL) {
   76             SPF_dns_rr_free(spfrr);
   77             return NULL;
   78         }
   79         spfrr->domain_buf_len = strlen(domain) + 1;
   80     }
   81     else {
   82         spfrr->domain = NULL;
   83         spfrr->domain_buf_len = 0;
   84     }
   85     spfrr->rr_type = rr_type;
   86     spfrr->ttl = ttl;
   87     spfrr->herrno = herrno;
   88 
   89     return spfrr;
   90 }
   91 
   92 SPF_dns_rr_t *
   93 SPF_dns_rr_new()
   94 {
   95     SPF_dns_rr_t    *spfrr;
   96 
   97     spfrr = malloc(sizeof(SPF_dns_rr_t));
   98     if (spfrr == NULL)
   99         return spfrr;
  100     memset(spfrr, 0, sizeof(SPF_dns_rr_t));
  101 
  102     spfrr->domain = NULL;
  103     spfrr->domain_buf_len = 0;
  104     spfrr->rr_type = ns_t_invalid;
  105     spfrr->num_rr = 0;
  106     spfrr->ttl = 0;
  107     spfrr->utc_ttl = 0;
  108     spfrr->herrno = HOST_NOT_FOUND;
  109 
  110     return spfrr;
  111 }
  112 
  113 void
  114 SPF_dns_rr_free(SPF_dns_rr_t *spfrr)
  115 {
  116     int  i;
  117 
  118     if (spfrr->domain)
  119         free(spfrr->domain);
  120     if (spfrr->rr) {
  121         for (i = 0; i < spfrr->rr_buf_num; i++)
  122             if (spfrr->rr[i])
  123                 free(spfrr->rr[i]);
  124         free(spfrr->rr);
  125     }
  126     if (spfrr->rr_buf_len)
  127         free(spfrr->rr_buf_len);
  128     if(spfrr->hook)
  129         free(spfrr->hook);
  130     free(spfrr);
  131 }
  132 
  133 SPF_errcode_t
  134 SPF_dns_rr_buf_realloc(SPF_dns_rr_t *spfrr, int idx, size_t len)
  135 {
  136     SPF_dns_rr_data_t   **new_data;
  137     size_t               *new_buf_len;
  138     int                   new_num;
  139     void                 *new_rr;
  140     int                   j;
  141     
  142     if (spfrr->rr_buf_num <= idx) {
  143         /* allocate lots so we don't have to remalloc often */
  144         new_num = spfrr->rr_buf_num + (idx + (idx >> 2) + 4 );
  145 
  146         new_data = realloc(spfrr->rr,
  147                         new_num * sizeof(*new_data));
  148         if (new_data == NULL)
  149             return SPF_E_NO_MEMORY;
  150         spfrr->rr = new_data;
  151         
  152         new_buf_len = realloc(spfrr->rr_buf_len,
  153                        new_num * sizeof(*new_buf_len));
  154         if (new_buf_len == NULL)
  155             return SPF_E_NO_MEMORY;
  156         spfrr->rr_buf_len = new_buf_len;
  157         
  158         for(j = spfrr->rr_buf_num; j < new_num; j++) {
  159             spfrr->rr[j] = NULL;
  160             spfrr->rr_buf_len[j] = 0;
  161         }
  162 
  163         spfrr->rr_buf_num = new_num;
  164     }
  165 
  166     if (len < sizeof(SPF_dns_rr_data_t))
  167         len = sizeof(SPF_dns_rr_data_t);
  168     if (spfrr->rr_buf_len[idx] >= len)
  169         return SPF_E_SUCCESS;
  170 
  171     new_rr = realloc(spfrr->rr[idx], len);
  172     if (new_rr == NULL)
  173         return SPF_E_NO_MEMORY;
  174     spfrr->rr[idx] = new_rr;
  175     spfrr->rr_buf_len[idx] = len;
  176 
  177     return SPF_E_SUCCESS;
  178 }
  179 
  180 
  181 /**
  182  * This function may return both an error code and an rr, or
  183  * one, or neither. 
  184  *
  185  * This function generates a valgrind error because strlen always reads in
  186  * blocks of 4 bytes, and can overrun the end of the allocated buffers.
  187  */
  188 SPF_errcode_t
  189 SPF_dns_rr_dup(SPF_dns_rr_t **dstp, SPF_dns_rr_t *src)
  190 {
  191     SPF_dns_rr_t    *dst;
  192     SPF_errcode_t   err;
  193     int         i;
  194 
  195     SPF_ASSERT_NOTNULL(src);
  196     SPF_ASSERT_NOTNULL(dstp);
  197     dst = SPF_dns_rr_new_init(src->source,
  198                     src->domain, src->rr_type, src->ttl, src->herrno);
  199     if (!dst) {
  200         *dstp = NULL;
  201         return SPF_E_NO_MEMORY;
  202     }
  203     *dstp = dst;
  204 
  205     dst->utc_ttl = src->utc_ttl;
  206     dst->num_rr  = src->num_rr;
  207 
  208 #define SPF_DNS_RR_REALLOC(d, i, s) do { \
  209             err = SPF_dns_rr_buf_realloc(d, i, s); \
  210             if (err) return err; \
  211         } while(0)
  212 
  213     for (i = dst->num_rr - 1; i >= 0; i--) {
  214         switch (dst->rr_type) {
  215             case ns_t_a:
  216                 SPF_DNS_RR_REALLOC(dst, i, sizeof(SPF_dns_rr_data_t));
  217                 dst->rr[i]->a = src->rr[i]->a;
  218                 break;
  219                 
  220             case ns_t_ptr:
  221                 SPF_DNS_RR_REALLOC(dst, i, strlen(src->rr[i]->ptr) + 1);
  222                 strcpy(dst->rr[i]->ptr, src->rr[i]->ptr);
  223                 break;
  224                 
  225             case ns_t_mx:
  226                 SPF_DNS_RR_REALLOC(dst, i, strlen(src->rr[i]->mx) + 1);
  227                 strcpy(dst->rr[i]->mx, src->rr[i]->mx);
  228                 break;
  229                 
  230             case ns_t_txt:
  231             case ns_t_spf:
  232                 SPF_DNS_RR_REALLOC(dst, i, strlen(src->rr[i]->txt) + 1);
  233                 strcpy(dst->rr[i]->txt, src->rr[i]->txt);
  234                 break;
  235                 
  236             case ns_t_aaaa:
  237                 SPF_DNS_RR_REALLOC(dst, i, sizeof(SPF_dns_rr_data_t));
  238                 dst->rr[i]->aaaa = src->rr[i]->aaaa;
  239                 break;
  240                 
  241             default:
  242                 SPF_warningf("Attempt to dup unknown rr type %d",
  243                                 dst->rr_type);
  244                 break;
  245         }
  246     }
  247 
  248     return SPF_E_SUCCESS;
  249 }