/* * InspIRCd -- Internet Relay Chat Daemon * * Copyright (C) 2013, 2017 Sadie Powell * Copyright (C) 2012 Robby * Copyright (C) 2009 Uli Schlachter * Copyright (C) 2008, 2010 Craig Edwards * Copyright (C) 2007-2008 Robin Burchell * Copyright (C) 2007-2008 Dennis Friis * * This file is part of InspIRCd. InspIRCd is free software: you can * redistribute it and/or modify it under the terms of the GNU General Public * License as published by the Free Software Foundation, version 2. * * This program is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more * details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "inspircd.h" static bool MatchInternal(const unsigned char* str, const unsigned char* mask, unsigned const char* map) { unsigned char* cp = NULL; unsigned char* mp = NULL; unsigned char* string = (unsigned char*)str; unsigned char* wild = (unsigned char*)mask; while ((*string) && (*wild != '*')) { if ((map[*wild] != map[*string]) && (*wild != '?')) { return 0; } wild++; string++; } while (*string) { if (*wild == '*') { if (!*++wild) { return 1; } mp = wild; cp = string+1; } else if ((map[*wild] == map[*string]) || (*wild == '?')) { wild++; string++; } else { wild = mp; string = cp++; } } while (*wild == '*') { wild++; } return !*wild; } // Below here is all wrappers around MatchInternal bool InspIRCd::Match(const std::string& str, const std::string& mask, unsigned const char* map) { if (!map) map = national_case_insensitive_map; return MatchInternal((const unsigned char*)str.c_str(), (const unsigned char*)mask.c_str(), map); } bool InspIRCd::Match(const char* str, const char* mask, unsigned const char* map) { if (!map) map = national_case_insensitive_map; return MatchInternal((const unsigned char*)str, (const unsigned char*)mask, map); } bool InspIRCd::MatchCIDR(const std::string& str, const std::string& mask, unsigned const char* map) { if (irc::sockets::MatchCIDR(str, mask, true)) return true; // Fall back to regular match return InspIRCd::Match(str, mask, map); } bool InspIRCd::MatchCIDR(const char* str, const char* mask, unsigned const char* map) { if (irc::sockets::MatchCIDR(str, mask, true)) return true; // Fall back to regular match return InspIRCd::Match(str, mask, map); } bool InspIRCd::MatchMask(const std::string& masks, const std::string& hostname, const std::string& ipaddr) { irc::spacesepstream masklist(masks); std::string mask; while (masklist.GetToken(mask)) { if (InspIRCd::Match(hostname, mask, ascii_case_insensitive_map) || InspIRCd::MatchCIDR(ipaddr, mask, ascii_case_insensitive_map)) { return true; } } return false; }