1
0
mirror of https://github.com/fwbuilder/fwbuilder synced 2026-03-25 12:47:44 +01:00

see #1942 refactored rule processors that deal with service so that they can be used by both policy and nat compilers

This commit is contained in:
Vadim Kurland 2011-01-17 17:12:35 -08:00
parent 5efb7ae3e5
commit 568e222fa5
4 changed files with 219 additions and 188 deletions

View File

@ -512,6 +512,163 @@ protected:
virtual bool processNext();
};
/**
* split rules with more than one service object, so that each
* rule has services with the same protocol
*/
class splitServices : public BasicRuleProcessor
{
protected:
public:
splitServices(const std::string &name) : BasicRuleProcessor(name) {}
virtual bool processNext();
};
/**
* separate service object that satisfies condition
* implemented in the virtual method "condition" so we have
* exactly one such object per rule.
*/
class separateServiceObject : public BasicRuleProcessor
{
protected:
virtual bool condition(const libfwbuilder::Service *srv) =0;
public:
separateServiceObject(const std::string &name);
virtual bool processNext();
};
/**
* separate TCP/UDP services that specify source port (can
* not be used in combination with destination port with
* multiport)
*/
class separateSrcPort : public separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separateSrcPort(const std::string &name) :
separateServiceObject(name) {}
};
/**
* separate Tag services so we have exactly one per rule.
*/
class separateTagged : public separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separateTagged(const std::string &name) :
separateServiceObject(name) {}
};
class separateUserServices : public separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separateUserServices(const std::string &name) :
separateServiceObject(name) {}
};
/**
* separate IPService objects with tos attrubute so we have
* exactly one per rule.
*/
class separateTOS : public separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separateTOS(const std::string &name) :
separateServiceObject(name) {}
};
/**
* split rules with more than one IPService object with
* options, so that each rule has only one such service
*/
class splitIpOptions : public separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
splitIpOptions(const std::string &name) :
separateServiceObject(name) {}
};
/**
* separate TCP services with flags (can't use those in combination
* with others in groups of services)
*/
class separateTCPWithFlags : public separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separateTCPWithFlags(const std::string &name) :
separateServiceObject(name) {}
};
/**
* separate TCP and UDP services that match port ranges and
* "any tcp" or "any udp" objects
*/
class separatePortRanges : public separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separatePortRanges(const std::string &name) :
separateServiceObject(name) {}
};
/**
* verify if custom services used in rules are configured for
* this platform
*/
class verifyCustomServices : public BasicRuleProcessor
{
public:
verifyCustomServices(const std::string &name) :
BasicRuleProcessor(name) {}
virtual bool processNext();
};
/**
* simply check if TCPService object with "established" flag
* set is used in Service and abort with an error saying that
* target firewall does not support this. Use for pretty much
* every platform except ipfw and router ACLs
*/
class CheckForTCPEstablished : public BasicRuleProcessor
{
public:
CheckForTCPEstablished(const std::string &name) :
BasicRuleProcessor(name) {}
virtual bool processNext();
};
/**
* simply check if UserService objectis used in Service and
* abort with an error saying that target firewall does not
* support this.
*/
class CheckForUnsupportedUserService : public BasicRuleProcessor
{
public:
CheckForUnsupportedUserService(const std::string &name) :
BasicRuleProcessor(name) {}
virtual bool processNext();
};
/**
* prepare interface string
*/

View File

