"Fossies" - the Fresh Open Source Software Archive

Member "bind-9.17.5/lib/dns/rdata/generic/mx_15.c" (4 Sep 2020, 8069 Bytes) of package /linux/misc/dns/bind9/9.17.5/bind-9.17.5.tar.xz:


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 "mx_15.c" see the Fossies "Dox" file reference documentation.

    1 /*
    2  * Copyright (C) Internet Systems Consortium, Inc. ("ISC")
    3  *
    4  * This Source Code Form is subject to the terms of the Mozilla Public
    5  * License, v. 2.0. If a copy of the MPL was not distributed with this
    6  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
    7  *
    8  * See the COPYRIGHT file distributed with this work for additional
    9  * information regarding copyright ownership.
   10  */
   11 
   12 #ifndef RDATA_GENERIC_MX_15_C
   13 #define RDATA_GENERIC_MX_15_C
   14 
   15 #include <string.h>
   16 
   17 #include <isc/net.h>
   18 
   19 #include <dns/fixedname.h>
   20 
   21 #define RRTYPE_MX_ATTRIBUTES (0)
   22 
   23 static bool
   24 check_mx(isc_token_t *token) {
   25     char tmp[sizeof("xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:123.123.123.123.")];
   26     struct in_addr addr;
   27     struct in6_addr addr6;
   28 
   29     if (strlcpy(tmp, DNS_AS_STR(*token), sizeof(tmp)) >= sizeof(tmp)) {
   30         return (true);
   31     }
   32 
   33     if (tmp[strlen(tmp) - 1] == '.') {
   34         tmp[strlen(tmp) - 1] = '\0';
   35     }
   36     if (inet_pton(AF_INET, tmp, &addr) == 1 ||
   37         inet_pton(AF_INET6, tmp, &addr6) == 1)
   38     {
   39         return (false);
   40     }
   41 
   42     return (true);
   43 }
   44 
   45 static inline isc_result_t
   46 fromtext_mx(ARGS_FROMTEXT) {
   47     isc_token_t token;
   48     dns_name_t name;
   49     isc_buffer_t buffer;
   50     bool ok;
   51 
   52     REQUIRE(type == dns_rdatatype_mx);
   53 
   54     UNUSED(type);
   55     UNUSED(rdclass);
   56 
   57     RETERR(isc_lex_getmastertoken(lexer, &token, isc_tokentype_number,
   58                       false));
   59     if (token.value.as_ulong > 0xffffU) {
   60         RETTOK(ISC_R_RANGE);
   61     }
   62     RETERR(uint16_tobuffer(token.value.as_ulong, target));
   63 
   64     RETERR(isc_lex_getmastertoken(lexer, &token, isc_tokentype_string,
   65                       false));
   66 
   67     ok = true;
   68     if ((options & DNS_RDATA_CHECKMX) != 0) {
   69         ok = check_mx(&token);
   70     }
   71     if (!ok && (options & DNS_RDATA_CHECKMXFAIL) != 0) {
   72         RETTOK(DNS_R_MXISADDRESS);
   73     }
   74     if (!ok && callbacks != NULL) {
   75         warn_badmx(&token, lexer, callbacks);
   76     }
   77 
   78     dns_name_init(&name, NULL);
   79     buffer_fromregion(&buffer, &token.value.as_region);
   80     if (origin == NULL) {
   81         origin = dns_rootname;
   82     }
   83     RETTOK(dns_name_fromtext(&name, &buffer, origin, options, target));
   84     ok = true;
   85     if ((options & DNS_RDATA_CHECKNAMES) != 0) {
   86         ok = dns_name_ishostname(&name, false);
   87     }
   88     if (!ok && (options & DNS_RDATA_CHECKNAMESFAIL) != 0) {
   89         RETTOK(DNS_R_BADNAME);
   90     }
   91     if (!ok && callbacks != NULL) {
   92         warn_badname(&name, lexer, callbacks);
   93     }
   94     return (ISC_R_SUCCESS);
   95 }
   96 
   97 static inline isc_result_t
   98 totext_mx(ARGS_TOTEXT) {
   99     isc_region_t region;
  100     dns_name_t name;
  101     dns_name_t prefix;
  102     bool sub;
  103     char buf[sizeof("64000")];
  104     unsigned short num;
  105 
  106     REQUIRE(rdata->type == dns_rdatatype_mx);
  107     REQUIRE(rdata->length != 0);
  108 
  109     dns_name_init(&name, NULL);
  110     dns_name_init(&prefix, NULL);
  111 
  112     dns_rdata_toregion(rdata, &region);
  113     num = uint16_fromregion(&region);
  114     isc_region_consume(&region, 2);
  115     snprintf(buf, sizeof(buf), "%u", num);
  116     RETERR(str_totext(buf, target));
  117 
  118     RETERR(str_totext(" ", target));
  119 
  120     dns_name_fromregion(&name, &region);
  121     sub = name_prefix(&name, tctx->origin, &prefix);
  122     return (dns_name_totext(&prefix, sub, target));
  123 }
  124 
  125 static inline isc_result_t
  126 fromwire_mx(ARGS_FROMWIRE) {
  127     dns_name_t name;
  128     isc_region_t sregion;
  129 
  130     REQUIRE(type == dns_rdatatype_mx);
  131 
  132     UNUSED(type);
  133     UNUSED(rdclass);
  134 
  135     dns_decompress_setmethods(dctx, DNS_COMPRESS_GLOBAL14);
  136 
  137     dns_name_init(&name, NULL);
  138 
  139     isc_buffer_activeregion(source, &sregion);
  140     if (sregion.length < 2) {
  141         return (ISC_R_UNEXPECTEDEND);
  142     }
  143     RETERR(mem_tobuffer(target, sregion.base, 2));
  144     isc_buffer_forward(source, 2);
  145     return (dns_name_fromwire(&name, source, dctx, options, target));
  146 }
  147 
  148 static inline isc_result_t
  149 towire_mx(ARGS_TOWIRE) {
  150     dns_name_t name;
  151     dns_offsets_t offsets;
  152     isc_region_t region;
  153 
  154     REQUIRE(rdata->type == dns_rdatatype_mx);
  155     REQUIRE(rdata->length != 0);
  156 
  157     dns_compress_setmethods(cctx, DNS_COMPRESS_GLOBAL14);
  158 
  159     dns_rdata_toregion(rdata, &region);
  160     RETERR(mem_tobuffer(target, region.base, 2));
  161     isc_region_consume(&region, 2);
  162 
  163     dns_name_init(&name, offsets);
  164     dns_name_fromregion(&name, &region);
  165 
  166     return (dns_name_towire(&name, cctx, target));
  167 }
  168 
  169 static inline int
  170 compare_mx(ARGS_COMPARE) {
  171     dns_name_t name1;
  172     dns_name_t name2;
  173     isc_region_t region1;
  174     isc_region_t region2;
  175     int order;
  176 
  177     REQUIRE(rdata1->type == rdata2->type);
  178     REQUIRE(rdata1->rdclass == rdata2->rdclass);
  179     REQUIRE(rdata1->type == dns_rdatatype_mx);
  180     REQUIRE(rdata1->length != 0);
  181     REQUIRE(rdata2->length != 0);
  182 
  183     order = memcmp(rdata1->data, rdata2->data, 2);
  184     if (order != 0) {
  185         return (order < 0 ? -1 : 1);
  186     }
  187 
  188     dns_name_init(&name1, NULL);
  189     dns_name_init(&name2, NULL);
  190 
  191     dns_rdata_toregion(rdata1, &region1);
  192     dns_rdata_toregion(rdata2, &region2);
  193 
  194     isc_region_consume(&region1, 2);
  195     isc_region_consume(&region2, 2);
  196 
  197     dns_name_fromregion(&name1, &region1);
  198     dns_name_fromregion(&name2, &region2);
  199 
  200     return (dns_name_rdatacompare(&name1, &name2));
  201 }
  202 
  203 static inline isc_result_t
  204 fromstruct_mx(ARGS_FROMSTRUCT) {
  205     dns_rdata_mx_t *mx = source;
  206     isc_region_t region;
  207 
  208     REQUIRE(type == dns_rdatatype_mx);
  209     REQUIRE(mx != NULL);
  210     REQUIRE(mx->common.rdtype == type);
  211     REQUIRE(mx->common.rdclass == rdclass);
  212 
  213     UNUSED(type);
  214     UNUSED(rdclass);
  215 
  216     RETERR(uint16_tobuffer(mx->pref, target));
  217     dns_name_toregion(&mx->mx, &region);
  218     return (isc_buffer_copyregion(target, &region));
  219 }
  220 
  221 static inline isc_result_t
  222 tostruct_mx(ARGS_TOSTRUCT) {
  223     isc_region_t region;
  224     dns_rdata_mx_t *mx = target;
  225     dns_name_t name;
  226 
  227     REQUIRE(rdata->type == dns_rdatatype_mx);
  228     REQUIRE(mx != NULL);
  229     REQUIRE(rdata->length != 0);
  230 
  231     mx->common.rdclass = rdata->rdclass;
  232     mx->common.rdtype = rdata->type;
  233     ISC_LINK_INIT(&mx->common, link);
  234 
  235     dns_name_init(&name, NULL);
  236     dns_rdata_toregion(rdata, &region);
  237     mx->pref = uint16_fromregion(&region);
  238     isc_region_consume(&region, 2);
  239     dns_name_fromregion(&name, &region);
  240     dns_name_init(&mx->mx, NULL);
  241     RETERR(name_duporclone(&name, mctx, &mx->mx));
  242     mx->mctx = mctx;
  243     return (ISC_R_SUCCESS);
  244 }
  245 
  246 static inline void
  247 freestruct_mx(ARGS_FREESTRUCT) {
  248     dns_rdata_mx_t *mx = source;
  249 
  250     REQUIRE(mx != NULL);
  251     REQUIRE(mx->common.rdtype == dns_rdatatype_mx);
  252 
  253     if (mx->mctx == NULL) {
  254         return;
  255     }
  256 
  257     dns_name_free(&mx->mx, mx->mctx);
  258     mx->mctx = NULL;
  259 }
  260 
  261 static unsigned char port25_offset[] = { 0, 3 };
  262 static unsigned char port25_ndata[] = "\003_25\004_tcp";
  263 static dns_name_t port25 = DNS_NAME_INITNONABSOLUTE(port25_ndata,
  264                             port25_offset);
  265 
  266 static inline isc_result_t
  267 additionaldata_mx(ARGS_ADDLDATA) {
  268     isc_result_t result;
  269     dns_fixedname_t fixed;
  270     dns_name_t name;
  271     dns_offsets_t offsets;
  272     isc_region_t region;
  273 
  274     REQUIRE(rdata->type == dns_rdatatype_mx);
  275 
  276     dns_name_init(&name, offsets);
  277     dns_rdata_toregion(rdata, &region);
  278     isc_region_consume(&region, 2);
  279     dns_name_fromregion(&name, &region);
  280 
  281     if (dns_name_equal(&name, dns_rootname)) {
  282         return (ISC_R_SUCCESS);
  283     }
  284 
  285     result = (add)(arg, &name, dns_rdatatype_a);
  286     if (result != ISC_R_SUCCESS) {
  287         return (result);
  288     }
  289 
  290     dns_fixedname_init(&fixed);
  291     result = dns_name_concatenate(&port25, &name,
  292                       dns_fixedname_name(&fixed), NULL);
  293     if (result != ISC_R_SUCCESS) {
  294         return (ISC_R_SUCCESS);
  295     }
  296 
  297     return ((add)(arg, dns_fixedname_name(&fixed), dns_rdatatype_tlsa));
  298 }
  299 
  300 static inline isc_result_t
  301 digest_mx(ARGS_DIGEST) {
  302     isc_region_t r1, r2;
  303     dns_name_t name;
  304 
  305     REQUIRE(rdata->type == dns_rdatatype_mx);
  306 
  307     dns_rdata_toregion(rdata, &r1);
  308     r2 = r1;
  309     isc_region_consume(&r2, 2);
  310     r1.length = 2;
  311     RETERR((digest)(arg, &r1));
  312     dns_name_init(&name, NULL);
  313     dns_name_fromregion(&name, &r2);
  314     return (dns_name_digest(&name, digest, arg));
  315 }
  316 
  317 static inline bool
  318 checkowner_mx(ARGS_CHECKOWNER) {
  319     REQUIRE(type == dns_rdatatype_mx);
  320 
  321     UNUSED(type);
  322     UNUSED(rdclass);
  323 
  324     return (dns_name_ishostname(name, wildcard));
  325 }
  326 
  327 static inline bool
  328 checknames_mx(ARGS_CHECKNAMES) {
  329     isc_region_t region;
  330     dns_name_t name;
  331 
  332     REQUIRE(rdata->type == dns_rdatatype_mx);
  333 
  334     UNUSED(owner);
  335 
  336     dns_rdata_toregion(rdata, &region);
  337     isc_region_consume(&region, 2);
  338     dns_name_init(&name, NULL);
  339     dns_name_fromregion(&name, &region);
  340     if (!dns_name_ishostname(&name, false)) {
  341         if (bad != NULL) {
  342             dns_name_clone(&name, bad);
  343         }
  344         return (false);
  345     }
  346     return (true);
  347 }
  348 
  349 static inline int
  350 casecompare_mx(ARGS_COMPARE) {
  351     return (compare_mx(rdata1, rdata2));
  352 }
  353 
  354 #endif /* RDATA_GENERIC_MX_15_C */