]> git.netwichtig.de Git - user/henk/code/inspircd.git/blob - src/wildcard.cpp
Merge branch 'insp20' into master.
[user/henk/code/inspircd.git] / src / wildcard.cpp
1 /*
2  * InspIRCd -- Internet Relay Chat Daemon
3  *
4  *   Copyright (C) 2008 Robin Burchell <robin+git@viroteck.net>
5  *   Copyright (C) 2003, 2006-2008 Craig Edwards <craigedwards@brainbox.cc>
6  *   Copyright (C) 2007-2008 Dennis Friis <peavey@inspircd.org>
7  *
8  * This file is part of InspIRCd.  InspIRCd is free software: you can
9  * redistribute it and/or modify it under the terms of the GNU General Public
10  * License as published by the Free Software Foundation, version 2.
11  *
12  * This program is distributed in the hope that it will be useful, but WITHOUT
13  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
14  * FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
15  * details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
19  */
20
21
22 #include "inspircd.h"
23
24 static bool MatchInternal(const unsigned char* str, const unsigned char* mask, unsigned const char* map)
25 {
26         unsigned char* cp = NULL;
27         unsigned char* mp = NULL;
28         unsigned char* string = (unsigned char*)str;
29         unsigned char* wild = (unsigned char*)mask;
30
31         while ((*string) && (*wild != '*'))
32         {
33                 if ((map[*wild] != map[*string]) && (*wild != '?'))
34                 {
35                         return 0;
36                 }
37                 wild++;
38                 string++;
39         }
40
41         while (*string)
42         {
43                 if (*wild == '*')
44                 {
45                         if (!*++wild)
46                         {
47                                 return 1;
48                         }
49                         mp = wild;
50                         cp = string+1;
51                 }
52                 else
53                         if ((map[*wild] == map[*string]) || (*wild == '?'))
54                         {
55                                 wild++;
56                                 string++;
57                         }
58                         else
59                         {
60                                 wild = mp;
61                                 string = cp++;
62                         }
63
64         }
65
66         while (*wild == '*')
67         {
68                 wild++;
69         }
70
71         return !*wild;
72 }
73
74 // Below here is all wrappers around MatchInternal
75
76 bool InspIRCd::Match(const std::string& str, const std::string& mask, unsigned const char* map)
77 {
78         if (!map)
79                 map = national_case_insensitive_map;
80
81         return MatchInternal((const unsigned char*)str.c_str(), (const unsigned char*)mask.c_str(), map);
82 }
83
84 bool InspIRCd::Match(const char* str, const char* mask, unsigned const char* map)
85 {
86         if (!map)
87                 map = national_case_insensitive_map;
88
89         return MatchInternal((const unsigned char*)str, (const unsigned char*)mask, map);
90 }
91
92 bool InspIRCd::MatchCIDR(const std::string& str, const std::string& mask, unsigned const char* map)
93 {
94         if (irc::sockets::MatchCIDR(str, mask, true))
95                 return true;
96
97         // Fall back to regular match
98         return InspIRCd::Match(str, mask, map);
99 }
100
101 bool InspIRCd::MatchCIDR(const char* str, const char* mask, unsigned const char* map)
102 {
103         if (irc::sockets::MatchCIDR(str, mask, true))
104                 return true;
105
106         // Fall back to regular match
107         return InspIRCd::Match(str, mask, map);
108 }
109
110 bool InspIRCd::MatchMask(const std::string& masks, const std::string& hostname, const std::string& ipaddr)
111 {
112         irc::spacesepstream masklist(masks);
113         std::string mask;
114         while (masklist.GetToken(mask))
115         {
116                 if (InspIRCd::Match(hostname, mask, ascii_case_insensitive_map) ||
117                         InspIRCd::MatchCIDR(ipaddr, mask, ascii_case_insensitive_map))
118                 {
119                         return true;
120                 }
121         }
122         return false;
123 }