]> jfr.im git - irc/rqf/shadowircd.git/blobdiff - src/hostmask.c
Branch merge.
[irc/rqf/shadowircd.git] / src / hostmask.c
index 334be5856e56dd777a4422235d57ff4b1e0af1f4..0b2b1605d0ba5383fdbb00025f6e2e81960e6613 100644 (file)
@@ -5,7 +5,7 @@
  *  Copyright (C) 1990 Jarkko Oikarinen and University of Oulu, Co Center
  *  Copyright (C) 1996-2002 Hybrid Development Team
  *  Copyright (C) 2002-2005 ircd-ratbox development team
- *  Copyright (C) 2005-2006 charybdis development team
+ *  Copyright (C) 2005-2008 charybdis development team
  *
  *  This program is free software; you can redistribute it and/or modify
  *  it under the terms of the GNU General Public License as published by
@@ -26,7 +26,6 @@
  */
 
 #include "stdinc.h"
-#include "memory.h"
 #include "ircd_defs.h"
 #include "s_conf.h"
 #include "hostmask.h"
 #include "send.h"
 #include "irc_string.h"
 
-#ifdef IPV6
+#ifdef RB_IPV6
 static unsigned long hash_ipv6(struct sockaddr *, int);
 #endif
 static unsigned long hash_ipv4(struct sockaddr *, int);
 
 
-/* int parse_netmask(const char *, struct irc_sockaddr_storage *, int *);
+/* int parse_netmask(const char *, struct rb_sockaddr_storage *, int *);
  * Input: A hostmask, or an IPV4/6 address.
  * Output: An integer describing whether it is an IPV4, IPV6 address or a
  *         hostmask, an address(if it is an IP mask),
@@ -52,7 +51,7 @@ parse_netmask(const char *text, struct sockaddr  *naddr, int *nb)
 {
        char *ip = LOCAL_COPY(text);
        char *ptr;
-       struct irc_sockaddr_storage *addr, xaddr;
+       struct rb_sockaddr_storage *addr, xaddr;
        int *b, xb;
        if(nb == NULL)
                b = &xb;
@@ -60,11 +59,11 @@ parse_netmask(const char *text, struct sockaddr  *naddr, int *nb)
                b = nb;
        
        if(naddr == NULL)
-               addr = (struct irc_sockaddr_storage *)&xaddr;
+               addr = (struct rb_sockaddr_storage *)&xaddr;
        else
-               addr = (struct irc_sockaddr_storage *)naddr;
+               addr = (struct rb_sockaddr_storage *)naddr;
        
-#ifdef IPV6
+#ifdef RB_IPV6
        if(strchr(ip, ':'))
        {       
                if((ptr = strchr(ip, '/')))
@@ -110,7 +109,7 @@ init_host_hash(void)
        memset(&atable, 0, sizeof(atable));
 }
 
-/* unsigned long hash_ipv4(struct irc_sockaddr_storage*)
+/* unsigned long hash_ipv4(struct rb_sockaddr_storage*)
  * Input: An IP address.
  * Output: A hash value of the IP address.
  * Side effects: None
@@ -129,12 +128,12 @@ hash_ipv4(struct sockaddr *saddr, int bits)
        return 0;
 }
 
-/* unsigned long hash_ipv6(struct irc_sockaddr_storage*)
+/* unsigned long hash_ipv6(struct rb_sockaddr_storage*)
  * Input: An IP address.
  * Output: A hash value of the IP address.
  * Side effects: None
  */
-#ifdef IPV6
+#ifdef RB_IPV6
 static unsigned long
 hash_ipv6(struct sockaddr *saddr, int bits)
 {
@@ -197,7 +196,7 @@ get_mask_hash(const char *text)
        return hash_text(text);
 }
 