@ -226,120 +226,6 @@ namespace fwcompiler {
*/
DECLARE_POLICY_RULE_PROCESSOR(addressRanges);
/**
* split rules with more than one service object, so that each
* rule has services with the same protocol
*/
DECLARE_POLICY_RULE_PROCESSOR(splitServices);
/**
* separate service object that satisfies condition
* implemented in the virtual method "condition" so we have
* exactly one such object per rule.
*/
class separateServiceObject : public PolicyRuleProcessor
{
protected:
virtual bool condition(const libfwbuilder::Service *srv) =0;
public:
separateServiceObject(const std::string &name);
virtual bool processNext();
};
/**
* separate TCP/UDP services that specify source port (can
* not be used in combination with destination port with
* multiport)
*/
class separateSrcPort : public PolicyCompiler::separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separateSrcPort(const std::string &name) :
PolicyCompiler::separateServiceObject(name) {}
};
/**
* separate Tag services so we have exactly one per rule.
*/
class separateTagged : public PolicyCompiler::separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separateTagged(const std::string &name) :
PolicyCompiler::separateServiceObject(name) {}
};
class separateUserServices : public PolicyCompiler::separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separateUserServices(const std::string &name) :
PolicyCompiler::separateServiceObject(name) {}
};
/**
* separate IPService objects with tos attrubute so we have
* exactly one per rule.
*/
class separateTOS : public PolicyCompiler::separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separateTOS(const std::string &name) :
PolicyCompiler::separateServiceObject(name) {}
};
/**
* split rules with more than one IPService object with
* options, so that each rule has only one such service
*/
class splitIpOptions : public PolicyCompiler::separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
splitIpOptions(const std::string &name) :
PolicyCompiler::separateServiceObject(name) {}
};
/**
* separate TCP services with flags (can't use those in combination
* with others in groups of services)
*/
class separateTCPWithFlags : public PolicyCompiler::separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separateTCPWithFlags(const std::string &name) :
PolicyCompiler::separateServiceObject(name) {}
};
/**
* separate TCP and UDP services that match port ranges and
* "any tcp" or "any udp" objects
*/
class separatePortRanges : public PolicyCompiler::separateServiceObject
{
protected:
virtual bool condition(const libfwbuilder::Service *srv);
public:
separatePortRanges(const std::string &name) :
PolicyCompiler::separateServiceObject(name) {}
};
/**
* verify if custom services used in rules are configured for
* this platform
*/
DECLARE_POLICY_RULE_PROCESSOR(verifyCustomServices);
/**
* checks for unnumbered interface in rule elements (one can
@ -370,21 +256,6 @@ namespace fwcompiler {
*/
DECLARE_POLICY_RULE_PROCESSOR(ConvertToAtomic);
/**
* simply check if TCPService object with "established" flag
* set is used in Service and abort with an error saying that
* target firewall does not support this. Use for pretty much
* every platform except ipfw and router ACLs
*/
DECLARE_POLICY_RULE_PROCESSOR(CheckForTCPEstablished);
/**
* simply check if UserService objectis used in Service and
* abort with an error saying that target firewall does not
* support this.
*/
DECLARE_POLICY_RULE_PROCESSOR(CheckForUnsupportedUserService);
/**
* drop rules that have ipv4 or ipv6 addresses (depending
* on the argument ipv6 passed to the constructor)

View File

@ -25,7 +25,7 @@
#include <assert.h>
#include "PolicyCompiler.h"
#include "Compiler.h"
#include "fwbuilder/RuleElement.h"
#include "fwbuilder/IPService.h"
@ -50,14 +50,19 @@ using namespace libfwbuilder;
using namespace std;
/*
* These rule processors should work for both Policy and NAT rules
* without having to build specialized classes inheriting from these.
*/
bool PolicyCompiler::splitServices::processNext()
bool Compiler::splitServices::processNext()
{
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Rule *rule = prev_processor->getNextRule(); if (rule==NULL) return false;
string re_type = PolicyRule::isA(rule) ?
RuleElementSrv::TYPENAME : RuleElementOSrv::TYPENAME;
RuleElement *re_srv = RuleElement::cast(rule->getFirstByType(re_type));
RuleElementSrv *srv=rule->getSrv();
if (srv->size()==1)
if (re_srv->size()==1)
{
tmp_queue.push_back(rule);
return true;
@ -65,11 +70,9 @@ bool PolicyCompiler::splitServices::processNext()
map<int, list<Service*> > services;
for (FWObject::iterator i=srv->begin(); i!=srv->end(); i++)
for (FWObject::iterator i=re_srv->begin(); i!=re_srv->end(); i++)
{
FWObject *o = FWReference::getObject(*i);
Service *s=Service::cast( o );
Service *s = Service::cast(FWReference::getObject(*i));
assert(s);
int proto = s->getProtocolNumber();
@ -81,10 +84,10 @@ bool PolicyCompiler::splitServices::processNext()
{
list<Service*> &sl=(*i1).second;
PolicyRule *r= compiler->dbcopy->createPolicyRule();
PolicyRule *r = compiler->dbcopy->createPolicyRule();
compiler->temp_ruleset->add(r);
r->duplicate(rule);
RuleElementSrv *nsrv=r->getSrv();
RuleElement *nsrv = RuleElement::cast(r->getFirstByType(re_type));
nsrv->clearChildren();
for (list<Service*>::iterator j=sl.begin(); j!=sl.end(); j++)
@ -99,24 +102,26 @@ bool PolicyCompiler::splitServices::processNext()
PolicyCompiler::separateServiceObject::separateServiceObject(
const string &name) : PolicyRuleProcessor(name)
Compiler::separateServiceObject::separateServiceObject(
const string &name) : BasicRuleProcessor(name)
{
}
bool PolicyCompiler::separateServiceObject::processNext()
bool Compiler::separateServiceObject::processNext()
{
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Rule *rule = prev_processor->getNextRule(); if (rule==NULL) return false;
string re_type = PolicyRule::isA(rule) ?
RuleElementSrv::TYPENAME : RuleElementOSrv::TYPENAME;
RuleElement *re_srv = RuleElement::cast(rule->getFirstByType(re_type));
RuleElementSrv *rel= rule->getSrv();
if (rel->size()==1) {
if (re_srv->size()==1)
{
tmp_queue.push_back(rule);
return true;
}
list<Service*> services;
for (FWObject::iterator i=rel->begin(); i!=rel->end(); i++)
for (FWObject::iterator i=re_srv->begin(); i!=re_srv->end(); i++)
{
FWObject *o= *i;
if (FWReference::cast(o)!=NULL) o=FWReference::cast(o)->getPointer();
@ -128,7 +133,7 @@ bool PolicyCompiler::separateServiceObject::processNext()
PolicyRule *r = compiler->dbcopy->createPolicyRule();
compiler->temp_ruleset->add(r);
r->duplicate(rule);
RuleElementSrv *nsrv=r->getSrv();
RuleElement *nsrv = RuleElement::cast(r->getFirstByType(re_type));
nsrv->clearChildren();
nsrv->addRef( s );
tmp_queue.push_back(r);
@ -136,9 +141,9 @@ bool PolicyCompiler::separateServiceObject::processNext()
}
}
for (list<Service*>::iterator i=services.begin(); i!=services.end(); i++)
rel->removeRef( (*i) );
re_srv->removeRef( (*i) );
if (!rel->isAny())
if (!re_srv->isAny())
tmp_queue.push_back(rule);
return true;
@ -150,7 +155,7 @@ bool PolicyCompiler::separateServiceObject::processNext()
* not be used in combination with destination port with
* multiport)
*/
bool PolicyCompiler::separateSrcPort::condition(const Service *srv)
bool Compiler::separateSrcPort::condition(const Service *srv)
{
if ( TCPService::isA(srv) || UDPService::isA(srv))
{
@ -164,35 +169,35 @@ bool PolicyCompiler::separateSrcPort::condition(const Service *srv)
return false;
}
bool PolicyCompiler::separateTagged::condition(const Service *srv)
bool Compiler::separateTagged::condition(const Service *srv)
{
return ( TagService::isA(srv));
}
bool PolicyCompiler::separateUserServices::condition(const Service *srv)
bool Compiler::separateUserServices::condition(const Service *srv)
{
return ( UserService::isA(srv));
}
bool PolicyCompiler::separateTOS::condition(const Service *srv)
bool Compiler::separateTOS::condition(const Service *srv)
{
const IPService *ip = IPService::constcast(srv);
return (ip && !ip->getTOSCode().empty());
}
bool PolicyCompiler::splitIpOptions::condition(const Service *srv)
bool Compiler::splitIpOptions::condition(const Service *srv)
{
const IPService *ip = IPService::constcast(srv);
return (ip && ip->hasIpOptions());
}
bool PolicyCompiler::separateTCPWithFlags::condition(const Service *srv)
bool Compiler::separateTCPWithFlags::condition(const Service *srv)
{
const TCPService *s = TCPService::constcast(srv);
return (s && s->inspectFlags() );
}
bool PolicyCompiler::separatePortRanges::condition(const Service *srv)
bool Compiler::separatePortRanges::condition(const Service *srv)
{
if ( TCPService::isA(srv) || UDPService::isA(srv) )
{
@ -226,15 +231,16 @@ bool PolicyCompiler::separatePortRanges::condition(const Service *srv)
bool PolicyCompiler::verifyCustomServices::processNext()
bool Compiler::verifyCustomServices::processNext()
{
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Rule *rule = prev_processor->getNextRule(); if (rule==NULL) return false;
string re_type = PolicyRule::isA(rule) ?
RuleElementSrv::TYPENAME : RuleElementOSrv::TYPENAME;
RuleElement *re_srv = RuleElement::cast(rule->getFirstByType(re_type));
tmp_queue.push_back(rule);
RuleElementSrv *srv=rule->getSrv();
for (FWObject::iterator i=srv->begin(); i!=srv->end(); i++)
for (FWObject::iterator i=re_srv->begin(); i!=re_srv->end(); i++)
{
FWObject *o = FWReference::getObject(*i);
assert(o!=NULL);
@ -246,16 +252,14 @@ bool PolicyCompiler::verifyCustomServices::processNext()
return true;
}
bool PolicyCompiler::CheckForTCPEstablished::processNext()
bool Compiler::CheckForTCPEstablished::processNext()
{
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Rule *rule = prev_processor->getNextRule(); if (rule==NULL) return false;
string re_type = PolicyRule::isA(rule) ?
RuleElementSrv::TYPENAME : RuleElementOSrv::TYPENAME;
RuleElement *re_srv = RuleElement::cast(rule->getFirstByType(re_type));
RuleElementSrv *srv=rule->getSrv();
for (FWObject::iterator i=srv->begin(); i!=srv->end(); i++)
for (FWObject::iterator i=re_srv->begin(); i!=re_srv->end(); i++)
{
FWObject *o = FWReference::getObject(*i);
@ -264,34 +268,33 @@ bool PolicyCompiler::CheckForTCPEstablished::processNext()
if (s->getEstablished())
compiler->abort(
rule,
string("TCPService object with option \"established\" "
"is not supported by firewall platform \"") +
compiler->myPlatformName() +
string("\". Use stateful rule instead."));
rule,
string("TCPService object with option \"established\" "
"is not supported by firewall platform \"") +
compiler->myPlatformName() +
string("\". Use stateful rule instead."));
}
tmp_queue.push_back(rule);
return true;
}
bool PolicyCompiler::CheckForUnsupportedUserService::processNext()
bool Compiler::CheckForUnsupportedUserService::processNext()
{
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Rule *rule = prev_processor->getNextRule(); if (rule==NULL) return false;
string re_type = PolicyRule::isA(rule) ?
RuleElementSrv::TYPENAME : RuleElementOSrv::TYPENAME;
RuleElement *re_srv = RuleElement::cast(rule->getFirstByType(re_type));
RuleElementSrv *srv=rule->getSrv();
for (FWObject::iterator i=srv->begin(); i!=srv->end(); i++)
for (FWObject::iterator i=re_srv->begin(); i!=re_srv->end(); i++)
{
FWObject *o = FWReference::getObject(*i);
if (UserService::isA(o))
compiler->abort(
rule,
string("UserService object is not supported by ") +
compiler->myPlatformName());
rule,
string("UserService object is not supported by ") +
compiler->myPlatformName());
}
tmp_queue.push_back(rule);

View File

@ -15,7 +15,7 @@ SOURCES = BaseCompiler.cpp \
NATCompiler.cpp \
OSConfigurator.cpp \
PolicyCompiler.cpp \
PolicyCompiler_srvre_functions.cpp \
ServiceRuleProcessors.cpp \
RoutingCompiler.cpp
HEADERS = BaseCompiler.h \