| /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */ |
| /** |
| * Copyright (c) 2013-2014 Regents of the University of California. |
| * |
| * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions). |
| * |
| * ndn-cxx library is free software: you can redistribute it and/or modify it under the |
| * terms of the GNU Lesser General Public License as published by the Free Software |
| * Foundation, either version 3 of the License, or (at your option) any later version. |
| * |
| * ndn-cxx library 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 Lesser General Public License for more details. |
| * |
| * You should have received copies of the GNU General Public License and GNU Lesser |
| * General Public License along with ndn-cxx, e.g., in COPYING.md file. If not, see |
| * <http://www.gnu.org/licenses/>. |
| * |
| * See AUTHORS.md for complete list of ndn-cxx authors and contributors. |
| * |
| * @author Yingdi Yu <http://irl.cs.ucla.edu/~yingdi/> |
| */ |
| |
| #ifndef NDN_SECURITY_CONF_FILTER_HPP |
| #define NDN_SECURITY_CONF_FILTER_HPP |
| |
| #include "../../common.hpp" |
| #include "../../data.hpp" |
| #include "../../interest.hpp" |
| #include "../../util/regex.hpp" |
| #include "../security-common.hpp" |
| #include <boost/algorithm/string.hpp> |
| |
| #include "common.hpp" |
| |
| namespace ndn { |
| namespace security { |
| namespace conf { |
| |
| /** |
| * @brief Filter is one of the classes used by ValidatorConfig. |
| * |
| * The ValidatorConfig class consists of a set of rules. |
| * The Filter class is a part of a rule and is used to match packet. |
| * Matched packets will be checked against the checkers defined in the rule. |
| */ |
| |
| class Filter |
| { |
| public: |
| |
| virtual |
| ~Filter() |
| { |
| } |
| |
| bool |
| match(const Data& data) |
| { |
| return matchName(data.getName()); |
| } |
| |
| bool |
| match(const Interest& interest) |
| { |
| if (interest.getName().size() < signed_interest::MIN_LENGTH) |
| return false; |
| |
| Name unsignedName = interest.getName().getPrefix(-signed_interest::MIN_LENGTH); |
| return matchName(unsignedName); |
| } |
| |
| protected: |
| virtual bool |
| matchName(const Name& name) = 0; |
| }; |
| |
| class RelationNameFilter : public Filter |
| { |
| public: |
| enum Relation |
| { |
| RELATION_EQUAL, |
| RELATION_IS_PREFIX_OF, |
| RELATION_IS_STRICT_PREFIX_OF |
| }; |
| |
| RelationNameFilter(const Name& name, Relation relation) |
| : m_name(name) |
| , m_relation(relation) |
| { |
| } |
| |
| virtual |
| ~RelationNameFilter() |
| { |
| } |
| |
| protected: |
| virtual bool |
| matchName(const Name& name) |
| { |
| switch (m_relation) |
| { |
| case RELATION_EQUAL: |
| return (name == m_name); |
| case RELATION_IS_PREFIX_OF: |
| return m_name.isPrefixOf(name); |
| case RELATION_IS_STRICT_PREFIX_OF: |
| return (m_name.isPrefixOf(name) && m_name.size() < name.size()); |
| default: |
| return false; |
| } |
| } |
| |
| private: |
| Name m_name; |
| Relation m_relation; |
| }; |
| |
| class RegexNameFilter : public Filter |
| { |
| public: |
| explicit |
| RegexNameFilter(const Regex& regex) |
| : m_regex(regex) |
| { |
| } |
| |
| virtual |
| ~RegexNameFilter() |
| { |
| } |
| |
| protected: |
| virtual bool |
| matchName(const Name& name) |
| { |
| return m_regex.match(name); |
| } |
| |
| private: |
| Regex m_regex; |
| }; |
| |
| class FilterFactory |
| { |
| public: |
| static shared_ptr<Filter> |
| create(const ConfigSection& configSection) |
| { |
| ConfigSection::const_iterator propertyIt = configSection.begin(); |
| |
| if (propertyIt == configSection.end() || !boost::iequals(propertyIt->first, "type")) |
| throw Error("Expect <filter.type>!"); |
| |
| std::string type = propertyIt->second.data(); |
| |
| if (boost::iequals(type, "name")) |
| return createNameFilter(configSection); |
| else |
| throw Error("Unsupported filter.type: " + type); |
| } |
| private: |
| static shared_ptr<Filter> |
| createNameFilter(const ConfigSection& configSection) |
| { |
| ConfigSection::const_iterator propertyIt = configSection.begin(); |
| propertyIt++; |
| |
| if (propertyIt == configSection.end()) |
| throw Error("Expect more properties for filter(name)"); |
| |
| if (boost::iequals(propertyIt->first, "name")) |
| { |
| // Get filter.name |
| Name name; |
| try |
| { |
| name = Name(propertyIt->second.data()); |
| } |
| catch (Name::Error& e) |
| { |
| throw Error("Wrong filter.name: " + propertyIt->second.data()); |
| } |
| |
| propertyIt++; |
| |
| // Get filter.relation |
| if (propertyIt == configSection.end() || !boost::iequals(propertyIt->first, "relation")) |
| throw Error("Expect <filter.relation>!"); |
| |
| std::string relationString = propertyIt->second.data(); |
| propertyIt++; |
| |
| RelationNameFilter::Relation relation; |
| if (boost::iequals(relationString, "equal")) |
| relation = RelationNameFilter::RELATION_EQUAL; |
| else if (boost::iequals(relationString, "is-prefix-of")) |
| relation = RelationNameFilter::RELATION_IS_PREFIX_OF; |
| else if (boost::iequals(relationString, "is-strict-prefix-of")) |
| relation = RelationNameFilter::RELATION_IS_STRICT_PREFIX_OF; |
| else |
| throw Error("Unsupported relation: " + relationString); |
| |
| |
| if (propertyIt != configSection.end()) |
| throw Error("Expect the end of filter!"); |
| |
| return make_shared<RelationNameFilter>(name, relation); |
| } |
| else if (boost::iequals(propertyIt->first, "regex")) |
| { |
| std::string regexString = propertyIt->second.data(); |
| propertyIt++; |
| |
| if (propertyIt != configSection.end()) |
| throw Error("Expect the end of filter!"); |
| |
| try |
| { |
| return shared_ptr<RegexNameFilter>(new RegexNameFilter(regexString)); |
| } |
| catch (Regex::Error& e) |
| { |
| throw Error("Wrong filter.regex: " + regexString); |
| } |
| } |
| else |
| throw Error("Wrong filter(name) properties"); |
| } |
| }; |
| |
| } // namespace conf |
| } // namespace security |
| } // namespace ndn |
| |
| #endif // NDN_SECURITY_CONF_FILTER_HPP |