-/* struct ConfItem* find_conf_by_address(const char*, struct irc_sockaddr_storage*,
+/* struct ConfItem* find_conf_by_address(const char*, struct rb_sockaddr_storage*,
  *         int type, int fam, const char *username)
  * Input: The hostname, the address, the type of mask to find, the address
  *        family, the username.
@@ -222,7 +221,7 @@ find_conf_by_address(const char *name, const char *sockhost,
        if(addr)
        {
                /* Check for IPV6 matches... */
-#ifdef IPV6
+#ifdef RB_IPV6
                if(fam == AF_INET6)
                {
 
@@ -344,7 +343,7 @@ find_conf_by_address(const char *name, const char *sockhost,
 }
 
 /* struct ConfItem* find_address_conf(const char*, const char*,
- *                                    struct irc_sockaddr_storage*, int);
+ *                                    struct rb_sockaddr_storage*, int);
  * Input: The hostname, username, address, address family.
  * Output: The applicable ConfItem.
  * Side-effects: None
@@ -417,7 +416,7 @@ find_address_conf(const char *host, const char *sockhost, const char *user,
        return iconf;
 }
 
-/* struct ConfItem* find_dline(struct irc_sockaddr_storage*, int)
+/* struct ConfItem* find_dline(struct rb_sockaddr_storage*, int)
  * Input: An address, an address family.
  * Output: The best matching D-line or exempt line.
  * Side effects: None.
@@ -432,6 +431,62 @@ find_dline(struct sockaddr *addr, int aftype)
        return find_conf_by_address(NULL, NULL, NULL, addr, CONF_DLINE | 1, aftype, NULL);
 }
 
+/* void find_exact_conf_by_address(const char*, int, const char *)
+ * Input: 
+ * Output: ConfItem if found
+ * Side-effects: None
+ */
+struct ConfItem *
+find_exact_conf_by_address(const char *address, int type, const char *username)
+{
+       int masktype, bits;
+       unsigned long hv;
+       struct AddressRec *arec;
+       struct rb_sockaddr_storage addr;
+
+       if(address == NULL)
+               address = "/NOMATCH!/";
+       arec = rb_malloc(sizeof(struct AddressRec));
+       masktype = parse_netmask(address, (struct sockaddr *)&addr, &bits);
+#ifdef RB_IPV6
+       if(masktype == HM_IPV6)
+       {
+               /* We have to do this, since we do not re-hash for every bit -A1kmm. */
+               hv = hash_ipv6((struct sockaddr *)&addr, bits - bits % 16);
+       }
+       else
+#endif
+       if(masktype == HM_IPV4)
+       {
+               /* We have to do this, since we do not re-hash for every bit -A1kmm. */
+               hv = hash_ipv4((struct sockaddr *)&addr, bits - bits % 8);
+       }
+       else
+       {
+               hv = get_mask_hash(address);
+       }
+       for (arec = atable[hv]; arec; arec = arec->next)
+       {
+               if (arec->type == type &&
+                               arec->masktype == masktype &&
+                               (arec->username == NULL || username == NULL ? arec->username == username : !irccmp(arec->username, username)))
+               {
+                       if (masktype == HM_HOST)
+                       {
+                               if (!irccmp(arec->Mask.hostname, address))
+                                       return arec->aconf;
+                       }
+                       else
+                       {
+                               if (arec->Mask.ipa.bits == bits &&
+                                       comp_with_mask_sock((struct sockaddr *)&arec->Mask.ipa.addr, (struct sockaddr *)&addr, bits))
+                                       return arec->aconf;
+                       }
+               }
+       }
+       return NULL;
+}
+
 /* void add_conf_by_address(const char*, int, const char *,
  *         struct ConfItem *aconf)
  * Input: 
@@ -448,11 +503,11 @@ add_conf_by_address(const char *address, int type, const char *username, struct
 
        if(address == NULL)
                address = "/NOMATCH!/";
-       arec = MyMalloc(sizeof(struct AddressRec));
+       arec = rb_malloc(sizeof(struct AddressRec));
        masktype = parse_netmask(address, (struct sockaddr *)&arec->Mask.ipa.addr, &bits);
        arec->Mask.ipa.bits = bits;
        arec->masktype = masktype;
-#ifdef IPV6
+#ifdef RB_IPV6
        if(masktype == HM_IPV6)
        {
                /* We have to do this, since we do not re-hash for every bit -A1kmm. */
@@ -493,9 +548,9 @@ delete_one_address_conf(const char *address, struct ConfItem *aconf)
        int masktype, bits;
        unsigned long hv;
        struct AddressRec *arec, *arecl = NULL;
-       struct irc_sockaddr_storage addr;
+       struct rb_sockaddr_storage addr;
        masktype = parse_netmask(address, (struct sockaddr *)&addr, &bits);
-#ifdef IPV6
+#ifdef RB_IPV6
        if(masktype == HM_IPV6)
        {
                /* We have to do this, since we do not re-hash for every bit -A1kmm. */
@@ -523,7 +578,7 @@ delete_one_address_conf(const char *address, struct ConfItem *aconf)
                        aconf->status |= CONF_ILLEGAL;
                        if(!aconf->clients)
                                free_conf(aconf);
-                       MyFree(arec);
+                       rb_free(arec);
                        return;
                }
                arecl = arec;
@@ -563,7 +618,7 @@ clear_out_address_conf(void)
                                arec->aconf->status |= CONF_ILLEGAL;
                                if(!arec->aconf->clients)
                                        free_conf(arec->aconf);
-                               MyFree(arec);
+                               rb_free(arec);
                        }
                }
                *store_next = NULL;
