Annotation of embedaddon/dnsmasq/src/domain.c, revision 1.1.1.2

1.1.1.2 ! misho       1: /* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
1.1       misho       2: 
                      3:    This program is free software; you can redistribute it and/or modify
                      4:    it under the terms of the GNU General Public License as published by
                      5:    the Free Software Foundation; version 2 dated June, 1991, or
                      6:    (at your option) version 3 dated 29 June, 2007.
                      7:  
                      8:    This program is distributed in the hope that it will be useful,
                      9:    but WITHOUT ANY WARRANTY; without even the implied warranty of
                     10:    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
                     11:    GNU General Public License for more details.
                     12:      
                     13:    You should have received a copy of the GNU General Public License
                     14:    along with this program.  If not, see <http://www.gnu.org/licenses/>.
                     15: */
                     16: 
                     17: #include "dnsmasq.h"
                     18: 
                     19: 
                     20: static struct cond_domain *search_domain(struct in_addr addr, struct cond_domain *c);
                     21: #ifdef HAVE_IPV6
                     22: static struct cond_domain *search_domain6(struct in6_addr *addr, struct cond_domain *c);
                     23: #endif
                     24: 
                     25: 
                     26: int is_name_synthetic(int flags, char *name, struct all_addr *addr)
                     27: {
                     28:   char *p;
                     29:   struct cond_domain *c = NULL;
                     30:   int prot = AF_INET;
                     31: 
                     32: #ifdef HAVE_IPV6
                     33:   if (flags & F_IPV6)
                     34:     prot = AF_INET6;
                     35: #endif
                     36: 
                     37:   for (c = daemon->synth_domains; c; c = c->next)
                     38:     {
                     39:       int found = 0;
                     40:       char *tail, *pref;
                     41:       
                     42:       for (tail = name, pref = c->prefix; *tail != 0 && pref && *pref != 0; tail++, pref++)
                     43:        {
                     44:          unsigned int c1 = (unsigned char) *pref;
                     45:          unsigned int c2 = (unsigned char) *tail;
                     46:          
                     47:          if (c1 >= 'A' && c1 <= 'Z')
                     48:            c1 += 'a' - 'A';
                     49:          if (c2 >= 'A' && c2 <= 'Z')
                     50:            c2 += 'a' - 'A';
                     51:          
                     52:          if (c1 != c2)
                     53:            break;
                     54:        }
                     55:       
                     56:       if (pref && *pref != 0)
                     57:        continue; /* prefix match fail */
                     58:       
                     59:       /* NB, must not alter name if we return zero */
                     60:       for (p = tail; *p; p++)
                     61:        {
                     62:          char c = *p;
                     63:          
                     64:          if ((c >='0' && c <= '9') || c == '-')
                     65:            continue;
                     66:          
                     67: #ifdef HAVE_IPV6
                     68:          if (prot == AF_INET6 && ((c >='A' && c <= 'F') || (c >='a' && c <= 'f'))) 
                     69:            continue;
                     70: #endif
                     71:          
                     72:          break;
                     73:        }
                     74:       
                     75:       if (*p != '.')
                     76:        continue;
                     77:       
                     78:       *p = 0;  
                     79:       
                     80:       /* swap . or : for - */
                     81:       for (p = tail; *p; p++)
                     82:        if (*p == '-')
                     83:          {
                     84:            if (prot == AF_INET)
                     85:              *p = '.';
                     86: #ifdef HAVE_IPV6
                     87:            else
                     88:              *p = ':';
                     89: #endif
                     90:          }
                     91:       
                     92:       if (hostname_isequal(c->domain, p+1) && inet_pton(prot, tail, addr))
                     93:        {
                     94:          if (prot == AF_INET)
                     95:            {
                     96:              if (!c->is6 &&
                     97:                  ntohl(addr->addr.addr4.s_addr) >= ntohl(c->start.s_addr) &&
                     98:                  ntohl(addr->addr.addr4.s_addr) <= ntohl(c->end.s_addr))
                     99:                found = 1;
                    100:            }
                    101: #ifdef HAVE_IPV6
                    102:          else
                    103:            {
                    104:              u64 addrpart = addr6part(&addr->addr.addr6);
                    105:              
                    106:              if (c->is6 &&
                    107:                  is_same_net6(&addr->addr.addr6, &c->start6, 64) &&
                    108:                  addrpart >= addr6part(&c->start6) &&
                    109:                  addrpart <= addr6part(&c->end6))
                    110:                found = 1;
                    111:            }
                    112: #endif
                    113:        }
                    114:       
                    115:       /* restore name */
                    116:       for (p = tail; *p; p++)
                    117:        if (*p == '.' || *p == ':')
                    118:          *p = '-';
                    119:       
                    120:       *p = '.';
                    121: 
                    122:       if (found)
                    123:        return 1;
                    124:     }
                    125:   
                    126:   return 0;
                    127: }
                    128: 
                    129: 
                    130: int is_rev_synth(int flag, struct all_addr *addr, char *name)
                    131: {
                    132:    struct cond_domain *c;
                    133: 
                    134:    if (flag & F_IPV4 && (c = search_domain(addr->addr.addr4, daemon->synth_domains))) 
                    135:      {
                    136:        char *p;
                    137:        
                    138:        *name = 0;
                    139:        if (c->prefix)
                    140:         strncpy(name, c->prefix, MAXDNAME - ADDRSTRLEN);
                    141:        
                    142:        inet_ntop(AF_INET, &addr->addr.addr4, name + strlen(name), ADDRSTRLEN);
                    143:        for (p = name; *p; p++)
                    144:         if (*p == '.')
                    145:           *p = '-';
                    146: 
                    147:        strncat(name, ".", MAXDNAME);
                    148:        strncat(name, c->domain, MAXDNAME);
                    149: 
                    150:        return 1;
                    151:      }
                    152: 
                    153: #ifdef HAVE_IPV6
                    154:    if (flag & F_IPV6 && (c = search_domain6(&addr->addr.addr6, daemon->synth_domains))) 
                    155:      {
                    156:        char *p;
                    157:        
                    158:        *name = 0;
                    159:        if (c->prefix)
                    160:         strncpy(name, c->prefix, MAXDNAME - ADDRSTRLEN);
                    161:        
                    162:        inet_ntop(AF_INET6, &addr->addr.addr6, name + strlen(name), ADDRSTRLEN);
                    163: 
                    164:        /* IPv6 presentation address can start with ":", but valid domain names
                    165:          cannot start with "-" so prepend a zero in that case. */
                    166:        if (!c->prefix && *name == ':')
                    167:         {
                    168:           *name = '0';
                    169:           inet_ntop(AF_INET6, &addr->addr.addr6, name+1, ADDRSTRLEN);
                    170:         }
                    171: 
                    172:        for (p = name; *p; p++)
                    173:         if (*p == ':')
                    174:           *p = '-';
                    175: 
                    176:        strncat(name, ".", MAXDNAME);
                    177:        strncat(name, c->domain, MAXDNAME);
                    178:        
                    179:        return 1;
                    180:      }
                    181: #endif
                    182:    
                    183:    return 0;
                    184: }
                    185: 
                    186: 
                    187: static struct cond_domain *search_domain(struct in_addr addr, struct cond_domain *c)
                    188: {
                    189:   for (; c; c = c->next)
                    190:     if (!c->is6 &&
                    191:        ntohl(addr.s_addr) >= ntohl(c->start.s_addr) &&
                    192:         ntohl(addr.s_addr) <= ntohl(c->end.s_addr))
                    193:       return c;
                    194: 
                    195:   return NULL;
                    196: }
                    197: 
                    198: char *get_domain(struct in_addr addr)
                    199: {
                    200:   struct cond_domain *c;
                    201: 
                    202:   if ((c = search_domain(addr, daemon->cond_domain)))
                    203:     return c->domain;
                    204: 
                    205:   return daemon->domain_suffix;
                    206: } 
                    207: 
                    208: #ifdef HAVE_IPV6
                    209: static struct cond_domain *search_domain6(struct in6_addr *addr, struct cond_domain *c)
                    210: {
                    211:   u64 addrpart = addr6part(addr);
                    212:   
                    213:   for (; c; c = c->next)
                    214:     if (c->is6 &&
                    215:        is_same_net6(addr, &c->start6, 64) &&
                    216:        addrpart >= addr6part(&c->start6) &&
                    217:         addrpart <= addr6part(&c->end6))
                    218:       return c;
                    219:   
                    220:   return NULL;
                    221: }
                    222: 
                    223: char *get_domain6(struct in6_addr *addr)
                    224: {
                    225:   struct cond_domain *c;
                    226: 
                    227:   if (addr && (c = search_domain6(addr, daemon->cond_domain)))
                    228:     return c->domain;
                    229: 
                    230:   return daemon->domain_suffix;
                    231: } 
                    232: #endif

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>