@@ -596,7 +651,7 @@ clear_out_address_conf_bans(void)
                                arec->aconf->status |= CONF_ILLEGAL;
                                if(!arec->aconf->clients)
                                        free_conf(arec->aconf);
-                               MyFree(arec);
+                               rb_free(arec);
                        }
                }
                *store_next = NULL;
@@ -622,22 +677,20 @@ show_iline_prefix(struct Client *sptr, struct ConfItem *aconf, char *name)
        prefix_ptr = prefix_of_host;
        if(IsNoTilde(aconf))
                *prefix_ptr++ = '-';
-       if(IsLimitIp(aconf))
-               *prefix_ptr++ = '!';
        if(IsNeedIdentd(aconf))
                *prefix_ptr++ = '+';
-       if(IsPassIdentd(aconf))
-               *prefix_ptr++ = '$';
-       if(IsNoMatchIp(aconf))
-               *prefix_ptr++ = '%';
        if(IsConfDoSpoofIp(aconf))
                *prefix_ptr++ = '=';
-       if(MyOper(sptr) && IsConfExemptKline(aconf))
+       if(IsOper(sptr) && IsConfExemptFlood(aconf))
+               *prefix_ptr++ = '|';
+       if(IsOper(sptr) && IsConfExemptGline(aconf) && !IsConfExemptKline(aconf))
+               *prefix_ptr++ = '_';
+       if(IsOper(sptr) && IsConfExemptDNSBL(aconf) && !IsConfExemptKline(aconf))
+               *prefix_ptr++ = '$';
+       if(IsOper(sptr) && IsConfExemptKline(aconf))
                *prefix_ptr++ = '^';
-       if(MyOper(sptr) && IsConfExemptLimits(aconf))
+       if(IsOper(sptr) && IsConfExemptLimits(aconf))
                *prefix_ptr++ = '>';
-       if(MyOper(sptr) && IsConfIdlelined(aconf))
-               *prefix_ptr++ = '<';
        *prefix_ptr = '\0';
        strncpy(prefix_ptr, name, USERLEN);
        return (prefix_of_host);
@@ -663,7 +716,7 @@ report_auth(struct Client *client_p)
                        {
                                aconf = arec->aconf;
 
-                               if(!MyOper(client_p) && IsConfDoSpoofIp(aconf))
+                               if(!IsOper(client_p) && IsConfDoSpoofIp(aconf))
                                        continue;
 
                                get_printable_conf(aconf, &name, &host, &pass, &user, &port,