1
0
mirror of https://github.com/fwbuilder/fwbuilder synced 2025-10-16 23:47:46 +02:00

merge from v3_1_merge

This commit is contained in:
Vadim Kurland 2009-09-23 17:00:48 +00:00
commit 23ee2d9531
750 changed files with 57549 additions and 24126 deletions

View File

@ -1,9 +1,10 @@
#-*- mode: shell-script; tab-width: 4; -*-
# $Id: VERSION,v 1.47 2007/07/21 23:44:19 vkurland Exp $
FWB_MAJOR_VERSION=3
FWB_MINOR_VERSION=1
FWB_MICRO_VERSION=0
# VERSION must be a string rather than $var because of the build scripts
VERSION="3.1.0"
SHORTVERSION="310"

View File

@ -1 +1 @@
#define BUILD_NUM 1067
#define BUILD_NUM 1481

View File

@ -90,6 +90,8 @@
#undef HAVE_ANTLR_RUNTIME
#undef HAVE_QTDBUS
/*
* on some platforms (OpenBSD) the second parameter to dlopen is different
*/

View File

@ -270,11 +270,15 @@ else
fi
AC_DEFINE_UNQUOTED(HAVE_ANTLR_RUNTIME, 1, [antlr_runtime])
AC_DEFINE_UNQUOTED(HAVE_EXTERNAL_ANTLR, $HAVE_EXTERNAL_ANTLR, [external_antlr])
AC_SUBST(HAVE_ANTLR_RUNTIME)
AC_SUBST(HAVE_EXTERNAL_ANTLR)
AC_SUBST(HAVE_ANTLR_RUNTIME)
AC_SUBST(HAVE_EXTERNAL_ANTLR)
AC_SUBST(ANTLR_LIBS)
AC_SUBST(ANTLR_INCLUDEPATH)
# Need real test for this, but at least for now it seems Qt comes with
# QtDBus support on all platforms except Windows
AC_DEFINE_UNQUOTED(HAVE_QTDBUS, 1, [qtdbus])
AC_SUBST(HAVE_QTDBUS)
dnl ********************************************************************
@ -419,6 +423,7 @@ test -n "$OS_SOLARIS" && AC_DEFINE_UNQUOTED(OS_SOLARIS,"${OS_SOLARIS}",[solaris]
test -n "$OS_FREEBSD" && AC_DEFINE_UNQUOTED(OS_FREEBSD,"${OS_FREEBSD}",[freebsd])
test -n "$OS_OPENBSD" && AC_DEFINE_UNQUOTED(OS_OPENBSD,"${OS_OPENBSD}",[openbsd])
test -n "$OS_LINUX" && AC_DEFINE_UNQUOTED(OS_LINUX, "${OS_LINUX}", [linux])
test -n "$OS_SECUWALL" && AC_DEFINE_UNQUOTED(OS_SECUWALL, "${OS_SECUWALL}", [secuwall])
test -n "$OS_UNKNOWN" && AC_DEFINE_UNQUOTED(OS_UNKNOWN,"${OS_UNKNOWN}",[unknown])
AC_SUBST(DISTRO)
@ -447,31 +452,7 @@ AC_CONFIG_FILES([ qmake.inc ])
AC_CONFIG_FILES([ src/res/objects_init.xml ])
AC_CONFIG_FILES([ src/res/templates.xml ])
AC_CONFIG_FILES([ src/res/resources.xml ])
AC_CONFIG_FILES([ src/res/os/endian.xml ])
AC_CONFIG_FILES([ src/res/os/freebsd.xml ])
AC_CONFIG_FILES([ src/res/os/fwsm_os.xml ])
AC_CONFIG_FILES([ src/res/os/ios.xml ])
AC_CONFIG_FILES([ src/res/os/ipcop.xml ])
AC_CONFIG_FILES([ src/res/os/linksys.xml ])
AC_CONFIG_FILES([ src/res/os/linux24.xml ])
AC_CONFIG_FILES([ src/res/os/macosx.xml ])
AC_CONFIG_FILES([ src/res/os/oneshield.xml ])
AC_CONFIG_FILES([ src/res/os/openbsd.xml ])
AC_CONFIG_FILES([ src/res/os/openwrt.xml ])
AC_CONFIG_FILES([ src/res/os/pix_os.xml ])
AC_CONFIG_FILES([ src/res/os/solaris.xml ])
AC_CONFIG_FILES([ src/res/os/unknown_os.xml ])
AC_CONFIG_FILES([ src/res/platform/fwsm.xml ])
AC_CONFIG_FILES([ src/res/platform/iosacl.xml ])
AC_CONFIG_FILES([ src/res/platform/ipf.xml ])
AC_CONFIG_FILES([ src/res/platform/ipfw.xml ])
AC_CONFIG_FILES([ src/res/platform/iptables.xml ])
AC_CONFIG_FILES([ src/res/platform/pf.xml ])
AC_CONFIG_FILES([ src/res/platform/pix.xml ])
AC_CONFIG_FILES([ src/res/platform/unknown.xml ])
AC_OUTPUT

View File

@ -1,3 +1,1159 @@
2009-09-18 vadim <vadim@vk.crocodile.org>
* PolicyCompiler.cpp (ItfNegation::processNext): (change in
libfwbuilder) fix for bug #2710034 "PF Compiler in 3.0.3
Unprotected Interface Bug". When we expand "interface" rule
element which uses negation, skip unprotected interfaces.
2009-09-16 vadim <vadim@vk.crocodile.org>
* RoutingCompiler_ipt_writers.cpp (PrintRule::processNext): Fixed
security issue with temporary file handling in the generated
iptables script. The problem only affects Linux systems where
Firewall Builder is used to generate static routing
configuration. The problem exists in Firewall Builder versions
3.0.4, 3.0.5, 3.0.6
2009-09-14 vadim <vadim@vk.crocodile.org>
* standardized compiler error and warning messages using format
fw_name:ruleset_name:rule_number: warning: message
fw_name:ruleset_name:rule_number: error: message
* dialogs that show compiler output recognize error and warning
messages and highlight them using different color and bold font.
2009-09-07 vadim <vadim@vk.crocodile.org>
* single rule compile feature implemented for all
platforms (iptables, ipfilter, pf, ipfw, iosacl, pix) and
integrated with the GUI. Currently using keyboard shortcut "x".
Fixes #23.
2009-09-06 vadim <vadim@vk.crocodile.org>
* RuleSetView_single_rule_compile.cpp (RuleSetView::compileForCurrentRow):
Single rule compile implementation. Currently this is triggered by
hitting keyboard key 'x', the event is processed by RuleSetView
class which calls RuleSetView::compileForCurrentRow(). This
creates compiler driver object and calls it to compile currently
selected rule. The result is shown in the editor panel. User can
select parts or the whole of the generated script in the editor
panel but it is read-only. Works only with iptables yet. Refs #23.
* src/iptlib/iptlib.pro (SOURCES): Moved all modules for fwb_ipt
except main module ipt.cpp to a separate library so that they can
be linked with either command line compiler fwb_ipt or the
GUI. Refs #23
2009-09-05 vadim <vadim@vk.crocodile.org>
* PolicyCompiler_iosacl_writers.cpp (PrintRule::_printDstService):
fixed bug (no #): policy compiler for Cisco IOS ACL did not add
icmp type to the generated ipv6 access-list statements for rules
that matched ICMPv6 services.
2009-09-03 vadim <vadim@vk.crocodile.org>
* src/res/configlets/linux24/update_bridge: configlet that updates
bridge interfaces will now completely synchronize interfaces with
configuration created in fwbuilder even if no bridge interfaces
are used in fwbuilder. Bridge interfaces that exist on the
firewall but not in fwbuilder will be deleted and those that exist
in fwbuilder but are missing on the machine will be added. Bridge
ports are deleted and added after bridge interfaces have been
synchronized.
* src/res/configlets/linux24/update_vlans: fixed command line in
the command that removed vlan interface
2009-08-30 vadim <vadim@vk.crocodile.org>
* instDialog_ui_ops.cpp (instDialog::addToLog): fixed bug #2847263
"Batch compiling incrementally slow". The time it took to add a
log line to the progress window in the "Compile" dialog slowed
down a lot as amount of text in QTextEditor increased.
2009-08-28 vadim <vadim@vk.crocodile.org>
* ProjectPanel.cpp (ProjectPanel::event): instead of several
methods in FWWindow that scan all project panel windows and
execute some operation, using user defined events. Currently have
two events: dataModifiedEvent and updateObjectInTreeEvent. The
first one signals that some object has changed so that
ProjectPanel::event() can update timestamps and do other things.
It then posts the second event, which it will catch and process on
the next event processing run. The second event does UI updates.
Both events carry file name and object ID. Only those ProjectPanel
objects that have the same file process the event. Events are
dispatched to project panels in FWWindow::event(). Concentrating
all UI update logic in one place helps avoid unnecessary redraws.
This replaces FWWIndow::updateLastModifiedTimestampForOneFirewall,
FWWindow::updateLastModifiedTimestampForAllFirewalls,
FWWindow::reloadAllWindowsWithFile.
* interfaceProperties.cpp (interfaceProperties::manageIpAddresses):
this is a generic method that implements a policy to decide
whether generated script should manage ip addresses of a given
interface. It checks if it belongs to a cluster or a firewall and
failover protocol (if it belongs to a cluster). It fills two
lists: one is the list of addresses that the interface should have
and another is a list of interfaces the script must not remove
even if they are assigned to the interface. The method uses data
from host_os XML resource file.
2009-08-27 vadim <vadim@vk.crocodile.org>
* CompilerDriver.cpp (CompilerDriver::mergeRuleSets): See #372:
this change reverses the logic of the program when it merges rule
sets from the cluster into its member firewalls. In the original
Secunet implementation rule sets of members were ignored and only
one top level rule set from the cluster was ever used. Now we
check if member firewall has rule set of the same name as cluster
and use it if it is not empty and issue a warning. If rule set of
the member firewall with the same name is empty, rules from the
cluster are used. All rule sets of the cluster that do not match
anything in member firewalls are merged into firewalls and used
for compilation. This way, we can have multiple rule sets in the
cluster and can have slightly different rules in member firewalls
if necessary. See ticket #372 for more details and info for the
documentation.
* PolicyCompiler_ipt.cpp (PolicyCompiler_ipt::addPredefinedPolicyRules):
fixes #388: "automatic rules are added to second rule set in
cluster member". IF a cluster member firewall had several policy
rule set objects, automatic rules for conntrackd, vrrp, heartbeat
were added multiple times.
* OSConfigurator_linux24_interfaces.cpp (printInterfaceConfigurationCommands):
fixes #387: add calls to update_addresses shell function in
generated script even for interfaces with no ip addresses. This
way, if such interface has an address on the machine, it will be
removed. This helps synchronize configuration with fwbuilder when
user removes all addresses from an interface and converts it to
"unnumbered". Note that update_addresses never removes scope link
and scope host addresses of the interface even if they are not
configured in fwbuilder GUI.
* PolicyCompiler_pf.cpp (SplitDirection::processNext): applied
patch per #2844561: "PF Compiler Direction Both Duplicate for
Route Action". Need to split the rule if direction is Both
and action is Route.
* newFirewallDialog.cpp (newFirewallDialog::templateSelected):
fixed bug #2844596: "Crash during newFirewallDialog". GUI crashed
if user clicked "next" in the new firewall dialog to open page
with templates, then clicked "Back" and then "Next" again.
* ObjectManipulator.cpp (ObjectManipulator::select): fixed bug
#2845667 "Crash after find object". When host object was found
using "Find object" function while searching by ip address,
clicking on the selected host in the tree caused crash.
* VERSION (LIBFWBUILDER_SOMAJOR): started 3.0.7
2009-08-26 vadim <vadim@vk.crocodile.org>
* ObjectManipulator.cpp (ObjectManipulator::validateForPaste):
User should be able to add vlan interface to a bridge (vlan
interface becomes bridge port). Fixes #384
* CompilerDriver.cpp (CompilerDriver::populateClusterElements):
moved this method from class Compiler. fixes #367
* CompilerDriver_compile.cpp (compileSingleRule): entry point for
single rule compile. Takes one argument - rule ID and returns a
QMap<QString,QString> where key is firewall name and value is
generated script for this rule. Currently using this entry point
in the command line compilers via cli argument -s rule_id. Fully
implemented in fwb_ipt. Fixes #358, #206
* CompilerDriver_ipt_run.cpp (CompilerDriver_ipt::run): using
std::auto_ptr to protect OSConfigurator, PolicyCompiler and
NATCompiler objects and to properly delete them to avoid memory
leaks in fwb_ipt. fixes #371
2009-08-24 vadim <vadim@vk.crocodile.org>
* CompilerDriver.cpp (CompilerDriver::commonChecks2): refactored
bunch of common sense checks from compilers for ipt and pf into
common module. This also fixes #337 by checking if it is ok for
the cluster interface to have no ip address using xml resource
file for the fw host OS. Protocols such as heartbeat and openais
can operate when failover interface has no shared cluster address
because these protocls can use multicast address. However
configuration when cluster interface using one of these protocols
has shared IP is also legit. The check here only suppresses error
message when interface has no ip.
* platforms.cpp (setInterfaceTypes): Fixes #335 : if interface
name matches naming convention for vlan interfaces and vlan type
is in the list that came from the resource file, then leave only
vlan in the list we return. Note that if resource file says this
subint can not be vlan, we dan't return vlan type on the list even
if its name looks like it could be one.
* ProjectPanel.cpp (ProjectPanel::updateTreeViewItemOrder):
Removed ProjectPanel::updateTreeViewItemOrder() and removed call
to it from ObjectEditor::notifyChangesApplied(). We take care of
QT bug workaround for improper sorting in other places. This
change fixes #329.
2009-08-21 vadim <vadim@vk.crocodile.org>
* ObjectManipulator.cpp (ObjectManipulator::newInterface): If
newly created interface object is a top-level interface, always
set its type to "ethernet". If it is subinterface, call
guessInterfaceType() to guess.
* ObjectManipulator.cpp (guessInterfaceType): fixes #334. the GUI
guesses correct subinterface type when it is created and when user
hits "Apply" in the interface object dialog after some changes
have been made. If inetrface name matches one of the patterns of
the vlan inetrface for the given OS, its type is set to "vlan" and
vlan ID is assigned. If its name does not match naming pattern of
a vlan interface but parent interface type is "bridge" or
"bonding", subinterface type is set to "ethernet". This covers
most of the use cases and makes subinterface type assignment
automatic.
* ObjectManipulator.cpp (ObjectManipulator::newInterfaceAddress):
fixes #330: the name of the ip address of an interface should
follow the schema "firewall:interface:subinterface:ip". The same
schema should be followed when address object is automatically
renamed when the user renames firewall or interface object.
* ObjectManipulator.cpp (ObjectManipulator::copyObj): call
Interface::getOptionsObject() at the beginning of copy and
dragStart operations to make sure interface has options object
later in paste and drop operations when we need it to do some
validation checks.
2009-08-20 vadim <vadim@vk.crocodile.org>
* ObjectManipulator.cpp (ObjectManipulator::validateForPaste):
perform checks for the valid vlan subinterface configuration
for copy/paste and d&d drop operations; this uses the same
algorithms as the check done when user renames an interface.
This means user can not copy/paste or d&d interface "eth1.100"
to make it a subinterface of "eth0" or top-level interface.
* InterfaceDialog.cpp (InterfaceDialog::validate): Additional
checks for validity of interface name: the name can not contain
white space, if the name looks like vlan interface, checking
if it is valid (base name must match name of the parent interface
and vlan ID must be in the allowed range)
* InterfaceDialog.cpp (InterfaceDialog::applyChanges): Fixes #328:
"automatically assign vlan id to interface based on interface
name". The GUI automatically sets interface type to "vlan" and
configures vlan ID if user changes name of the interface to
something that matches regex for vlan interfaces on given OS.
This is done when user hits "Apply" button in the Interface object
dialog.
* src/compiler_lib/interfaceProperties.h (class
interfaceProperties): refactored class linux24Intrfaces into class
hierarchy with base class interfaceProperties and factory
class interfacePropertiesObjectFactory. These classes are now
part of the compiler extensions library in src/compiler_lib
and can be used by both the GUI and compilers.
* Configlet.cpp (Configlet::Configlet): New constructor for the
class Configlet accepts os name perifx and default os name prefix.
If configlet file is not found in the directory defined by the
first prefix, the program tries to find it in the default place
defined by the second prefix.
* src/res/configlets/sveasoft/script_skeleton: Using separate
configlets for Linksys/Sveasoft host os.
2009-08-19 vadim <vadim@vk.crocodile.org>
* ObjectManipulator.cpp (ObjectManipulator::newInterfaceAddress):
fixes #318: New ip address of interface was always created with
the same name even if there was an address object with the same
name under the same interface.
* OSConfigurator_linux24_interfaces.cpp (validateInterfaces):
Tests for unsupported interface configurations, see #315, 324.
The first test scans all subinterfaces of each interface and tries
to find top level inetrfaces wth the same name, then checks their
type. For the combination some_interface/br1, we look for the top
level interface "br1" and if it exists and its type is "bridge",
then this is unsupported configuration. This test does not allow
subinterface to have the same name as a bridge interface
regardless of the type of the parent interface. So, bridge/bridge
or bonding/bridge combinations are not allowed. The test has to
search top level interfaces because bridge port subinterfaces can
be copies (e.g. when a vlan interface is at the same time a bridge
port).
The second test looks for the following combinations: 1) vlan
interfaces under bridge interface (e.g. br0 = [eth1, eth2], vlan
inetrface br0.100 is not supported) and 2) vlan interfaces as
slaves of bonding interfaces (e.g. eth0.100, eth1.100, bond0
= [eth0.100, eth1.100], note the difference between this and vlan
of bonding interface such as bond0.201). Only regular interfaces
can be slaves of bonding interface. If subinterface type is
"ethernet" but its name matches one of the vlan interface regexes,
assume this is vlan. Slave subintrfaces do not have to be copies,
one can have "eth4" only once, as a slave, so we cant search for a
top level interface with the same name and rely on the
subinterface type.
2009-08-18 vadim <vadim@vk.crocodile.org>
* ObjectManipulator.cpp (ObjectManipulator::makeNameUnique): The
program should never change the name of vlan interface when such
interface is being copied/pasted or dropped to become a
subinterface. The name of the vlan interface carries vlan ID and
changing name is not allowed. One of the typical usage patterns is
to create vlan interface "eth0.101" and then immediately try to
copy/paste it to under br0 to make it bridge port. In this case
interface eth0.101 wont have type "8021q" just yet because the
user did not open interface "advanced" settings dialog to set its
type and VLAN ID. Users assume that if its name is "eth0.101",
then it must be vlan interface. We should follow this assumption
too. Also, check for names "vlanNNN" as well.
* ObjectManipulator.cpp (ObjectManipulator::actuallyPasteTo):
during "paste" operation, call makeNameUnique() to make the name
of the copy unique before actually adding the object to its
parent. Otherwise makeNameUnique() finds it and changes the name.
* src/res/configlets/ipcop/script_skeleton: Using configlet to
define script structure for generated IPCOP script. IPCOP script
is executed as /etc/rc.d/rc.firewall.local and does not manage ip
addresses of interfaces or vlan/bond/bridge interfaces so it does
not need corresponding shell functions. Script can check if
interfaces configured in fwbuilder GUI match actual appliance, so
the shell code to do that is included. Since we should be able to
use interfaces with addresses assigned dynamically in rules, the
code that gets their addresses at run time is included. Code to
check if data files used by run time address table objects exist
is also included. Using configlets helps better manage what is
included for the given os family ("linux24" or "ipcop" or some
other in the future). Also, user can override our configlets by
placing file with the same name in "fwbuilder/configlets"
directory in their $HOME.
2009-08-17 vadim <vadim@vk.crocodile.org>
* src/res/configlets/linux24/shell_functions: cleaned up coding
style in shell functions in configlets: using uniform 4 spaces
indentation.
* src/res/configlets/linux24/script_skeleton: This configlet
defines structure of generated iptables script. Script recognizes
the following command line options: start|stop|interfaces
* CompilerDriver_ipt_run.cpp (CompilerDriver_ipt::run): Building
whole iptables script from configlet.
* OSConfigurator_linux24.cpp (OSConfigurator_linux24::configureInterfaces):
See #314. Need to update vlans and bond interfaces first and only
then deal with bridges because bridge may use bonding interface or
vlan created in the first step. Unsupported configurations: vlan
interfaces under bridge interface (e.g. br0 = [eth1, eth2], vlan
inetrface br0.100 is not supported), bridge interface as part of
bonding interface (e.g. bond0 = [br0, br1]), vlan interface as a
slave of bonding interface (e.g. eth0.100, eth1.100, bond0
= [eth0.100, eth1.100]). Only regular interfaces can be slaves of
bonding interface; vlans can be created under bonding interface
(e.g. bond0.100), both regular interfaces and vlans can be bridge
ports. Script first updates bonding interfaces, then updates all
vlans, including possibly those under bonding interfaces, and
finally updates bridge configurations using interfaces created in
first two steps.
2009-08-12 vadim <vadim@vk.crocodile.org>
* NATCompiler_ipt.cpp (splitSDNATRule::processNext): fixed bug
#2836321: "SNAT rule that changes Trans Src and Trans Port does
not work". Dual translation rule that changes source address and
destination port was not supported.
2009-08-10 vadim <vadim@vk.crocodile.org>
* PolicyCompiler_pf_writers.cpp (PrintRule::processNext): For bug
#2835193: "Modulate state doesnt work for PF". Check variable
"modulate state" in rule optiopns and global firewall options. If
checkbox is turned on in the firewall options, then we always use
"modulate state". This option can also be turned on for an
individual rule using rule options dialog.
* pfAdvancedDialog.cpp (pfAdvancedDialog::pfAdvancedDialog): Fixed
bug #2835193: "Modulate state doesnt work for PF". The name Xml
attribute used to hold the value of "module state" option was
entered incorrectly in the dialog.
2009-08-09 vadim <vadim@vk.crocodile.org>
* ipfw.cpp (main): compiler for ipfw uses new manifest format
and supports remote file name for the generated .fw script
Fixes #308
* ipf.cpp (main): compiler for ipfilter uses new manifest format
and supports remote file names for generated .fw and .conf
files. Fixes #307
* CompilerDriver_pf.cpp (CompilerDriver_pf::getRemoteConfFileName):
compiler for PF uses new manifest format and supports remote file names
for generated .fw and .conf files. Fixes #306
* CompilerDriver_ipt_run.cpp (CompilerDriver_ipt::run): compiler
for iptables uses new manifest format to implement support for
alternative name of the script on the firewall. Fixes #305
2009-08-08 vadim <vadim@vk.crocodile.org>
* instDialog.cpp: Installation process is controlled by sevral
variables that the user can change in the "advanced" dialog
for the firewall platform:
Tab "Compiler":
- output file name
- script name on the firewall
- for PF and ipfilter additionally .conf file name on the firewall
Tab "Installer":
- directory on the firewall where script should be installed
- command that installer should execute on the firewall
These variables have default values if input fields are left blank
in the dialog as follows:
output file name: the name of the firewall object, plus extension
".fw". For PF two files are generated: <firewall>.fw and
<firewall>.conf; for ipfilter files <firewall>.fw, <firewall>-ipf.conf
and <firewall>-nat.conf are generated.
script name on the firewall: the same as the output file name
directory on the firewall: "/etc"
command that installer executes to activate policy: installer runs
script <firewall>.fw
If user enters alternative name in the "script name on the
firewall", it is used when generated script is copied to the
firewall. There are two input fields in the dialogs for PF and ipf
where user can enter alternative name for the .fw script and .conf
file. The name can be relative or absolute path. If it is a
relative path or just a file name, it is treated as a file name in
the directory specified by the "directory on the firewall" input
field in the "Installer" tab. If the name is an absolute path, the
directory entered in "directory on the firewall..." input field is
ignored. If user entered alternative name for the script on the
firewall, the command that installer should execute to activate it
must be entered as well. If the alternative name was entered as an
absolute path, activation command should take this into account
and use the same absolute path. The command can start with "sudo "
if user account used to copy and activate policy is not root.
* iptAdvancedDialog.cpp (iptAdvancedDialog::iptAdvancedDialog):
Added input fields to the "advanced" dialogs for iptables, pf,
ipfilter and ipfw to make it possible to specify the name of the
generated script on the firewall. With this change, fwbuilder can
generate the script using unique name but use standard common name
such as "rc.firewall" when the script is copied to the firewall
machine. This is important when two firewalls that are part of a
cluster are compiled at the same time. In this case we can not use
name such as "rc.firewall" for the output script because file
generated for the second firewall in the pair overwrites the one
generated earlier for the first. Now we can use unique names for
scripts generated for each member of the pair but copy them to the
firewall machines using the same common name. Fixes #304 The
implementation is not complete yet, I still need to make changes
in the installer and policy compilers.
2009-08-07 vadim <vadim@vk.crocodile.org>
* src/res/configlets/linux24/process_bridge: Configlets that
updated ip addresses, vlan, bridge and bonding interfaces bring
interfaces up using $IFCONFIG command. Fixes #301
2009-08-06 vadim <vadim@vk.crocodile.org>
* ObjectManipulator.cpp (ObjectManipulator::actuallyPasteTo): When
a subinterface is copied to make a subinterface of another
interface, the type of the copy is reset to "ethernet". If the
type was retained, it was easy to create subinterface with invalid
type without obvious signs in the GUI that this has happened. For
example, if vlan subinterface was copied to make subinterface of a
bridge interface, it retained type "8021q" but ended up as a child
of interface with the name that did not match. The intention was
to use vlan subinterface as a bridge port, but compiler issued an
error because of a subinterface having illegal name (name is only
checked for vlan subinterfaces). Fixes #299
* PrefsDialog.cpp: Added a page to the global Preferences dialog
where user can enable/disable target firewall platforms and host
OS. Disabled platforms and OS do not appear in the drop-down lists
in a "new firewall" and "new cluster" dialogs, as well as object
editor panel. This helps reduce clutter if user only works with a
couple of platforms and OS. Default setting of the status for each
platform and os comes from the corresponding XML resource
file. This way we can ship the program with some host OS or
platforms disabled by default, but the user can still enable them.
Settings in users preferences override default status setting
in the resource file. Fixes #262
* ObjectManipulator.cpp (ObjectManipulator::newAddressRange):
newly created objects get default name that is the same as the
type name with no "New ..." prefix.
* ObjectTreeView.cpp (ObjectTreeView::dropEvent): if user drags an
object in the tree and drops it beyond the last tree item, the
program should ignore this drop operation and do nothing (it used
to crash). Added checks for this condition. Fixes #294
* ObjectManipulator.cpp (ObjectManipulator::makeNameUnique): while
guessing the name of the new interface or trying to avoid
duplicate names during copy/paste, we should not change names of
the vlan interfaces. Fixes #296
2009-08-05 vadim <vadim@vk.crocodile.org>
* FWWindow.cpp (FWWindow::prepareToolsMenu): disable
Tools/Discover menu if all internal windows were closed and there
is no active object tree where discovered objects could be
created. Fixes #291
* ObjectManipulator.cpp (ObjectManipulator::relocateTo): Added
check for when user tries to drag&drop an object onto itself in
the tree. Fixes #292
2009-08-04 vadim <vadim@vk.crocodile.org>
* ObjectManipulator.cpp (ObjectManipulator::newInterface): when
user creates interfaces of a firewall or a cluster using context
menu "Add Interface" in the object tree, the program finds
interface that was created most recently and uses its name as a
prototype, automatically incrementing its number. For example, if
the user needs to create several "eth" interfaces, the program
will automatically create "eth0", "eth1", "eth2" etc. whithout the
need for the user to rename them. Fixes #277
* configure.in: Removed all .xml.in resource files in src/res/
src/res/os and src/res/platform. The only configurable attribute
in these was "version", which is not required and was not used
anywhere. Fixes #269
* PolicyCompiler_PrintRule.cpp (PrintRule::_printOptionalGlobalRules):
automatically added rule that matches packets in state INVALID
should use log prefix that says it is for state INVALID. The rule
now ignores user-defined global logging prefix and always uses
"INVALID state -- DENY ". Fixes #283
2009-08-04 Vadim Kurland <vadim@vk.crocodile.org>
* heartbeatOptionsDialog.cpp (heartbeatOptionsDialog::heartbeatOptionsDialog):
Added GUI elements to allow the user to change multicast address
for heartbeat. Deafault address is 224.0.10.100. Fixes #213
* clusterMembersDialog.cpp (clusterMembersDialog::firewallAdd):
enabled multiple object selection in the left panel of the cluster
member management dialog. User can select several interfaces using
Ctrl-click (or Command-Click on Mac OS X) and then move them all
to the right panel at once. Fixes #254
* ObjectEditor.cpp (ObjectEditor::notifyChangesApplied): Dialogs
that have buttons to open "advanced" settings dialogs now save
changes and disable "Apply" button when such additional dialog is
opened. This includes Firewall, Interface, cluster group and few
other objects. Previously changes were saved as well but the
"Apply" button was not disabled, making impression that changes
were not saved into the object. Fixes #286
2009-08-03 Vadim Kurland <vadim@vk.crocodile.org>
* ObjectManipulator.cpp (ObjectManipulator::autorename): See #273:
"child objects not getting renamed". Autorename function should
rename ip and mac addresses of interfaces and subinterfaces when
the host or parent interface name changes.
* newClusterDialog.cpp (newClusterDialog::finishClicked): See
#211: "interface type mismatch between member interfaces and
cluster interface". When cluster object was created manually and
failover type was set to "heartbeat" or "openais" for its
interfaces, the type was not properly set in created objects.
2009-08-02 vadim <vadim@vk.crocodile.org>
* ObjectTreeView.cpp (ObjectTreeView::dropEvent): Dragging several
subinterfaces from one parent interface to another created
bizzarre tree-like structure where each of these subinterfaces
became subinterface of another. See #280. Fixed in r1254
* PolicyCompiler_ipt.cpp (PolicyCompiler_ipt::insertConntrackRule):
Added test to make sure ip address entered by the user in the
StateSync group dialog for conntrack is valid. Fixes #220
* CompilerDriver_ipt_cluster.cpp (CompilerDriver_ipt::processStateSyncGroups):
The program did not find StateSync group member inetrfaces when
they were subinterfaces and as the result compiler did not
generate automatic policy rules for conntrack. Fixed in r1253
* ObjectManipulator.cpp (ObjectManipulator::prepareForInsertion):
DTD does not allow nested subinterfaces; only one level of
subinterfaces is supported. Interface::validateChild() now checks
for this condition and the GUI shows detailed error message dialog
when user tries to move interface that has subinterfaces under
another interface using copy/paste or d&d. Fixes #275
* ObjectManipulator.cpp (ObjectManipulator::relocateTo): When user
dragged an interface that has child objects (ip address, MAC
address) and dropped it in a different place in the object tree,
the program would show only the interface object in the new place
but not its children. Should be using insertSubtree() to fix
this. Fixes #276
2009-08-01 vadim <vadim@vk.crocodile.org>
* ProjectPanel_file_ops.cpp (ProjectPanel::chooseNewFileName): If
user forgot to add .fwb suffix to the file name they entered in
the "Save As" function, the program automatically adds it.
See #234
* CompilerDriver.cpp (CompilerDriver::commonChecks): compiler
should check that cluster member firewalls are configured to use
different output file names. See #237
* OSConfigurator_linux24::printVerifyInterfacesCommands: function
verify_interfaces uses configlet "verify_interfaces" and checks if
all interfaces of the firewall defined in the GUI really exist,
including bonding, vlan and bridge interfaces.
* OSConfigurator_linux24::printInterfaceConfigurationCommands:
Using configlet process_addresses to implement shell commands that
incrementally add and remove addresses on interfaces. Added
support for IPv6 addresses. Addresses found on the actual
interfaces of the firewall are compared with those defined in
fwbuilder objects and missing ones are added and those not defined
in fwbuilder are deleted. If a firewall is a cluster member using
heratbeat for failover, ip addresses associated with heartbeat
failover groups are skipped. The script wont delete these on the
firewall that is active at the moment when script runs and wont
add them to the passive firewall because that would interfere with
operation of heartbeat. The same is done for OpenAIS
protocol. Fixes #270 , See #261
2009-07-31 vadim <vadim@vk.crocodile.org>
* OSConfigurator_linux24_interfaces.cpp (OSConfigurator_linux24::printVlanInterfaceConfigurationCommands):
Using configlets to generate shell script that incrementally
updates (adds and removed) VLAN, bridge and bonding interfaces.
See #261
* OSConfigurator_linux24.cpp (OSConfigurator_linux24::printShellFunctions):
Using configlets to generate iptables script.
* Configlet.cpp (Configlet::Configlet): generic class to read
fragment of generated script from an external file, possibly do
macro substitution and then insert the contents into generated
script. Configlets are stored in files in the resources directory
that is part if installed package (/usr/share/fwbuilder/configlets
on Linux, fwbuilder31.app/Contents/Resources/configlets on Mac OS
X, c:\FWBuilder31\resources\configlets on Windows) or in the
subdirectory "fwbuilder/configlets" in users home directory on all
OS. If configlet file is found in the home directory, it overrides
the one installed with the package. This provides for simple way
for users to override parts of the generated configuration
scripts. Currently configlets are only impletened for Linux-based
OS. Fixes #263
2009-07-30 vadim <vadim@vk.crocodile.org>
* OSConfigurator_linux24.cpp (OSConfigurator_linux24::printShellFunctions):
fixes #259 Generated script should check if brctl, vconfig and
ifenslave tools are available before using them.
* Host.cpp (Host::getManagementAddress): the program failed to
retrieve ip address that should be used to talk to the fw when
management interface was subinterface. Fixes #260
* linux24advanceddialog_q.ui: Fixes #258 fixed tab order in the
dialog.
2009-07-29 vadim <vadim@vk.crocodile.org>
* linux24AdvancedDialog.cpp (linux24AdvancedDialog::linux24AdvancedDialog):
Added input fields for vconfig, brctl and ifenslave to the host
settings dialogs for linux24, linksys, ipcop, openwrt. See #256
* DiscoveryDruid.cpp (DiscoveryDruid::addInterface): Removed
obsolete checkbox "Add virtual addresses", we always discover
virtual addresses. Instead added checkbox "Add interfaces with no
ip addresses". If this option is turned on, discovery druid
creates interfaces with no ip addresses as "unnumbered". Even when
this option is off, interfaces with no addresses are created if
they are discovered to have vlan, bridge or bodning subinterfaces.
Fixes #246 and 229
* NetworkDialog.cpp (NetworkDialog::validate): Fixes #251: do not
allow 0 bit netmask for Network and NetworkIPv6 objects.
* linux24Interfaces.cpp (linux24Interfaces::rearrangeInterfaces):
Special treatment of the vlan subinterface that are members of
bridge group: snmp discovery now creates subinterfaces for these
vlan interfaces twice, first time as a child of the bridge
interface and then also as a vlan subinterface of the parent
physical interface. For example, in the confgiuration such as the
following
bridge name bridge id STP enabled interfaces
br0 8000.000c29f6bebe no eth4.102
eth5
We create interface br0 with subinterfaces eth4.102, eth5, and
also we create interface eth4 with subinterface eth4.102
* ObjectManipulator.cpp (ObjectManipulator::makeNameUnique):
duplicate names are automatically fixed only if objects with the
same name belong to the same parent. Identical names on different
levels are allowed. For example, interface "eth0" can be direct
child of a Firewall object (so it can have vlan subinterfaces) and
a member of the bridge group where it is a child of another
interface.
2009-07-28 vadim <vadim@vk.crocodile.org>
* NATCompiler_pf_writers.cpp (PrintRule::_printSrcPort): remove
extra white space after tcp port spec if source port match was not
used in the rule.
* PolicyCompiler_pf.cpp (fillDirection::processNext): Applied
patch per bug report #2828633: "Patch: Warning when changing rule
direction in compiler". This adds warning when rule direction is
changed by the compiler because object in source or destination
was firewall itself.
* PolicyCompiler_pf.cpp (PolicyCompiler_pf::compile): Implemented
change per bug #2828602: "PF Compiler Direction Both no
Duplication Patch". PF rules with direction "both" used to be
split to make two rules, one with direction "inbound" and another
with direction "outbound". This was an artefact of old rule
generation model where user could choose to permit everything
outbound and only generate inbound rules, or generate both inbound
and outbound rules. Since we now always generate both in abd out
rules and PF matches both directions when neither "in" or "out" is
specificed, this splitting has become redundant.
* Compiler_cluster.cpp (Compiler::populateClusterElements): while
scanning interfaces-members of a failover group, use only those
that are children of the firewall that we are compiling. fixes
#242 "fwb_ipt generates duplicate automatic rules for heartbeat
and other protocols"
* FWWindow.cpp (FWWindow::disableActions): Always enable toolbar
buttons "Compile" and "Install". Fixes #249
* FirewallDialog.cpp (FirewallDialog::validate): fixes #248
"setting firewall type as empty space crashes". Note that the
combobox with firewall platforms will have separators instead of
spaces if QT version is 4.5 or above. Separators are not
selectable so this problem can not happen with late versions of
QT. Old versions of QT do not support separators in QComboBox
widget, which is why spaces are inserted in the list. This change
makes the program validate platform and host os settings and not
allow empty strings.
* RoutingRuleOptionsDialog.cpp (RoutingRuleOptionsDialog::loadFWObject):
fixes #247 - "lusters->fw->routing->insert rule->options causes
segfault". Needed to check for Firewall and Cluster types here and
in a few other places.
* instDialog_ui_ops.cpp (instDialog::completeInstallerOptions):
fixes #244: "installer does not check subinterfaces when it is
looking for management interface"
* OSConfigurator_linux24_interfaces.cpp (OSConfigurator_linux24::printVlanInterfaceConfigurationCommands):
fixes #243 - need to set naming schema for vlan interfaces in
a separate command before creating vlan interface. Doing so in
one vconfig command causes error.
* DiscoveryDruid.cpp (DiscoveryDruid::createRealObjects):
discovery druid guesses which interfaces from the list found by
SNMP crawler are vlan subinterfaces and creates them as children
of the corresponding top level interface. It also sets interface
type and vlan ID. Fixes #239 Bonding and bridge subinterfaces
are also recognized.
* DiscoveryDruid.cpp (DiscoveryDruid::createRealObjects):
discovery druid sets firewall platform and host OS using
information from sysDescr OID. fixes #241
* linux24Interfaces.cpp (linux24Interfaces::rearrangeInterfaces):
this new class implements various algorithms used to guess which
interfaces discovered by SNMP crawler might be vlan subinterfaces.
It will also find bonding and bridge interfaces. Fixes #240
2009-07-27 vadim <vadim@vk.crocodile.org>
* clusterMembersDialog.cpp (clusterMembersDialog::createMember):
support for subinterfaces as cluster group members. Fixes #235
2009-07-26 vadim <vadim@vk.crocodile.org>
* PolicyCompiler_ipt_optimizer.cpp (optimizeForMinusIOPlus::processNext):
Better way to do optimization for "-i +", "-o +" for bug #2822098:
check for interfaceStr equal to "*" instead of re->isAny()
* CompilerDriver_ipt_run.cpp (CompilerDriver_ipt::run): check all
interfaces, including subinterfaces to make sure all the ones
marked as "regular" have IP addresses.
* DialogFactory.cpp (DialogFactory::createClusterGroupOptionsDialog):
fixed bug introduced in r1208 - clicking button "Edit protocol
settings" in the failover group with type "heartbeat" failed to
open the dialog.
* PolicyCompiler_ipt_optimizer.cpp (optimizeForMinusIOPlus::processNext):
Better way to do optimization for "-i +", "-o +" for bug #2822098:
check for interfaceStr equal to "*" instead of re->isAny()
2009-07-25 vadim <vadim@vk.crocodile.org>
* OSConfigurator_linux24_interfaces.cpp (printInterfaceConfigurationCommands):
the program did not create commands to add ip addresses to VLAN
subinterfaces. Fixes #226
* openaisOptionsDialog.cpp (openaisOptionsDialog::openaisOptionsDialog):
Added support for OpenAIS failover protocol in the GUI and
policy compiler for iptables. Fixes #214
* newFirewallDialog.cpp (newFirewallDialog::finishClicked): the
program left platform and os settings undefined of the new
firewall object created from template. Fixes #210
* PolicyCompiler_ipt.cpp (PolicyCompiler_ipt::insertFailoverRule):
Policy compiler for iptables adds automatic rules for heartbeat
protocol if it is used for failover. Rules permit all udp port 694
in and out on the given interface. Refs #213
* Cluster.cpp (Cluster::getMembersList): need to scan not only
StateSyncClusterGroup child objects but also all
FailoverClusterGroup objects in order to find all member
firewalls. The program used to look only at StateSyncClusterGroup
objects, which meant it did not recognize any members if state
sync group was empty. This fixes issue #4 in the bug #2826765:
"problems and suggestions for 3.1.0-b1187".
2009-07-24 vadim <vadim@vk.crocodile.org>
* PolicyCompiler_ipt.cpp (decideOnChainIfDstFW::processNext):
There was no rule in INPUT chain generated when cluster object was
in "destination". Fixes #215
* CompilerDriver_ipt.cpp (CompilerDriver_ipt::processPolicyRuleSet):
fixed problem #2 "duplicate rules" reported in the bug #2826765:
"problems and suggestions for 3.1.0-b1187". Compiler did not add a
call to the shell function reset_iptables_v4 to reset all chains.
* Rule.cpp (PolicyRule::getBranch): fixed problem #4 "GUI crash
when setting action to be a chain." reported in the bug #2826765:
"problems and suggestions for 3.1.0-b1187". The GUI crashed when
policy rule in the cluster policy was set to action "Chain".
2009-07-23 vadim <vadim@vk.crocodile.org>
* PolicyCompiler_ipt.cpp (PolicyCompiler_ipt::insertConntrackRule):
automatically added rules that permit conntrackd messages use
address and port configured in the protocol options for the state
sync group for the cluster, or if these are empty, default values
from the host OS xml resource file. Generated rules are configured
to go into INPUT and OUTPUT chains. Refs #212
* conntrackOptionsDialog.cpp (conntrackOptionsDialog::conntrackOptionsDialog):
make conntrackd multicast address and udp port configurable in the
protocol options dialog for conntrackd state sync protocol. Default
address and port are stored in the host OS xml resource file. Refs #212
2009-07-19 vadim <vadim@vk.crocodile.org>
* PolicyCompiler_ipt.cpp (specialCaseWithFWInDstAndOutbound::processNext):
fixed bug #2823951: "unnecessary rules in FORWARD chain". Policy
rules that have interface object in "Interface" column and
direction "Both" generate unnecessary iptables commands in the
FORWARD chain when destination matches one of the addresses that
belong to the firewall.
2009-07-18 vadim <vadim@vk.crocodile.org>
* RuleSetView.cpp (RuleSetView::moveRule): fixed bug #2823668:
"MDI window glitch". If the GUI had two or more MDI windows and
user moved rules in one of them, the GUI switched to another after
the operation was complete.
* resources.xml.in: Removed unused XML elements from the resource
file. A lot of the stuff was obsolete in there.
* ObjectTreeView.cpp (ObjectTreeView::updateTreeItems): New icons
for v4. Cleanup in the code to make sure we use proper icons
everywhere.
2009-07-17 vadim <vadim@vk.crocodile.org>
* linux24.xml.in: Moved tables of allowed failover and state sync
types as well as interface and subinterface types from the code in
platforms.cpp to the OS resource files in src/res/os/*.xml.in
Fixes #58
* fwbuilder.dtd.in (Library): fixed bug #2823424: "Deleting
UserService object breaks data file format". When user deleted
UserService object, it was moved to the "Deleted Objects" library
which broke XML file because DTD did not allow UserService element
as a child of Library
2009-07-16 vadim <vadim@vk.crocodile.org>
* newClusterDialog.cpp (newClusterDialog::shrinkListOfPlatforms):
clean-up in the newClusterDialog class. List of platforms shown on
the first page should include only platforms that support
clustering. Fixes #197
* FWBTree.cpp (systemObjects): system group "Clusters" moves to
the top level of the tree. Fixes #167
2009-07-15 vadim <vadim@vk.crocodile.org>
* PolicyCompiler_ipt_optimizer.cpp (optimizeForMinusIOPlus::processNext):
fixed bug #2822098: "IPT: adds useless "-i +" iin some cases".
Added optimization to remove redundant "-i +" and "-o +" if
chain is INPUT or OUTPUT.
2009-07-14 vadim <vadim@vk.crocodile.org>
* PolicyCompiler_ipt.cpp (singleItfNegation::processNext): fixed
bug #2819901: "sub-optimal expansion of negated interface". Policy
rules with single interface object in "interface" rule element
with negation should generate iptables commands using "-i ! itf"
or "-o ! itf" rather than multiply the rule using all other
interfaces of the firewall. Note that for iptables v1.4.3 and
later, extrapositioned syntax is used, such as "! -i itf".
* PolicyCompiler_PrintRule.cpp, NATCompiler_PrintRule.cpp: fixed
bug #2821050: "loading new fw rules on iptables 1.4.3.2+ gives
warnings". starting with v1.4.3.1 iptables started giving warnings
when negation ("!") is used after --option. This fix adds version
"1.4.3" to the list of recognized iptables versions in fwbuilder
and makes compiler generate extrapositioned version of the option
such as "! --option arg".
2009-07-13 vadim <vadim@vk.crocodile.org>
* iptAdvancedDialog.cpp (iptAdvancedDialog::iptAdvancedDialog):
fixed bug #2820840: "IPT: prolog script+iptables-restore silent
incompatibility". With this fix the GUI does not allow for the
prolog script to be placed after policy reset if iptables-restore
is used to activate iptables rules. Also policy compiler for
iptables checks for this condition and aborts with an error
message if prolog place is set to "after reset" but
iptables-restore is used to activate policy. Configuration may end
up with this combination of options if user set prolog place to
"after reset" first and switched activation method to
iptables-restore later.
* ACL.cpp (ciscoACL::addRemark): fixed bug #1778536 "IOSACL -
remark command". Remarks now include rule comments; if comment
consists of several lines, each line is added using separate
remark statement. This works for both IOS ACL and PIX platforms.
2009-07-12 vadim <vadim@vk.crocodile.org>
* printerStream.cpp (printerStream::printQTable): fix bug
#2807724: "Print out FWB still not ok". Taking into account hidden
rable rows associated with rule groups while printing rule sets.
Before this fix some rules disappeared between pages in the
printout.
2009-07-11 vadim <vadim@vk.crocodile.org>
* PrintingController.cpp (PrintingController::printRuleSet): bug
#2807724: "Print out FWB still not ok". Rule groups were always
printed expanded, even if they were collapsed by the user in the
GUI.
* OSConfigurator_openbsd.cpp (processFirewallOptions): fixed bug
#2820162 "Bad sysctl name for OpenBSD pf" - the sysctl argument
for IPv6 forwarding was incorrect.
* AddressRange.h (libfwbuilder): fixed bug #2820152: "Address
ranges and other such need IPv4/v6 typing". AddressRange object
should be recognized and removed from the rule if it is used in
ipv6 rule set. To do this, add virtual method
hasInetAddress() (should return true) to indicate that this object
has an address. This works since virtual method getAddressPtr()
has been implemented anyway.
* VERSION (VERSION): started v3.0.6
2009-07-11 vadim <vadim@vk.crocodile.org>
* FindObjectWidget.cpp (FindObjectWidget::inSelectedFirewall):
Search and replace did not work in scope "policy of opened
firewall" for cluster policies. Fixes #185
* InterfaceDialog.cpp (InterfaceDialog::loadFWObject): since
current implementation can not generate configuration commands for
interfaces of the member firewalls using attributes of the cluster
interface, disable GUI controls in the interface object dialog if
it is an interface of a cluster. fixes #187
* Summary of changes in the "interface advanced options" dialogs
for cluster interfaces. The "Advanced settings" button is now
disabled in the dialog for the main cluster interface. The code
has been changed to always check the type of the failover group
instead of the interface type where it needs to determine failover
protocol (vrrp, heartbeat or carp). All parameters of the failover
protocol should be configured using failover group object. The
"advanced options" dialog is still available for interfaces of the
real firewalls and their subinterfaces. Fixes #109, refs #180,
#183, #181, #187, #179, #163
2009-07-09 Vadim Kurland <vadim@vk.crocodile.org>
* OSConfigurator_linux24_interfaces.cpp (printInterfaceConfigurationCommands):
user can now add loopback interface to the cluster object and use
it in rules. This interface does not have failover group and has
the usual 127.0.0.1/8 ip address. fixes #163
* OSConfigurator_bsd.cpp (OSConfigurator_bsd::configureInterfaces):
ref #181: using failover group type instead of cluster interface
type.
* newClusterDialog.cpp (newClusterDialog::finishClicked): ref
#183: set type of the cluster intrfaces to "cluster_intrface".
Before, new cluster wizard unconditionally set it to "vrrp". Still
need to add dialog elements to let user choose failover protocol.
* linux24IfaceOptsDialog.cpp (linux24IfaceOptsDialog::linux24IfaceOptsDialog):
fixes #180: hide "interface type" gui element from the "advanced"
interface options dialog for the main interfaces of cluster
objects. These interfaces have no parameters and their type always
matches the type of failover cluster group object. All parameters
of the failover protocol are set in the dialog of the failover
group.
* InterfaceDialog.cpp (InterfaceDialog::loadFWObject): ref #180 :
disable "Advanced settings" button in the interface object
dialog if it is main intrface of a cluster object.
2009-06-29 Vadim Kurland <vadim@vk.crocodile.org>
* CompilerDriver_ipt_run.cpp (CompilerDriver_ipt::run): Compiler
checks types of state sync and failover groups and aborts if
it finds unsupported type. Fixes #164
* ClusterDialog.cpp (ClusterDialog::resetClusterGroupTypes): fix
types of state sync and failover groups when user changes host OS
and/or platform. Fixes #164
2009-06-28 Vadim Kurland <vadim@vk.crocodile.org>
* OSConfigurator_linux24_interfaces.cpp (printBondingInterfaceConfigurationCommands):
Support for intrface bonding for generic Linux firewall.
"Advanced" interface settings dialog provides three interface types:
"vlan", "bridge", "bonding". For bonding interfaces, GUI controls
are provided for the following parameters: mode, xmit_hash_policy
and a free-style single line input field for other driver options.
Fixes #172
* platforms.cpp (getInterfaceTypes): Support for "heartbeat"
failover protocol in clusters: "heartbeat" interface type,
"heartbeat" failover group type. Compiler adds rules to permit
vrrp only when failover type is set to "vrrp". For "heartbeat"
failover no rules are added atm. Fixes #169
* Compiler_cluster.cpp (Compiler::processFailoverGroup): (change
in libfwbuilder) fixes #166: cluster should be allowed to have
interfaces with the same name as interfaces of the member
firewall (i.e. "eth0"). This is necessary to support failover
protocols that do not create virtual interfaces, but rather
operate over normal interfaces, such as heartbeat.
2009-06-23 vadim <vadim@vk.crocodile.org>
* pfAdvancedDialog.cpp (pfAdvancedDialog::pfAdvancedDialog): force
the tab widget to open tab 0 on creation of the dialog. Often
after the dialog was modified in Designer, it is left in the state
when it opens on some random page. This fixes #155 "pf advanced
settings dialog opens on tab "Script" by default"
* OSConfigurator_bsd.h: common class for all supported BSD-like
host OS (freebsd, openbsd, macosx). Using common base class to
avoid code duplication. This fixes #162 "ifconfig commands to
create carp and pfsync interfaces are not generated for FreeBSD".
* ClusterGroupDialog.cpp (ClusterGroupDialog::addIcon): fixes #161:
pfsync protocol does not require "master" setting in cluster group.
* clusterMembersDialog.cpp (clusterMembersDialog::availableClicked):
Let user click in any column of the list except the very first to
select interface to be added to the list of cluster group members.
* clusterMembersDialog.cpp (clusterMembersDialog::updateAvailableTree):
fixes #111 "Member dialog should keep the tree on the left hand
side expanded all the time". The left hand side panel used to
collapse all available firewalls, thus hiding their interfaces
from view every time user added an interface to the right hand
side panel.
* CompilerDriver.cpp (CompilerDriver::configure): Using separator
"," between fw object id and file name instead of ':' which was a
poor choice because it is part of the file path on Windows. Fixes #157
* CompilerDriver_pf.cpp (CompilerDriver_pf::getConfFileName): Using
QT classes QFileInfo and QDir to manipulate output file names
and paths portably.
* freebsd.xml.in: Support CARP/pfsync clusters on FreeBSD.
2009-06-19 vadim <vadim@vk.crocodile.org>
* release_notes_3.1.0_en_US.html: fixes #146: A warning telling
the user that the way bridging interfaces should be configured has
changed. Uses a one-time dialog created per #145. Refs #145 #147.
* FWWindow.cpp (FWWindow::startupLoad): Fixes #145: universal
facility for a one-time dialog shown to the user on program start.
These dialogs will have important information about the
release. Dialog is shown once for each version.
2009-06-18 vadim <vadim@vk.crocodile.org>
* newFirewallDialog.cpp (newFirewallDialog::newFirewallDialog):
Fixes #90: Interface attribute "bridgeport" has been deprecated,
removing GUI controls in the new firewall dialog and interface
dialog.
* InterfaceDialog.cpp (InterfaceDialog::loadFWObject): Fixes #143:
If inetrface is a bridge port, then GUI elemnts "regular",
"dynamic" "unnumbered" should be disabled b/c it can not have an
ip address. Instead, showing text label "Bridge Port Interface".
* ObjectManipulator.cpp (ObjectManipulator::relocateTo):
Implemented drag&drop function to move objects from one place in
the tree to another. Dragging with Ctrl button pressed creates a
copy. Fixes #141.
2009-06-17 vadim <vadim@vk.crocodile.org>
* v3.0.5 released in the main production branch
2009-06-14 vadim <vadim@vk.crocodile.org>
* InterfaceDialog.cpp (InterfaceDialog::loadFWObject): Ticket #55:
(libfwbuilder) deprecated isExt() and setExt() methods. Platforms
that care about interface being external should use security
levels. Currently this is only PIX and it uses sec. levels
already. Also removed dialog element in InterfaceDialog class
and references to these methods elsewhere. Compilers did not
use the flag "ext" already.
2009-06-11 vadim <vadim@vk.crocodile.org>
* PolicyCompiler_iosacl_writers.cpp (PrintRule::_printRule):
@ -88,8 +1244,44 @@
care of the situation when group A referenced group B, which in
turn referenced group A again.
* OSConfigurator_linux24_interfaces.cpp (OSConfigurator_linux24::printBridgeInterfaceConfigurationCommands):
implemented support for bridge configuration on Linux using brctl
tool. Of bridge options only "stp on" is supported, it turns on
STP protocol support on the bridge.
2009-06-02 vadim <vadim@vk.crocodile.org>
* OSConfigurator_linux24.cpp (OSConfigurator_linux24::configureInterfaces):
implemented support for VLAN interfaces for Linux24 host os.
Generated script uses "vconfig" to create and configure vlan
interfaces. GUI provides elements for VLAN ID and VLAN interface
name type (VLAN_PLUS_VID (vlan0005), VLAN_PLUS_VID_NO_PAD (vlan5),
DEV_PLUS_VID (eth0.0005), DEV_PLUS_VID_NO_PAD (eth0.5). Compiler
verifies that the name of the vlan interface object matches
requested name type.
2009-06-01 vadim <vadim@vk.crocodile.org>
* OSConfigurator_openbsd.cpp (OSConfigurator_openbsd::configureInterfaces):
implemented support for pfsync interface configuration for
OpenBSD. Unicast communication method can be configured using
checkbox in the pfsync protocol options dialog. Compiler generates
ifconfig commands to configure pfsync virtual interfaces if
checkbox "Configure pfsync interfaces" is turned on in the pf
"advanced" settings dialog. Only one pfsync interface per firewall
is supported (pfsync0), only with IPv4 addresses.
* OSConfigurator_openbsd.cpp (OSConfigurator_openbsd::configureInterfaces):
implemented support for CARP interface configuration for OpenBSD.
Generated script uses ifconfig to create and configure carpN
interfaces. The script is added only if option "Configure CARP
interfaces" is turned on in the "advanced" settings dialog for PF.
Currently only IPv4 addresses are supported and only one address
per CARP interface is configured. CARP password and VHID are
defined in the failover protocol settings dialog that user can open
by clicking "Protocol parameters" button in the Failover group
object dialog.
* newHostDialog.cpp (newHostDialog::selectedInterface): fixed the
same error reported in bug #2799163: "crash on correcting an
error". The GUI crashed if user tried to add, then delete
@ -127,6 +1319,11 @@
running copies. Copy/Paste and Drag&Drop between separate copies
are not supported at this time.
2009-05-30 vadim <vadim@vk.crocodile.org>
* CompilerDriver_pf_run.cpp (CompilerDriver_pf::run): ref #22:
compiler for PF uses CompilerDriver class.
2009-05-29 vadim <vadim@vk.crocodile.org>
* newFirewallDialog.cpp (newFirewallDialog::finishClicked): better
@ -260,16 +1457,80 @@
support for Secuwall and is easier to maintain than separate
platform-os pairs for each appliance.
2009-05-08 vadim <vadim@vk.crocodile.org>
* clusterMembersDialog.h (class clusterMembersDialog): Renamed
class and module secuwallClusterConfDialog to
clusterMembersDialog. This dialog is generic and is not specific
to secunet wall in any way. This fixes #13.
* PolicyCompiler_ipt.cpp (removeFW::processNext): fixes #15: using
Compiler::isFirewallOrCluster to match object in rules to both
firewall or it parent cluster. This helps compiler idenitify
cluster in rules and choose correct chains (INPUT/OUTPUT) as if
firewall object was there.
* CompilerDriver.cpp (CompilerDriver::determineOutputFileName):
this method implements logic that extracts enforced output file
names from command line parameters of the compiler or determines
these names automatically.
* instDialog_compile.cpp (instDialog::prepareArgForCompiler):
While compiling firewall cluster, passing output file name to the
compiler using "-O" command line option. The old option "-o" is
preserved for backwards compatibility and is used while compiling
stand-alone firewall objects.
2009-05-07 vadim <vadim@vk.crocodile.org>
* instDialog_ui_ops.cpp (instDialog::createTreeItem): dialog that
lists firewalls and clusters for compilation and installation puts
checkbox for compile next to a cluster and checkbox for install
next to a real firewall. Checkboxes are pre-checked if
corresponding objects require compilation and installtion. Mutual
dependencies between cluster and its members are tracked. this
fixes #19
* ipt.cpp (main): Policy compiler for iptables accepts either
Firewall or Cluster object as an argument. If Cluster is
specified, compiler runs itself several times, generating script
for each member firewall. Object can be defined by its name or ID
as before. This fixes #18.
* CompilerDriver.h (class CompilerDriver): Introduced class
CompilerDriver that controls invocation of Policy, Mangle, NAT and
Routing compilers for one firewall. The firewall may be part of a
cluster, in which case we create several objects of this class and
process each member firewall separately.
* PolicyCompiler_secuwall.cpp (PolicyCompiler_secuwall::addMgmtRule):
fixes #16: using RuleSet::insertRuleAtTop with arg hidden_rule to
make automatic rules added for secunet wall "hidden". This way,
these rules are ignored during shadowing detection and their
position numbers are forced negative so that position numbers of
regular rules do not change.
2009-05-06 vadim <vadim@vk.crocodile.org>
* FirewallInstallerCisco.cpp (FirewallInstallerCisco::activatePolicy):
fixed bug #2787932 "External install script is not supported for
PIX".
* fixed bug #2787857: "b847 crashes on Start". v3.0.5 build 847
links with QtDBus framework as part of the future development but
the framework file was not included in the bundle. This caused
crash on Mac OS X.
2009-05-04 vadim <vadim@vk.crocodile.org>
* instDialog_ui_ops.cpp (instDialog::fillCompileSelectList):
dialog that shows list of firewalls for compilation and
installation now uses QTreeWidget and displays firewall clusters
and corresponding member firewalls as branches in the tree. The
rest of the functionality remains the same as before. If user
selected a cluster object in the object tree and clicked "Compile"
in its context menu, only member firewalls of this clusters are
going to be checked for compilation. Clicking "Compile" toolbar
button or main menu selects all firewalls for compilation as
before. Cluster objects can not be selected (do not have
checkboxes in the widget) because compiler and installer works
with actual firewall objects rather than cluster objects. This
fixes ticket #7.
2009-05-02 vadim <vadim@vk.crocodile.org>
@ -312,6 +1573,16 @@
group". The GUI crashed if user clicked and dragged mouse inside
empty list of group members in the dialog of the new group object.
2009-04-17 vadim <vadim@vk.crocodile.org>
* ClusterDialog.cpp (ClusterDialog::ClusterDialog): Support for
clusters of firewalls
* Merging patches from Secunet Security Networks AG to add support
for Secuwall firewall.
* VERSION: start v3.1.0 branch v3_1_secunet
2009-04-15 vadim <vadim@vk.crocodile.org>
* ipcopAdvancedDialog.cpp (ipcopAdvancedDialog::ipcopAdvancedDialog):

196
doc/README.cluster Normal file
View File

@ -0,0 +1,196 @@
Firewall Builder Clustering Add-On
==================================
Copyright (c) 2009 secunet Security Networks AG, Germany
Copyright (c) 2009 Adrian-Ken Rueegsegger <rueegsegger@swiss-it.ch>
Copyright (c) 2009 Reto Buerki <buerki@swiss-it.ch>
Index
-----
1 - Introduction
2 - Definition
3 - Usage
4 - Example
5 - Things to consider
6 - References
Introduction
------------
The Firewall Builder Clustering Add-On provides the possibility to manage
multiple firewall objects together as one Cluster object. Cluster objects are
used to configure HA (High Availability) features like conntrack [1] and VRRP [2]
(Virtual Router Redundancy Protocol).
Definition
----------
In the context of this Add-On a 'cluster' object is regarded as a meta-object
grouping multiple firewall objects. This allows for a much simpler and convenient
configuration of a HA scenario. The configuration is done once for the meta-object
'Cluster' and automatically compiled and distributed for each cluster member firewall.
[cluster] (meta-object)
|
|
+-----------------+-----------------+
| | |
[fw1] (object) [fw2] (object) [fwX] (object)
Usage
-----
To use the clustering feature, you need to create firewalls which will be part
of a HA cluster and create the cluster itself. The following two sections
describe the necessary steps.
Firewall configuration
~~~~~~~~~~~~~~~~~~~~~~
Make sure that all firewalls of a cluster use the same host OS and platform. The
host OS and platform of all cluster member firewalls must match the one
specified for the cluster itself.
The following diagram defines two firewalls configured appropriately as cluster
members:
[fw1] [OS: secunet wall, Platform: iptables]
|
+---o eth0: outside (ext)
| +---o IP: 172.24.0.2/255.255.0.0
|
+---o eth1: inside
+---o IP: 192.168.1.2/255.255.255.0
[fw2] [OS: secunet wall, Platform: iptables]
|
+---o eth0: outside (ext)
| +---o IP: 172.24.0.3/255.255.0.0
|
+---o eth1: inside
+---o IP: 192.168.1.3/255.255.255.0
Both firewalls have an outside and an inside interface. In a cluster scenario,
these interfaces will be combined to a redundant VRRP cluster interface.
VRRP requires all interfaces joined to a VRRP group to be in the same subnet,
with unique IP addresses.
Cluster configuration
~~~~~~~~~~~~~~~~~~~~~
Now it's time to create a Cluster object which will act as meta-object for fw1
and fw2:
[cluster1] [OS: secunet wall, Platform: iptables]
|
+---o vrrp0: outside (ext)
| +---o IP: 172.24.0.1/255.255.0.0
| +---o Failover group0 (vrrp)
|
+---o vrrp1: inside (mgmt)
| +---o IP: 192.168.1.1/255.255.255.0
| +---o Failover group1 (vrrp)
|
+---o State synchronization group (conntrack)
Use the 'Manage Members' button to add firewall interfaces to the failover and
state synchronization groups of the cluster. Additionally you need to specify
which firewall interface is to act as master of the group.
The firewall interfaces added to the state synchronization group will be used to
keep the state information of the cluster members in sync. Typically the
internal management interfaces are chosen as members of the conntrack group.
For all cluster groups the IP addresses of it's firewall member interfaces have
to be in the same subnet and the subnet mask must be identical to the one of the
cluster interface.
The following table shows the mapping of interfaces to cluster groups for our
example configuration:
+-----------------+--------------------+
| group | mapped interfaces |
+-----------------+--------------------+
| State sync | fw1:eth1, fw2:eth1 |
| Failover group0 | fw1:eth0, fw2:eth0 |
| Failover group1 | fw1:eth1, fw2:eth1 |
+-----------------+--------------------+
NAT/Policy/Routing Rules
~~~~~~~~~~~~~~~~~~~~~~~~
NAT, policy and routing rules are configured on the cluster meta-object. Rules
are specified in the usual manner. Use the cluster object or it's interfaces as
rule elements as you would for a regular firewall.
NOTE: Rules defined on cluster member firewalls will be ignored on compilation,
only the rules defined on the cluster object are considered.
Compilation/Installation/Export
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
It's possible to compile, install and export firewalls which are part of a
cluster the usual way by selecting a single firewall and the corresponding
action (Compile/Install/Export).
If you perform such an action on the cluster meta-object, all member firewalls
will be selected automatically. Thus the cluster object provides a convenient
way to perform actions on all cluster member firewalls.
Cluster template
~~~~~~~~~~~~~~~~
This Add-On includes Cluster templates which can be used as starting point for
complex cluster configurations. Enable the 'Use preconfigured template cluster
object' checkbox when creating a new cluster object to use these templates.
Example
-------
The scenario described in this README can be found as example Firewall Builder
file here [3].
Things to consider
------------------
* Host OS and platform of firewall members must match OS and platform of the
cluster.
* Cluster member firewalls must have at least one physical interface attached.
* Rules must be configured on the Cluster meta-object. Rules for cluster member
firewalls are ignored.
* All IP addresses of interfaces added to a cluster group must be in the same
subnet.
* All addresses of a cluster group must be unique.
* Cluster interface names must be unique per cluster.
References
----------
[1] - http://conntrack-tools.netfilter.org/
[2] - RFC3768 - Virtual Router Redundancy Protocol (VRRP)
[3] - doc/cluster_examples.fwb

266
doc/cluster_examples.fwb Normal file
View File

@ -0,0 +1,266 @@
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE FWObjectDatabase SYSTEM "fwbuilder.dtd">
<FWObjectDatabase xmlns="http://www.fwbuilder.org/1.0/" version="12" lastModified="1244032500" id="root">
<Library id="sysid99" name="Deleted Objects" comment="" ro="False"/>
<Library id="id1495X26217" color="#d2ffd0" name="User" comment="" ro="False">
<ObjectGroup id="id1502X26217" name="Clusters" comment="" ro="False">
<Cluster id="id2835X30406" host_OS="secuwall" inactive="False" lastCompiled="1244034211" lastInstalled="0" lastModified="1244034079" platform="iptables" name="cluster1" comment="This cluster has two interfaces. vrrp0 faces outside; vrrp1 faces inside. Policy includes basic rules to permit unrestricted outbound access and anti-spoofing rules. The firewall uses one of the machines on the external network for DNS. Internal network is configured with address 192.168.1.0/255.255.255.0, external network with 172.24.0.0/255.255.0.0. Outside vrrp0 cluster interface has address 172.24.0.1/255.255.0.0; inside vrrp1 interface has address 192.168.1.1/255.255.255.0. This cluster has two firewall members configured: fw1 and fw2." ro="False">
<NAT id="id2839X30406" name="NAT" comment="" ro="False" ipv4_rule_set="False" ipv6_rule_set="False" top_rule_set="True"/>
<Policy id="id2838X30406" name="Policy" comment="" ro="False" ipv4_rule_set="False" ipv6_rule_set="False" top_rule_set="True">
<PolicyRule id="id7725X31743" disabled="False" group="" log="True" position="0" action="Deny" direction="Inbound" comment="anti spoofing rule">
<Src neg="False">
<ObjectRef ref="id3DC75CE7-1"/>
<ObjectRef ref="id2835X30406"/>
</Src>
<Dst neg="False">
<ObjectRef ref="sysid0"/>
</Dst>
<Srv neg="False">
<ServiceRef ref="sysid1"/>
</Srv>
<Itf neg="False">
<ObjectRef ref="id2843X30406"/>
</Itf>
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions/>
</PolicyRule>
<PolicyRule id="id4654X31417" disabled="False" group="" log="False" position="1" action="Accept" direction="Both" comment="">
<Src neg="False">
<ObjectRef ref="id3DC75CE7-1"/>
</Src>
<Dst neg="False">
<ObjectRef ref="sysid0"/>
</Dst>
<Srv neg="False">
<ServiceRef ref="sysid1"/>
</Srv>
<Itf neg="False">
<ObjectRef ref="sysid0"/>
</Itf>
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions/>
</PolicyRule>
<PolicyRule id="id4482X31743" disabled="False" group="" log="True" position="2" action="Accept" direction="Both" comment="firewall uses one of the machines on external network for DNS">
<Src neg="False">
<ObjectRef ref="id2835X30406"/>
</Src>
<Dst neg="True">
<ObjectRef ref="id3DC75CE7-1"/>
</Dst>
<Srv neg="False">
<ServiceRef ref="id3F530CC8"/>
</Srv>
<Itf neg="False">
<ObjectRef ref="id2843X30406"/>
</Itf>
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions>
<Option name="stateless">False</Option>
</PolicyRuleOptions>
</PolicyRule>
<PolicyRule id="id4386X31417" disabled="False" log="True" position="3" action="Deny" direction="Both" comment="">
<Src neg="False">
<ObjectRef ref="sysid0"/>
</Src>
<Dst neg="False">
<ObjectRef ref="sysid0"/>
</Dst>
<Srv neg="False">
<ServiceRef ref="sysid1"/>
</Srv>
<Itf neg="False">
<ObjectRef ref="sysid0"/>
</Itf>
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions>
<Option name="stateless">True</Option>
</PolicyRuleOptions>
</PolicyRule>
</Policy>
<Routing id="id2840X30406" name="Routing" comment="" ro="False" ipv4_rule_set="False" ipv6_rule_set="False" top_rule_set="True"/>
<Interface id="id2843X30406" dyn="False" label="outside" security_level="0" unnum="False" unprotected="False" name="vrrp0" comment="" ro="False">
<IPv4 id="id2844X30406" name="cluster1:vrrp0:ip" comment="" ro="False" address="172.24.0.1" netmask="255.255.0.0"/>
<InterfaceOptions>
<Option name="iface_mtu">1500</Option>
<Option name="type">vrrp</Option>
</InterfaceOptions>
<FailoverClusterGroup id="id2846X30406" master_iface="id1522X26217" type="vrrp" name="cluster1:vrrp0:members" comment="">
<ObjectRef ref="id1522X26217"/>
<ObjectRef ref="id2830X30406"/>
<ClusterGroupOptions>
<Option name="vrrp_secret">my_secret</Option>
<Option name="vrrp_vrid">1</Option>
</ClusterGroupOptions>
</FailoverClusterGroup>
</Interface>
<Interface id="id2848X30406" dyn="False" label="inside" security_level="0" unnum="False" unprotected="False" name="vrrp1" comment="" ro="False">
<IPv4 id="id2849X30406" name="cluster1:vrrp1:ip" comment="" ro="False" address="192.168.1.1" netmask="255.255.255.0"/>
<InterfaceOptions>
<Option name="iface_mtu">1500</Option>
<Option name="type">vrrp</Option>
</InterfaceOptions>
<FailoverClusterGroup id="id2851X30406" master_iface="id1524X26217" type="vrrp" name="cluster1:vrrp1:members" comment="">
<ObjectRef ref="id1524X26217"/>
<ObjectRef ref="id2832X30406"/>
<ClusterGroupOptions>
<Option name="vrrp_secret">my_secret</Option>
<Option name="vrrp_vrid">2</Option>
</ClusterGroupOptions>
</FailoverClusterGroup>
</Interface>
<FirewallOptions/>
<StateSyncClusterGroup id="id2841X30406" master_iface="id1524X26217" type="conntrack" name="State Sync Group" comment="">
<ObjectRef ref="id1524X26217"/>
<ObjectRef ref="id2832X30406"/>
<ClusterGroupOptions/>
</StateSyncClusterGroup>
</Cluster>
</ObjectGroup>
<ObjectGroup id="id1496X26217" name="Objects" comment="" ro="False">
<ObjectGroup id="id1497X26217" name="Addresses" comment="" ro="False"/>
<ObjectGroup id="id1498X26217" name="DNS Names" comment="" ro="False"/>
<ObjectGroup id="id1499X26217" name="Address Tables" comment="" ro="False"/>
<ObjectGroup id="id1500X26217" name="Groups" comment="" ro="False"/>
<ObjectGroup id="id1501X26217" name="Hosts" comment="" ro="False"/>
<ObjectGroup id="id1503X26217" name="Networks" comment="" ro="False"/>
<ObjectGroup id="id1504X26217" name="Address Ranges" comment="" ro="False"/>
</ObjectGroup>
<ServiceGroup id="id1505X26217" name="Services" comment="" ro="False">
<ServiceGroup id="id1506X26217" name="Groups" comment="" ro="False"/>
<ServiceGroup id="id1507X26217" name="ICMP" comment="" ro="False"/>
<ServiceGroup id="id1508X26217" name="IP" comment="" ro="False"/>
<ServiceGroup id="id1509X26217" name="TCP" comment="" ro="False"/>
<ServiceGroup id="id1510X26217" name="UDP" comment="" ro="False"/>
<ServiceGroup id="id1511X26217" name="Users" comment="" ro="False"/>
<ServiceGroup id="id1512X26217" name="Custom" comment="" ro="False"/>
<ServiceGroup id="id1513X26217" name="TagServices" comment="" ro="False"/>
</ServiceGroup>
<ObjectGroup id="id1514X26217" name="Firewalls" comment="" ro="False">
<Firewall id="id1516X26217" host_OS="secuwall" inactive="False" lastCompiled="0" lastInstalled="0" lastModified="1244032311" platform="iptables" version="" name="fw1" comment="This firewall has two interfaces. eth0 faces outside and has a static address of 172.24.0.2/255.255.0.0; eth1 faces inside with an address of 192.168.1.2/255.255.255.0. This firewall is a member of cluster 'cluster1'." ro="False">
<NAT id="id1520X26217" name="NAT" comment="" ro="False" ipv4_rule_set="False" ipv6_rule_set="False" top_rule_set="True"/>
<Policy id="id1519X26217" name="Policy" comment="" ro="False" ipv4_rule_set="False" ipv6_rule_set="False" top_rule_set="True"/>
<Routing id="id1521X26217" name="Routing" comment="" ro="False" ipv4_rule_set="False" ipv6_rule_set="False" top_rule_set="True"/>
<Interface id="id1522X26217" dyn="False" label="outside" security_level="0" unnum="False" unprotected="False" name="eth0" comment="" ro="False">
<IPv4 id="id1523X26217" name="fw1:eth0:ip" comment="" ro="False" address="172.24.0.2" netmask="255.255.0.0"/>
<InterfaceOptions>
<Option name="iface_mtu">1500</Option>
<Option name="iface_type">ethernet</Option>
</InterfaceOptions>
</Interface>
<Interface id="id1524X26217" dyn="False" label="inside" security_level="100" unnum="False" unprotected="False" name="eth1" comment="" ro="False">
<IPv4 id="id1525X26217" name="fw1:eth1:ip" comment="" ro="False" address="192.168.1.2" netmask="255.255.255.0"/>
<InterfaceOptions>
<Option name="iface_mtu">1500</Option>
<Option name="iface_type">ethernet</Option>
</InterfaceOptions>
</Interface>
<Management address="0.0.0.0">
<SNMPManagement enabled="False" snmp_read_community="" snmp_write_community=""/>
<FWBDManagement enabled="False" identity="" port="-1"/>
<PolicyInstallScript arguments="" command="" enabled="False"/>
</Management>
<FirewallOptions>
<Option name="accept_established">true</Option>
<Option name="accept_new_tcp_with_no_syn">true</Option>
<Option name="check_shading">true</Option>
<Option name="configure_interfaces">true</Option>
<Option name="firewall_is_part_of_any_and_networks">true</Option>
<Option name="flush_and_set_default_policy">True</Option>
<Option name="limit_value">0</Option>
<Option name="linux24_ip_forward">1</Option>
<Option name="load_modules">true</Option>
<Option name="local_nat">false</Option>
<Option name="log_level">info</Option>
<Option name="log_prefix">RULE %N -- %A </Option>
<Option name="loopback_interface">lo</Option>
<Option name="manage_virtual_addr">true</Option>
<Option name="modules_dir">/lib/modules/`uname -r`/kernel/net/</Option>
<Option name="secuwall_add_files">False</Option>
<Option name="secuwall_add_files_dir">/opt/secuwall/templates/default</Option>
<Option name="secuwall_dns_reso1">files</Option>
<Option name="ulog_nlgroup">1</Option>
<Option name="verify_interfaces">true</Option>
</FirewallOptions>
</Firewall>
<Firewall id="id2824X30406" host_OS="secuwall" inactive="False" lastCompiled="0" lastInstalled="0" lastModified="1244032419" platform="iptables" version="" name="fw2" comment="This firewall has two interfaces. eth0 faces outside and has a static address of 172.24.0.3/255.255.0.0; eth1 faces inside with an address of 192.168.1.3/255.255.255.0. This firewall is a member of cluster 'cluster1'." ro="False">
<NAT id="id2828X30406" name="NAT" comment="" ro="False" ipv4_rule_set="False" ipv6_rule_set="False" top_rule_set="True"/>
<Policy id="id2827X30406" name="Policy" comment="" ro="False" ipv4_rule_set="False" ipv6_rule_set="False" top_rule_set="True"/>
<Routing id="id2829X30406" name="Routing" comment="" ro="False" ipv4_rule_set="False" ipv6_rule_set="False" top_rule_set="True"/>
<Interface id="id2830X30406" dyn="False" label="outside" security_level="0" unnum="False" unprotected="False" name="eth0" comment="" ro="False">
<IPv4 id="id2831X30406" name="fw2:eth0:ip" comment="" ro="False" address="172.24.0.3" netmask="255.255.0.0"/>
<InterfaceOptions>
<Option name="iface_mtu">1500</Option>
<Option name="iface_type">ethernet</Option>
</InterfaceOptions>
</Interface>
<Interface id="id2832X30406" dyn="False" label="inside" security_level="100" unnum="False" unprotected="False" name="eth1" comment="" ro="False">
<IPv4 id="id2833X30406" name="fw2:eth1:ip" comment="" ro="False" address="192.168.1.3" netmask="255.255.255.0"/>
<InterfaceOptions>
<Option name="iface_mtu">1500</Option>
<Option name="iface_type">ethernet</Option>
</InterfaceOptions>
</Interface>
<Management address="0.0.0.0">
<SNMPManagement enabled="False" snmp_read_community="" snmp_write_community=""/>
<FWBDManagement enabled="False" identity="" port="-1"/>
<PolicyInstallScript arguments="" command="" enabled="False"/>
</Management>
<FirewallOptions>
<Option name="accept_established">true</Option>
<Option name="accept_new_tcp_with_no_syn">true</Option>
<Option name="check_shading">true</Option>
<Option name="configure_interfaces">true</Option>
<Option name="firewall_is_part_of_any_and_networks">true</Option>
<Option name="flush_and_set_default_policy">True</Option>
<Option name="limit_value">0</Option>
<Option name="linux24_ip_forward">1</Option>
<Option name="load_modules">true</Option>
<Option name="local_nat">false</Option>
<Option name="log_level">info</Option>
<Option name="log_prefix">RULE %N -- %A </Option>
<Option name="loopback_interface">lo</Option>
<Option name="manage_virtual_addr">true</Option>
<Option name="modules_dir">/lib/modules/`uname -r`/kernel/net/</Option>
<Option name="secuwall_add_files">False</Option>
<Option name="secuwall_add_files_dir">/opt/secuwall/templates/default</Option>
<Option name="secuwall_dns_reso1">files</Option>
<Option name="ulog_nlgroup">1</Option>
<Option name="verify_interfaces">true</Option>
</FirewallOptions>
</Firewall>
</ObjectGroup>
<IntervalGroup id="id1515X26217" name="Time" comment="" ro="False"/>
</Library>
<Library id="syslib000" color="#d4f8ff" name="Standard" comment="Standard objects" ro="True">
<ObjectGroup id="stdid01" name="Objects" comment="" ro="False">
<ObjectGroup id="stdid03" name="Networks" comment="" ro="False">
<Network id="id3DC75CE7-1" name="net-192.168.1.0" comment="192.168.1.0/24 - Address often used for home and small office networks.&#10;" ro="False" address="192.168.1.0" netmask="255.255.255.0"/>
</ObjectGroup>
</ObjectGroup>
<AnyNetwork id="sysid0" name="Any" comment="Any Network" ro="False" address="0.0.0.0" netmask="0.0.0.0"/>
<AnyIPService id="sysid1" protocol_num="0" name="Any" comment="Any IP Service" ro="False"/>
<AnyInterval id="sysid2" days_of_week="0,1,2,3,4,5,6" from_day="-1" from_hour="-1" from_minute="-1" from_month="-1" from_weekday="-1" from_year="-1" to_day="-1" to_hour="-1" to_minute="-1" to_month="-1" to_weekday="-1" to_year="-1" name="Any" comment="Any Interval" ro="False"/>
<ServiceGroup id="stdid05" name="Services" comment="" ro="False">
<ServiceGroup id="stdid10" name="Groups" comment="" ro="False">
<ServiceGroup id="id3F530CC8" name="DNS" comment="" ro="False">
<ServiceRef ref="udp-DNS"/>
<ServiceRef ref="tcp-DNS"/>
</ServiceGroup>
</ServiceGroup>
<ServiceGroup id="stdid08" name="UDP" comment="" ro="False">
<UDPService id="udp-DNS" name="domain" comment="" ro="False" src_range_start="0" src_range_end="0" dst_range_start="53" dst_range_end="53"/>
</ServiceGroup>
<ServiceGroup id="stdid09" name="TCP" comment="" ro="False">
<TCPService id="tcp-DNS" ack_flag="False" ack_flag_mask="False" fin_flag="False" fin_flag_mask="False" psh_flag="False" psh_flag_mask="False" rst_flag="False" rst_flag_mask="False" syn_flag="False" syn_flag_mask="False" urg_flag="False" urg_flag_mask="False" name="domain" comment="" ro="False" src_range_start="0" src_range_end="0" dst_range_start="53" dst_range_end="53"/>
</ServiceGroup>
</ServiceGroup>
</Library>
</FWObjectDatabase>

View File

@ -48,6 +48,7 @@ man.files = fwbedit.1 \
fwb_ipt.1 \
fwb_pf.1 \
fwb_pix.1 \
export_secuwall.1 \
# fwb_install.1 \
# fwb_compile_all.1 \

View File

@ -1,446 +1,1406 @@
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE FWObjectDatabase SYSTEM "fwbuilder.dtd">
<FWObjectDatabase xmlns="http://www.fwbuilder.org/1.0/" version="2.1.5" lastModified="1150430669" id="root">
<FWObjectDatabase xmlns="http://www.fwbuilder.org/1.0/" version="11" id="root">
<Library color="#d2ffd0" id="id449356F828075" name="User">
<ObjectGroup id="id449356F928075" name="Objects">
<ObjectGroup id="id449356FA28075" name="Addresses"/>
<ObjectGroup id="id449356FB28075" name="DNS Names"/>
<ObjectGroup id="id449356FC28075" name="Address Tables"/>
<ObjectGroup id="id449356FD28075" name="Groups"/>
<ObjectGroup id="id449356FE28075" name="Hosts">
<ObjectGroup id="id449356F928075_clusters" name="Clusters"/>
<ObjectGroup id="id449356FA28075" name="Addresses"/><ObjectGroup id="id449356FB28075" name="DNS Names"/><ObjectGroup id="id449356FC28075" name="Address Tables"/><ObjectGroup id="id449356FD28075" name="Groups"/><ObjectGroup id="id449356FE28075" name="Hosts">
<Host comment="This object represents a PC with a single network interface" id="id44935FEF28075" name="server">
<Interface bridgeport="False" dyn="False" id="id44935FF128075" label="" name="eth0" security_level="0" unnum="False">
<IPv4 address="192.168.1.1" comment="" id="id44935FF228075" name="server:eth0:ip" netmask="255.255.255.0"/>
</Interface>
<Management address="0.0.0.0">
<SNMPManagement enabled="False" snmp_read_community="" snmp_write_community=""/>
<FWBDManagement enabled="False" identity="" port="-1"/>
<PolicyInstallScript arguments="" command="" enabled="False"/>
</Management>
<HostOptions>
<Option name="use_mac_addr_filter">False</Option>
</HostOptions>
</Host>
</ObjectGroup><ObjectGroup id="id449356FF28075" name="Networks"/><ObjectGroup id="id4493570028075" name="Address Ranges"/>
</ObjectGroup>
<ObjectGroup id="id449356FF28075" name="Networks"/>
<ObjectGroup id="id4493570028075" name="Address Ranges"/>
</ObjectGroup>
<ServiceGroup id="id4493570128075" name="Services">
<ServiceGroup id="id4493570228075" name="Groups"/>
<ServiceGroup id="id4493570328075" name="ICMP"/>
<ServiceGroup id="id4493570428075" name="IP"/>
<ServiceGroup id="id4493570528075" name="TCP"/>
<ServiceGroup id="id4493570628075" name="UDP"/>
<ServiceGroup id="id4493570728075" name="Custom"/>
<ServiceGroup id="id4493570128075_userservices" name="Users"/>
<ServiceGroup id="id4493570228075" name="Groups"/>
<ServiceGroup id="id4493570328075" name="ICMP"/>
<ServiceGroup id="id4493570428075" name="IP"/>
<ServiceGroup id="id4493570528075" name="TCP"/>
<ServiceGroup id="id4493570628075" name="UDP"/>
<ServiceGroup id="id4493570728075" name="Custom"/>
<ServiceGroup id="id4493570828075" name="TagServices">
<TagService comment="" id="id44935FFA28075" name="tag-isp1" tagcode="1"/>
<TagService comment="" id="id44935FFB28075" name="tag-isp2" ro="False" tagcode="2"/>
<TagService comment="" id="id44935FFB28075" name="tag-isp2" ro="False" tagcode="2"/>
</ServiceGroup>
</ServiceGroup>
</ServiceGroup>
<ObjectGroup id="id4493570928075" name="Firewalls">
<Firewall comment="this firewall demonstrates technique for the redundant Internet connection through two different ISPs. Firewall provides outgoing access for hosts on internal network through ISP1 and allows access to a server on internal net using NAT through IP addresses provided by both ISPs." host_OS="linux24" id="id44935AA428075" inactive="False" lastCompiled="1150429960" lastInstalled="0" lastModified="1150430669" name="example1" platform="iptables" ro="False" version="">
<NAT id="id44935B3E28075">
<NAT top_rule_set="True" id="id44935B3E28075" name="NAT">
<NATRule comment="Translate source address&#10;for outgoing connections" disabled="False" id="id44935B4D28075" position="0">
<OSrc neg="False">
<ObjectRef ref="id3DC75CE7-1"/>
</OSrc>
<ODst neg="False">
<ObjectRef ref="sysid0"/>
</ODst>
<OSrv neg="False">
<ServiceRef ref="sysid1"/>
</OSrv>
<TSrc neg="False">
<ObjectRef ref="id44935B6E28075"/>
</TSrc>
<TDst neg="False">
<ObjectRef ref="sysid0"/>
</TDst>
<TSrv neg="False">
<ServiceRef ref="sysid1"/>
</TSrv>
<NATRuleOptions/>
</NATRule>
<NATRule disabled="False" id="id44935B5C28075" position="1">
<NATRule disabled="False" id="id44935B5C28075" position="1">
<OSrc neg="False">
<ObjectRef ref="sysid0"/>
</OSrc>
<ODst neg="False">
<ObjectRef ref="id44935B7428075"/>
</ODst>
<OSrv neg="False">
<ServiceRef ref="tcp-HTTP"/>
<ServiceRef ref="tcp-SMTP"/>
</OSrv>
<TSrc neg="False">
<ObjectRef ref="sysid0"/>
</TSrc>
<TDst neg="False">
<ObjectRef ref="id44935FEF28075"/>
</TDst>
<TSrv neg="False">
<ServiceRef ref="sysid1"/>
</TSrv>
<NATRuleOptions/>
</NATRule>
<NATRule disabled="False" id="id4493621228075" position="2">
<NATRule disabled="False" id="id4493621228075" position="2">
<OSrc neg="False">
<ObjectRef ref="sysid0"/>
</OSrc>
<ODst neg="False">
<ObjectRef ref="id44935B6E28075"/>
</ODst>
<OSrv neg="False">
<ServiceRef ref="tcp-SMTP"/>
<ServiceRef ref="tcp-HTTP"/>
</OSrv>
<TSrc neg="False">
<ObjectRef ref="sysid0"/>
</TSrc>
<TDst neg="False">
<ObjectRef ref="id44935FEF28075"/>
</TDst>
<TSrv neg="False">
<ServiceRef ref="sysid1"/>
</TSrv>
<NATRuleOptions/>
</NATRule>
</NAT>
<Policy id="id44935AAA28075">
</NAT>
<Policy top_rule_set="True" id="id44935AAA28075" name="Policy">
<PolicyRule action="Tag" direction="Inbound" disabled="False" id="id44935B8828075" log="False" position="0">
<Src neg="False">
<ObjectRef ref="sysid0"/>
</Src>
<Dst neg="False">
<Dst neg="False">
<ObjectRef ref="sysid0"/>
</Dst>
<Srv neg="False">
<Srv neg="False">
<ServiceRef ref="sysid1"/>
</Srv>
<Itf neg="False">
<Itf neg="False">
<ObjectRef ref="id44935B6E28075"/>
</Itf>
<When neg="False">
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions>
<Option name="action_on_reject"></Option>
<Option name="branch_anchor_name"></Option>
<Option name="branch_chain_name"></Option>
<Option name="classify_str"></Option>
<Option name="custom_str"></Option>
<Option name="ipf_route_opt_addr"></Option>
<Option name="ipf_route_opt_if"></Option>
<Option name="action_on_reject"/>
<Option name="branch_anchor_name"/>
<Option name="branch_chain_name"/>
<Option name="classify_str"/>
<Option name="custom_str"/>
<Option name="ipf_route_opt_addr"/>
<Option name="ipf_route_opt_if"/>
<Option name="ipf_route_option">Route through</Option>
<Option name="ipfw_classify_method">2</Option>
<Option name="ipfw_pipe_port_num">0</Option>
<Option name="ipfw_pipe_queue_num">0</Option>
<Option name="ipt_continue">False</Option>
<Option name="ipt_gw"></Option>
<Option name="ipt_iif"></Option>
<Option name="ipt_gw"/>
<Option name="ipt_iif"/>
<Option name="ipt_mark_connections">True</Option>
<Option name="ipt_oif"></Option>
<Option name="ipt_oif"/>
<Option name="ipt_tee">False</Option>
<Option name="pf_fastroute">False</Option>
<Option name="pf_route_opt_addr"></Option>
<Option name="pf_route_opt_if"></Option>
<Option name="pf_route_opt_addr"/>
<Option name="pf_route_opt_if"/>
<Option name="pf_route_option">Route through</Option>
<Option name="rule_name_accounting"></Option>
<Option name="tagvalue">1</Option>
<Option name="rule_name_accounting"/>
<Option name="tagobject_id">id44935FFA28075</Option>
</PolicyRuleOptions>
</PolicyRule>
<PolicyRule action="Tag" direction="Inbound" disabled="False" id="id44935FFD28075" log="False" position="1">
<Src neg="False">
<ObjectRef ref="sysid0"/>
</Src>
<Dst neg="False">
<Dst neg="False">
<ObjectRef ref="sysid0"/>
</Dst>
<Srv neg="False">
<Srv neg="False">
<ServiceRef ref="sysid1"/>
</Srv>
<Itf neg="False">
<Itf neg="False">
<ObjectRef ref="id44935B7428075"/>
</Itf>
<When neg="False">
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions>
<Option name="action_on_reject"></Option>
<Option name="branch_anchor_name"></Option>
<Option name="branch_chain_name"></Option>
<Option name="classify_str"></Option>
<Option name="custom_str"></Option>
<Option name="ipf_route_opt_addr"></Option>
<Option name="ipf_route_opt_if"></Option>
<Option name="action_on_reject"/>
<Option name="branch_anchor_name"/>
<Option name="branch_chain_name"/>
<Option name="classify_str"/>
<Option name="custom_str"/>
<Option name="ipf_route_opt_addr"/>
<Option name="ipf_route_opt_if"/>
<Option name="ipf_route_option">Route through</Option>
<Option name="ipfw_classify_method">2</Option>
<Option name="ipfw_pipe_port_num">0</Option>
<Option name="ipfw_pipe_queue_num">0</Option>
<Option name="ipt_continue">False</Option>
<Option name="ipt_gw"></Option>
<Option name="ipt_iif"></Option>
<Option name="ipt_gw"/>
<Option name="ipt_iif"/>
<Option name="ipt_mark_connections">True</Option>
<Option name="ipt_oif"></Option>
<Option name="ipt_oif"/>
<Option name="ipt_tee">False</Option>
<Option name="pf_fastroute">False</Option>
<Option name="pf_route_opt_addr"></Option>
<Option name="pf_route_opt_if"></Option>
<Option name="pf_route_opt_addr"/>
<Option name="pf_route_opt_if"/>
<Option name="pf_route_option">Route through</Option>
<Option name="rule_name_accounting"></Option>
<Option name="tagvalue">2</Option>
<Option name="rule_name_accounting"/>
<Option name="tagobject_id">id44935FFB28075</Option>
</PolicyRuleOptions>
</PolicyRule>
<PolicyRule action="Route" direction="Both" disabled="False" id="id4493608A28075" log="False" position="2">
<Src neg="False">
<ObjectRef ref="sysid0"/>
</Src>
<Dst neg="False">
<Dst neg="False">
<ObjectRef ref="sysid0"/>
</Dst>
<Srv neg="False">
<Srv neg="False">
<ServiceRef ref="id44935FFA28075"/>
</Srv>
<Itf neg="False">
<Itf neg="False">
<ObjectRef ref="sysid0"/>
</Itf>
<When neg="False">
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions>
<Option name="action_on_reject"></Option>
<Option name="branch_anchor_name"></Option>
<Option name="branch_chain_name"></Option>
<Option name="classify_str"></Option>
<Option name="custom_str"></Option>
<Option name="ipf_route_opt_addr"></Option>
<Option name="ipf_route_opt_if"></Option>
<Option name="ipf_route_option">Route through</Option>
<Option name="ipfw_classify_method">2</Option>
<Option name="ipfw_pipe_port_num">0</Option>
<Option name="ipfw_pipe_queue_num">0</Option>
<Option name="ipt_continue">False</Option>
<Option name="ipt_gw"></Option>
<Option name="ipt_iif"></Option>
<Option name="ipt_mark_connections">False</Option>
<Option name="ipt_oif">eth1</Option>
<Option name="ipt_tee">False</Option>
<Option name="pf_fastroute">False</Option>
<Option name="pf_route_opt_addr"></Option>
<Option name="pf_route_opt_if"></Option>
<Option name="pf_route_option">Route through</Option>
<Option name="rule_name_accounting"></Option>
<Option name="action_on_reject"/>
<Option name="branch_anchor_name"/>
<Option name="branch_chain_name"/>
<Option name="classify_str"/>
<Option name="custom_str"/>
<Option name="ipf_route_opt_addr"/>
<Option name="ipf_route_opt_if"/>
<Option name="ipf_route_option">Route through</Option>
<Option name="ipfw_classify_method">2</Option>
<Option name="ipfw_pipe_port_num">0</Option>
<Option name="ipfw_pipe_queue_num">0</Option>
<Option name="ipt_continue">False</Option>
<Option name="ipt_gw"/>
<Option name="ipt_iif"/>
<Option name="ipt_mark_connections">False</Option>
<Option name="ipt_oif">eth1</Option>
<Option name="ipt_tee">False</Option>
<Option name="pf_fastroute">False</Option>
<Option name="pf_route_opt_addr"/>
<Option name="pf_route_opt_if"/>
<Option name="pf_route_option">Route through</Option>
<Option name="rule_name_accounting"/>
<Option name="stateless">True</Option>
</PolicyRuleOptions>
</PolicyRule>
<PolicyRule action="Route" direction="Both" disabled="False" id="id4493609728075" log="False" position="3">
<Src neg="False">
<ObjectRef ref="sysid0"/>
</Src>
<Dst neg="False">
<Dst neg="False">
<ObjectRef ref="sysid0"/>
</Dst>
<Srv neg="False">
<Srv neg="False">
<ServiceRef ref="id44935FFB28075"/>
</Srv>
<Itf neg="False">
<Itf neg="False">
<ObjectRef ref="sysid0"/>
</Itf>
<When neg="False">
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions>
<Option name="action_on_reject"></Option>
<Option name="branch_anchor_name"></Option>
<Option name="branch_chain_name"></Option>
<Option name="classify_str"></Option>
<Option name="custom_str"></Option>
<Option name="ipf_route_opt_addr"></Option>
<Option name="ipf_route_opt_if"></Option>
<Option name="ipf_route_option">Route through</Option>
<Option name="ipfw_classify_method">2</Option>
<Option name="ipfw_pipe_port_num">0</Option>
<Option name="ipfw_pipe_queue_num">0</Option>
<Option name="ipt_continue">False</Option>
<Option name="ipt_gw"></Option>
<Option name="ipt_iif"></Option>
<Option name="ipt_mark_connections">False</Option>
<Option name="ipt_oif">eth2</Option>
<Option name="ipt_tee">False</Option>
<Option name="pf_fastroute">False</Option>
<Option name="pf_route_opt_addr"></Option>
<Option name="pf_route_opt_if"></Option>
<Option name="pf_route_option">Route through</Option>
<Option name="rule_name_accounting"></Option>
<Option name="action_on_reject"/>
<Option name="branch_anchor_name"/>
<Option name="branch_chain_name"/>
<Option name="classify_str"/>
<Option name="custom_str"/>
<Option name="ipf_route_opt_addr"/>
<Option name="ipf_route_opt_if"/>
<Option name="ipf_route_option">Route through</Option>
<Option name="ipfw_classify_method">2</Option>
<Option name="ipfw_pipe_port_num">0</Option>
<Option name="ipfw_pipe_queue_num">0</Option>
<Option name="ipt_continue">False</Option>
<Option name="ipt_gw"/>
<Option name="ipt_iif"/>
<Option name="ipt_mark_connections">False</Option>
<Option name="ipt_oif">eth2</Option>
<Option name="ipt_tee">False</Option>
<Option name="pf_fastroute">False</Option>
<Option name="pf_route_opt_addr"/>
<Option name="pf_route_opt_if"/>
<Option name="pf_route_option">Route through</Option>
<Option name="rule_name_accounting"/>
<Option name="stateless">True</Option>
</PolicyRuleOptions>
</PolicyRule>
<PolicyRule action="Accept" direction="Both" disabled="False" id="id4493613C28075" log="False" position="4">
<Src neg="False">
<ObjectRef ref="sysid0"/>
</Src>
<Dst neg="False">
<Dst neg="False">
<ObjectRef ref="id44935FEF28075"/>
</Dst>
<Srv neg="False">
<Srv neg="False">
<ServiceRef ref="tcp-HTTP"/>
</Srv>
<Itf neg="False">
<Itf neg="False">
<ObjectRef ref="sysid0"/>
</Itf>
<When neg="False">
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions/>
</PolicyRule>
<PolicyRule action="Accept" direction="Both" disabled="False" id="id4493615428075" log="False" position="5">
<Src neg="False">
<ObjectRef ref="id3DC75CE7-1"/>
</Src>
<Dst neg="False">
<Dst neg="False">
<ObjectRef ref="sysid0"/>
</Dst>
<Srv neg="False">
<Srv neg="False">
<ServiceRef ref="sysid1"/>
</Srv>
<Itf neg="False">
<Itf neg="False">
<ObjectRef ref="sysid0"/>
</Itf>
<When neg="False">
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions/>
</PolicyRule>
<PolicyRule action="Deny" disabled="False" id="id44935B3228075" log="True" position="6">
<Src neg="False">
<ObjectRef ref="sysid0"/>
</Src>
<Dst neg="False">
<Dst neg="False">
<ObjectRef ref="sysid0"/>
</Dst>
<Srv neg="False">
<Srv neg="False">
<ServiceRef ref="sysid1"/>
</Srv>
<Itf neg="False">
<Itf neg="False">
<ObjectRef ref="sysid0"/>
</Itf>
<When neg="False">
<When neg="False">
<IntervalRef ref="sysid2"/>
</When>
<PolicyRuleOptions/>
<PolicyRuleOptions>
<Option name="stateless">True</Option>
</PolicyRuleOptions>
</PolicyRule>
</Policy>
<Routing id="id44935B6A28075"/>
<Interface bridgeport="False" comment="this interface is internal, it is connected to LAN behind the firewall" dyn="False" id="id44935B6B28075" label="" mgmt="True" name="eth0" security_level="100" unnum="False">
</Policy>
<Routing top_rule_set="True" id="id44935B6A28075" name="Routing">
</Routing>
<Interface bridgeport="False" comment="this interface is internal, it is connected to LAN behind the firewall" dyn="False" id="id44935B6B28075" label="" mgmt="True" name="eth0" security_level="100" unnum="False">
<IPv4 address="192.168.1.1" comment="" id="id44935B6D28075" name="example1:eth0:ip" netmask="255.255.255.0"/>
</Interface>
<Interface bridgeport="False" comment="first external interface connected to ISP1" dyn="False" id="id44935B6E28075" label="" mgmt="False" name="eth1" security_level="0" unnum="False">
<Interface bridgeport="False" comment="first external interface connected to ISP1" dyn="False" id="id44935B6E28075" label="" mgmt="False" name="eth1" security_level="0" unnum="False">
<IPv4 address="192.0.2.1" comment="" id="id44935B7028075" name="example1:eth1:ip" netmask="255.255.255.0"/>
</Interface>
<Interface bridgeport="False" comment="loopback interface" dyn="False" id="id44935B7128075" label="" mgmt="False" name="lo" security_level="100" unnum="False">
<Interface bridgeport="False" comment="loopback interface" dyn="False" id="id44935B7128075" label="" mgmt="False" name="lo" security_level="100" unnum="False">
<IPv4 address="127.0.0.1" comment="" id="id44935B7328075" name="example1:lo:ip" netmask="255.0.0.0"/>
</Interface>
<Interface bridgeport="False" comment="the second external interface, connected to ISP2" dyn="False" id="id44935B7428075" label="" mgmt="False" name="eth2" security_level="0" unnum="False">
<Interface bridgeport="False" comment="the second external interface, connected to ISP2" dyn="False" id="id44935B7428075" label="" mgmt="False" name="eth2" security_level="0" unnum="False">
<IPv4 address="192.0.3.1" comment="" id="id44935B7628075" name="example1:eth2:ip" netmask="255.255.255.0"/>
</Interface>
<Management address="192.168.1.1">
<Management address="192.168.1.1">
<SNMPManagement enabled="False" snmp_read_community="" snmp_write_community=""/>
<FWBDManagement enabled="False" identity="" port="-1"/>
<PolicyInstallScript arguments="" command="" enabled="False"/>
</Management>
<FirewallOptions>
<FirewallOptions>
<Option name="accept_established">True</Option>
<Option name="accept_new_tcp_with_no_syn">True</Option>
<Option name="action_on_reject"></Option>
<Option name="activationCmd"></Option>
<Option name="admUser"></Option>
<Option name="altAddress"></Option>
<Option name="action_on_reject"/>
<Option name="activationCmd"/>
<Option name="admUser"/>
<Option name="altAddress"/>
<Option name="bridging_fw">False</Option>
<Option name="check_shading">True</Option>
<Option name="clamp_mss_to_mtu">False</Option>
<Option name="cmdline"></Option>
<Option name="compiler"></Option>
<Option name="cmdline"/>
<Option name="compiler"/>
<Option name="configure_interfaces">True</Option>
<Option name="debug">False</Option>
<Option name="drop_invalid">False</Option>
<Option name="eliminate_duplicates">true</Option>
<Option name="epilog_script"></Option>
<Option name="epilog_script"/>
<Option name="firewall_dir">/etc</Option>
<Option name="firewall_is_part_of_any_and_networks">True</Option>
<Option name="freebsd_ip_forward">1</Option>
<Option name="ignore_empty_groups">False</Option>
<Option name="in_out_code">true</Option>
<Option name="limit_suffix"></Option>
<Option name="limit_suffix"/>
<Option name="limit_value">0</Option>
<Option name="linux24_ip_forward">1</Option>
<Option name="load_modules">True</Option>
<Option name="local_nat">False</Option>
<Option name="log_all">False</Option>
<Option name="log_invalid">False</Option>
<Option name="log_ip_opt">False</Option>
<Option name="log_level">info</Option>
<Option name="log_prefix">RULE %N -- %A </Option>
<Option name="log_tcp_opt">False</Option>
<Option name="log_tcp_seq">False</Option>
<Option name="loopback_interface">lo0</Option>
<Option name="macosx_ip_forward">1</Option>
<Option name="manage_virtual_addr">True</Option>
<Option name="mgmt_addr"></Option>
<Option name="mgmt_addr"/>
<Option name="mgmt_ssh">False</Option>
<Option name="openbsd_ip_forward">1</Option>
<Option name="output_file"></Option>
<Option name="output_file"/>
<Option name="pass_all_out">false</Option>
<Option name="pf_limit_frags">5000</Option>
<Option name="pf_limit_states">10000</Option>
<Option name="pf_scrub_maxmss">1460</Option>
<Option name="pf_timeout_frag">30</Option>
<Option name="pf_timeout_interval">10</Option>
<Option name="pix_add_clear_statements">true</Option>
<Option name="pix_assume_fw_part_of_any">true</Option>
<Option name="pix_default_logint">300</Option>
<Option name="pix_emblem_log_format">false</Option>
<Option name="pix_emulate_out_acl">true</Option>
<Option name="pix_floodguard">true</Option>
<Option name="pix_include_comments">true</Option>
<Option name="pix_route_dnat_supported">true</Option>
<Option name="pix_rule_syslog_settings">false</Option>
<Option name="pix_security_fragguard_supported">true</Option>
<Option name="pix_syslog_device_id_supported">false</Option>
<Option name="pix_use_acl_remarks">true</Option>
<Option name="prolog_place">top</Option>
<Option name="prolog_script"></Option>
<Option name="prolog_script"/>
<Option name="prompt1">$ </Option>
<Option name="prompt2"> # </Option>
<Option name="solaris_ip_forward">1</Option>
<Option name="sshArgs"></Option>
<Option name="sshArgs"/>
<Option name="ulog_cprange">0</Option>
<Option name="ulog_nlgroup">1</Option>
<Option name="ulog_qthreshold">1</Option>
<Option name="use_ULOG">False</Option>
<Option name="use_iptables_restore">False</Option>
<Option name="use_numeric_log_levels">False</Option>
<Option name="verify_interfaces">True</Option>
</FirewallOptions>
</Firewall>
</Firewall>
</ObjectGroup>
<IntervalGroup id="id4493570A28075" name="Time"/>
</Library>
<Library id="sysid99" name="Deleted Objects" ro="False">
<ObjectRef ref="id3DC75CE7-2"/>
</Library>
<Library color="#d4f8ff" comment="Standard objects" id="syslib000" name="Standard" ro="False">
<AnyNetwork comment="Any Network" id="sysid0" name="Any" address="0.0.0.0" netmask="0.0.0.0"/>
<AnyIPService comment="Any IP Service" id="sysid1" name="Any" protocol_num="0"/>
<AnyInterval comment="Any Interval" from_day="-1" from_hour="-1" from_minute="-1" from_month="-1" from_weekday="-1" from_year="-1" id="sysid2" name="Any" to_day="-1" to_hour="-1" to_minute="-1" to_month="-1" to_weekday="-1" to_year="-1"/>
<ServiceGroup id="stdid05" name="Services">
<ServiceGroup id="stdid09" name="TCP">
<ServiceGroup id="stdid05_userservices" name="Users"/>
<ServiceGroup id="stdid09" name="TCP">
<TCPService ack_flag="False" ack_flag_mask="False" comment="" dst_range_end="80" dst_range_start="80" fin_flag="False" fin_flag_mask="False" id="tcp-HTTP" name="http" psh_flag="False" psh_flag_mask="False" rst_flag="False" rst_flag_mask="False" src_range_end="0" src_range_start="0" syn_flag="False" syn_flag_mask="False" urg_flag="False" urg_flag_mask="False"/>
<TCPService ack_flag="False" ack_flag_mask="False" comment="" dst_range_end="25" dst_range_start="25" fin_flag="False" fin_flag_mask="False" id="tcp-SMTP" name="smtp" psh_flag="False" psh_flag_mask="False" rst_flag="False" rst_flag_mask="False" src_range_end="0" src_range_start="0" syn_flag="False" syn_flag_mask="False" urg_flag="False" urg_flag_mask="False"/>
</ServiceGroup>
</ServiceGroup>
</ServiceGroup>
<ObjectGroup id="stdid01" name="Objects">
<ObjectGroup id="stdid01_clusters" name="Clusters"/>
<ObjectGroup id="stdid03" name="Networks">
<Network comment="192.168.1.0/24 - Address often used for home and small office networks.&#10;" id="id3DC75CE7-1" name="net-192.168.1.0" address="192.168.1.0" netmask="255.255.255.0"/>
<Network comment="192.168.2.0/24 - Address often used for home and small office networks.&#10;" id="id3DC75CE7-2" name="net-192.168.2.0" address="192.168.2.0" netmask="255.255.255.0"/>
</ObjectGroup>
</ObjectGroup>
</ObjectGroup>
</Library>
</FWObjectDatabase>

77
doc/transfer_secuwall.1 Normal file
View File

@ -0,0 +1,77 @@
.\" Title: transfer_secuwall
.\" Author:
.\" Generator: DocBook XSL Stylesheets v1.73.2 <http://docbook.sf.net/>
.\" Date: 06/23/2009
.\" Manual:
.\" Source:
.\"
.TH "TRANSFER_SECUWALL" "1" "06/23/2009" "" ""
.\" disable hyphenation
.nh
.\" disable justification (adjust text to left margin only)
.ad l
.SH "NAME"
transfer_secuwall \- secunet wall configuration export utility
.SH "SYNOPSIS"
\fBtransfer_secuwall\fR [\-l] [\-h] [\-a] \-v \fIvolumeid\fR [\-f \fIfilename\&.xml\fR] [\-d \fIworkdir\fR] \fIfirewall_object_name\fR
.sp
The switches \-a, \-f and \-d are optional\&. If they are not specified, the appropriate defaults are used\&.
.sp
.SH "DESCRIPTION"
transfer_secuwall(1) is a helper utility to compress and export secunet wall host OS specific firewall configuration to a portable device\&.
.sp
It is also capable of searching and displaying all transfer devices of a system which are suitable for config transfer\&.
.sp
.SH "OPTIONS"
.PP
\fB\-l\fR
.RS 4
List all portable devices of the system\&.
.RE
.PP
\fB\-h\fR
.RS 4
Display help text\&.
.RE
.PP
\fB\-a\fR
.RS 4
Append firewall object name to transfer tarball\&. The default is
\fBfalse\fR\&.
.RE
.PP
\fB\-v\fR
.RS 4
Transfer partition\&. Specifies the destination partition for firewall configuration export (e\&.g\&. /dev/sdc1)\&.
.RE
.PP
\fB\-f\fR
.RS 4
Firewall Builder XML file with object definition of firewall to export config\&. If not specified, the filename will be constructed from the
\fIworkdir\fR
and
\fIfirewall_object_name\fR
values:
\fIworkdir\fR
+
\fIfwobjectname\fR
+ \&.fwb
.RE
.PP
\fB\-d\fR
.RS 4
Defines the working directory\&. If not specified, the current directory will be used\&.
.RE
.PP
\fIfirewall_object_name\fR
.RS 4
Firewall object name\&.
.RE
.SH "EXAMPLES"
$ transfer_secuwall \-f /tmp/cluster\&.fwb \-d /tmp \-v /dev/sdc1 fw3
.sp
This will export the configuration of secunet wall firewall \fBfw3\fR to the partition \fB/dev/sdc1\fR, using the Firewall Builder XML file \fBcluster\&.fwb\fR in the working directory \fB/tmp\fR\&.
.sp
.SH "AUTHOR"
Written by Reto Buerki <buerki@swiss\-it\&.ch>\&.
.sp

View File

@ -0,0 +1,65 @@
TRANSFER_SECUWALL(1)
====================
NAME
----
transfer_secuwall - secunet wall configuration export utility
SYNOPSIS
--------
*transfer_secuwall* [-l] [-h] [-a] -v 'volumeid' [-f 'filename.xml'] [-d 'workdir'] 'firewall_object_name'
The switches -a, -f and -d are optional. If they are not specified, the
appropriate defaults are used.
DESCRIPTION
-----------
transfer_secuwall(1) is a helper utility to compress and export secunet wall host
OS specific firewall configuration to a portable device.
It is also capable of searching and displaying all transfer devices of a system
which are suitable for config transfer.
OPTIONS
-------
*-l*::
List all portable devices of the system.
*-h*::
Display help text.
*-a*::
Append firewall object name to transfer tarball. The default is *false*.
*-v*::
Transfer partition. Specifies the destination partition for firewall configuration export (e.g. /dev/sdc1).
*-f*::
Firewall Builder XML file with object definition of firewall to export config.
If not specified, the filename will be constructed from the 'workdir' and 'firewall_object_name' values:
'workdir' \+ 'fwobjectname' \+ .fwb
*-d*::
Defines the working directory. If not specified, the current directory will be used.
'firewall_object_name'::
Firewall object name.
EXAMPLES
--------
$ transfer_secuwall -f /tmp/cluster.fwb -d /tmp -v /dev/sdc1 fw3
This will export the configuration of secunet wall firewall *fw3* to the
partition */dev/sdc1*, using the Firewall Builder XML file *cluster.fwb* in the
working directory */tmp*.
AUTHOR
------
Written by Reto Buerki <buerki@swiss-it.ch>.

View File

@ -1,6 +1,6 @@
#-*- mode: makefile; tab-width: 4; -*-
#
######### fwbuilder/qmake.inc.in
########## fwbuilder/qmake.inc.in
#
QTDIR = $$(QTDIR)
TEMPLATE = app
@ -20,6 +20,7 @@ unix {
ANTLR_INCLUDEPATH = @ANTLR_INCLUDEPATH@
ANTLR_LIBS = @ANTLR_LIBS@
FWBPARSER_LIB = ../parsers/libfwbparser.a
FWTRANSFER_LIB = ../fwtransfer/libfwtransfer.a
QMAKE_CXX = @CCACHE@ g++
@ -47,8 +48,10 @@ unix {
res.path = @RES_DIR@
res_os.path = @RES_DIR@/os/
res_platform.path = @RES_DIR@/platform/
res_help.path = @RES_DIR@/help/
res_desktop.path = @DATADIR@/applications/
res_help_C.path = @RES_DIR@/help/C
res_help_en_US.path = @RES_DIR@/help/en_US
res_configlets_linux24.path = @RES_DIR@/configlets/linux24
INSTALLS += res
INSTALLS += res_os
@ -58,6 +61,8 @@ unix {
PKGLOCALEDIR = $$res.path/locale
LIBS += $$LIBS_FWBUILDER @LIBS@
CONFIG += warn_on debug
QMAKE_CFLAGS_DEBUG += -Wno-unused-parameter
QMAKE_CFLAGS_RELEASE += -Wno-unused-parameter

View File

@ -36,18 +36,37 @@ string ciscoACL::addLine(const std::string &s)
return printLastLine();
}
/*
* Adds remark to access list. Checks and adds each remark only
* once. We use rule labels for remarks
*/
string ciscoACL::addRemark(const std::string &rl)
/*
* Adds remark to access list. Checks and adds each remark only
* once. We use rule labels for remarks
*/
string ciscoACL::addRemark(const std::string &rl, const std::string &comment)
{
if (_last_rule_label!=rl)
string output;
if (_last_rule_label != rl)
{
acl.push_back(" remark "+rl);
_last_rule_label=rl;
acl.push_back(" remark " + rl);
output += printLastLine();
nlines++;
return printLastLine();
if (!comment.empty())
{
string::size_type n, c1;
c1 = 0;
while ( (n = comment.find("\n", c1)) != string::npos )
{
acl.push_back(" remark " + comment.substr(c1, n-c1));
output += printLastLine();
nlines++;
c1 = n + 1;
}
acl.push_back(" remark " + comment.substr(c1));
output += printLastLine();
nlines++;
}
_last_rule_label = rl;
return output;
}
return "";
}

View File

@ -73,9 +73,9 @@ class ciscoACL {
/*
* Adds remark to access list. Checks and adds each remark only
* once. We use rule labels for remarks
* once. We use rule labels and comments for remarks
*/
std::string addRemark(const std::string &rl);
std::string addRemark(const std::string &rl, const std::string &comment);
void setName(const std::string &s) { _name=s; }
std::string name() { return _name; }

View File

@ -0,0 +1,266 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include "../../build_num"
#include <fstream>
#include <iostream>
#include <algorithm>
#include <functional>
#include <stdexcept>
#include <assert.h>
#include <string>
#include <cstring>
#include <iomanip>
#include "fwbuilder/Resources.h"
#include "fwbuilder/FWOptions.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/Interface.h"
#include "CompilerDriver_iosacl.h"
#include "PolicyCompiler_iosacl.h"
#include <QFileInfo>
#include <QDir>
using namespace std;
using namespace libfwbuilder;
using namespace fwcompiler;
#ifdef _WIN32
string fs_separator = "\\";
#else
string fs_separator = "/";
#endif
CompilerDriver_iosacl::CompilerDriver_iosacl(FWObjectDatabase *db) :
CompilerDriver(db)
{
}
// create a copy of itself, including objdb
CompilerDriver* CompilerDriver_iosacl::clone()
{
return new CompilerDriver_iosacl(objdb);
}
void CompilerDriver_iosacl::printProlog(QTextStream &file, const string &prolog_code)
{
file << endl;
file << "#" << endl;
file << "# Prolog script" << endl;
file << "#" << endl;
file << prolog_code << endl;
file << "#" << endl;
file << "# End of prolog script" << endl;
file << "#" << endl;
}
string CompilerDriver_iosacl::safetyNetInstall(Firewall *fw)
{
ostringstream output;
if ( fw->getOptionsObject()->getBool("iosacl_acl_substitution") )
{
/* Generate short temporary ACL and assign it to all
* interfaces. This ACL permits IPSEC (IP proto 50 and UDP port 500)
as well as ssh from given subnet to any.
*/
string platform = fw->getStr("platform");
string version = fw->getStr("version");
string temp_acl = "tmp_acl";
string temp_acl_addr = fw->getOptionsObject()->getStr(
"iosacl_acl_temp_addr");
if (temp_acl_addr.empty())
{
cerr << "Missing address for management host or subnet for temporary ACL.\nPlease enter it in the tab 'Script options' in 'Firewall Settings' dialog"
<< endl;
exit(-1);
}
// if templ_acl_addr is ipv4 address, then we can not create this
// temporary ACL while compiling ipv6 policy. And vice versa.
bool create_temp_acl = false;
bool tmp_acl_ipv6 = false;
if (temp_acl_addr.find(":")!=string::npos)
{
//looks like ipv6
create_temp_acl = true;
tmp_acl_ipv6 = true;
} else
{
// not ipv6, assume ipv4
create_temp_acl = true;
tmp_acl_ipv6 = false;
}
if (create_temp_acl)
{
string::size_type slash_idx = temp_acl_addr.find('/');
string addr = temp_acl_addr;
string netmask = "255.255.255.255";
bool tmp_acl_v6 = false;
// check if addr is v6
try
{
InetAddr addrv6(AF_INET6, temp_acl_addr);
tmp_acl_v6 = true;
} catch(FWException &ex)
{
// Assume cnf->maddr is ipv4
if (slash_idx!=string::npos)
{
addr = temp_acl_addr.substr(0,slash_idx);
netmask = temp_acl_addr.substr(slash_idx+1);
try
{
if (netmask.find(".")!=string::npos)
{
InetAddr nm(netmask);
nm.getLength(); // to avoid warning abt unused var
} else
{
int nm_length;
istringstream str(netmask);
str >> nm_length;
InetAddr nm(nm_length);
netmask = nm.toString();
}
} catch(FWException &ex)
{
cerr << "Invalid netmask for management subnet: '"+netmask+"'"
<< endl;
exit(-1);
}
}
try
{
InetAddr a(addr);
a.isAny();
} catch(FWException &ex)
{
cerr << "Invalid address for management subnet: '"+addr+"'"
<< endl;
exit(-1);
}
}
string xml_element = "clear_ip_acl";
if (tmp_acl_ipv6) xml_element = "clear_ipv6_acl";
string clearACLcmd = Resources::platform_res[platform]->getResourceStr(
string("/FWBuilderResources/Target/options/")+
"version_"+version+"/iosacl_commands/" + xml_element);
output << endl;
string addr_family_prefix = "ip";
string access_group_cmd =
PolicyCompiler_iosacl::getAccessGroupCommandForAddressFamily(tmp_acl_v6);
output << "! temporary access list for \"safety net install\""
<< endl;
output << endl;
if (tmp_acl_v6)
{
addr_family_prefix = "ipv6";
output << clearACLcmd << " " << temp_acl << endl;
output << "ipv6 access-list " << temp_acl << endl;
if (slash_idx!=string::npos)
output << " permit ipv6 " << addr << " any " << endl;
else
output << " permit ipv6 host " << addr << " any " << endl;
output << " permit icmp any any " << endl;
output << " deny ipv6 any any " << endl;
output << "exit" << endl;
output << endl;
} else
{
// cisco uses "wildcards" instead of netmasks
//long nm = InetAddr(netmask).to32BitInt();
//struct in_addr na;
//na.s_addr = ~nm;
InetAddr nnm( ~(InetAddr(netmask)) );
addr_family_prefix = "ip";
output << clearACLcmd << " " << temp_acl << endl;
output << "ip access-list extended " << temp_acl << endl;
output << " permit ip "
<< addr << " " << nnm.toString() << " any " << endl;
output << " deny ip any any " << endl;
output << "exit" << endl;
output << endl;
}
// find management interface
int nmi = 0;
list<FWObject*> ll = fw->getByType(Interface::TYPENAME);
for (FWObject::iterator i=ll.begin(); i!=ll.end(); i++)
{
Interface *intf = Interface::cast( *i );
if (intf->isManagement())
{
nmi++;
output << "interface " << intf->getName() << endl;
output << " no " << addr_family_prefix << " ";
output << access_group_cmd;
output << " in" << endl;
output << " no " << addr_family_prefix << " ";
output << access_group_cmd;
output << " out" << endl;
output << " " << addr_family_prefix << " ";
output << access_group_cmd;
output << " " << temp_acl << " in" << endl;
output << "exit" << endl;
}
}
if (nmi==0)
{
cerr << "One of the interfaces of the firewall must be marked as management interface."
<< endl;
exit(-1);
}
output << endl;
}
}
return output.str();
}

View File

@ -0,0 +1,70 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef __COMPILER_DRIVER_IOSACL_HH__
#define __COMPILER_DRIVER_IOSACL_HH__
#include "CompilerDriver.h"
#include <string>
#include <sstream>
#include <QTextStream>
namespace libfwbuilder {
class FWObjectDatabase;
class Cluster;
class ClusterGroup;
class Firewall;
class RuleSet;
class Interface;
};
namespace fwcompiler {
class CompilerDriver_iosacl : public CompilerDriver {
protected:
std::string safetyNetInstall(libfwbuilder::Firewall *fw);
void printProlog(QTextStream &file, const std::string &prolog_code);
public:
CompilerDriver_iosacl(libfwbuilder::FWObjectDatabase *db);
// create a copy of itself, including objdb
virtual CompilerDriver* clone();
virtual std::string run(const std::string &cluster_id,
const std::string &firewall_id,
const std::string &single_rule_id);
};
};
#endif

View File

@ -0,0 +1,405 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include "../../build_num"
#ifndef _WIN32
# include <unistd.h>
# include <pwd.h>
#else
# include <direct.h>
# include <stdlib.h>
# include <io.h>
#endif
#include <fstream>
#include <iostream>
#include <algorithm>
#include <functional>
#include <stdexcept>
#include <memory>
#include <assert.h>
#include <cstring>
#include <iomanip>
#include "CompilerDriver_iosacl.h"
#include "PolicyCompiler_iosacl.h"
#include "RoutingCompiler_iosacl.h"
#include "OSConfigurator_ios.h"
#include "fwbuilder/Resources.h"
#include "fwbuilder/FWObjectDatabase.h"
#include "fwbuilder/XMLTools.h"
#include "fwbuilder/FWException.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/Interface.h"
#include "fwbuilder/Policy.h"
#include "fwbuilder/NAT.h"
#include "fwbuilder/Routing.h"
#include "fwcompiler/Preprocessor.h"
#include "fwbuilder/Resources.h"
#include "fwbuilder/FWObjectDatabase.h"
#include "fwbuilder/FWException.h"
#include "fwbuilder/Cluster.h"
#include "fwbuilder/ClusterGroup.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/Interface.h"
#include "fwbuilder/Policy.h"
#include "fwbuilder/StateSyncClusterGroup.h"
#include "fwbuilder/FailoverClusterGroup.h"
#include <QStringList>
#include <QFileInfo>
#include <QFile>
#include <QTextStream>
using namespace std;
using namespace libfwbuilder;
using namespace fwcompiler;
string CompilerDriver_iosacl::run(const std::string &cluster_id,
const std::string &firewall_id,
const std::string &single_rule_id)
{
Cluster *cluster = NULL;
if (!cluster_id.empty())
cluster = Cluster::cast(
objdb->findInIndex(objdb->getIntId(cluster_id)));
Firewall *fw = Firewall::cast(
objdb->findInIndex(objdb->getIntId(firewall_id)));
assert(fw);
// Copy rules from the cluster object
populateClusterElements(cluster, fw);
commonChecks2(cluster, fw);
// Note that fwobjectname may be different from the name of the
// firewall fw This happens when we compile a member of a cluster
current_firewall_name = fw->getName().c_str();
QString ofname = determineOutputFileName(fw, !cluster_id.empty(), ".fw");
FWOptions* options = fw->getOptionsObject();
string fwvers = fw->getStr("version");
if (fwvers == "") fw->setStr("version", "12.x");
string platform = fw->getStr("platform");
string clearACLCmd = Resources::platform_res[platform]->getResourceStr(
string("/FWBuilderResources/Target/options/") +
"version_" + fwvers + "/iosacl_commands/clear_ip_acl");
if (clearACLCmd.empty())
{
// incorrect version. This could have happened if user converted
// firewall platform. See bug #2662290
fw->setStr("version", "12.x");
}
bool ios_acl_basic = options->getBool("ios_acl_basic");
bool ios_acl_no_clear = options->getBool("ios_acl_no_clear");
bool ios_acl_substitution = options->getBool("ios_acl_substitution");
bool ios_add_clear_statements = options->getBool("ios_add_clear_statements");
if ( !ios_acl_basic &&
!ios_acl_no_clear &&
!ios_acl_substitution )
{
if ( ios_add_clear_statements ) options->setBool("ios_acl_basic",true);
else options->setBool("ios_acl_no_clear",true);
}
Helper helper(NULL);
char timestr[256];
time_t tm;
tm=time(NULL);
strcpy(timestr,ctime(&tm));
timestr[ strlen(timestr)-1 ]='\0';
#ifdef _WIN32
char* user_name=getenv("USERNAME");
#else
char* user_name=getenv("USER");
#endif
if (user_name==NULL)
throw FWException("Can't figure out your user name, aborting");
std::auto_ptr<OSConfigurator_ios> oscnf(new OSConfigurator_ios(objdb, fw, false));
oscnf->prolog();
oscnf->processFirewallOptions();
list<FWObject*> all_policies = fw->getByType(Policy::TYPENAME);
int policy_rules_count = 0;
vector<int> ipv4_6_runs;
string generated_script;
if (!single_rule_compile_on)
generated_script = safetyNetInstall(fw);
// command line options -4 and -6 control address family for which
// script will be generated. If "-4" is used, only ipv4 part will
// be generated. If "-6" is used, only ipv6 part will be generated.
// If neither is used, both parts will be done.
if (options->getStr("ipv4_6_order").empty() ||
options->getStr("ipv4_6_order") == "ipv4_first")
{
if (ipv4_run) ipv4_6_runs.push_back(AF_INET);
if (ipv6_run) ipv4_6_runs.push_back(AF_INET6);
}
if (options->getStr("ipv4_6_order") == "ipv6_first")
{
if (ipv6_run) ipv4_6_runs.push_back(AF_INET6);
if (ipv4_run) ipv4_6_runs.push_back(AF_INET);
}
for (vector<int>::iterator i=ipv4_6_runs.begin();
i!=ipv4_6_runs.end(); ++i)
{
int policy_af = *i;
bool ipv6_policy = (policy_af == AF_INET6);
// Count rules for each address family
int policy_count = 0;
for (list<FWObject*>::iterator p=all_policies.begin();
p!=all_policies.end(); ++p)
{
Policy *policy = Policy::cast(*p);
if (policy->matchingAddressFamily(policy_af)) policy_count++;
}
if (policy_count)
{
std::auto_ptr<Preprocessor> prep(new Preprocessor(objdb, fw, false));
prep->compile();
}
for (list<FWObject*>::iterator p=all_policies.begin();
p!=all_policies.end(); ++p )
{
Policy *policy = Policy::cast(*p);
if (!policy->matchingAddressFamily(policy_af)) continue;
PolicyCompiler_iosacl c(objdb, fw, ipv6_policy, oscnf.get());
c.setSourceRuleSet( policy );
c.setRuleSetName(policy->getName());
c.setSingleRuleCompileMode(single_rule_id);
if (inTestMode()) c.setTestMode();
if (inEmbeddedMode()) c.setEmbeddedMode();
c.setDebugLevel( dl );
if (rule_debug_on) c.setDebugRule( drp );
c.setVerbose( verbose );
if ( c.prolog() > 0 )
{
c.compile();
c.epilog();
if (!single_rule_compile_on)
{
if (ipv6_policy)
{
generated_script += "\n\n";
generated_script += "! ================ IPv6\n";
generated_script += "\n\n";
} else
{
generated_script += "\n\n";
generated_script += "! ================ IPv4\n";
generated_script += "\n\n";
}
}
if (c.haveErrorsAndWarnings())
{
all_errors.push_back(c.getErrors("").c_str());
// generated_script +=
// "! Policy compiler errors and warnings:";
// generated_script += "\n";
// generated_script += c.getErrors("! ");
}
generated_script += c.getCompiledScript();
} else
info(" Nothing to compile in Policy");
}
if (!ipv6_policy)
{
list<FWObject*> all_routing = fw->getByType(Routing::TYPENAME);
RuleSet *routing = RuleSet::cast(all_routing.front());
// currently routing is supported only for ipv4
RoutingCompiler_iosacl r(objdb, fw, false, oscnf.get());
r.setSourceRuleSet(routing);
r.setRuleSetName(routing->getName());
r.setSingleRuleCompileMode(single_rule_id);
if (inTestMode()) r.setTestMode();
if (inEmbeddedMode()) r.setEmbeddedMode();
r.setDebugLevel( dl );
if (rule_debug_on) r.setDebugRule( drp );
r.setVerbose( verbose );
if ( r.prolog() > 0 )
{
r.compile();
r.epilog();
if (r.haveErrorsAndWarnings())
{
all_errors.push_back(r.getErrors("").c_str());
// generated_script +=
// "! Routing compiler errors and warnings:";
// generated_script += "\n";
// generated_script += r.getErrors("! ");
}
generated_script += r.getCompiledScript();
} else
info(" Nothing to compile in Routing");
}
}
if (haveErrorsAndWarnings())
{
all_errors.push_front(getErrors("").c_str());
}
if (single_rule_compile_on)
{
return
all_errors.join("\n").toStdString() +
generated_script;
}
QString script_buffer;
QTextStream script(&script_buffer, QIODevice::WriteOnly);
script << "!\n\
! This is automatically generated file. DO NOT MODIFY !\n\
!\n\
! Firewall Builder fwb_iosacl v" << VERSION << "-" << RELEASE_NUM << " \n\
!\n\
! Generated " << timestr
<< " "
<< tzname[0]
<< " by "
<< user_name;
script << endl;
script << "!" << endl;
script << "!" << " Compiled for " << platform << " " << fwvers << endl;
script << "!" << endl;
script << "!" << MANIFEST_MARKER << "* " << ofname << endl;
script << "!" << endl;
script << prepend("! ", all_errors.join("\n")) << endl;
script << endl;
script << "!" << endl;
script << "! Prolog script:" << endl;
script << "!" << endl;
string pre_hook= fw->getOptionsObject()->getStr("iosacl_prolog_script");
script << pre_hook << endl;
script << "!" << endl;
script << "! End of prolog script:" << endl;
script << "!" << endl;
script << oscnf->getCompiledScript();
script << endl;
script << generated_script;
script << endl;
script << endl;
script << "!" << endl;
script << "! Epilog script:" << endl;
script << "!" << endl;
string post_hook= fw->getOptionsObject()->getStr("iosacl_epilog_script");
script << post_hook << endl;
script << endl;
script << "! End of epilog script:" << endl;
script << "!" << endl;
QFile fw_file(ofname);
if (fw_file.open(QIODevice::WriteOnly))
{
QTextStream fw_str(&fw_file);
fw_str << script_buffer;
fw_file.close();
fw_file.setPermissions(QFile::ReadOwner | QFile::WriteOwner |
QFile::ReadGroup | QFile::ReadOther |
QFile::ExeOwner |
QFile::ExeGroup |
QFile::ExeOther );
info(" Compiled successfully");
} else
{
throw FWException(string(" Failed to open file ") +
fw_file_name.toStdString() +
" for writing");
}
return "";
}

View File

@ -0,0 +1,90 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include "../../build_num"
#include <fstream>
#include <iostream>
#include <algorithm>
#include <functional>
#include <stdexcept>
#include <assert.h>
#include <string>
#include <cstring>
#include <iomanip>
#include "fwbuilder/Resources.h"
#include "fwbuilder/FWOptions.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/Interface.h"
#include "CompilerDriver_pix.h"
#include "PolicyCompiler_pix.h"
#include "OSConfigurator_pix_os.h"
#include <QFileInfo>
#include <QDir>
using namespace std;
using namespace libfwbuilder;
using namespace fwcompiler;
CompilerDriver_pix::CompilerDriver_pix(FWObjectDatabase *db) :
CompilerDriver(db)
{
}
// create a copy of itself, including objdb
CompilerDriver* CompilerDriver_pix::clone()
{
return new CompilerDriver_pix(objdb);
}
string CompilerDriver_pix::protocolInspectorCommands(Firewall *fw)
{
OSConfigurator_pix_os *oscnf =
new OSConfigurator_pix_os(objdb , fw, false);
oscnf->prolog();
string res = oscnf->getProtocolInspectionCommands();
delete oscnf;
return res;
}
void CompilerDriver_pix::printProlog(QTextStream &file, const string &prolog_code)
{
file << endl;
file << "#" << endl;
file << "# Prolog script" << endl;
file << "#" << endl;
file << prolog_code << endl;
file << "#" << endl;
file << "# End of prolog script" << endl;
file << "#" << endl;
}

View File

@ -0,0 +1,71 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef __COMPILER_DRIVER_PIX_HH__
#define __COMPILER_DRIVER_PIX_HH__
#include "CompilerDriver.h"
#include <string>
#include <sstream>
#include <QTextStream>
namespace libfwbuilder {
class FWObjectDatabase;
class Cluster;
class ClusterGroup;
class Firewall;
class RuleSet;
class Interface;
};
namespace fwcompiler {
class CompilerDriver_pix : public CompilerDriver {
protected:
std::string safetyNetInstall(libfwbuilder::Firewall *fw);
void printProlog(QTextStream &file, const std::string &prolog_code);
public:
CompilerDriver_pix(libfwbuilder::FWObjectDatabase *db);
// create a copy of itself, including objdb
virtual CompilerDriver* clone();
virtual std::string run(const std::string &cluster_id,
const std::string &firewall_id,
const std::string &single_rule_id);
std::string protocolInspectorCommands(libfwbuilder::Firewall *fw);
};
};
#endif

View File

@ -0,0 +1,593 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include "../../build_num"
#ifndef _WIN32
# include <unistd.h>
# include <pwd.h>
#else
# include <direct.h>
# include <stdlib.h>
# include <io.h>
#endif
#include <fstream>
#include <iostream>
#include <algorithm>
#include <functional>
#include <stdexcept>
#include <memory>
#include <assert.h>
#include <cstring>
#include <iomanip>
#include "CompilerDriver_pix.h"
#include "PolicyCompiler_pix.h"
#include "NATCompiler_pix.h"
#include "RoutingCompiler_pix.h"
#include "OSConfigurator_pix_os.h"
#include "Helper.h"
#include "fwbuilder/Resources.h"
#include "fwbuilder/FWObjectDatabase.h"
#include "fwbuilder/XMLTools.h"
#include "fwbuilder/FWException.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/Interface.h"
#include "fwbuilder/Policy.h"
#include "fwbuilder/NAT.h"
#include "fwbuilder/Routing.h"
#include "fwcompiler/Preprocessor.h"
#include "fwbuilder/Cluster.h"
#include "fwbuilder/ClusterGroup.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/Interface.h"
#include "fwbuilder/Policy.h"
#include "fwbuilder/StateSyncClusterGroup.h"
#include "fwbuilder/FailoverClusterGroup.h"
#include <QStringList>
#include <QFileInfo>
#include <QFile>
#include <QTextStream>
using namespace std;
using namespace libfwbuilder;
using namespace fwcompiler;
class sort_by_net_zone {
string any_address_id;
public:
explicit sort_by_net_zone()
{
any_address_id = FWObjectDatabase::getStringId(
FWObjectDatabase::ANY_ADDRESS_ID);
}
bool operator()(const FWObject *a, const FWObject *b)
{
if (Interface::constcast(a) && Interface::constcast(b))
{
string netzone_a=a->getStr("network_zone");
string netzone_b=b->getStr("network_zone");
if ( netzone_a==any_address_id) return false;
if ( netzone_b==any_address_id) return true;
}
return false;
}
};
string CompilerDriver_pix::run(const std::string &cluster_id,
const std::string &firewall_id,
const std::string &single_rule_id)
{
Cluster *cluster = NULL;
if (!cluster_id.empty())
cluster = Cluster::cast(
objdb->findInIndex(objdb->getIntId(cluster_id)));
Firewall *fw = Firewall::cast(
objdb->findInIndex(objdb->getIntId(firewall_id)));
assert(fw);
// Copy rules from the cluster object
populateClusterElements(cluster, fw);
commonChecks2(cluster, fw);
// Note that fwobjectname may be different from the name of the
// firewall fw This happens when we compile a member of a cluster
current_firewall_name = fw->getName().c_str();
QString ofname = determineOutputFileName(fw, !cluster_id.empty(), ".fw");
FWOptions* options = fw->getOptionsObject();
bool pix_acl_basic=options->getBool("pix_acl_basic");
bool pix_acl_no_clear=options->getBool("pix_acl_no_clear");
bool pix_acl_substitution=options->getBool("pix_acl_substitution");
bool pix_add_clear_statements=options->getBool("pix_add_clear_statements");
if ( !pix_acl_basic &&
!pix_acl_no_clear &&
!pix_acl_substitution )
{
if ( pix_add_clear_statements ) options->setBool("pix_acl_basic",true);
else options->setBool("pix_acl_no_clear",true);
}
Helper helper(NULL);
multimap<string, FWObject*> netzone_objects;
std::list<FWObject*> l2=fw->getByType(Interface::TYPENAME);
for (std::list<FWObject*>::iterator i=l2.begin(); i!=l2.end(); ++i)
{
Interface *iface=dynamic_cast<Interface*>(*i);
assert(iface);
/*
* missing labels on interfaces
*/
if (iface->getLabel()=="")
{
string lbl;
if (iface->getSecurityLevel()==0) lbl="outside";
else
{
if (iface->getSecurityLevel()==100) lbl="inside";
else
{
char s[64];
sprintf(s,"dmz%d",iface->getSecurityLevel());
lbl=s;
}
}
iface->setLabel(lbl);
}
/*
* there shouldn't be two interfaces with the same security level
*/
for (std::list<FWObject*>::iterator j=l2.begin(); j!=l2.end(); ++j)
{
Interface *iface2=dynamic_cast<Interface*>(*j);
assert(iface2);
if (iface->getId()==iface2->getId()) continue;
if (iface->getSecurityLevel()==iface2->getSecurityLevel())
{
QString err(
"Security level of each interface should be unique, "
"however interfaces %1 (%2) and %3 (%4)"
" have the same security level."
);
abort(fw, NULL, NULL,
err.arg(iface->getName().c_str())
.arg(iface->getLabel().c_str())
.arg(iface2->getName().c_str())
.arg(iface2->getLabel().c_str()).toStdString());
}
}
/*
* in PIX, we need network zones to be defined for all interfaces
*/
string netzone_id=iface->getStr("network_zone");
if (netzone_id=="")
{
QString err("Network zone definition is missing for interface %1 (%2)");
abort(fw, NULL, NULL,
err.arg(iface->getName().c_str())
.arg(iface->getLabel().c_str()).toStdString());
}
FWObject *netzone=objdb->findInIndex(
FWObjectDatabase::getIntId(netzone_id));
if (netzone==NULL)
{
QString err("Network zone points at nonexisting object for interface %1 (%2)");
abort(fw, NULL, NULL,
err.arg(iface->getName().c_str())
.arg(iface->getLabel().c_str()).toStdString());
}
/*
* netzone may be a group, in which case we need to expand it
* (recursively).
*
* 1. We create new temporary object (type Group).
*
* 2. put it in the database somewhere
*
* 3. add all objects that belong to the network zone to this
* group. We add objects directly, not as a reference.
*
* 4. finally replace reference to the old network zone object in the
* interface with reference to this new group.
*
* 5. we store ID of the original network zone object
* using iface->setStr("orig_netzone_id")
*
* This ensures netzones do not contain other groups and do not
* require any recursive expanding anymore. Since objects were added
* to netzones directly, we do not need to bother with dereferencing,
* too.
*/
list<FWObject*> ol;
helper.expand_group_recursive_no_cache(netzone,ol);
FWObject *nz = objdb->createObjectGroup();
assert(nz!=NULL);
nz->setName("netzone_"+iface->getLabel());
objdb->add(nz);
for (list<FWObject*>::iterator j=ol.begin(); j!=ol.end(); ++j)
{
netzone_objects.insert( pair<string,FWObject*>(iface->getLabel(),*j));
nz->add(*j);
}
iface->setStr("orig_netzone_id", netzone_id );
iface->setStr("network_zone",
FWObjectDatabase::getStringId(nz->getId()) );
}
/*
* the same object (network or host) can not belong to network zones
* of two different interfaces. Map netzone_objects holds pairs
* interface_id/object. We just make sure the same object does not
* appear in two pairs with different interfaces.
*/
multimap<string,FWObject*>::iterator k;
for (k=netzone_objects.begin(); k!=netzone_objects.end(); ++k)
{
multimap<string,FWObject*>::iterator l;
l=k;
++l;
for ( ; l!=netzone_objects.end(); ++l)
{
if ( l->second->getId() == k->second->getId() )
{
if (k->first==l->first)
{
QString err("Object %1 is used more than once in network zone of interface %2");
abort(fw, NULL, NULL,
err.arg(l->second->getName().c_str())
.arg(k->first.c_str()).toStdString());
} else
{
QString err("Object %1 is used in network zones of "
"interfaces %2 and %3");
abort(fw, NULL, NULL,
err.arg(l->second->getName().c_str())
.arg(k->first.c_str())
.arg(l->first.c_str()).toStdString());
}
}
}
}
/*
* now sort interfaces by their network zone "width" (that is, more narrow
* network zone should go first, interface with network zone "any" should be
* the last)
*
std::sort(fw->begin(), fw->end(), sort_by_net_zone() );
*/
char timestr[256];
time_t tm;
tm=time(NULL);
strcpy(timestr,ctime(&tm));
timestr[ strlen(timestr)-1 ]='\0';
#ifdef _WIN32
char* user_name=getenv("USERNAME");
#else
char* user_name=getenv("USER");
#endif
if (user_name==NULL)
abort("Can't figure out your user name");
std::auto_ptr<Preprocessor> prep(new Preprocessor(objdb , fw, false));
prep->compile();
/*
* Process firewall options, build OS network configuration script
*/
std::auto_ptr<OSConfigurator> oscnf(new OSConfigurator_pix_os(objdb , fw, false));
oscnf->prolog();
oscnf->processFirewallOptions();
/* create compilers and run the whole thing */
std::auto_ptr<NATCompiler_pix> n(new NATCompiler_pix(objdb, fw, false, oscnf.get()));
RuleSet *nat = RuleSet::cast(fw->getFirstByType(NAT::TYPENAME));
if (nat)
{
n->setSourceRuleSet(nat);
n->setRuleSetName(nat->getName());
if (inTestMode()) n->setTestMode();
if (inEmbeddedMode()) n->setEmbeddedMode();
n->setSingleRuleCompileMode(single_rule_id);
n->setDebugLevel( dl );
if (rule_debug_on) n->setDebugRule( drn );
n->setVerbose( verbose );
if ( n->prolog() > 0 )
{
n->compile();
n->epilog();
} else
info(" Nothing to compile in NAT");
}
std::auto_ptr<PolicyCompiler_pix> c(
new PolicyCompiler_pix(objdb, fw, false, oscnf.get() , n.get()));
RuleSet *policy = RuleSet::cast(fw->getFirstByType(Policy::TYPENAME));
if (policy)
{
c->setSourceRuleSet(policy);
c->setRuleSetName(policy->getName());
if (inTestMode()) c->setTestMode();
if (inEmbeddedMode()) c->setEmbeddedMode();
c->setSingleRuleCompileMode(single_rule_id);
c->setDebugLevel( dl );
if (rule_debug_on) c->setDebugRule( drp );
c->setVerbose( verbose );
if ( c->prolog() > 0 )
{
c->compile();
c->epilog();
} else
info(" Nothing to compile in Policy");
}
std::auto_ptr<RoutingCompiler_pix> r(new RoutingCompiler_pix(objdb, fw, false, oscnf.get()));
RuleSet *routing = RuleSet::cast(fw->getFirstByType(Routing::TYPENAME));
if (routing)
{
r->setSourceRuleSet(routing);
r->setRuleSetName(routing->getName());
if (inTestMode()) r->setTestMode();
if (inEmbeddedMode()) r->setEmbeddedMode();
r->setSingleRuleCompileMode(single_rule_id);
r->setDebugLevel( dl );
if (rule_debug_on) r->setDebugRule( drp );
r->setVerbose( verbose );
if ( r->prolog() > 0 )
{
r->compile();
r->epilog();
} else
info(" Nothing to compile in Routing");
}
if (haveErrorsAndWarnings())
{
all_errors.push_front(getErrors("").c_str());
}
if (single_rule_compile_on)
{
ostringstream ostr;
if (c->haveErrorsAndWarnings())
{
all_errors.push_back(c->getErrors("").c_str());
// ostr << "! Policy compiler errors and warnings:"
// << endl;
// ostr << c->getErrors("! ");
}
ostr << c->getCompiledScript();
if (n->haveErrorsAndWarnings())
{
all_errors.push_back(n->getErrors("").c_str());
// ostr << "! NAT compiler errors and warnings:"
// << endl;
// ostr << n->getErrors("! ");
}
ostr << n->getCompiledScript();
if (r->haveErrorsAndWarnings())
{
all_errors.push_back(r->getErrors("").c_str());
// ostr << "! Routing compiler errors and warnings:"
// << endl;
// ostr << r->getErrors("! ");
}
ostr << r->getCompiledScript();
return
all_errors.join("\n").toStdString() +
ostr.str();
}
QString script_buffer;
QTextStream script(&script_buffer, QIODevice::WriteOnly);
script << "!\n\
! This is automatically generated file. DO NOT MODIFY !\n\
!\n\
! Firewall Builder fwb_pix v" << VERSION << "-" << BUILD_NUM << " \n\
!\n\
! Generated " << timestr
<< " "
<< tzname[0]
<< " by "
<< user_name;
script << endl;
string vers = fw->getStr("version");
string platform = fw->getStr("platform");
bool outbound_acl_supported = Resources::platform_res[platform]->getResourceBool(
string("/FWBuilderResources/Target/options/")+
"version_"+vers+
"/pix_outbound_acl_supported");
bool afpa = options->getBool("pix_assume_fw_part_of_any");
bool emulate_outb_acls = options->getBool("pix_emulate_out_acl");
bool generate_outb_acls = options->getBool("pix_generate_out_acl");
script << "!" << endl;
script << "!"
<< " Compiled for "
<< platform
<< " " << vers << endl;
script << "!"
<< " Outbound ACLs "
<< string((outbound_acl_supported)?"supported":"not supported")
<< endl;
if (!outbound_acl_supported)
{
script << "!"
<< " Emulate outbound ACLs: "
<< string((emulate_outb_acls)?"yes":"no")
<< endl;
}
script << "!"
<< " Generating outbound ACLs: "
<< string((generate_outb_acls)?"yes":"no")
<< endl;
script << "!"
<< " Assume firewall is part of 'any': "
<< string((afpa)?"yes":"no")
<< endl;
script << "!" << endl;
script << "!" << MANIFEST_MARKER << "* " << ofname << endl;
script << "!" << endl;
if (c->haveErrorsAndWarnings())
all_errors.push_back(c->getErrors("C ").c_str());
if (n->haveErrorsAndWarnings())
all_errors.push_back(n->getErrors("N ").c_str());
if (r->haveErrorsAndWarnings())
all_errors.push_back(r->getErrors("R ").c_str());
script << prepend("! ", all_errors.join("\n")).toStdString() << endl;
script << endl;
script << "!" << endl;
script << "! Prolog script:" << endl;
script << "!" << endl;
string pre_hook= fw->getOptionsObject()->getStr("pix_prolog_script");
script << pre_hook << endl;
script << "!" << endl;
script << "! End of prolog script:" << endl;
script << "!" << endl;
script << oscnf->getCompiledScript();
script << endl;
// if (c->haveErrorsAndWarnings())
// {
// script << "! Policy compiler errors and warnings:"
// << endl;
// script << c->getErrors("! ");
// }
script << c->getCompiledScript();
script << endl;
// if (n->haveErrorsAndWarnings())
// {
// script << "! NAT compiler errors and warnings:"
// << endl;
// script << n->getErrors("! ");
// }
script << n->getCompiledScript();
script << endl;
// if (r->haveErrorsAndWarnings())
// {
// script << "! Routing compiler errors and warnings:"
// << endl;
// script << r->getErrors("! ");
// }
script << r->getCompiledScript();
script << "!" << endl;
script << "! Epilog script:" << endl;
script << "!" << endl;
string post_hook = fw->getOptionsObject()->getStr("pix_epilog_script");
script << post_hook << endl;
script << endl;
script << "! End of epilog script:" << endl;
script << "!" << endl;
QFile fw_file(ofname);
if (fw_file.open(QIODevice::WriteOnly))
{
QTextStream fw_str(&fw_file);
fw_str << script_buffer;
fw_file.close();
fw_file.setPermissions(QFile::ReadOwner | QFile::WriteOwner |
QFile::ReadGroup | QFile::ReadOther |
QFile::ExeOwner |
QFile::ExeGroup |
QFile::ExeOther );
info(" Compiled successfully");
} else
{
throw FWException(string(" Failed to open file ") +
fw_file_name.toStdString() +
" for writing");
}
return "";
}

View File

@ -233,10 +233,10 @@ list<int> Helper::findInterfaceByNetzoneOrAll(RuleElement *re)
{
Rule *rule = Rule::cast(re->getParent());
compiler->abort(
re->getParent(),
string("findInterfaceByNetzoneOrAll failed to retrieve first "
"object from the rule element; is argument not of "
"the type RuleElementSrc or RuleElementDst ? Rule ") +
rule->getLabel());
"the type RuleElementSrc or RuleElementDst ?"));
}
try
{
@ -253,7 +253,8 @@ list<int> Helper::findInterfaceByNetzoneOrAll(RuleElement *re)
Resources::getTargetCapabilityBool(
compiler->fw->getStr("platform"), "network_zones");
if (supports_network_zones) compiler->warning(err);
if (supports_network_zones)
compiler->warning(err);
FWObjectTypedChildIterator i = compiler->fw->findByType(
Interface::TYPENAME);

View File

@ -54,10 +54,10 @@ using namespace std;
string NATCompiler_pix::myPlatformName() { return "pix"; }
NATCompiler_pix::NATCompiler_pix(FWObjectDatabase *_db,
const std::string &fwname,
Firewall *fw,
bool ipv6_policy,
OSConfigurator *_oscnf) :
NATCompiler(_db, fwname, ipv6_policy, _oscnf) , helper(this)
NATCompiler(_db, fw, ipv6_policy, _oscnf) , helper(this)
{
}
@ -105,8 +105,8 @@ string NATCompiler_pix::debugPrintRule(Rule *r)
{
NATRule *rule=NATRule::cast(r);
Interface *iface1 = getCachedFwInterface( rule->getInt("nat_iface_orig") );
Interface *iface2 = getCachedFwInterface( rule->getInt("nat_iface_trn") );
FWObject *iface1 = dbcopy->findInIndex( rule->getInt("nat_iface_orig") );
FWObject *iface2 = dbcopy->findInIndex( rule->getInt("nat_iface_trn") );
string iface1_name=(iface1!=NULL)?iface1->getName():"";
string iface2_name=(iface2!=NULL)?iface2->getName():"";
@ -257,10 +257,15 @@ bool NATCompiler_pix::VerifyRules::processNext()
RuleElementTSrv *tsrv=rule->getTSrv(); assert(tsrv);
if (rule->getRuleType()==NATRule::LB)
compiler->abort("Load balancing rules are not supported. Rule "+rule->getLabel());
compiler->abort(
rule,
"Load balancing rules are not supported.");
if (rule->getRuleType()==NATRule::NONAT && (!osrv->isAny() || !tsrv->isAny()))
compiler->abort("'no nat' rules should have no services");
compiler->abort(
rule,
"'no nat' rules should have no services");
if (osrc->getNeg() ||
@ -269,7 +274,10 @@ bool NATCompiler_pix::VerifyRules::processNext()
tsrc->getNeg() ||
tdst->getNeg() ||
tsrv->getNeg())
compiler->abort("Negation is not supported in NAT rules. Rule "+rule->getLabel());
compiler->abort(
rule,
"Negation is not supported in NAT rules.");
if (rule->getRuleType()==NATRule::SNAT)
{
@ -278,7 +286,11 @@ bool NATCompiler_pix::VerifyRules::processNext()
if ( ! odst->isAny() && version_lt_63) // can do on fwsm
{
compiler->warning("Original destination is ignored in 'nat' NAT rules when compiling for PIX v6.2 and earlier. Rule "+rule->getLabel());
compiler->warning(
rule,
"Original destination is ignored in 'nat' NAT rules "
"when compiling for PIX v6.2 and earlier.");
odst->clearChildren();
odst->setAnyElement();
}
@ -287,20 +299,36 @@ bool NATCompiler_pix::VerifyRules::processNext()
if (rule->getRuleType()==NATRule::DNAT)
{
if ( odst->size()!=1 && version_lt_63)
compiler->abort("There should be no more than one object in original destination in the rule "+rule->getLabel());
compiler->abort(
rule,
"There should be no more than one object in original destination");
if ( ! osrc->isAny() && version_lt_63)
compiler->warning("Original source is ignored in 'static' NAT rules when compiling for PIX v6.2 and earlier. Rule "+rule->getLabel());
compiler->warning(
rule,
"Original source is ignored in 'static' NAT rules "
"when compiling for PIX v6.2 and earlier.");
}
if (osrv->size()!=1 && !tsrv->isAny())
compiler->abort("Can not translate multiple services into one service in one rule. Rule: "+rule->getLabel());
compiler->abort(
rule,
"Can not translate multiple services into one service in one rule. ");
if (tsrv->size()!=1)
compiler->abort("Translated service should be 'Original' or should contain single object. Rule: "+rule->getLabel());
compiler->abort(
rule,
"Translated service should be 'Original' or should contain single object.");
if ( Group::cast( compiler->getFirstTSrv(rule) )!=NULL)
compiler->abort("Can not use group in translated service. Rule "+rule->getLabel());
compiler->abort(
rule,
"Can not use group in translated service.");
if (rule->getRuleType()==NATRule::SNetnat && !tsrc->isAny() )
{
@ -308,7 +336,10 @@ bool NATCompiler_pix::VerifyRules::processNext()
Network *a2=Network::cast(compiler->getFirstTSrc(rule));
if ( a1==NULL || a2==NULL ||
a1->getNetmaskPtr()->getLength()!=a2->getNetmaskPtr()->getLength() )
compiler->abort("Original and translated source should both be networks of the same size . Rule "+rule->getLabel());
compiler->abort(
rule,
"Original and translated source should both be networks of the same size");
}
if (rule->getRuleType()==NATRule::DNetnat && !tsrc->isAny() )
@ -317,7 +348,10 @@ bool NATCompiler_pix::VerifyRules::processNext()
Network *a2=Network::cast(compiler->getFirstTDst(rule));
if ( a1==NULL || a2==NULL ||
a1->getNetmaskPtr()->getLength()!=a2->getNetmaskPtr()->getLength() )
compiler->abort("Original and translated destination should both be networks of the same size . Rule "+rule->getLabel());
compiler->abort(
rule,
"Original and translated destination should both be networks of the same size.");
}
if (rule->getRuleType()==NATRule::SNetnat) rule->setRuleType(NATRule::SNAT);
@ -355,17 +389,18 @@ bool NATCompiler_pix::AssignInterface::processNext()
rule->setInt("nat_iface_trn", helper.findInterfaceByNetzone(a2));
if ( rule->getInt("nat_iface_orig")==-1 )
compiler->abort("Object '" + a1->getName() +
"' does not belong to any known network zone. Rule: " +
rule->getLabel());
compiler->abort(
rule,
"Object '" + a1->getName() +
"' does not belong to any known network zone.");
if ( rule->getInt("nat_iface_trn")==-1 )
compiler->abort("Object '" + a2->getName() +
"' does not belong to any known network zone. Rule: " +
rule->getLabel());
// if ( rule->getInt("nat_iface_orig")==rule->getInt("nat_iface_trn"))
// compiler->abort("Objects '"+a1->getName()+"' and '"+a2->getName()+"' belong to the same network zone. Can not build NAT configuration. Rule: "+rule->getLabel());
compiler->abort(
rule,
"Object '" + a2->getName() +
"' does not belong to any known network zone.");
return true;
}
@ -394,11 +429,12 @@ bool NATCompiler_pix::verifyInterfaces::processNext()
sprintf(lvl1,"%d",iface1->getSecurityLevel());
sprintf(lvl2,"%d",iface2->getSecurityLevel());
compiler->abort(
"Security level of internal interface "+
iface1->getName() + " (level "+ lvl1 +") "+
" set lower than that of external interface "+
iface2->getName() + " (level "+ lvl2 +") "+
" for NAT rule "+rule->getLabel());
rule,
"Security level of internal interface "+
iface1->getName() + " (level "+ lvl1 +") "+
" set lower than that of external interface "+
iface2->getName() + " (level "+ lvl2 +") ");
}
}
}
@ -425,16 +461,20 @@ bool NATCompiler_pix::verifyRuleElements::processNext()
if (rule->getRuleType()==NATRule::SNAT)
{
if ((! osrv->isAny() || ! tsrv->isAny()) && version_lt_63)
compiler->abort("only PIX v6.3 recognizes services in global NAT. "
"Rule: "+rule->getLabel() );
compiler->abort(
rule,
"only PIX v6.3 and later recognizes services in global NAT.");
}
if (rule->getRuleType()==NATRule::DNAT)
{
if (AddressRange::cast(odst) || AddressRange::cast(tdst))
compiler->abort(
"Address ranges are not supported in original destination or "
"translated destination in NAT rule "+rule->getLabel() );
rule,
"Address ranges are not supported in original destination or "
"translated destination ");
if (Network::isA(odst) && Network::isA(tdst))
{
@ -445,18 +485,25 @@ bool NATCompiler_pix::verifyRuleElements::processNext()
if ( !(n1==n2) )
compiler->abort(
"Original and translated destination must be of the same "
"size in the NAT rule "+rule->getLabel());
rule,
"Original and translated destination must be of the same "
"size");
}
if (osrv->getTypeName()!=tsrv->getTypeName())
compiler->abort("Original and translated services must be of "
"the same type. Rule: "+rule->getLabel());
compiler->abort(
rule,
"Original and translated services must be of "
"the same type.");
if (ICMPService::isA(osrv))
compiler->abort("ICMP services are not supported in static NAT. "
"Rule: "+rule->getLabel());
compiler->abort(
rule,
"ICMP services are not supported in static NAT. ");
if (TCPService::isA(osrv) || UDPService::isA(osrv))
{
@ -464,8 +511,11 @@ bool NATCompiler_pix::verifyRuleElements::processNext()
int dre=TCPUDPService::cast(osrv)->getDstRangeEnd();
if (drs!=dre)
compiler->abort("TCP or UDP service with a port range is not "
"supported in NAT. Rule "+rule->getLabel());
compiler->abort(
rule,
"TCP or UDP service with a port range is not "
"supported in NAT.");
}
if (TCPService::isA(tsrv) || UDPService::isA(tsrv))
{
@ -473,8 +523,11 @@ bool NATCompiler_pix::verifyRuleElements::processNext()
int dre=TCPUDPService::cast(tsrv)->getDstRangeEnd();
if (drs!=dre)
compiler->abort("TCP or UDP service with a port range is not "
"supported in NAT. Rule "+rule->getLabel());
compiler->abort(
rule,
"TCP or UDP service with a port range is not "
"supported in NAT.");
}
}
@ -562,11 +615,12 @@ bool NATCompiler_pix::ReplaceFirewallObjectsODst::processNext()
{
list<FWObject*> l2=compiler->fw->getByType(Interface::TYPENAME);
for (list<FWObject*>::iterator i=l2.begin(); i!=l2.end(); ++i) {
Interface *interface_=Interface::cast(*i);
for (list<FWObject*>::iterator i=l2.begin(); i!=l2.end(); ++i)
{
Interface *iface = Interface::cast(*i);
if (! interface_->isLoopback() &&
interface_->isExt() ) cl.push_back(interface_);
if (! iface->isLoopback() && iface->getSecurityLevel()==0 )
cl.push_back(iface);
}
if ( ! cl.empty() ) {
while (rel->size())
@ -608,8 +662,9 @@ bool NATCompiler_pix::ReplaceFirewallObjectsTSrc::processNext()
if ( ! rule->getOSrc()->isAny())
{
osrc=compiler->getFirstOSrc(rule); assert(osrc!=NULL);
osrc_iface=compiler->getCachedFwInterface( helper.findInterfaceByNetzone(osrc ) );
osrc_level=osrc_iface->getSecurityLevel();
osrc_iface = Interface::cast(
compiler->dbcopy->findInIndex( helper.findInterfaceByNetzone(osrc)));
osrc_level = osrc_iface->getSecurityLevel();
}
rel=rule->getTSrc(); assert(rel);
@ -627,15 +682,14 @@ bool NATCompiler_pix::ReplaceFirewallObjectsTSrc::processNext()
list<FWObject*> l2=compiler->fw->getByType(Interface::TYPENAME);
for (list<FWObject*>::iterator i=l2.begin(); i!=l2.end(); ++i)
{
Interface *interface_=Interface::cast(*i);
if (interface_->getSecurityLevel()<osrc_level )
cl.push_back(interface_);
Interface *iface = Interface::cast(*i);
if (iface->getSecurityLevel()<osrc_level )
cl.push_back(iface);
}
} else
{
Address *odst=compiler->getFirstODst(rule); assert(odst!=NULL);
Interface *odst_iface=compiler->getCachedFwInterface( helper.findInterfaceByNetzone(odst ) );
Address *odst=compiler->getFirstODst(rule); assert(odst!=NULL);
FWObject *odst_iface=compiler->dbcopy->findInIndex( helper.findInterfaceByNetzone(odst ) );
if (odst_iface!=NULL) cl.push_back(odst_iface);
}
if ( ! cl.empty() ) {
@ -661,13 +715,15 @@ void NATCompiler_pix::UseFirewallInterfaces::scanInterfaces(RuleElement *rel)
if (FWReference::cast(o)!=NULL) o=FWReference::cast(o)->getPointer();
Address *obj=Address::cast(o);
if(obj==NULL)
compiler->abort("Broken rule element "+
rel->getTypeName()+
" in rule "+
NATRule::cast(rel->getParent())->getLabel()+
" ( found object with type "+
string((o!=NULL)?o->getTypeName():"<NULL>") +
")");
compiler->abort(
rel->getParent(),
"Broken rule element "+
rel->getTypeName()+
" in rule "+
NATRule::cast(rel->getParent())->getLabel()+
" ( found object with type "+
string((o!=NULL)?o->getTypeName():"<NULL>") +
")");
const InetAddr *obj_addr = obj->getAddressPtr();
if (obj_addr==NULL) return;
@ -714,11 +770,13 @@ bool NATCompiler_pix::processNONATRules::processNext()
Address *osrc=compiler->getFirstOSrc(rule); assert(osrc);
Address *odst=compiler->getFirstODst(rule); assert(odst);
Interface *osrc_iface=compiler->getCachedFwInterface( helper.findInterfaceByNetzone(osrc ) );
Interface *odst_iface=compiler->getCachedFwInterface( helper.findInterfaceByNetzone(odst ) );
Interface *osrc_iface = Interface::cast(
compiler->dbcopy->findInIndex(helper.findInterfaceByNetzone(osrc)));
Interface *odst_iface = Interface::cast(
compiler->dbcopy->findInIndex(helper.findInterfaceByNetzone(odst)));
int osrc_level=osrc_iface->getSecurityLevel();
int odst_level=odst_iface->getSecurityLevel();
int osrc_level = osrc_iface->getSecurityLevel();
int odst_level = odst_iface->getSecurityLevel();
/*
* PIX has two types of NONAT rules, one is when connection goes from
@ -774,11 +832,11 @@ bool NATCompiler_pix::createNATCmd::processNext()
natcmd->o_src = osrc;
natcmd->o_dst = odst;
natcmd->o_srv = osrv;
natcmd->o_iface = compiler->getCachedFwInterface(
rule->getInt("nat_iface_orig") );
natcmd->o_iface = Interface::cast(compiler->dbcopy->findInIndex(
rule->getInt("nat_iface_orig")));
natcmd->t_addr = tsrc;
natcmd->t_iface = compiler->getCachedFwInterface(
rule->getInt("nat_iface_trn" ) );
natcmd->t_iface = Interface::cast(compiler->dbcopy->findInIndex(
rule->getInt("nat_iface_trn")));
natcmd->nat_acl_name = pix_comp->getNATACLname(rule,"");
pix_comp->registerACL(natcmd->nat_acl_name);
@ -807,7 +865,11 @@ bool NATCompiler_pix::createNATCmd::processNext()
if (natcmd->outside && compiler->fw->getStr("platform")=="pix" &&
libfwbuilder::XMLTools::version_compare(compiler->fw->getStr("version"),"6.2")<0 )
compiler->abort("Bi-Directional NAT of source addresses is only supported in PIX 6.2 and newer. Rule "+rule->getLabel());
compiler->abort(
rule,
"Bi-Directional NAT of source addresses is only "
"supported in PIX 6.2 and newer.");
/*
* map is sorted container, this means that objects are going to be arranged
@ -1125,7 +1187,10 @@ bool NATCompiler_pix::processMultiAddressObjectsInRE::processNext()
if (FWReference::cast(o)!=NULL) o=FWReference::cast(o)->getPointer();
MultiAddress *atrt = MultiAddress::cast(o);
if (atrt!=NULL && atrt->isRunTime())
compiler->abort("Run-time AddressTable and DNSName objects are not supported. Rule " + rule->getLabel());
compiler->abort(
rule,
"Run-time AddressTable and DNSName objects are not supported.");
}
tmp_queue.push_back(rule);
@ -1213,20 +1278,24 @@ bool NATCompiler_pix::DetectGlobalPoolProblems::processNext()
{
if (checkOverlapping(*(natcmd->t_addr),
*(natcmd->t_iface->getAddressPtr())))
compiler->abort("Global pool "
+printGlobalPoolAddress(*(natcmd->t_addr))
+" overlaps with interface address. Rule "
+rule->getLabel());
compiler->abort(
rule,
"Global pool "
+printGlobalPoolAddress(*(natcmd->t_addr))
+" overlaps with interface address.");
if (checkOverlapping(*(natcmd->t_addr),
*(natcmd->t_iface->getBroadcastAddressPtr()))
||
checkOverlapping(*(natcmd->t_addr),
*(natcmd->t_iface->getAddressPtr())) )
compiler->warning("Global pool "
+printGlobalPoolAddress(*(natcmd->t_addr))
+" overlaps with broadcast address. Rule "
+rule->getLabel());
compiler->warning(
rule,
"Global pool "
+printGlobalPoolAddress(*(natcmd->t_addr))
+" overlaps with broadcast address.");
}
for (map<int,NATCmd*>::iterator i1=pix_comp->nat_commands.begin();
@ -1246,12 +1315,14 @@ bool NATCompiler_pix::DetectGlobalPoolProblems::processNext()
{
if ( ! fwcompiler::_find_obj_intersection(natcmd->t_addr,nc->t_addr).empty() )
{
compiler->abort(string("Global pool overlapping: \n")
+" "+rule->getLabel()+" : "
+printGlobalPoolAddress(*(natcmd->t_addr))
+"\n"
+" "+nc->rule_label+" : "
+printGlobalPoolAddress(*(nc->t_addr)) );
compiler->abort(
rule,
string("Global pool overlap: ")
+ rule->getLabel() + " : "
+ printGlobalPoolAddress(*(natcmd->t_addr))
+ nc->rule_label + " : "
+ printGlobalPoolAddress(*(nc->t_addr)) );
}
}
@ -1310,12 +1381,15 @@ bool NATCompiler_pix::DetectOverlappingGlobalPoolsAndStaticRules::processNext()
if ( checkOverlapping( addr, *(outa->getAddressPtr())) ||
checkOverlapping( *outa, *(addr.getAddressPtr())) )
compiler->abort("Global pool "
+printGlobalPoolAddress(addr)
+" from rule "
+natcmd->rule_label
+" overlaps with static translation address in rule "
+rule->getLabel());
compiler->abort(
rule,
"Global pool "
+printGlobalPoolAddress(addr)
+" from rule "
+natcmd->rule_label
+" overlaps with static translation address in rule "
+rule->getLabel());
}
}
return true;
@ -1378,7 +1452,7 @@ bool NATCompiler_pix::DetectDuplicateNAT::processNext()
<< "/"
<< TCPUDPService::cast(natcmd->o_srv)->getDstRangeEnd();
compiler->abort(str.str());
compiler->abort(rule, str.str());
}
}
}
@ -1410,13 +1484,15 @@ bool NATCompiler_pix::DetectOverlappingStatics::processNext()
*(sc->osrc) == *(scmd->osrc) &&
sc->oaddr->getId() == scmd->oaddr->getId())
compiler->abort(
"Static NAT rules overlap or are redundant : rules "+
sc->rule+" and "+scmd->rule+" : "+
"outside address: "+
"interface "+Interface::cast(scmd->oaddr)->getLabel()+
" inside address: "+
scmd->iaddr->getAddressPtr()->toString()+"/"+
scmd->iaddr->getNetmaskPtr()->toString());
rule,
"Static NAT rules overlap or are redundant : rules "+
sc->rule+" and "+scmd->rule+" : "+
"outside address: "+
"interface "+Interface::cast(scmd->oaddr)->getLabel()+
" inside address: "+
scmd->iaddr->getAddressPtr()->toString()+"/"+
scmd->iaddr->getNetmaskPtr()->toString());
} else
{
if ( *(sc->osrv) == *(scmd->osrv) &&
@ -1436,14 +1512,16 @@ bool NATCompiler_pix::DetectOverlappingStatics::processNext()
if ( ! getOverlap(*(ia1), *(ia2)).empty() ||
! getOverlap(*(oa1), *(oa2)).empty() )
compiler->abort(
"Static NAT rules overlap or are redundant: rules "+
sc->rule+" and "+scmd->rule+" : "+
"outside address: "+
scmd->oaddr->getAddressPtr()->toString()+"/"+
scmd->oaddr->getNetmaskPtr()->toString()+
" inside address: "+
scmd->iaddr->getAddressPtr()->toString()+"/"+
scmd->iaddr->getNetmaskPtr()->toString());
rule,
"Static NAT rules overlap or are redundant: rules "+
sc->rule+" and "+scmd->rule+" : "+
"outside address: "+
scmd->oaddr->getAddressPtr()->toString()+"/"+
scmd->oaddr->getNetmaskPtr()->toString()+
" inside address: "+
scmd->iaddr->getAddressPtr()->toString()+"/"+
scmd->iaddr->getNetmaskPtr()->toString());
}
}
}
@ -1455,16 +1533,17 @@ bool NATCompiler_pix::DetectOverlappingStatics::processNext()
void NATCompiler_pix::compile()
{
cout << " Compiling NAT rules for " << fw->getName() << " ..." << endl << flush;
info(" Compiling NAT rules for " + fw->getName());
try {
Compiler::compile();
add( new Begin( "Begin processing"));
add( new printTotalNumberOfRules());
add( new singleRuleFilter());
if (fw->getOptionsObject()->getBool( "pix_optimize_default_nat"))
add (new optimizeDefaultNAT(
"optimize commands 'nat (interface) 0.0.0.0 0.0.0.0'"));
@ -1568,7 +1647,8 @@ void NATCompiler_pix::compile()
runRuleProcessors();
} catch (FWException &ex) {
} catch (FWException &ex)
{
error(ex.toString());
exit(1);
}
@ -1629,7 +1709,7 @@ void NATCompiler_pix::epilog()
{
if ( fw->getOptionsObject()->getBool("pix_regroup_commands"))
{
cout << " Regrouping commands \n" << flush;
info(" Regrouping commands");
regroup();
}
}

View File

@ -460,7 +460,7 @@ namespace fwcompiler {
public:
NATCompiler_pix(libfwbuilder::FWObjectDatabase *_db,
const std::string &fwname,
libfwbuilder::Firewall *fw,
bool ipv6_policy,
fwcompiler::OSConfigurator *_oscnf);

View File

@ -59,7 +59,8 @@ bool NATCompiler_pix::PrintClearCommands::processNext()
compiler->output << endl;
if ( !compiler->fw->getOptionsObject()->getBool("pix_acl_no_clear") )
if ( !compiler->fw->getOptionsObject()->getBool("pix_acl_no_clear") &&
!compiler->inSingleRuleCompileMode())
{
compiler->output << Resources::platform_res[platform]->getResourceStr(
string("/FWBuilderResources/Target/options/")+
@ -172,10 +173,10 @@ void NATCompiler_pix::PrintRule::_printNONAT(NATRule *rule)
Address *osrc=compiler->getFirstOSrc(rule); assert(osrc);
Address *odst=compiler->getFirstODst(rule); assert(odst);
Interface *osrc_iface = compiler->getCachedFwInterface(
helper.findInterfaceByNetzone(osrc ) );
Interface *odst_iface = compiler->getCachedFwInterface(
helper.findInterfaceByNetzone(odst ) );
Interface *osrc_iface = Interface::cast(
compiler->dbcopy->findInIndex(helper.findInterfaceByNetzone(osrc)));
Interface *odst_iface = Interface::cast(
compiler->dbcopy->findInIndex(helper.findInterfaceByNetzone(odst)));
string addr=odst->getAddressPtr()->toString();
string mask;
@ -299,7 +300,8 @@ bool NATCompiler_pix::PrintRule::processNext()
NATRule *rule=getNext(); if (rule==NULL) return false;
tmp_queue.push_back(rule);
if ( compiler->fw->getOptionsObject()->getBool("pix_include_comments") )
if ( compiler->fw->getOptionsObject()->getBool("pix_include_comments") &&
!compiler->inSingleRuleCompileMode())
{
string rl=rule->getLabel();
if (rl!=current_rule_label)
@ -321,6 +323,8 @@ bool NATCompiler_pix::PrintRule::processNext()
}
}
string err = rule->getStr(".error_msg");
if (!err.empty()) compiler->output << "! " << err << endl;
Address *osrc=compiler->getFirstOSrc(rule); assert(osrc);
Address *odst=compiler->getFirstODst(rule); assert(odst);
@ -330,9 +334,10 @@ bool NATCompiler_pix::PrintRule::processNext()
Address *tdst=compiler->getFirstTDst(rule); assert(tdst);
Service *tsrv=compiler->getFirstTSrv(rule); assert(tsrv);
Interface *iface_orig = compiler->getCachedFwInterface( rule->getInt("nat_iface_orig") );
Interface *iface_trn = compiler->getCachedFwInterface( rule->getInt("nat_iface_trn" ) );
Interface *iface_orig = Interface::cast(
compiler->dbcopy->findInIndex(rule->getInt("nat_iface_orig")));
Interface *iface_trn = Interface::cast(
compiler->dbcopy->findInIndex(rule->getInt("nat_iface_trn")));
switch (rule->getRuleType())
{

View File

@ -45,9 +45,9 @@ namespace fwcompiler {
virtual ~OSConfigurator_ios() {};
OSConfigurator_ios(libfwbuilder::FWObjectDatabase *_db,
const std::string &fwname,
libfwbuilder::Firewall *fw,
bool ipv6_policy) :
OSConfigurator(_db, fwname, ipv6_policy) {}
OSConfigurator(_db, fw, ipv6_policy) {}
virtual int prolog();

View File

@ -200,7 +200,7 @@ string OSConfigurator_pix_os::_printLogging()
if (iface_id == -1)
abort("Log server " + syslog_host +
" does not belong to any known network zone");
Interface *syslog_iface = getCachedFwInterface(iface_id);
Interface *syslog_iface = Interface::cast(dbcopy->findInIndex(iface_id));
str << endl;
@ -267,7 +267,7 @@ string OSConfigurator_pix_os::_printSNMPServer(const std::string &srv,
if (iface_id == -1)
abort(string("SNMP server ") + srv +
" does not belong to any known network zone");
Interface *snmp_iface = getCachedFwInterface(iface_id);
Interface *snmp_iface = Interface::cast(dbcopy->findInIndex(iface_id));
str << "snmp-server host " << snmp_iface->getLabel() << " " << srv;
switch (poll_trap)
{
@ -356,7 +356,7 @@ string OSConfigurator_pix_os::_printNTPServer(const std::string &srv,bool pref)
int iface_id=helper.findInterfaceByNetzone(&srv_addr);
if (iface_id == -1)
abort("NTP server "+srv+" does not belong to any known network zone");
Interface *ntp_iface = getCachedFwInterface(iface_id);
Interface *ntp_iface = Interface::cast(dbcopy->findInIndex(iface_id));
str << "ntp server " << srv << " source " << ntp_iface->getLabel();
if (pref) str << " prefer";
str << endl;
@ -515,7 +515,7 @@ string OSConfigurator_pix_os::_printServiceTimeout(
return res.str();
}
string OSConfigurator_pix_os::_printTimeouts()
string OSConfigurator_pix_os::_printTimeouts()
{
ostringstream res;

View File

@ -60,9 +60,9 @@ namespace fwcompiler {
virtual ~OSConfigurator_pix_os() {};
OSConfigurator_pix_os(libfwbuilder::FWObjectDatabase *_db,
const std::string &fwname,
libfwbuilder::Firewall *fw,
bool ipv6_policy) :
OSConfigurator(_db, fwname, ipv6_policy) {}
OSConfigurator(_db, fw, ipv6_policy) {}
virtual int prolog();

View File

@ -61,10 +61,10 @@ using namespace std;
string PolicyCompiler_cisco::myPlatformName() { return ""; }
PolicyCompiler_cisco::PolicyCompiler_cisco(FWObjectDatabase *_db,
const std::string &fwname,
Firewall *fw,
bool ipv6_policy,
OSConfigurator *_oscnf) :
PolicyCompiler(_db, fwname, ipv6_policy, _oscnf) , helper(this)
PolicyCompiler(_db, fw, ipv6_policy, _oscnf) , helper(this)
{
}
@ -88,13 +88,17 @@ string PolicyCompiler_cisco::createRuleLabel(const string &txt,
string PolicyCompiler_cisco::debugPrintRule(Rule *r)
{
ostringstream str;
PolicyRule *rule=PolicyRule::cast(r);
Interface *rule_iface = getCachedFwInterface(rule->getInterfaceId());
string iname=(rule_iface!=NULL)?rule_iface->getName():"";
FWObject *rule_iface = dbcopy->findInIndex(rule->getInterfaceId());
string iname = (rule_iface!=NULL)?rule_iface->getName():"";
string dir= rule->getDirectionAsString();
return PolicyCompiler::debugPrintRule(rule)+
" "+dir+" "+iname+" "+rule->getStr("acl");
str << PolicyCompiler::debugPrintRule(rule) <<
" " << dir << " " << iname << " " << rule->getStr("acl") <<
" intfId=" << rule->getInterfaceId() <<
" intfstr=" << rule->getInterfaceStr();
return str.str();
}
@ -111,14 +115,12 @@ void PolicyCompiler_cisco::addDefaultPolicyRule()
ssh->setDstRangeStart(22);
ssh->setDstRangeEnd(22);
dbcopy->add(ssh,false);
cacheObj(ssh); // to keep cache consistent
Network *mgmt_workstation = dbcopy->createNetwork();
mgmt_workstation->setAddressNetmask(
getCachedFwOpt()->getStr("mgmt_addr"));
dbcopy->add(mgmt_workstation, false);
cacheObj(mgmt_workstation); // to keep cache consistent
r= dbcopy->createPolicyRule();
temp_ruleset->add(r);
@ -126,7 +128,7 @@ void PolicyCompiler_cisco::addDefaultPolicyRule()
r->setLogging(false);
r->setDirection(PolicyRule::Inbound);
r->setPosition(-1);
r->setComment(" backup ssh access rule ");
// r->setComment(" backup ssh access rule ");
r->setHidden(true);
r->setFallback(false);
r->setLabel("backup ssh access rule");
@ -437,7 +439,7 @@ bool PolicyCompiler_cisco::specialCaseWithDynInterface::dropDynamicInterface(
PolicyRule *rule, PolicyRule::Direction cmp_dir, RuleElement *re)
{
PolicyRule::Direction dir=rule->getDirection();
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
FWObject *rule_iface = compiler->dbcopy->findInIndex(rule->getInterfaceId());
list<FWObject*> cl;
for (list<FWObject*>::iterator i1=re->begin(); i1!=re->end(); ++i1)
@ -570,7 +572,7 @@ bool PolicyCompiler_cisco::tcpServiceToFW::processNext()
bool PolicyCompiler_cisco::replaceFWinSRCInterfacePolicy::processNext()
{
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
FWObject *rule_iface = compiler->dbcopy->findInIndex(rule->getInterfaceId());
if (rule_iface!=NULL && rule->getDirection()==PolicyRule::Outbound)
{
@ -590,7 +592,7 @@ bool PolicyCompiler_cisco::replaceFWinSRCInterfacePolicy::processNext()
bool PolicyCompiler_cisco::replaceFWinDSTInterfacePolicy::processNext()
{
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
FWObject *rule_iface = compiler->dbcopy->findInIndex(rule->getInterfaceId());
if (rule_iface!=NULL && rule->getDirection()==PolicyRule::Inbound)
{
@ -615,7 +617,7 @@ bool PolicyCompiler_cisco::replaceFWinDSTPolicy::processNext()
{
Helper helper(compiler);
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
FWObject *rule_iface = compiler->dbcopy->findInIndex(rule->getInterfaceId());
if (rule_iface==NULL)
{
@ -628,7 +630,7 @@ bool PolicyCompiler_cisco::replaceFWinDSTPolicy::processNext()
{
int iface_id = helper.findInterfaceByNetzone(
compiler->getFirstSrc(rule));
Interface *iface = compiler->getCachedFwInterface(iface_id);
FWObject *iface = compiler->dbcopy->findInIndex(iface_id);
dst->clearChildren();
dst->addRef(iface);
@ -636,10 +638,8 @@ bool PolicyCompiler_cisco::replaceFWinDSTPolicy::processNext()
{
ostringstream str;
str << "Address " << addr
<< " does not match address or network zone of any interface. Rule "
<< rule->getLabel()
<< endl;
compiler->abort(str.str());
<< " does not match address or network zone of any interface." ;
compiler->abort(rule, str.str());
}
}
}
@ -710,7 +710,7 @@ bool PolicyCompiler_cisco::splitByNetworkZonesForRE::processNext()
compiler->fw->getStr("platform"), "network_zones");
if (supports_network_zones)
compiler->warning(err + " Rule " + rule->getLabel());
compiler->warning(rule, err);
FWObjectTypedChildIterator i =
compiler->fw->findByType(Interface::TYPENAME);
@ -796,7 +796,10 @@ bool PolicyCompiler_cisco::processMultiAddressObjectsInRE::processNext()
if (FWReference::cast(o)!=NULL) o = FWReference::cast(o)->getPointer();
MultiAddress *atrt = MultiAddress::cast(o);
if (atrt!=NULL && atrt->isRunTime())
compiler->abort("Run-time AddressTable and DNSName objects are not supported. Rule " + rule->getLabel());
compiler->abort(
rule,
"Run-time AddressTable and DNSName objects are not supported.");
}
tmp_queue.push_back(rule);

View File

@ -434,7 +434,7 @@ protected:
public:
PolicyCompiler_cisco(libfwbuilder::FWObjectDatabase *_db,
const std::string &fwname,
libfwbuilder::Firewall *fw,
bool ipv6_policy,
fwcompiler::OSConfigurator *_oscnf);
virtual ~PolicyCompiler_cisco() {}

View File

@ -209,12 +209,12 @@ bool PolicyCompiler_cisco::pickACL::processNext()
compiler);
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Interface *rule_iface = compiler->getCachedFwInterface(
rule->getInterfaceId());
Interface *rule_iface = Interface::cast(compiler->dbcopy->findInIndex(
rule->getInterfaceId()));
if(rule_iface==NULL)
{
compiler->abort("Missing interface assignment for rule " +
rule->getLabel());
compiler->abort(
rule, "Missing interface assignment");
}
/*
@ -240,7 +240,11 @@ bool PolicyCompiler_cisco::pickACL::processNext()
}
if (rule->getDirection() == PolicyRule::Outbound && !generate_out_acl)
compiler->abort("Rule with direction 'Outbound' requires outbound ACL but option 'Generate outbound access lists' is OFF. Rule " + rule->getLabel());
compiler->abort(
rule,
"Rule with direction 'Outbound' requires outbound ACL "
"but option 'Generate outbound access lists' is OFF.");
/* The choice of the ACL name depends on whether this is a named
* acl or not. If not, should use unique numbers. Also need to

View File

@ -61,10 +61,10 @@ using namespace std;
string PolicyCompiler_iosacl::myPlatformName() { return "iosacl"; }
PolicyCompiler_iosacl::PolicyCompiler_iosacl(FWObjectDatabase *_db,
const std::string &fwname,
Firewall *fw,
bool ipv6_policy,
OSConfigurator *_oscnf) :
PolicyCompiler_cisco(_db, fwname, ipv6_policy, _oscnf)
PolicyCompiler_cisco(_db, fw, ipv6_policy, _oscnf)
{
resetinbound=false;
fragguard=false;
@ -82,7 +82,7 @@ int PolicyCompiler_iosacl::prolog()
object_groups = new Group();
dbcopy->add( object_groups );
output << "!################" << endl;
// output << "!################" << endl;
return PolicyCompiler::prolog();
}
@ -98,7 +98,9 @@ bool PolicyCompiler_iosacl::checkForDynamicInterface::findDynamicInterface(
if (FWReference::cast(o)!=NULL) obj=FWReference::cast(o)->getPointer();
Interface *iface=Interface::cast(obj);
if (iface!=NULL && iface->isDyn())
compiler->abort("Dynamic interface can not be used in the IOS ACL rules. Rule "+rule->getLabel());
compiler->abort(
rule,
"Dynamic interface can not be used in the IOS ACL rules.");
}
return true;
@ -126,14 +128,20 @@ bool PolicyCompiler_iosacl::SpecialServices::processNext()
if (s->getBool("rr") ||
s->getBool("ssrr") ||
s->getBool("ts") )
compiler->abort("IOS ACL does not support checking for IP options in ACLs. Rule: "+rule->getLabel());
compiler->abort(
rule,
"IOS ACL does not support checking for IP options in ACLs.");
}
if (TCPService::cast(s)!=NULL) {
if (s->getBool("ack_flag") ||
s->getBool("fin_flag") ||
s->getBool("rst_flag") ||
s->getBool("syn_flag") )
compiler->abort("IOS ACL does not support checking for TCP options in ACLs. Rule: "+rule->getLabel());
compiler->abort(
rule,
"IOS ACL does not support checking for TCP options in ACLs.");
}
tmp_queue.push_back(rule);
@ -142,10 +150,9 @@ bool PolicyCompiler_iosacl::SpecialServices::processNext()
void PolicyCompiler_iosacl::compile()
{
cout << endl;
cout << " Compiling ruleset " << getSourceRuleSet()->getName();
if (ipv6) cout << ", IPv6";
cout << endl << flush;
string banner = " Compiling ruleset " + getSourceRuleSet()->getName();
if (ipv6) banner += ", IPv6";
info(banner);
try
{
@ -156,7 +163,8 @@ void PolicyCompiler_iosacl::compile()
addDefaultPolicyRule();
if ( fw->getOptionsObject()->getBool ("check_shading") )
if ( fw->getOptionsObject()->getBool ("check_shading") &&
! inSingleRuleCompileMode())
{
add( new Begin("Detecting rule shadowing" ) );
add( new printTotalNumberOfRules());
@ -193,6 +201,8 @@ void PolicyCompiler_iosacl::compile()
add( new Begin (" Start processing rules" ) );
add( new printTotalNumberOfRules ( ) );
add( new singleRuleFilter());
add( new recursiveGroupsInSrc( "check for recursive groups in SRC" ) );
add( new recursiveGroupsInDst( "check for recursive groups in DST" ) );
add( new recursiveGroupsInSrv( "check for recursive groups in SRV" ) );
@ -289,7 +299,8 @@ void PolicyCompiler_iosacl::compile()
runRuleProcessors();
} catch (FWException &ex) {
} catch (FWException &ex)
{
error(ex.toString());
exit(1);
}
@ -330,7 +341,7 @@ void PolicyCompiler_iosacl::epilog()
if ( fw->getOptionsObject()->getBool("iosacl_regroup_commands") )
{
cout << " Regrouping commands \n" << flush;
info(" Regrouping commands");
regroup();
}
}

View File

@ -252,7 +252,7 @@ namespace fwcompiler {
public:
PolicyCompiler_iosacl(libfwbuilder::FWObjectDatabase *_db,
const std::string &fwname,
libfwbuilder::Firewall *fw,
bool ipv6_policy,
fwcompiler::OSConfigurator *_oscnf);
virtual ~PolicyCompiler_iosacl() {}

View File

@ -60,6 +60,7 @@
#include <assert.h>
using namespace libfwbuilder;
using namespace fwcompiler;
using namespace std;
@ -198,7 +199,7 @@ string PolicyCompiler_iosacl::PrintRule::_printRule(PolicyRule *rule)
string rl=rule->getLabel();
if (write_comments)
if (write_comments && !compiler->inSingleRuleCompileMode())
{
if (rl!=current_rule_label1)
{
@ -219,6 +220,9 @@ string PolicyCompiler_iosacl::PrintRule::_printRule(PolicyRule *rule)
}
}
string err = rule->getStr(".error_msg");
if (!err.empty()) ruleout << "! " << err << endl;
/*
* all three rule elements contain exactly one object, which can
* be either group (in case processor CreateObjectGroups created
@ -280,7 +284,9 @@ string PolicyCompiler_iosacl::PrintRule::_printRule(PolicyRule *rule)
// aclstr << endl;
if (compiler->fw->getOptionsObject()->getBool("iosacl_use_acl_remarks"))
ruleout << acl->addRemark( rule->getLabel() );
{
ruleout << acl->addRemark(rule->getLabel(), rule->getComment());
}
ruleout << acl->addLine(aclstr.str());
@ -355,8 +361,8 @@ string PolicyCompiler_iosacl::PrintRule::_printIPServiceOptions(PolicyRule *r)
{
if (ip->getBool("lsrr") || ip->getBool("ssrr") || ip->getBool("rr"))
compiler->abort(
string("Source routing options match is not supported. Rule ") +
r->getLabel());
r,
"Source routing options match is not supported.");
if (srv->getBool("fragm") || srv->getBool("short_fragm"))
return "fragments ";
@ -395,7 +401,7 @@ string PolicyCompiler_iosacl::PrintRule::_printDstService(Service *srv)
if (TCPService::isA(srv) && srv->getBool("established"))
str << "established ";
if (ICMPService::isA(srv) && srv->getInt("type")!=-1)
if ((ICMPService::isA(srv) || ICMP6Service::isA(srv)) && srv->getInt("type")!=-1)
str << srv->getStr("type") << " ";
if (CustomService::isA(srv))

View File

@ -65,11 +65,11 @@ using namespace std;
string PolicyCompiler_pix::myPlatformName() { return "pix"; }
PolicyCompiler_pix::PolicyCompiler_pix(FWObjectDatabase *_db,
const std::string &fwname,
Firewall *fw,
bool ipv6_policy,
OSConfigurator *_oscnf,
NATCompiler_pix *_natcmp) :
PolicyCompiler_cisco(_db, fwname, ipv6_policy, _oscnf)
PolicyCompiler_cisco(_db, fw, ipv6_policy, _oscnf)
{
natcmp=_natcmp;
resetinbound=false;
@ -88,93 +88,99 @@ int PolicyCompiler_pix::prolog()
object_groups=new Group();
dbcopy->add( object_groups );
output << "!################" << endl;
if (platform=="fwsm")
if (!inSingleRuleCompileMode())
{
if (fw->getOptionsObject()->getBool("pix_use_manual_commit") )
output << "access-list mode manual" << endl;
else
output << "access-list mode auto" << endl;
}
output << "!################" << endl;
if ( fw->getOptionsObject()->getBool("pix_acl_substitution") )
{
/* Generate short temporary ACL and assign it to all
* interfaces. This ACL permits IPSEC (IP proto 50 and UDP port 500)
as well as ssh from given subnet to any.
*/
string temp_acl = "tmp_acl";
string temp_acl_addr = fw->getOptionsObject()->getStr("pix_acl_temp_addr");
if (temp_acl_addr.empty())
if (platform=="fwsm")
{
abort("Missing address for management host or subnet for temporary ACL.\nPlease enter it in the tab 'Script options' in 'Firewall Settings' dialog");
if (fw->getOptionsObject()->getBool("pix_use_manual_commit") )
output << "access-list mode manual" << endl;
else
output << "access-list mode auto" << endl;
}
string::size_type slash_idx = temp_acl_addr.find('/');
string addr = temp_acl_addr;
string netmask = "255.255.255.255";
if (slash_idx!=string::npos)
if ( fw->getOptionsObject()->getBool("pix_acl_substitution") )
{
addr = temp_acl_addr.substr(0,slash_idx);
netmask = temp_acl_addr.substr(slash_idx+1);
/* Generate short temporary ACL and assign it to all
* interfaces. This ACL permits IPSEC (IP proto 50 and UDP port 500)
as well as ssh from given subnet to any.
*/
string temp_acl = "tmp_acl";
string temp_acl_addr = fw->getOptionsObject()->getStr("pix_acl_temp_addr");
if (temp_acl_addr.empty())
{
abort(
"Missing address for management host or subnet for "
"temporary ACL. Enter it in the tab 'Script "
"options' in 'Firewall Settings' dialog");
}
string::size_type slash_idx = temp_acl_addr.find('/');
string addr = temp_acl_addr;
string netmask = "255.255.255.255";
if (slash_idx!=string::npos)
{
addr = temp_acl_addr.substr(0,slash_idx);
netmask = temp_acl_addr.substr(slash_idx+1);
try
{
if (netmask.find(".")!=string::npos)
{
InetAddr nm(netmask);
nm.isAny(); // to avoid warning abt unused var
} else
{
int nm_length;
istringstream str(netmask);
str >> nm_length;
InetAddr nm(nm_length);
netmask = nm.toString();
}
} catch(FWException &ex)
{
abort("Invalid netmask for management subnet: '"+netmask+"'");
}
}
try
{
if (netmask.find(".")!=string::npos)
{
InetAddr nm(netmask);
nm.isAny(); // to avoid warning abt unused var
} else
{
int nm_length;
istringstream str(netmask);
str >> nm_length;
InetAddr nm(nm_length);
netmask = nm.toString();
}
InetAddr(addr);
} catch(FWException &ex)
{
abort("Invalid netmask for management subnet: '"+netmask+"'");
abort("Invalid address for management subnet: '"+addr+"'");
}
string clearACLcmd = Resources::platform_res[platform]->getResourceStr(
string("/FWBuilderResources/Target/options/")+
"version_"+version+"/pix_commands/clear_acl");
output << endl;
output << clearACLcmd << " " << temp_acl << endl;
output << "access-list " << temp_acl
<< " permit ip "
<< addr << " " << netmask
<< " any "
<< endl;
output << "access-list " << temp_acl
<< " deny ip any any "
<< endl;
if (platform=="fwsm" &&
fw->getOptionsObject()->getBool("pix_use_manual_commit") )
output << "access-list commit" << endl;
output << endl;
output << "access-group " << temp_acl
<< " in interface outside" << endl;
output << "access-group " << temp_acl
<< " in interface inside" << endl;
output << endl;
}
try
{
InetAddr(addr);
} catch(FWException &ex)
{
abort("Invalid address for management subnet: '"+addr+"'");
}
string clearACLcmd = Resources::platform_res[platform]->getResourceStr(
string("/FWBuilderResources/Target/options/")+
"version_"+version+"/pix_commands/clear_acl");
output << endl;
output << clearACLcmd << " " << temp_acl << endl;
output << "access-list " << temp_acl
<< " permit ip "
<< addr << " " << netmask
<< " any "
<< endl;
output << "access-list " << temp_acl
<< " deny ip any any "
<< endl;
if (platform=="fwsm" &&
fw->getOptionsObject()->getBool("pix_use_manual_commit") )
output << "access-list commit" << endl;
output << endl;
output << "access-group " << temp_acl
<< " in interface outside" << endl;
output << "access-group " << temp_acl
<< " in interface inside" << endl;
output << endl;
}
return PolicyCompiler::prolog();
@ -191,7 +197,10 @@ bool PolicyCompiler_pix::checkVersionAndDynamicInterface::findDynamicInterface(
if (FWReference::cast(o)!=NULL) obj=FWReference::cast(o)->getPointer();
Interface *iface=Interface::cast(obj);
if (iface!=NULL && iface->isDyn() && (vers=="6.1" || vers=="6.2"))
compiler->abort("Dynamic interface can be used in the policy rule only in v6.3 or later. Rule "+rule->getLabel());
compiler->abort(
rule,
"Dynamic interface can be used in the policy rule only "
"in v6.3 or later.");
}
return true;
@ -238,14 +247,20 @@ bool PolicyCompiler_pix::SpecialServices::processNext()
if (s->getBool("rr") ||
s->getBool("ssrr") ||
s->getBool("ts") )
compiler->abort("PIX does not support checking for IP options in ACLs. Rule: "+rule->getLabel());
compiler->abort(
rule,
"PIX does not support checking for IP options in ACLs.");
}
if (TCPService::cast(s)!=NULL) {
if (s->getBool("ack_flag") ||
s->getBool("fin_flag") ||
s->getBool("rst_flag") ||
s->getBool("syn_flag") )
compiler->abort("PIX does not support checking for TCP options in ACLs. Rule: "+rule->getLabel());
compiler->abort(
rule,
"PIX does not support checking for TCP options in ACLs.");
}
tmp_queue.push_back(rule);
@ -332,7 +347,7 @@ bool PolicyCompiler_pix::replaceNATtedObjects::processNext()
{
PolicyRule *rule=getNext(); if (rule==NULL) return false;
PolicyCompiler_pix *pix_comp=dynamic_cast<PolicyCompiler_pix*>(compiler);
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
FWObject *rule_iface = compiler->dbcopy->findInIndex(rule->getInterfaceId());
// string rule_iface_id=rule->getInterfaceId();
// Address *src=compiler->getFirstSrc(rule);
@ -551,9 +566,9 @@ PIXGroup* PolicyCompiler_pix::CreateObjectGroups::findObjectGroup(RuleElement *r
bool PolicyCompiler_pix::CreateObjectGroups::processNext()
{
PolicyRule *rule=getNext(); if (rule==NULL) return false;
PolicyRule *rule=getNext(); if (rule==NULL) return false;
PolicyCompiler_pix *pix_comp=dynamic_cast<PolicyCompiler_pix*>(compiler);
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
Interface *rule_iface = Interface::cast(compiler->dbcopy->findInIndex(rule->getInterfaceId()));
assert(rule_iface);
RuleElement *re=RuleElement::cast(rule->getFirstByType(re_type));
@ -582,7 +597,6 @@ bool PolicyCompiler_pix::CreateObjectGroups::processNext()
rule_iface->getLabel()+"."+rule->getUniqueId()+"."+name_suffix);
pix_comp->object_groups->add(obj_group);
pix_comp->cacheObj(obj_group);
for (FWObject::iterator i1=re->begin(); i1!=re->end(); ++i1)
{
@ -604,10 +618,9 @@ bool PolicyCompiler_pix::CreateObjectGroups::processNext()
void PolicyCompiler_pix::compile()
{
cout << endl;
cout << " Compiling ruleset " << getSourceRuleSet()->getName();
if (ipv6) cout << ", IPv6";
cout << endl << flush;
string banner = " Compiling ruleset " + getSourceRuleSet()->getName();
if (ipv6) banner += ", IPv6";
info(banner);
try
{
@ -630,7 +643,8 @@ void PolicyCompiler_pix::compile()
addDefaultPolicyRule();
if ( fw->getOptionsObject()->getBool ("check_shading"))
if ( fw->getOptionsObject()->getBool ("check_shading") &&
! inSingleRuleCompileMode())
{
add( new Begin ("Detecting rule shadowing" ));
add( new printTotalNumberOfRules ( ));
@ -659,6 +673,9 @@ void PolicyCompiler_pix::compile()
add( new Begin (" Start processing rules" ));
add( new printTotalNumberOfRules ( ));
add( new singleRuleFilter());
add( new RejectAction ("check for action 'Reject'" ));
add( new recursiveGroupsInSrc( "check for recursive groups in SRC" ));
@ -803,7 +820,8 @@ void PolicyCompiler_pix::compile()
*/
runRuleProcessors();
} catch (FWException &ex) {
} catch (FWException &ex)
{
error(ex.toString());
exit(1);
}
@ -844,7 +862,7 @@ void PolicyCompiler_pix::epilog()
if ( fw->getOptionsObject()->getBool("pix_regroup_commands"))
{
cout << " Regrouping commands \n" << flush;
info(" Regrouping commands");
regroup();
}
}

View File

@ -310,7 +310,7 @@ namespace fwcompiler {
public:
PolicyCompiler_pix(libfwbuilder::FWObjectDatabase *_db,
const std::string &fwname,
libfwbuilder::Firewall *fw,
bool ipv6_policy,
fwcompiler::OSConfigurator *_oscnf,
NATCompiler_pix *_natcmp);

View File

@ -84,7 +84,7 @@ bool PolicyCompiler_pix::InterfaceAndDirection_v6::processNext()
if (interface_id==-1 && !icmp_cmd && !ssh_telnet_cmd && (
rule->getDirection()==PolicyRule::Inbound ||
rule->getDirection()==PolicyRule::Outbound)
) compiler->abort(string("Direction set without interface in rule ")+rule->getLabel());
) compiler->abort(rule, "Direction set without interface");
return true;
}
@ -104,7 +104,7 @@ bool PolicyCompiler_pix::InterfaceAndDirection_v6::processNext()
bool PolicyCompiler_pix::SplitDirection_v6::processNext()
{
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
FWObject *rule_iface = compiler->dbcopy->findInIndex(rule->getInterfaceId());
if (rule->getDirection()==PolicyRule::Both)
{
@ -173,7 +173,7 @@ bool PolicyCompiler_pix::EmulateOutboundACL_v6::processNext()
{
Helper helper(compiler);
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
FWObject *rule_iface = compiler->dbcopy->findInIndex(rule->getInterfaceId());
if (rule->getDirection()==PolicyRule::Outbound && rule_iface!=NULL)
{
@ -231,10 +231,14 @@ bool PolicyCompiler_pix::EmulateOutboundACL_v6::processNext()
<< "Address " << addr
<< " does not match address or network zone of any interface"
<< endl;
compiler->abort(str.str());
compiler->abort(rule, str.str());
}
} else
compiler->abort("Outbound ACLs are not supported and emulation is not activated: Rule "+rule->getLabel());
compiler->abort(
rule,
"Outbound ACLs are not supported and emulation is "
"not activated");
} else
tmp_queue.push_back(rule);
@ -322,7 +326,7 @@ bool PolicyCompiler_pix::assignRuleToInterface_v6::processNext()
<< "Address " << addr
<< " does not match address or network zone of any interface"
<< endl;
compiler->abort(str.str());
compiler->abort(rule, str.str());
}
} else {
@ -338,16 +342,18 @@ bool PolicyCompiler_pix::pickACL_v6::processNext()
{
PolicyCompiler_pix *pix_comp=dynamic_cast<PolicyCompiler_pix*>(compiler);
PolicyRule *rule=getNext(); if (rule==NULL) return false;
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
Interface *rule_iface = Interface::cast(compiler->dbcopy->findInIndex(rule->getInterfaceId()));
if(rule_iface==NULL)
{
compiler->abort("Missing interface assignment for rule "+rule->getLabel());
compiler->abort(
rule, "Missing interface assignment");
}
string acl_name= rule_iface->getLabel() + "_acl_in";
rule->setStr("acl",acl_name);
ciscoACL *acl = new ciscoACL(acl_name,rule_iface, "in");
ciscoACL *acl = new ciscoACL(acl_name, rule_iface, "in");
pix_comp->acls[acl_name] = acl;
acl->setWorkName(acl_name);

View File

@ -89,29 +89,34 @@ bool PolicyCompiler_pix::PrintObjectGroupsAndClearCommands::processNext()
slurp();
if (tmp_queue.size()==0) return false;
if ( compiler->fw->getOptionsObject()->getBool("pix_acl_basic") )
if (!compiler->inSingleRuleCompileMode())
{
compiler->output << clearACLcmd << endl;
compiler->output << clearOGcmd << endl;
}
// No need to output "clear" commands in single rule compile mode
if (compiler->fw->getOptionsObject()->getBool("pix_acl_substitution"))
{
for (map<string,ciscoACL*>::iterator i=pix_comp->acls.begin();
i!=pix_comp->acls.end(); ++i)
if ( compiler->fw->getOptionsObject()->getBool("pix_acl_basic") )
{
ciscoACL *acl=(*i).second;
compiler->output << clearACLcmd << " " << acl->workName() << endl;
compiler->output << clearACLcmd << endl;
compiler->output << clearOGcmd << endl;
}
compiler->output << clearOGcmd << endl;
compiler->output << endl;
}
if ( !compiler->fw->getOptionsObject()->getBool("pix_acl_no_clear") )
{
compiler->output << clearICMPcmd << endl;
compiler->output << clearTelnetcmd << endl;
compiler->output << clearSSHcmd << endl;
if (compiler->fw->getOptionsObject()->getBool("pix_acl_substitution"))
{
for (map<string,ciscoACL*>::iterator i=pix_comp->acls.begin();
i!=pix_comp->acls.end(); ++i)
{
ciscoACL *acl=(*i).second;
compiler->output << clearACLcmd << " " << acl->workName() << endl;
}
compiler->output << clearOGcmd << endl;
compiler->output << endl;
}
if ( !compiler->fw->getOptionsObject()->getBool("pix_acl_no_clear") )
{
compiler->output << clearICMPcmd << endl;
compiler->output << clearTelnetcmd << endl;
compiler->output << clearSSHcmd << endl;
}
}
for (FWObject::iterator i=pix_comp->object_groups->begin();
@ -146,7 +151,8 @@ bool PolicyCompiler_pix::PrintObjectGroupsAndClearCommands::processNext()
pix_comp->output << "object-group service "
<< og->getName() << " udp" << endl;
break;
default: compiler->abort("Unknown object group");
default:
compiler->abort("Unknown object group type");
}
for (FWObject::iterator i1=og->begin(); i1!=og->end(); ++i1)
@ -218,7 +224,7 @@ bool PolicyCompiler_pix::PrintObjectGroupsAndClearCommands::processNext()
break;
}
default:
compiler->abort("Unknown object group");
compiler->abort("Unknown object group type");
}
}
pix_comp->output << " exit" << endl << endl;
@ -420,7 +426,7 @@ string PolicyCompiler_pix::PrintRule::_printICMPCommand(PolicyRule *rule)
FWObject *srv=srvrel->front();
if (FWReference::cast(srv)!=NULL) srv=FWReference::cast(srv)->getPointer();
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
Interface *rule_iface = Interface::cast(compiler->dbcopy->findInIndex(rule->getInterfaceId()));
assert(rule_iface);
if ( PIXGroup::cast(srv)!=NULL &&
@ -473,7 +479,7 @@ string PolicyCompiler_pix::PrintRule::_printSSHTelnetCommand(PolicyRule *rule
RuleElementSrc *rel=rule->getSrc();
Service *srv=compiler->getFirstSrv(rule);
Interface *rule_iface = compiler->getCachedFwInterface(rule->getInterfaceId());
Interface *rule_iface = Interface::cast(compiler->dbcopy->findInIndex(rule->getInterfaceId()));
assert(rule_iface);
port=TCPUDPService::cast(srv)->getDstRangeStart();
@ -493,13 +499,15 @@ string PolicyCompiler_pix::PrintRule::_printSSHTelnetCommand(PolicyRule *rule
o1=FWReference::cast(o1)->getPointer();
Address *a=Address::cast(o1);
assert(a!=NULL);
str << _printSingleSSHTelnetCommand(port,a,rule_iface->getLabel());
str << _printSingleSSHTelnetCommand(
port, a, rule_iface->getLabel());
}
} else
{
Address *a=Address::cast(o);
assert(a!=NULL);
str << _printSingleSSHTelnetCommand(port,a,rule_iface->getLabel());
str << _printSingleSSHTelnetCommand(
port, a, rule_iface->getLabel());
}
}
@ -550,7 +558,7 @@ bool PolicyCompiler_pix::PrintRule::processNext()
string rl=rule->getLabel();
if (write_comments)
if (write_comments && !compiler->inSingleRuleCompileMode())
{
if (rl!=current_rule_label1)
{
@ -573,6 +581,9 @@ bool PolicyCompiler_pix::PrintRule::processNext()
compiler->output << comment.str();
string err = rule->getStr(".error_msg");
if (!err.empty()) compiler->output << "! " << err << endl;
if (rule->getBool("icmp_cmd"))
{
compiler->output << _printICMPCommand(rule);
@ -635,7 +646,7 @@ bool PolicyCompiler_pix::PrintRule::processNext()
if (compiler->fw->getOptionsObject()->getBool("pix_use_acl_remarks"))
{
compiler->output << acl->addRemark( rule->getLabel() );
compiler->output << acl->addRemark(rule->getLabel(), rule->getComment());
}
/*

View File

@ -84,8 +84,8 @@ bool RoutingCompiler_cisco::eliminateDuplicateRules::processNext()
msg = "Two of the sub rules created from the gui routing rules " +
rules_it->second + " and " + rule->getLabel() +
" are identical, skipping the second. " +
"Please revise them to avoid this warning";
compiler->warning( msg.c_str() );
"Revise them to avoid this warning";
compiler->warning(rule, msg.c_str() );
return true;
}

View File

@ -114,9 +114,9 @@ namespace fwcompiler
RoutingCompiler_cisco::PrintRule *printRule;
RoutingCompiler_cisco(libfwbuilder::FWObjectDatabase *_db,
const std::string &fwname, bool ipv6_policy,
libfwbuilder::Firewall *fw, bool ipv6_policy,
fwcompiler::OSConfigurator *_oscnf) :
RoutingCompiler(_db, fwname, ipv6_policy, _oscnf) {}
RoutingCompiler(_db, fw, ipv6_policy, _oscnf) {}
virtual int prolog();
virtual void compile();

View File

@ -90,7 +90,7 @@ bool RoutingCompiler_iosacl::ExpandMultipleAddressesExceptInterface::processNext
Address *gtw = Address::cast(
FWReference::cast(gtwrel->front())->getPointer());
if (gtw == NULL)
compiler->abort("Broken GTW in " + rule->getLabel());
compiler->abort(rule, "Broken GTW");
if (Interface::isA(gtw) && gtw->isChildOf(compiler->fw)) return true;
compiler->_expandAddr(rule, gtwrel);
return true;
@ -104,8 +104,7 @@ void RoutingCompiler_iosacl::compile()
{
printRule = new RoutingCompiler_iosacl::PrintRule("");
cout << " Compiling routing rules for "
<< fw->getName() << " ..." << endl << flush;
info(" Compiling routing rules for " + fw->getName());
try
{
@ -114,6 +113,8 @@ void RoutingCompiler_iosacl::compile()
add(new RoutingCompiler::Begin());
add(new printTotalNumberOfRules());
add( new singleRuleFilter());
add(new recursiveGroupsInRDst("Check for recursive Groups in RDst"));
add(new emptyGroupsInRDst("Check for empty Groups in RDst"));
add(new emptyRDstAndRItf("Check if RDst and RItf are both empty"));
@ -153,7 +154,8 @@ void RoutingCompiler_iosacl::compile()
runRuleProcessors();
} catch (FWException &ex) {
} catch (FWException &ex)
{
error(ex.toString());
exit(1);
}

View File

@ -73,9 +73,9 @@ namespace fwcompiler
public:
RoutingCompiler_iosacl(libfwbuilder::FWObjectDatabase *_db,
const std::string &fwname, bool ipv6_policy,
libfwbuilder::Firewall *fw, bool ipv6_policy,
fwcompiler::OSConfigurator *_oscnf) :
RoutingCompiler_cisco(_db, fwname, ipv6_policy, _oscnf) {};
RoutingCompiler_cisco(_db, fw, ipv6_policy, _oscnf) {};
virtual int prolog();
virtual void compile();

View File

@ -77,18 +77,18 @@ bool RoutingCompiler_iosacl::PrintRule::processNext()
string::size_type c1, c2;
c1 = 0;
if (rl != current_rule_label)
if (!compiler->inSingleRuleCompileMode() && rl != current_rule_label)
{
compiler->output << "! " << endl;
compiler->output << "! Rule " << rl << endl;
compiler->output << "! " << endl;
compiler->output << "! \"Routing rule " << rl << "\"" << endl;
compiler->output << "! " << endl;
compiler->output << "! " << endl;
compiler->output << "! Rule " << rl << endl;
compiler->output << "! " << endl;
compiler->output << "! \"Routing rule " << rl << "\"" << endl;
compiler->output << "! " << endl;
}
if( rule->getRuleType() != RoutingRule::MultiPath )
{
if (rl != current_rule_label)
if (!compiler->inSingleRuleCompileMode() && rl != current_rule_label)
{
while ( (c2 = comm.find('\n',c1)) != string::npos )
{
@ -96,10 +96,8 @@ bool RoutingCompiler_iosacl::PrintRule::processNext()
c1 = c2 + 1;
}
compiler->output << "! " << comm.substr(c1) << endl;
compiler->output << "! " << endl;
current_rule_label=rl;
current_rule_label = rl;
}
string command_line = RoutingRuleToString(rule);

View File

@ -68,8 +68,7 @@ void RoutingCompiler_pix::compile()
{
printRule = new RoutingCompiler_pix::PrintRule("");
cout << " Compiling routing rules for "
<< fw->getName() << " ..." << endl << flush;
info(" Compiling routing rules for " + fw->getName());
try
{
@ -78,6 +77,8 @@ void RoutingCompiler_pix::compile()
add(new RoutingCompiler::Begin());
add(new printTotalNumberOfRules());
add( new singleRuleFilter());
add(new recursiveGroupsInRDst("Check for recursive Groups in RDst"));
add(new emptyGroupsInRDst("Check for empty Groups in RDst"));
add(new emptyRDstAndRItf("Check if RDst and RItf are both empty"));
@ -115,7 +116,8 @@ void RoutingCompiler_pix::compile()
runRuleProcessors();
} catch (FWException &ex) {
} catch (FWException &ex)
{
error(ex.toString());
exit(1);
}

View File

@ -52,9 +52,9 @@ namespace fwcompiler {
public:
RoutingCompiler_pix(libfwbuilder::FWObjectDatabase *_db,
const std::string &fwname, bool ipv6_policy,
libfwbuilder::Firewall *fw, bool ipv6_policy,
fwcompiler::OSConfigurator *_oscnf) :
RoutingCompiler_cisco(_db, fwname, ipv6_policy, _oscnf) {};
RoutingCompiler_cisco(_db, fw, ipv6_policy, _oscnf) {};
virtual int prolog();
virtual void compile();

View File

@ -69,18 +69,18 @@ bool RoutingCompiler_pix::PrintRule::processNext()
string::size_type c1, c2;
c1 = 0;
if (rl != current_rule_label)
if (!compiler->inSingleRuleCompileMode() && rl != current_rule_label)
{
compiler->output << "! " << endl;
compiler->output << "! Rule " << rl << endl;
compiler->output << "! " << endl;
compiler->output << "! \"Routing rule " << rl << "\"" << endl;
compiler->output << "! " << endl;
compiler->output << "! " << endl;
compiler->output << "! Rule " << rl << endl;
compiler->output << "! " << endl;
compiler->output << "! \"Routing rule " << rl << "\"" << endl;
compiler->output << "! " << endl;
}
if( rule->getRuleType() != RoutingRule::MultiPath )
{
if (rl != current_rule_label)
if (!compiler->inSingleRuleCompileMode() && rl != current_rule_label)
{
while ( (c2 = comm.find('\n',c1)) != string::npos )
{
@ -88,9 +88,7 @@ bool RoutingCompiler_pix::PrintRule::processNext()
c1 = c2 + 1;
}
compiler->output << "! " << comm.substr(c1) << endl;
compiler->output << "! " << endl;
current_rule_label=rl;
}

View File

@ -9,16 +9,51 @@ SOURCES = PolicyCompiler_cisco.cpp \
RoutingCompiler_cisco.cpp \
RoutingCompiler_cisco_writers.cpp \
ACL.cpp \
Helper.cpp
Helper.cpp \
OSConfigurator_ios.cpp \
CompilerDriver_iosacl.cpp \
CompilerDriver_iosacl_run.cpp \
PolicyCompiler_iosacl.cpp \
PolicyCompiler_iosacl_writers.cpp \
RoutingCompiler_iosacl.cpp \
RoutingCompiler_iosacl_writers.cpp \
CompilerDriver_pix.cpp \
CompilerDriver_pix_run.cpp \
NATCompiler_pix.cpp \
NATCompiler_pix_writers.cpp \
OSConfigurator_pix_os.cpp \
OSConfigurator_pix_os_fixups.cpp \
PIXObjectGroup.cpp \
PolicyCompiler_pix.cpp \
PolicyCompiler_pix_writers.cpp \
PolicyCompiler_pix_v6_acls.cpp \
RoutingCompiler_pix.cpp \
RoutingCompiler_pix_writers.cpp
HEADERS = ../../config.h \
ACL.h \
Helper.h \
PolicyCompiler_cisco.h \
RoutingCompiler_cisco.h
RoutingCompiler_cisco.h \
CompilerDriver_iosacl.h \
OSConfigurator_ios.h \
PolicyCompiler_iosacl.h \
CompilerDriver_pix.h \
NATCompiler_pix.h \
OSConfigurator_pix_os.h \
PIXObjectGroup.h \
PolicyCompiler_pix.h \
RoutingCompiler_pix.h \
!macx:LIBS += $$LIBS_FWCOMPILER
# macx:LIBS += -L../../../libfwbuilder2-2.0.0/src/fwcompiler -lfwcompiler-2.0
macx:LIBS += $$LIBS_FWCOMPILER
INCLUDEPATH += ../compiler_lib
win32:LIBS += ../compiler_lib/release/compilerdriver.lib
!win32:LIBS += ../compiler_lib/libcompilerdriver.a
win32:PRE_TARGETDEPS = ../compiler_lib/release/compilerdriver.lib
!win32:PRE_TARGETDEPS = ../compiler_lib/libcompilerdriver.a
CONFIG += staticlib

View File

@ -1,6 +1,8 @@
#include "../../config.h"
#include <qglobal.h>
#if defined(Q_OS_MACX) || defined(Q_OS_WIN32)
# include <qsettings.h>
# include <QDir>

View File

@ -0,0 +1,901 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include "../../build_num"
#include <fstream>
#include <iostream>
#include <iomanip>
#include <set>
#include <algorithm>
#include <functional>
#ifndef _WIN32
# include <unistd.h>
# include <pwd.h>
#else
# include <direct.h>
# include <stdlib.h>
# include <io.h>
#endif
#include "CompilerDriver.h"
#include "fwbuilder/FWObject.h"
#include "fwbuilder/FWObjectDatabase.h"
#include "fwbuilder/FWException.h"
#include "fwbuilder/Cluster.h"
#include "fwbuilder/ClusterGroup.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/Interface.h"
#include "fwbuilder/IPv4.h"
#include "fwbuilder/IPv6.h"
#include "fwbuilder/Rule.h"
#include "fwbuilder/Policy.h"
#include "fwbuilder/NAT.h"
#include "fwbuilder/Routing.h"
#include "fwbuilder/Resources.h"
#include "fwbuilder/StateSyncClusterGroup.h"
#include "fwbuilder/FailoverClusterGroup.h"
#include "fwcompiler/Compiler.h"
#include <QStringList>
using namespace std;
using namespace libfwbuilder;
using namespace fwcompiler;
CompilerDriver::CompilerDriver(FWObjectDatabase *db) : BaseCompiler()
{
fwbdebug = 0;
filename = "";
wdir = "";
fwobjectname = "";
fw_file_name = "";
dl = 0;
drp = -1;
rule_debug_on = false;
single_rule_compile_on = false;
drn = -1;
verbose = 0;
have_dynamic_interfaces = false;
ipv4_run = true;
ipv6_run = true;
fw_by_id = false;
objdb = new FWObjectDatabase(*db);
prolog_done = false;
epilog_done = false;
}
CompilerDriver::~CompilerDriver()
{
delete objdb;
}
// create a copy of itself, including objdb
CompilerDriver* CompilerDriver::clone()
{
return new CompilerDriver(objdb);
}
bool CompilerDriver::configure(const QStringList &args)
{
QString last_arg;
for (int idx=0; idx < args.size(); idx++)
{
QString arg = args.at(idx);
last_arg = arg;
if (arg == "-i")
{
fw_by_id = true;
continue;
}
if (arg == "-v")
{
verbose++;
continue;
}
if (arg == "-4")
{
ipv4_run = true;
ipv6_run = false;
continue;
}
if (arg == "-6")
{
ipv4_run = false;
ipv6_run = true;
continue;
}
if (arg == "-d")
{
idx++;
wdir = string(args.at(idx).toLatin1().constData());
continue;
}
if (arg == "-f")
{
idx++;
filename = string(args.at(idx).toLatin1().constData());
continue;
}
if (arg == "-o")
{
idx++;
fw_file_name = args.at(idx);
continue;
}
if (arg == "-O")
{
// parameter is ',' separated list of <member fw object ID>,
// <corresponding output file name>
// All separated by commands, the id and file name just
// follow one after another.
idx++;
QString member_files = args.at(idx);
QStringList mf_list = member_files.split(",");
QStringListIterator it(mf_list);
while (it.hasNext())
{
QString fw_id = it.next();
if (it.hasNext())
{
QString file_name = it.next();
member_file_names[fw_id] = file_name;
} else
{
QString err("Misconfigured -O option, missing file "
"name component for ID %1");
abort(err.arg(fw_id).toStdString());
}
}
continue;
}
if (arg == "-xt")
{
setTestMode();
info("*** Running in test mode, fatal errors are treated as warnings");
continue;
}
if (arg == "-xp")
{
idx++;
bool ok = false;
drp = args.at(idx).toInt(&ok);
if (!ok) return false;
rule_debug_on = true;
continue;
}
if (arg == "-xn")
{
idx++;
bool ok = false;
drn = args.at(idx).toInt(&ok);
if (!ok) return false;
rule_debug_on = true;
continue;
}
if (arg == "-s")
{
idx++;
single_rule_id = args.at(idx).toStdString();
single_rule_compile_on = true;
continue;
}
}
fwobjectname = last_arg;
if (wdir.empty()) wdir="./";
return true;
}
void CompilerDriver::chDir()
{
if (
#ifdef _WIN32
_chdir(wdir.c_str())
#else
chdir(wdir.c_str())
#endif
) {
cerr << "Can't change to: " << wdir << endl;
exit(1);
}
}
void CompilerDriver::commonChecks(Firewall *fw)
{
if (Cluster::isA(fw))
{
Cluster *cluster = Cluster::cast(fw);
// Check #1 : make sure output file names are different in member
// firewalls
set<string> output_file_names;
list<Firewall*> members;
cluster->getMembersList(members);
for (list<Firewall*>::iterator it=members.begin(); it!=members.end(); ++it)
{
FWOptions *fwopt = (*it)->getOptionsObject();
string ofname = fwopt->getStr("output_file");
if (ofname.empty()) continue;
if (output_file_names.count(ofname) > 0)
{
string err =
string("Member firewalls use the same output file name ") +
ofname;
throw FWException(err);
}
output_file_names.insert(ofname);
}
}
}
void CompilerDriver::commonChecks2(Cluster *cluster, Firewall *fw)
{
QString current_firewall_name = fw->getName().c_str();
string host_os = fw->getStr("host_OS");
if (cluster)
{
// firewall is a member of a cluster.
// Rely on the caller to make sure this firewall is really a member
// of this cluster. Do not perform redundant check here.
processStateSyncGroups(cluster, fw);
// some initial sanity checks
validateClusterGroups(cluster);
}
list<FWObject*> interfaces = fw->getByTypeDeep(Interface::TYPENAME);
for (list<FWObject*>::iterator i=interfaces.begin(); i!=interfaces.end(); ++i)
{
Interface *iface = Interface::cast(*i);
assert(iface);
string::size_type n;
if ( (n=iface->getName().find("*"))!=string::npos)
{
/* this is a special 'wildcard' interface. Its name must end with '*',
* it must be dynamic and should not have a child IPv4 or
* physAddress object
*/
if (n!=iface->getName().length()-1)
{
QString err("'*' must be the last character in "
"the wildcard's interface name: '%1'.");
abort(fw, NULL, NULL,
err.arg(iface->getName().c_str()).toStdString());
}
/*
removed test to implement RFE #837238: "unnummbered wildcard interfaces"
if (!iface->isDyn())
{
char errstr[256];
sprintf(errstr,
_("Wildcard interface '%s' must be dynamic."),
iface->getName().c_str() );
throw FWException(errstr);
}
*/
list<FWObject*> l3=iface->getByType(physAddress::TYPENAME);
if (l3.size()>0)
{
QString err("Wildcard interface '%1' should not have "
"physcal address object attached to it. "
"The physical address object will be ignored.");
error(fw, NULL, NULL,
err.arg(iface->getName().c_str()).toStdString());
for (list<FWObject*>::iterator j=l3.begin(); j!=l3.end(); ++j)
iface->remove(*j);
}
}
if ( iface->isUnnumbered()) continue;
if ( iface->isDyn())
{
have_dynamic_interfaces=true;
iface->setBool("use_var_address",true);
list<FWObject*> l3=iface->getByType(IPv4::TYPENAME);
if (l3.size()>0)
{
for (list<FWObject*>::iterator j=l3.begin(); j!=l3.end(); ++j)
if ( objdb->findAllReferences(*j).size()!=0 )
{
QString err("Dynamic interface %1 has IP address "
"that is used in the firewall policy rule.");
abort(fw, NULL, NULL,
err.arg(iface->getName().c_str()).toStdString());
}
QString err("Dynamic interface %1 should not have an "
"IP address object attached to it. "
"This IP address object will be ignored.");
error(fw, NULL, NULL,
err.arg(iface->getName().c_str()).toStdString());
for (list<FWObject*>::iterator j=l3.begin(); j!=l3.end(); ++j)
iface->remove(*j);
}
} else
{
bool no_addr_ok = false;
if (iface->getOptionsObject()->getBool("cluster_interface"))
{
// cluster interface with failover type heartbeat or
// openais may have no ip address. Other failover
// types require an address.
FWObject *failover_group =
iface->getFirstByType(FailoverClusterGroup::TYPENAME);
if (failover_group)
{
string failover_type = failover_group->getStr("type");
no_addr_ok = Resources::os_res[host_os]->getResourceBool(
"/FWBuilderResources/Target/protocols/" + failover_type + "/no_ip_ok");
}
}
list<FWObject*> all_addr = iface->getByType(IPv4::TYPENAME);
list<FWObject*> all_ipv6 = iface->getByType(IPv6::TYPENAME);
all_addr.insert(all_addr.begin(), all_ipv6.begin(), all_ipv6.end());
if (iface->isRegular() &&
!no_addr_ok &&
all_addr.empty() &&
all_ipv6.empty())
{
QString err("Missing IP address for interface %1");
abort(fw, NULL, NULL,
err.arg(iface->getName().c_str()).toStdString());
}
for (list<FWObject*>::iterator j = all_addr.begin();
j != all_addr.end(); ++j)
{
const InetAddr *ip_addr = Address::cast(*j)->getAddressPtr();
if (ip_addr && ip_addr->isAny())
{
QString err("Interface %1 (id=%2) has IP address %3.");
abort(fw, NULL, NULL,
err.arg(iface->getName().c_str())
.arg(FWObjectDatabase::getStringId(
iface->getId()).c_str())
.arg(ip_addr->toString().c_str()).toStdString());
}
}
}
}
}
Firewall* CompilerDriver::locateObject()
{
Firewall* obj;
if (fw_by_id)
{
// fwobjectname is actually object id
obj = Firewall::cast(
objdb->findInIndex(
objdb->getIntId(fwobjectname.toAscii().constData())));
//fwobjectname = obj->getName().c_str();
}
else
obj = objdb->findFirewallByName(fwobjectname.toUtf8().constData());
return obj;
}
/**
* Determine output file name. If compiling standalone firewall, the
* name can be enforced via -o command line switch in which case it
* is in fw_file_name already. If not, determine automatically using
* firewall name.
*
* If compiling a cluster, the name could have been enforced via -O
* command line switch, in which case it will be found in
* member_file_names. If not, determine automatically using member
* firewall name.
*
* Returns determined output file name
*/
QString CompilerDriver::determineOutputFileName(Firewall *current_fw,
bool cluster_member,
const QString &ext)
{
QString current_firewall_name = current_fw->getName().c_str();
if (!cluster_member)
{
// standalone firewall
if (fw_file_name.isEmpty())
{
return current_firewall_name + ext;
} else
return fw_file_name;
}
// member of a cluster
QString fw_id = objdb->getStringId(current_fw->getId()).c_str();
if (member_file_names.contains(fw_id))
return member_file_names[fw_id];
else
return current_firewall_name + ext;
}
/* Find rulesets that belong to other firewall objects but are
* referenced by rules of this firewall using action Branch.
*
* Important: rulesets that belong to other firewalls may be marked as
* "top rulesets", which means they should be translated into the
* built-in chains INPUT/OUTPUT/FORWARD rather then into named chain
* with the name the same as the name of the ruleset. However this
* does not make sense if we want to jump to that ruleset from a rule
* from a ruleset that belongs to the firewall we are compiling. If we
* compile such "foreighn" ruleset as "top ruleset", then we do not
* create chain we would jump to. To avoid this will reset "top
* ruleset" flag of rulesets of other firewalls referenced by
* branching rules of the firewall being compiled.
*/
void CompilerDriver::findImportedRuleSets(Firewall *fw,
list<FWObject*> &all_policies)
{
list<FWObject*> imported_policies;
for (list<FWObject*>::iterator i=all_policies.begin();
i!=all_policies.end(); ++i)
{
for (list<FWObject*>::iterator r=(*i)->begin(); r!=(*i)->end(); ++r)
{
PolicyRule *rule = PolicyRule::cast(*r);
RuleSet *ruleset = NULL;
if (rule->getAction() == PolicyRule::Branch &&
(ruleset = rule->getBranch())!=NULL &&
!ruleset->isChildOf(fw))
{
ruleset->setTop(false);
imported_policies.push_back(ruleset);
}
}
}
if (imported_policies.size() > 0)
all_policies.insert(all_policies.end(),
imported_policies.begin(), imported_policies.end());
}
string CompilerDriver::run(const std::string&, const std::string&, const std::string&)
{
return "";
}
void CompilerDriver::validateClusterGroups(Cluster *cluster)
{
string host_os = cluster->getStr("host_OS");
Resources* os_res = Resources::os_res[host_os];
if (os_res==NULL) return;
// check if state sync groups are of supported type
list<string> state_sync_protocols;
os_res->getResourceStrList("/FWBuilderResources/Target/protocols/state_sync",
state_sync_protocols);
for (FWObjectTypedChildIterator it = cluster->findByType(StateSyncClusterGroup::TYPENAME);
it != it.end(); ++it)
{
string state_sync_type = (*it)->getStr("type");
if (!isSupported(&state_sync_protocols, state_sync_type))
{
QString err("State sync group type %1 is not supported");
throw FWException(err.arg(state_sync_type.c_str()).toStdString());
}
}
// same for failover groups
list<string> failover_protocols;
os_res->getResourceStrList("/FWBuilderResources/Target/protocols/failover",
failover_protocols);
list<FWObject*> failover_groups = cluster->getByTypeDeep(FailoverClusterGroup::TYPENAME);
for (list<FWObject*>::iterator it = failover_groups.begin(); it != failover_groups.end(); ++it)
{
string failover_type = (*it)->getStr("type");
if (!isSupported(&failover_protocols, failover_type))
{
QString err("Failover group type %1 is not supported");
throw FWException(err.arg(failover_type.c_str()).toStdString());
}
}
}
bool CompilerDriver::isSupported(list<string> *protocols, const string &cluster_group_type)
{
bool supported = false;
for (list<string>::iterator supported_types=protocols->begin();
supported_types!=protocols->end(); ++supported_types)
{
QString str = QString(supported_types->c_str());
QStringList pl = str.split(",");
if (cluster_group_type.c_str() == pl[0])
{
supported = true;
break;
}
}
return supported;
}
QTextStream& operator<< (QTextStream &text_stream, const string &str)
{
text_stream << str.c_str();
return text_stream;
}
/*
* Add indentation to each line in txt
*/
string CompilerDriver::indent(int n_spaces, const string &txt)
{
ostringstream output;
istringstream str(txt);
char line[65536];
while (!str.eof())
{
str.getline(line, sizeof(line));
output << std::setw(n_spaces) << std::setfill(' ') << " " << line << endl;
}
return output.str();
}
QString CompilerDriver::indent(int n_spaces, const QString &txt)
{
QString fill = QString("%1").arg("", n_spaces, ' ');
return prepend(fill, txt);
}
QString CompilerDriver::prepend(const QString &prep, const QString &txt)
{
QStringList str;
foreach (QString line, txt.split("\n"))
{
str.append(line.prepend(prep));
}
return str.join("\n");
}
void CompilerDriver::mergeRuleSets(Cluster *cluster, Firewall *fw,
const string &type)
{
list<FWObject*> all_rulesets = cluster->getByType(type);
for (list<FWObject*>::iterator p = all_rulesets.begin();
p != all_rulesets.end(); ++p)
{
FWObject *ruleset = *p;
FWObject::iterator i = std::find_if(fw->begin(), fw->end(),
FWObjectNameEQPredicate(ruleset->getName()));
if (i!=fw->end() && (*i)->getTypeName() == type)
{
FWObject *fw_ruleset = *i;
/*
* fw has rule set with the same name. See ticket #372
* for details.
*
* if member firewall has rule set of the same type and
* with the same name as cluster and firewall's rule set
* is not empty, cluster's rule set is ignored and warning
* is ussued
*
* if matching firewall's rule set is empty, cluster's
* rule set is used
*
* all rule sets from the cluster that do not have
* matching ones in the member firewall are merged into
* the firewall before compilation and used.
*/
if (fw_ruleset->size() > 0)
{
QString err("ignoring cluster rule set \"%1\" "
"because member firewall \"%2\" "
"has rule set with the same name.");
warning(fw, fw_ruleset, NULL,
err.arg(fw_ruleset->getName().c_str())
.arg(fw->getName().c_str()).toStdString());
} else
{
fw_ruleset->clear();
fw_ruleset->duplicate(ruleset, false);
}
} else
{
// fw does not have rule set with this name
fw->addCopyOf(ruleset, false);
}
}
}
/*
* 1. Iterate over all fw interfaces and check if they are referenced in a
* ClusterGroup.
* -> if yes then make copy of vrrp interface and set BASEDEV accordingly
* 2. clear Policy, NAT & Routing rules of the firewall, then copy cluster
* policy, NAT and routing rules.
*/
void CompilerDriver::populateClusterElements(Cluster *cluster, Firewall *fw)
{
if (cluster==NULL) return;
// int addedPolicies = 0;
set<string> state_sync_types;
checkCluster(cluster);
for (FWObjectTypedChildIterator it = cluster->findByType(StateSyncClusterGroup::TYPENAME);
it != it.end(); ++it)
{
StateSyncClusterGroup *state_sync_group = StateSyncClusterGroup::cast(*it);
/* For the state syncing cluster group, hierarchy looks like this:
* Cluster->StateSyncClusterGroup->ObjectRef
*/
string grp_type = state_sync_group->getStr("type");
if (state_sync_types.count(grp_type) > 0)
throw FWException("Several state synchronization groups of the same type in one cluster object.");
state_sync_types.insert(grp_type);
for (FWObjectTypedChildIterator it =
state_sync_group->findByType(FWObjectReference::TYPENAME);
it != it.end(); ++it)
{
Interface *iface = Interface::cast(FWObjectReference::getObject(*it));
assert(iface);
//processStateSyncGroup(cluster, fw, state_sync_group, iface);
iface->getOptionsObject()->setBool("state_sync_group_member", true);
iface->getOptionsObject()->setStr(
"state_sync_group_id",
FWObjectDatabase::getStringId(state_sync_group->getId()));
string master_id = state_sync_group->getStr("master_iface");
string iface_str_id = FWObjectDatabase::getStringId(iface->getId());
iface->getOptionsObject()->setBool("state_sync_master",
master_id == iface_str_id);
fw->getOptionsObject()->setBool("cluster_member", true);
}
}
/* For VRRP references the hierarchy is as follows:
* Cluster->Interface->FailoverClusterGroup->ObjectRef
*/
FWObjectTypedChildIterator cl_iface = cluster->findByType(Interface::TYPENAME);
for (; cl_iface != cl_iface.end(); ++cl_iface)
{
FailoverClusterGroup *failover_group =
FailoverClusterGroup::cast(
(*cl_iface)->getFirstByType(FailoverClusterGroup::TYPENAME));
if (failover_group)
{
for (FWObjectTypedChildIterator it =
failover_group->findByType(FWObjectReference::TYPENAME);
it != it.end(); ++it)
{
Interface *iface = Interface::cast(FWObjectReference::getObject(*it));
assert(iface);
// We need to do some sanity checks of cluster
// interfaces for VRRP and then add them to the
// firewall object.
// These actions are very generic and have nothing specific
// to VRRP. Unless new protocol is added that requires
// something radically different, will always call this method
// for failover groups.
//if (failover_group->getStr("type") == "vrrp")
if (iface->isChildOf(fw))
copyFailoverInterface(cluster, fw, failover_group, iface);
}
} else
{
// cluster interface without failover group
// is this a loopback interface ?
Interface *cluster_interface = Interface::cast(*cl_iface);
if (cluster_interface->isLoopback())
{
/* Add copy of the interface from the cluster to the
* firewall object so that when it is encountered in
* the "intrface" rule element of its rules, it
* belongs to the firewall and is therefore valid.
*/
Interface* new_cl_if = Interface::cast(fw->addCopyOf(cluster_interface, true));
assert(new_cl_if != NULL);
new_cl_if->getOptionsObject()->setBool("cluster_interface", true);
}
}
}
mergeRuleSets(cluster, fw, Policy::TYPENAME);
mergeRuleSets(cluster, fw, NAT::TYPENAME);
mergeRuleSets(cluster, fw, Routing::TYPENAME);
// finally need to remember cluster object ID so that compiler can later
// associate it in rules with the firewall.
//
// The alternative is to find all references to the cluster object
// in rules and replace them with refs to the firewall. That could
// be done either in prolog or in a special rule processor. It is
// _much_ cheaper to just remember cluster ID though.
fw->setInt("parent_cluster_id", cluster->getId());
// return addedPolicies;
}
/*
* Perform checks for fialover interfaces and their addresses, add a
* copy of failover interface form the cluster to the firewall object.
*
* This method assumes the following:
*
* - Failover interface owns its ip address which is different from
* addresses of either firewall
*
* - address of the failover interface must be on the same subnet as
* addresses of the firewalls (perhaps this restriction can be
* lifted? Was originally implemented by Secunet folks like this)
*/
void CompilerDriver::copyFailoverInterface(Cluster *cluster,
Firewall *fw,
FailoverClusterGroup *cluster_group,
Interface *iface)
{
Interface* cluster_if = Interface::cast(cluster_group->getParent());
assert(cluster_if != NULL);
string cluster_if_name = cluster_if->getName();
/* Check that VRRP interface and fw interface are in same subnet.
* Exception: if interface is dynamic and does not have an ip address in
* fwbuilder configuration, assume it is ok.
*/
if (iface->isRegular())
{
const Address *iface_addr = iface->getAddressObject();
// even regular interface may have no address if user forgot
// to add one, so check if iface_addr == NULL
// Also check if cluster interface has ip address, it does not
// always need one.
if (iface_addr && cluster_if->getAddressObject() &&
!isReachable(cluster_if->getAddressObject(), iface_addr->getAddressPtr())
)
{
QString err("%1 and %2 are not on the same subnet");
warning(fw, NULL, NULL,
err.arg(cluster_if_name.c_str()).arg(iface->getName().c_str()).toStdString());
}
}
assert(fw->getOptionsObject() != NULL);
iface->getOptionsObject()->setStr(
"failover_group_id", FWObjectDatabase::getStringId(cluster_group->getId()));
/* Add copy of the cluster interface to the firewall object
*
* While adding a copy of cluster interface to the firewall, make
* sure it has new unique ID instead of a copy of the ID of the
* cluster's interface object. If the ID is the same,
* RuleElementItf::validateChild() finds clusters' interface which
* is not a child of the firewall object and therefore is
* rejected.
*/
Interface* new_cl_if = Interface::cast(fw->addCopyOf(cluster_if, true));
assert(new_cl_if != NULL);
new_cl_if->getOptionsObject()->setBool("cluster_interface", true);
new_cl_if->getOptionsObject()->setStr("base_device", iface->getName());
new_cl_if->getOptionsObject()->setStr(
"base_interface_id", FWObjectDatabase::getStringId(iface->getId()));
/* Set master property if interface is referenced
* as master_iface
*/
string master_id = cluster_group->getStr("master_iface");
string iface_str_id = FWObjectDatabase::getStringId(iface->getId());
new_cl_if->getOptionsObject()->setBool("failover_master",
master_id == iface_str_id);
fw->getOptionsObject()->setBool("cluster_member", true);
/* Add copy of firewall's real interface to the cluster to make sure
* compiler recognizes it when it encounters cluster object in rules.
* This fixes #15 (makes compiler choose correct chains)
*/
cluster->addCopyOf(iface, true);
}
/*
* Verify that there is at least one Cluster interface and that all
* have unique names and IP addresses.
*/
int CompilerDriver::checkCluster(Cluster* cluster)
{
assert(cluster != NULL);
FWObjectTypedChildIterator cluster_ifaces = cluster->findByType(Interface::TYPENAME);
if (cluster_ifaces == cluster_ifaces.end())
{
/* No configured cluster interface found */
abort(cluster, NULL, NULL, "The cluster has no interfaces.");
}
for (; cluster_ifaces != cluster_ifaces.end(); ++cluster_ifaces)
{
string iface_name = Interface::cast(*cluster_ifaces)->getName();
const InetAddr* iface_address = Interface::cast(*cluster_ifaces)->getAddressPtr();
if (iface_address==NULL) continue; // cluster interface with no address
FWObjectTypedChildIterator other_ifaces = cluster_ifaces;
for (++other_ifaces; other_ifaces != cluster_ifaces.end(); ++other_ifaces)
{
if (iface_name == Interface::cast(*other_ifaces)->getName())
{
QString err("Found duplicate cluster interface %1");
abort(cluster, NULL, NULL, err.arg(iface_name.c_str()).toStdString());
}
const InetAddr *other_iface_address = Interface::cast(*other_ifaces)->getAddressPtr();
if (other_iface_address==NULL) continue; // cluster interface with no address
if (*iface_address == *other_iface_address)
{
QString err("Found duplicate cluster interface address %1");
abort(cluster, NULL, NULL, err.arg(iface_address->toString().c_str()).toStdString());
}
}
}
return 0;
}
bool CompilerDriver::isReachable(const Address* const client,
const InetAddr* const server)
{
const InetAddr *addr = client->getAddressPtr();
const InetAddr *netm = client->getNetmaskPtr();
if (addr)
{
InetAddrMask fw_net(*addr, *netm);
if (fw_net.belongs(*server))
return true;
}
return false;
}

View File

@ -0,0 +1,187 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef __COMPILER_DRIVER_HH__
#define __COMPILER_DRIVER_HH__
#include "fwcompiler/BaseCompiler.h"
#include <string>
#include <sstream>
#include <QTextStream>
#include <QString>
#include <QStringList>
#include <QMap>
namespace libfwbuilder {
class FWObject;
class FWObjectDatabase;
class Cluster;
class ClusterGroup;
class FailoverClusterGroup;
class Firewall;
class RuleSet;
class Interface;
class Address;
class InetAddr;
};
namespace fwcompiler {
class CompilerDriver : public BaseCompiler {
protected:
QStringList all_errors;
QStringList args;
int fwbdebug;
std::string filename;
std::string wdir;
QString fwobjectname;
QString current_firewall_name;
// fw_file_name is the name of the output file. Can be enforced via -o command
// line option or automatically determined using firewall object name
QString fw_file_name;
// member_file_names is the mapping between member firewall object ID and
// corresponding output file name. Can be enfirced via -O command line option
// or determined automatically using member firewall name. Used only when
// compiling Cluster
QMap<QString,QString> member_file_names;
int dl;
int drp;
bool rule_debug_on;
bool single_rule_compile_on;
std::string single_rule_id;
int drn;
int verbose;
bool have_dynamic_interfaces;
bool ipv4_run;
bool ipv6_run;
bool fw_by_id;
bool prolog_done;
bool epilog_done;
std::map<std::string,libfwbuilder::RuleSet*> branches;
libfwbuilder::FWObjectDatabase *objdb;
QString determineOutputFileName(libfwbuilder::Firewall *current_fw,
bool cluster_member,
const QString &ext);
bool isSupported(std::list<std::string> *protocols,
const std::string &cluster_group_type);
virtual int checkCluster(libfwbuilder::Cluster* cluster);
void mergeRuleSets(libfwbuilder::Cluster *cluster,
libfwbuilder::Firewall *fw, const std::string &type);
// checks if address @addr belongs to the subnet defined by @subnet
static bool isReachable(const libfwbuilder::Address* const subnet,
const libfwbuilder::InetAddr* const addr);
public:
CompilerDriver(libfwbuilder::FWObjectDatabase *db);
virtual ~CompilerDriver();
// create a copy of itself, including objdb
virtual CompilerDriver* clone();
/**
* Process command line arguments
*/
virtual bool configure(const QStringList &args);
/**
* create right compiler objects and compile policy, nat and
* routing rules for given firewall which can be a member of a
* cluster. If firewall is standalone, @cluster_id is an empty
* string. Cluster and firewall are defined by their string IDs.
* In single compile mode rule ID is provided in @single_rule_id
* and generated script is returned. For compilers that create
* several files it is up to the actual cmopiler class to decide
* what should be returned in the single rule compile mode. In
* normal (not single rule) compile mode returned string is
* undefined and should not be used.
*/
virtual std::string run(const std::string &cluster_id,
const std::string &firewall_id,
const std::string &single_rule_id);
virtual void commonChecks(libfwbuilder::Firewall *fw);
virtual void commonChecks2(libfwbuilder::Cluster *cluster,
libfwbuilder::Firewall *fw);
void copyFailoverInterface(libfwbuilder::Cluster *cluster,
libfwbuilder::Firewall *fw,
libfwbuilder::FailoverClusterGroup *cluster_group,
libfwbuilder::Interface *iface);
virtual void populateClusterElements(libfwbuilder::Cluster *cluster,
libfwbuilder::Firewall *fw);
virtual void processStateSyncGroups(libfwbuilder::Cluster*,
libfwbuilder::Firewall*) {};
std::string indent(int n_spaces, const std::string &txt);
QString indent(int n_spaces, const QString &txt);
QString prepend(const QString &prep, const QString &txt);
/*
* Verifies that state sync and failover group types configured in
* the GUI are supported for the given host OS. List of supported
* protocols is taken from the os resource file. If unsupported
* protocol is found, calls compiler->abort to abort immediately.
*/
virtual void validateClusterGroups(libfwbuilder::Cluster *cluster);
/*
* Use chdir to change working directory. In case of failure, exit(1)
*/
void chDir();
/*
* Find firewall or cluster object we should process.
*/
virtual libfwbuilder::Firewall* locateObject();
void findImportedRuleSets(libfwbuilder::Firewall *fw,
std::list<libfwbuilder::FWObject*> &all_policies);
virtual bool prepare(const QStringList &args);
virtual void compile();
virtual QMap<QString,QString> compileSingleRule(const std::string &rule_id);
};
};
QTextStream& operator<< (QTextStream &text_stream, const std::string &str);
#endif

View File

@ -0,0 +1,167 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include <fstream>
#include <iostream>
#include <iomanip>
#include "CompilerDriver.h"
#include "fwbuilder/FWObjectDatabase.h"
#include "fwbuilder/FWException.h"
#include "fwbuilder/Cluster.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/Interface.h"
#include "fwbuilder/Rule.h"
#include "fwcompiler/Compiler.h"
#include <QString>
#include <QStringList>
#include <QMap>
using namespace std;
using namespace libfwbuilder;
using namespace fwcompiler;
bool CompilerDriver::prepare(const QStringList &_args)
{
args = _args;
if (!configure(args)) return false;
if (!single_rule_compile_on)
{
Firewall *fw = locateObject();
if (fw == NULL)
{
cerr << "Firewall or cluster object not found" << endl;
return false;
}
}
return true;
}
void CompilerDriver::compile()
{
if (single_rule_compile_on)
{
QMapIterator<QString,QString> it(compileSingleRule(single_rule_id));
while (it.hasNext())
{
it.next();
info("Firewall " + it.key().toStdString());
info(it.value().toStdString());
info("\n");
}
return;
}
Firewall *fw = locateObject();
if (Cluster::isA(fw))
{
commonChecks(fw);
// compiling cluster.
list<Firewall*> members;
Cluster::cast(fw)->getMembersList(members);
for (list<Firewall*>::iterator it=members.begin(); it!=members.end(); ++it)
{
info("\n");
info(" Firewall " + (*it)->getName() + " member of cluster " + fw->getName());
CompilerDriver *cl_driver = clone();
cl_driver->configure(args);
cl_driver->chDir();
cl_driver->run(objdb->getStringId(fw->getId()),
objdb->getStringId((*it)->getId()),
"");
delete cl_driver;
}
}
else
{
chDir();
commonChecks(fw);
run("", objdb->getStringId(fw->getId()), "");
}
}
/*
* Compile single rule and return generated code. Rule is defined by
* its ID, this is sufficient to locate the rule, ruleset and firewall
* objects. If ruleset belongs to a cluster, compile all members and
* return code generated for all of them. Returned code is placed in
* QMap where the key is member firewall name and value is generated
* script. If the rule belongs to a firewall rather than a cluster,
* returned QMap contains one item.
*/
QMap<QString,QString> CompilerDriver::compileSingleRule(const string &rule_id)
{
Cluster *cluster = NULL;
Firewall *fw = NULL;
Rule *rule = Rule::cast(
objdb->findInIndex(FWObjectDatabase::getIntId(rule_id)));
if (rule==NULL)
throw FWException(string("Rule with ID=") + rule_id + " not found");
FWObject *p = rule;
while (p && Firewall::cast(p)==NULL) p = p->getParent();
if (Cluster::isA(p)) cluster = Cluster::cast(p);
if (Firewall::isA(p)) fw = Firewall::cast(p);
QMap<QString,QString> result;
if (cluster)
{
commonChecks(cluster);
list<Firewall*> members;
Cluster::cast(cluster)->getMembersList(members);
for (list<Firewall*>::iterator it=members.begin(); it!=members.end(); ++it)
{
CompilerDriver *cl_driver = clone();
cl_driver->single_rule_compile_on = true;
if (inTestMode()) cl_driver->setTestMode();
if (inEmbeddedMode()) cl_driver->setEmbeddedMode();
result[(*it)->getName().c_str()] = cl_driver->run(
objdb->getStringId(cluster->getId()),
objdb->getStringId((*it)->getId()),
rule_id).c_str();
delete cl_driver;
}
} else
{
commonChecks(fw);
single_rule_compile_on = true;
result[fw->getName().c_str()] =
run("", objdb->getStringId(fw->getId()), rule_id).c_str();
}
return result;
}

View File

@ -0,0 +1,252 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include "Configlet.h"
#include <QRegExp>
#include <QTextStream>
#include <QDir>
#include <QFile>
#include <iostream>
extern std::string respath;
using namespace std;
/*
* @filename is a name of the configlet file. The program searches for
* it in resources directory, subdirectory configlets/@prefix. If
* @filename is absolute path, the program tries to open file as
* specified.
*/
Configlet::Configlet(const std::string &prefix, const QString &file_name)
{
reload(prefix, file_name);
}
Configlet::Configlet(const std::string &prefix,
const std::string &default_prefix,
const QString &file_name)
{
remove_comments = true;
comment_str = "##";
collapse_empty_strings = false;
if (!reload(prefix, file_name)) reload(default_prefix, file_name);
}
Configlet::~Configlet()
{
}
bool Configlet::reload(const std::string &_prefix, const QString &file_name)
{
prefix = _prefix.c_str();
code.clear();
if (QDir::isAbsolutePath(file_name))
file_path = file_name;
else
file_path = getConfigletPath(file_name);
if (!file_path.isEmpty())
{
QFile file(file_path);
if (file.exists() && file.open(QFile::ReadOnly))
{
QTextStream ts(&file);
do
{
QString line = ts.readLine();
code.push_back(line);
} while (!ts.atEnd());
return true;
}
}
return false;
}
QString Configlet::getFullPath(const QString &path)
{
if (QDir::isRelativePath(path))
return QString(respath.c_str()) + "/configlets/" + path;
else
return path;
}
QString Configlet::getConfigletPath(const QString &configlet_name)
{
QString home = QDir::homePath();
QString file_path;
file_path = home + "/fwbuilder/configlets/" + prefix + "/" + configlet_name;
if (QFile(file_path).exists()) return file_path;
file_path = getFullPath(prefix + "/" + configlet_name);
if (QFile(file_path).exists()) return file_path;
return "";
}
// ************************************************************************
void Configlet::setVariable(const QString &name, const QString &value)
{
vars[name] = value.trimmed();
}
void Configlet::setVariable(const QString &name, int value)
{
QString val;
val.setNum(value);
vars[name] = val;
}
QString Configlet::expand()
{
// Need non-greedy matching so that if_re matches only one {{?var}} ... {{?}}
// clause
QRegExp var_re("\\{\\{\\$([^}]*)\\}\\}", Qt::CaseSensitive, QRegExp::RegExp2);
var_re.setMinimal(true);
QStringList res;
QString all_code = code.join("\n");
while (all_code.contains(var_re))
{
QString var = var_re.cap(1);
if (vars.count(var) > 0)
{
all_code.replace(QString("{{$%1}}").arg(var), vars[var]);
} else
{
// template has a variable that has not been defined
// remove '$' from the macro but leave it in place for debugging
all_code.replace(QString("{{$%1}}").arg(var), QString("{{%1}}").arg(var));
}
}
while (processIf(all_code, 0));
QStringList code_lines = all_code.split("\n");
if (remove_comments)
{
res.clear();
foreach(QString line, code_lines)
{
if (line.startsWith(comment_str)) continue;
res.push_back(line);
}
code_lines = res;
}
if (collapse_empty_strings)
{
res.clear();
foreach(QString line, code_lines)
{
if (line.trimmed().isEmpty()) continue;
res.push_back(line);
}
code_lines = res;
}
return code_lines.join("\n");
}
/*
* pos points to the position of "{{?var}}" in the stream
*/
bool Configlet::processIf(QString &stream, int pos)
{
QRegExp if_re("\\{\\{if {1,}([^}]{1,})\\}\\}", Qt::CaseSensitive, QRegExp::RegExp2);
QRegExp endif_re("\\{\\{endif\\}\\}", Qt::CaseSensitive, QRegExp::RegExp2);
if_re.setMinimal(true);
endif_re.setMinimal(true);
int current_if_pos = if_re.indexIn(stream, pos);
if (current_if_pos == -1) return false;
int current_if_length = if_re.cap(0).length();
QString current_if_var = if_re.cap(1);
// look what is next, another opening if or closing endif
int next_if_pos = if_re.indexIn(
stream, current_if_pos + current_if_length);
int next_endif_pos = endif_re.indexIn(
stream, current_if_pos + current_if_length);
if (next_if_pos != -1 && next_if_pos < next_endif_pos)
{
processIf(stream, next_if_pos);
// the next if statement has been replaced, process current if
// statement again
return true;
}
if (next_endif_pos != -1)
{
int next_endif_length = endif_re.cap(0).length();
// current if statement starts at current_if_pos
// and ends at next_endif_pos + next_endif_length
int current_if_clause_length =
next_endif_pos + next_endif_length - current_if_pos;
QString body = stream.mid(
current_if_pos + current_if_length,
next_endif_pos - current_if_pos - current_if_length);
QString replacement;
if (vars.count(current_if_var) > 0)
{
bool ok = false;
int f = vars[current_if_var].toInt(&ok);
if (ok && f)
replacement = body;
}
stream.replace(current_if_pos, current_if_clause_length, replacement);
}
return true;
}
/**
* Set internal flag to remove comments from the produced script and
* set comment string. By default comment string is "##". This means
* we can still put comments with single "#" in templates and have
* these comments appear in the generated script. At the same time,
# comments marked with "##" will be removed.
*/
void Configlet::removeComments(const QString &_str)
{
remove_comments = true;
comment_str = _str;
}
void Configlet::collapseEmptyStrings(bool f)
{
collapse_empty_strings = f;
}

View File

@ -0,0 +1,69 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef __CONFIGLET_HH__
#define __CONFIGLET_HH__
#include <QString>
#include <QStringList>
#include <QMap>
class Configlet {
bool processIf(QString &stream, int pos);
protected:
QString prefix;
QString file_path;
QStringList code;
QMap<QString, QString> vars;
bool remove_comments;
QString comment_str;
bool collapse_empty_strings;
QString getFullPath(const QString &rel_path);
public:
Configlet(const std::string &prefix, const QString &filename);
Configlet(const std::string &prefix, const std::string &default_prefix,
const QString &filename);
virtual ~Configlet();
bool reload(const std::string &prefix, const QString &filename);
QString getConfigletPath(const QString &configlet_name);
void setVariable(const QString &name, const QString &value);
void setVariable(const QString &name, int value);
QString expand();
void removeComments(const QString &comment_str="##");
void collapseEmptyStrings(bool f);
};
#endif

View File

@ -0,0 +1,30 @@
#-*- mode: makefile; tab-width: 4; -*-
#
# This library is separate from fwcompiler library because it has dependency
# on QT
include(../../qmake.inc)
TEMPLATE = lib
SOURCES = CompilerDriver.cpp \
CompilerDriver_compile.cpp \
Configlet.cpp \
interfaceProperties.cpp \
linux24Interfaces.cpp \
interfacePropertiesObjectFactory.cpp
HEADERS = ../../config.h \
CompilerDriver.h \
Configlet.h \
interfaceProperties.h \
linux24Interfaces.h \
interfacePropertiesObjectFactory.h
!macx:LIBS += $$LIBS_FWCOMPILER
CONFIG += staticlib
TARGET = compilerdriver
INSTALLS -= target

View File

@ -0,0 +1,155 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@fwbuilder.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include "interfaceProperties.h"
#include "fwbuilder/Interface.h"
#include "fwbuilder/IPv4.h"
#include "fwbuilder/IPv6.h"
#include "fwbuilder/Resources.h"
#include "fwbuilder/FailoverClusterGroup.h"
#include <string>
#include <list>
#include <QObject>
#include <QStringList>
using namespace std;
using namespace libfwbuilder;
void interfaceProperties::getListOfAddresses(Interface *intf, QStringList &addr_list)
{
list<FWObject*> addresses = intf->getByType(IPv4::TYPENAME);
list<FWObject*> ipv6_addresses = intf->getByType(IPv6::TYPENAME);
addresses.splice(addresses.begin(), ipv6_addresses);
for (FWObject::iterator j=addresses.begin(); j!=addresses.end(); ++j)
{
const InetAddr *iaddr_addr = Address::cast(*j)->getAddressPtr();
const InetAddr *iaddr_netm = Address::cast(*j)->getNetmaskPtr();
addr_list.push_back(
QString("%1/%2").
arg(iaddr_addr->toString().c_str()).
arg(iaddr_netm->getLength()));
}
}
/*
* we manage only addresses of vrrp cluster interfaces.
*
* We ignore addresses of heartbeat and openais cluster interfaces.
* To ignore them, we pass list of addresses managed by heartbeat to
* shell function update_addresses (defined in configlet
* "update_addresses") as its second argument to make it ignore these
*
* This code assumes the name of the cluster interface is the same as
* names of the corresponding interfaces of member firewalls.
*/
bool interfaceProperties::manageIpAddresses(Interface *intf,
QStringList &update_addresses,
QStringList &ignore_addresses)
{
update_addresses.clear();
ignore_addresses.clear();
FWObject *fw = intf->getParentHost();
Resources *os_res = Resources::os_res[fw->getStr("host_OS")];
assert(os_res != NULL);
if (intf->isDyn()) return false;
if (intf->isBridgePort()) return false;
if (intf->isSlave()) return false;
string intf_name = intf->getName();
if (intf->getOptionsObject()->getBool("cluster_interface"))
{
if (intf->isLoopback()) return false;
if (intf->isFailoverInterface())
{
FWObject *failover_group =
intf->getFirstByType(FailoverClusterGroup::TYPENAME);
string failover_type = failover_group->getStr("type");
if (os_res->getResourceBool(
"/FWBuilderResources/Target/protocols/" + failover_type + "/manage_addresses"))
{
getListOfAddresses(intf, update_addresses);
return true;
} else
return false;
}
/*
* if this is cluster interface with the same name as fw interface
* (as happens in case of hearbeat or openais), skip it
*/
if (intf->getOptionsObject()->getStr("base_device") == intf_name)
return false;
} else
{
// regular interface. Lets see if there is cluster interface
// with the same name. If there is and its failover protocol
// is heartbeat or openais, we should ignore all addresses it
// might have.
getListOfAddresses(intf, update_addresses);
FWObject *parent_fw = intf->getParentHost();
list<FWObject*> interfaces = fw->getByTypeDeep(Interface::TYPENAME);
list<FWObject*>::iterator i;
for (i=interfaces.begin(); i!=interfaces.end(); ++i )
{
Interface *iface = Interface::cast(*i);
assert(iface);
if (iface->getName() == intf_name &&
iface->getOptionsObject()->getBool("cluster_interface") &&
iface->isFailoverInterface())
{
FWObject *failover_group =
iface->getFirstByType(FailoverClusterGroup::TYPENAME);
string failover_type = failover_group->getStr("type");
// some protocols do not like it when failover ip address
// is managed outside their software
if (! os_res->getResourceBool(
"/FWBuilderResources/Target/protocols/" + failover_type + "/manage_addresses"))
getListOfAddresses(iface, ignore_addresses);
break;
}
}
}
return true;
}

View File

@ -0,0 +1,94 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@fwbuilder.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef INTERFACE_PROPERTIES_HH
#define INTERFACE_PROPERTIES_HH
#include <QString>
#include <QRegExp>
#include <QList>
#include <map>
#include "fwbuilder/InterfaceData.h"
class interfaceProperties {
protected:
typedef enum {BONDING_INTERFACE,
ETH_NO_DOT,
VLAN_INTERFACE,
BRIDGE_INTERFACE,
UNKNOWN} interface_type;
QList<QRegExp> vlan_name_patterns;
/*
* collects all ip addresses of the interface (only direct
* addresses, not addresses of subinterfaces) and fills the list
* with string representation in the form "address/masklen"
*/
void getListOfAddresses(libfwbuilder::Interface *intf,
QStringList &addr_list);
public:
interfaceProperties() {}
virtual ~interfaceProperties() {}
virtual void rearrangeInterfaces(
std::map<int,libfwbuilder::InterfaceData> &interfaces,
std::list<libfwbuilder::InterfaceData*> &interface_tree)
{
// default rearranger: just copy the data
std::map<int,libfwbuilder::InterfaceData>::iterator i;
for (i=interfaces.begin(); i!=interfaces.end(); ++i)
{
interface_tree.push_back(&(i->second));
}
}
virtual void parseVlan(libfwbuilder::InterfaceData*) {};
virtual void parseVlan(const QString&, QString*, int*) {};
virtual bool isValidVlanInterfaceName(const QString &,
const QString &,
QString&) { return false; }
virtual bool looksLikeVlanInterface(libfwbuilder::InterfaceData*) { return false; }
virtual bool looksLikeVlanInterface(const QString&) { return false; }
/**
* for the given interface return list of its ip addresses that we
* should manage using update_addresses shell function and list of
* addresses we should ignore (as in the case of hearbeat or openais
* cluster interfaces). Returns true if we should manage ip addresses
* of this interface and false otherwise. Note that it is possible to
* return true even when there are no addresses to manage, in which
* case lists update_addresses and ignore_addresses are empty.
*/
virtual bool manageIpAddresses(libfwbuilder::Interface *intf,
QStringList &update_addresses,
QStringList &ignore_addresses);
};
#endif

View File

@ -0,0 +1,43 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@fwbuilder.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "interfacePropertiesObjectFactory.h"
#include "interfaceProperties.h"
#include "linux24Interfaces.h"
#include <iostream>
using namespace std;
interfaceProperties* interfacePropertiesObjectFactory::getInterfacePropertiesObject(
const std::string &host_os)
{
if (host_os == "linux24") return new linux24Interfaces();
// by default return object of the base class. It performs some
// reasonable default actions.
return new interfaceProperties();
}

View File

@ -0,0 +1,40 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@fwbuilder.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef INTERFACE_PROPERTIES_OBJECT_FACTORY_HH
#define INTERFACE_PROPERTIES_OBJECT_FACTORY_HH
#include <string>
#include "interfaceProperties.h"
class interfacePropertiesObjectFactory {
public:
static interfaceProperties* getInterfacePropertiesObject(const std::string &host_os);
};
#endif

View File

@ -0,0 +1,373 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@fwbuilder.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include "linux24Interfaces.h"
#include <string>
#include <iostream>
#include <QObject>
using namespace std;
using namespace libfwbuilder;
linux24Interfaces::linux24Interfaces()
{
vlan_name_patterns.append(QRegExp("([a-zA-Z-]+\\d{1,})\\.(\\d{1,})"));
vlan_name_patterns.append(QRegExp("vlan(\\d{1,})"));
}
/*
* Take original information about interfaces provided by the crawler
* and try to arrange it into a tree or interfaces and
* subinterfaces. Guess based on host OS, inetrface names and their
* MAC addresses. Returns data in the argument @interface_tree
*/
void linux24Interfaces::rearrangeInterfaces(map<int,InterfaceData> &interfaces,
list<InterfaceData*> &interface_tree)
{
/*
how to find vlan subinterfaces:
if interface 1 has name with a dot and numbers after the
dot, AND its MAC address is the same as MAC address of an
interface 2 with the name matching the part before the dot,
then interface 1 is subinterface of 1 and type of interface 2
should be 8021q
Example of mixed configuration :
Bridge: br0 -> eth4
Bonding: bond0 -> eth2 eth3
Vlans: eth1 -> eth1.100 eth1.101 eth1.102
bond0 -> bond0.200 bond0.201 bond0.202
eth0 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:96
bond0 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:AA
bond0.200 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:AA
bond0.201 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:AA
bond0.202 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:AA
eth2 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:AA
eth3 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:AA
eth1 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:A0
eth1.100 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:A0
eth1.101 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:A0
eth1.102 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:A0
br0 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:BE
eth4 Link encap:Ethernet HWaddr 00:0C:29:F6:BE:BE
*/
// map mac addresse to list of InterfaceData objects. Note that
// there can be several interfaces with the same mac address
map<string, list<InterfaceData*> > all_mac_addresses;
// pass 1: group interfaces by mac address
map<int,InterfaceData>::iterator i;
for (i=interfaces.begin(); i!=interfaces.end(); ++i)
{
// loopback, tunnels and p2p interfaces have no mac address
if (i->second.mac_addr.empty())
interface_tree.push_back(&(i->second));
else
all_mac_addresses[i->second.mac_addr].push_back(&(i->second));
}
// pass 2: for each unique mac address, create top level interface and
// subinterfaces
map<string, list<InterfaceData*> >::iterator it;
for (it=all_mac_addresses.begin(); it!=all_mac_addresses.end(); ++it)
{
if (it->second.size() > 1)
{
// several interfaces with the same mac address
//
// Can be:
// eth0 and eth0.100, eth0.101
// eth0 and vlan1, vlan2
// bond0 and eth0, eth1
// br0 and eth0, eth1
list<InterfaceData*> vlan_subinterfaces;
list<InterfaceData*> bond_subinterfaces;
list<InterfaceData*> bridge_subinterfaces;
InterfaceData *vlan_parent_interface = NULL;
InterfaceData *bond_parent_interface = NULL;
InterfaceData *bridge_parent_interface = NULL;
list<InterfaceData*>::iterator intf;
bool bonding = false;
bool bridge = false;
bool vlans = false;
bool have_dots = false;
for (intf=it->second.begin(); intf!=it->second.end(); ++intf)
{
if ((*intf)->name.find("br") == 0) bridge = true;
if ((*intf)->name.find("bond") == 0) bonding = true;
if ((*intf)->name.find("vlan") == 0) vlans = true;
if ((*intf)->name.find(".") != string::npos) have_dots = true;
}
// assume that interface with a dot in names are vlan
// interfaces such as "eth0.100".
// But vlan interfaces can be "bond0.100" as well.
if (!vlans && have_dots) vlans = true;
for (intf=it->second.begin(); intf!=it->second.end(); ++intf)
{
linux24Interfaces::interface_type itype;
if ((*intf)->name.find("bond") == 0 &&
(*intf)->name.find(".") == string::npos)
itype = BONDING_INTERFACE;
if ((*intf)->name.find("eth") == 0 &&
(*intf)->name.find(".") == string::npos)
itype = ETH_NO_DOT;
if ((*intf)->name.find(".") != string::npos ||
(*intf)->name.find("vlan") == 0)
itype = VLAN_INTERFACE;
if ((*intf)->name.find("br") == 0 &&
(*intf)->name.find(".") == string::npos)
itype = BRIDGE_INTERFACE;
if (bonding)
{
switch (itype)
{
case BONDING_INTERFACE:
// interface name starts with "bond" and has no dot
// like "bond0"
(*intf)->interface_type = "bonding";
bond_parent_interface = *intf;
continue;
case ETH_NO_DOT:
// interface name starts with "eth" and has no dot
// like "eth0"
// This is physical interface that is a member of bonding group
(*intf)->interface_type = "ethernet";
bond_subinterfaces.push_back(*intf);
continue;
case VLAN_INTERFACE:
parseVlan(*intf);
bond_subinterfaces.push_back(*intf);
continue;
default:
break;
}
}
if (bridge)
{
switch (itype)
{
case BRIDGE_INTERFACE:
// interface name starts with "br" and has no dot
// like "br0"
(*intf)->interface_type = "bridge";
bridge_parent_interface = *intf;
continue;
case ETH_NO_DOT:
// interface name starts with "eth" and has no dot
// like "eth0"
// This is physical interface that is a member of a bridge
(*intf)->interface_type = "ethernet";
bridge_subinterfaces.push_back(*intf);
// special case: eth0 can be part of the bridge and
// vlan parent interface
// break from switch but continue the loop
// continue;
break;
case VLAN_INTERFACE:
parseVlan(*intf);
bridge_subinterfaces.push_back(*intf);
// special case: vlan interface can be part of
// the bridge and part of the vlan configuration
// break from switch but continue the loop
// continue;
break;
default:
break;
}
}
if (vlans)
{
switch (itype)
{
case ETH_NO_DOT:
// interface name starts with "eth" and has no dot
// like "eth0"
(*intf)->interface_type = "ethernet";
vlan_parent_interface = *intf;
continue;
case VLAN_INTERFACE:
parseVlan(*intf);
vlan_subinterfaces.push_back(*intf);
continue;
default:
break;
}
}
// if we get here, then interface was not covered by either
// of the cases above. Just create it as top-level
interface_tree.push_back(*intf);
}
if (bond_parent_interface)
{
for (intf=bond_subinterfaces.begin(); intf!=bond_subinterfaces.end(); ++intf)
bond_parent_interface->subinterfaces.push_back(*intf);
interface_tree.push_back(bond_parent_interface);
}
if (bridge_parent_interface)
{
for (intf=bridge_subinterfaces.begin(); intf!=bridge_subinterfaces.end(); ++intf)
bridge_parent_interface->subinterfaces.push_back(*intf);
interface_tree.push_back(bridge_parent_interface);
}
if (vlan_parent_interface)
{
for (intf=vlan_subinterfaces.begin(); intf!=vlan_subinterfaces.end(); ++intf)
vlan_parent_interface->subinterfaces.push_back(*intf);
interface_tree.push_back(vlan_parent_interface);
}
} else
{
// single interface with this mac, just create it as top-level
interface_tree.push_back(it->second.front());
}
}
}
void linux24Interfaces::parseVlan(InterfaceData *intf)
{
intf->interface_type = "8021q";
QString base_name;
parseVlan(intf->name.c_str(), &base_name, &(intf->vlan_id));
}
void linux24Interfaces::parseVlan(const QString &name,
QString *base_name,
int *vlan_id)
{
if (vlan_name_patterns[0].indexIn(name) != -1)
{
*base_name = vlan_name_patterns[0].cap(1);
*vlan_id = vlan_name_patterns[0].cap(2).toInt();
}
if (vlan_name_patterns[1].indexIn(name) != -1)
{
*base_name = "vlan";
*vlan_id = vlan_name_patterns[1].cap(1).toInt();
}
}
bool linux24Interfaces::looksLikeVlanInterface(InterfaceData *intf)
{
return looksLikeVlanInterface(intf->name.c_str());
}
bool linux24Interfaces::looksLikeVlanInterface(const QString &int_name)
{
if (vlan_name_patterns[0].indexIn(int_name) != -1 ||
vlan_name_patterns[1].indexIn(int_name) != -1) return true;
return false;
}
/*
* While looksLikeVlanInterface only checks interface name format,
* this method does more detailed check to determine if the interface
* is valid vlan. In particular, it checks that given interface is
* indeed a subinterface (parent is also interface) and its base name
* matches the name of the parent
*/
bool linux24Interfaces::isValidVlanInterfaceName(const QString &subint_name,
const QString &parent_name,
QString &err)
{
if (!looksLikeVlanInterface(subint_name))
{
err = QObject::tr("'%1' is not a valid vlan interface name").arg(subint_name);
return false;
}
if (vlan_name_patterns[0].indexIn(subint_name) != -1)
{
if (!parent_name.isEmpty() && parent_name != vlan_name_patterns[0].cap(1))
{
err = QObject::tr("'%1' looks like a name of a vlan interface "
"but it does not match the name of the parent "
"interface '%2'").arg(subint_name).arg(parent_name);
return false;
}
int vlan_id = vlan_name_patterns[0].cap(2).toInt();
if (vlan_id > 4095)
{
err = QObject::tr("'%1' looks like a name of a vlan interface "
"but vlan ID it defines is outside of the valid range."
"").arg(subint_name);
return false;
}
}
if (vlan_name_patterns[1].indexIn(subint_name) != -1)
{
int vlan_id = vlan_name_patterns[1].cap(1).toInt();
if (vlan_id > 4095)
{
err = QObject::tr("'%1' looks like a name of a vlan interface "
"but vlan ID it defines is outside of the valid range."
"").arg(subint_name);
return false;
}
}
return true;
}

View File

@ -0,0 +1,59 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@fwbuilder.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef LINUX24_INTERFACE_PROPERTIES_HH
#define LINUX24_INTERFACE_PROPERTIES_HH
#include <map>
#include <list>
#include <QString>
#include "interfaceProperties.h"
#include "fwbuilder/InterfaceData.h"
class linux24Interfaces : public interfaceProperties {
public:
linux24Interfaces();
virtual void rearrangeInterfaces(
std::map<int,libfwbuilder::InterfaceData> &interfaces,
std::list<libfwbuilder::InterfaceData*> &interface_tree);
virtual void parseVlan(libfwbuilder::InterfaceData *intf);
virtual void parseVlan(const QString &name,
QString *base_name,
int *vlan_id);
virtual bool isValidVlanInterfaceName(const QString &subint_name,
const QString &parent_name,
QString &err);
virtual bool looksLikeVlanInterface(libfwbuilder::InterfaceData *intf);
virtual bool looksLikeVlanInterface(const QString &interface_name);
};
#endif

View File

@ -578,7 +578,6 @@ void _modObject(FWObject *nobj, const string &comment_txt, operands ops)
Interface *o = Interface::cast(nobj);
int sl = atoi(security.c_str());
o->setSecurityLevel(sl);
o->setExt((sl==0)?true:false);
o->setDyn(addrtype=="dynamic");
o->setUnnumbered(addrtype=="unnumbered");
o->setManagement(getBool(management));

View File

@ -0,0 +1,388 @@
/*
* TransferDevice.cpp - fwtransfer library implementation
*
* Copyright (c) 2008 secunet Security Networks AG
* Copyright (c) 2008 Adrian-Ken Rueegsegger <rueegsegger@swiss-it.ch>
* Copyright (c) 2008 Reto Buerki <buerki@swiss-it.ch>
*
* This work is dual-licensed under:
*
* o The terms of the GNU General Public License as published by the Free
* Software Foundation, either version 2 of the License, or (at your option)
* any later version.
*
* o The terms of NetCitadel End User License Agreement
*/
#include <cmath>
#include <algorithm>
#include <string>
#include <sys/types.h>
#include <QDebug>
#include <QString>
#include <QStringList>
#include <QtDBus/QtDBus>
#include "TransferDevice.h"
using namespace fwtransfer;
using namespace libfwbuilder;
#ifdef HAVE_QTDBUS
QVariant getProperty(QDBusInterface &interface, QString prop)
throw(FWException)
{
QDBusMessage msg = interface.call("GetProperty", prop);
if (msg.type() == QDBusMessage::ErrorMessage)
{
throw FWException(interface.path().toStdString() +
": could not get property => " + prop.toStdString());
}
QVariant ret = msg.arguments()[0];
return ret;
}
QString TransferDevice::getVolumeSizeStr() const
{
// get size in bytes
qlonglong size = getVolumeSize();
QString size_str;
QString unit = "KB";
QVariant size_v;
if (size != 0)
{
// smallest unit is kb
size = size / 1024;
size_v = size;
if (size > 1024)
{
size = size / 1024;
size_v = size;
unit = "MB";
}
if (size > 1024)
{
float f_size = float(size) / 1024;
size_v = floor(f_size * 100.0 + 0.5) / 100;
unit = "GB";
}
size_str = size_v.toString() + " " + unit;
}
else
{
size_str = "0";
}
return size_str;
}
void TransferDevice::dump() const
{
// header
qDebug() << "( dump of transfer device " << getDeviceName() << " )";
// actual dump
QString mounted = is_mounted ? "yes" : "no";
QString removable = is_removable ? "yes" : "no";
QString hotpluggable = is_hotpluggable ? "yes" : "no";
qDebug() << "volume UDI\t:\t" + getVolumeUDI();
qDebug() << "fstype\t\t:\t" + getVolumeFS();
qDebug() << "size (MB)\t:\t" + getVolumeSizeStr();
qDebug() << "device UDI\t:\t" + getDeviceUDI();
qDebug() << "device\t\t:\t" + getDeviceName();
qDebug() << "bus\t\t:\t" + getDeviceBus();
qDebug() << "type\t\t:\t" + getDeviceType();
qDebug() << "mountpoint\t:\t" + getMountpoint();
qDebug() << "mounted\t:\t" + mounted;
qDebug() << "removable\t:\t" + removable;
qDebug() << "hotpluggable\t:\t" + hotpluggable;
qDebug();
}
void TransferDevice::mount() throw(FWException)
{
// ignore request if already mounted
if (is_mounted)
{
return;
}
QDBusConnection conn = QDBusConnection::systemBus();
QDBusInterface mountiface("org.freedesktop.Hal", getVolumeUDI(),
"org.freedesktop.Hal.Device.Volume", conn);
QStringList options;
#ifndef WIN32
// special mount options for vfat filesystems
if (getVolumeFS() == "vfat")
{
QVariant user_v = getuid();
QString user = "uid=" + user_v.toString();
options << "quiet" << "shortname=mixed" << user << "umask=077";
}
#endif
// send mount DBus message
QDBusMessage replyMsg = mountiface.call("Mount", "", "", options);
if (replyMsg.type() == QDBusMessage::ErrorMessage)
{
qDebug() << "Could not mount : " <<
replyMsg.errorMessage() << ", " <<
replyMsg.errorName();
throw FWException(replyMsg.errorName().toStdString() + " : " +
replyMsg.errorMessage().toStdString());
}
else
{
// re-read mountpoint
QDBusInterface volumeiface("org.freedesktop.Hal", getVolumeUDI(),
"org.freedesktop.Hal.Device", conn);
setMountpoint(getProperty(volumeiface, "volume.mount_point").toString());
}
}
void TransferDeviceList::init() throw(FWException)
{
if (!checkDBus())
{
throw FWException("Cannot connect to the D-BUS system bus.");
}
QDBusInterface hal("org.freedesktop.Hal",
"/org/freedesktop/Hal/Manager",
"org.freedesktop.Hal.Manager",
QDBusConnection::systemBus());
// clear 'old' devices
clear();
// get all volumes from HAL
QDBusMessage msg = hal.call("FindDeviceByCapability", "volume");
QList<QVariant> volumes = msg.arguments();
foreach (QVariant name, volumes)
{
QStringList volume_list = name.toStringList();
foreach (QString vol, volume_list)
{
addNewVolume(vol);
}
}
bool success;
// connect HAL signals to our observer slots
success = hal.connection().connect("org.freedesktop.Hal",
"/org/freedesktop/Hal/Manager",
"org.freedesktop.Hal.Manager",
"DeviceAdded", this,
SLOT(newDeviceDetected(const QString &)));
if (!success)
{
throw FWException("Cannot subscribe to HAL 'DeviceAdded' signal.");
}
success = hal.connection().connect("org.freedesktop.Hal",
"/org/freedesktop/Hal/Manager",
"org.freedesktop.Hal.Manager",
"DeviceRemoved", this,
SLOT(deviceRemovedDetected(const QString &)));
if (!success)
{
throw FWException("Cannot subscribe to HAL 'DeviceRemoved' signal.");
}
}
void TransferDeviceList::dump() const
{
TransferDeviceList::const_iterator it;
for (it = this->begin(); it != this->end(); it++)
{
(*it).dump();
}
}
bool TransferDeviceList::checkDBus() const
{
if (!QDBusConnection::systemBus().isConnected())
{
fprintf(stderr, "Cannot connect to the D-BUS system bus.\n");
return false;
}
return true;
}
bool TransferDeviceList::addNewVolume(const QString &udi)
{
QDBusConnection conn = QDBusConnection::systemBus();
QDBusInterface volume("org.freedesktop.Hal", udi,
"org.freedesktop.Hal.Device", conn);
// only consider volumes for addition
QVariant is_volume;
try
{
// getProperty throws an exception if property is not there
is_volume = getProperty(volume, "block.is_volume");
}
catch (FWException &ex)
{
return false;
}
// property is there, but still it is not a volume
if (!is_volume.toBool())
{
return false;
}
// read in new volume/device
TransferDevice new_device;
new_device.setVolumeUDI(udi);
// get physical device UDI and path for volume
new_device.setDeviceUDI(getProperty(volume,
"block.storage_device").toString());
new_device.setDeviceName(getProperty(volume,
"block.device").toString());
// check if its already mounted
new_device.setMounted(getProperty(volume,
"volume.is_mounted").toBool());
// if mounted, read mountpoint
if (new_device.isMounted())
{
new_device.setMountpoint(getProperty(volume,
"volume.mount_point").toString());
}
// volume filesystem type
new_device.setVolumeFS(getProperty(volume,
"volume.fstype").toString());
// volume size
new_device.setVolumeSize(getProperty(volume,
"volume.size").toLongLong());
// get properties for storage device
QDBusInterface device("org.freedesktop.Hal",
new_device.getDeviceUDI(),
"org.freedesktop.Hal.Device", conn);
new_device.setDeviceBus(getProperty(device,
"storage.bus").toString());
new_device.setRemovable(getProperty(device,
"storage.removable").toBool());
new_device.setDeviceType(getProperty(device,
"storage.drive_type").toString());
new_device.setHotpluggable(getProperty(device,
"storage.hotpluggable").toBool());
// only store portable usb based volumes
if (new_device.isHotpluggable() &&
new_device.isRemovable() &&
new_device.getDeviceBus() == "usb" &&
new_device.getDeviceType() == "disk")
{
push_back(new_device);
}
return true;
}
bool TransferDeviceList::removeVolume(const QString &udi)
{
TransferDeviceList::iterator it;
PredFindVolumeUDI pred;
pred.setSearchString(udi);
it = find_if(begin(), end(), pred);
// not found
if (it == end())
{
return false;
}
// remove volume
erase(it);
return true;
}
TransferDeviceList::const_iterator
TransferDeviceList::getDeviceByName(const QString &name) const
{
TransferDeviceList::const_iterator it;
PredFindName pred;
pred.setSearchString(name);
it = find_if(begin(), end(), pred);
return it;
}
TransferDeviceList::const_iterator
TransferDeviceList::getDeviceByName(const std::string &name) const
{
return getDeviceByName(QString(name.c_str()));
}
void TransferDeviceList::newDeviceDetected(const QString &udi)
{
// add this volume/device to the list
if (addNewVolume(udi))
{
// qDebug() << "TransferDeviceList : DeviceAdded : " << udi;
emit devicesChanged();
}
}
void TransferDeviceList::deviceRemovedDetected(const QString &udi)
{
if (removeVolume(udi))
{
// qDebug() << "TransferDeviceList : DeviceRemoved : " << udi;
emit devicesChanged();
}
}
#else
#ifndef _WIN32
#warning "QT D-BUS support not available!"
#endif
QString TransferDevice::getVolumeSizeStr() const { return ""; }
void TransferDevice::dump() const {}
void TransferDevice::mount() throw(FWException)
{
throw FWException("Cannot connect to the D-BUS system bus.");
}
void TransferDeviceList::init() throw(FWException)
{
throw FWException("Cannot connect to the D-BUS system bus.");
}
TransferDeviceList::const_iterator
TransferDeviceList::getDeviceByName(const QString&) const
{
return end();
}
TransferDeviceList::const_iterator
TransferDeviceList::getDeviceByName(const std::string&) const
{
return end();
}
void TransferDeviceList::dump() const
{}
#endif

View File

@ -0,0 +1,394 @@
/*
* TransferDevice.cpp - QDBus based config transfer library
*
* Copyright (c) 2008 secunet Security Networks AG
* Copyright (c) 2008 Adrian-Ken Rueegsegger <rueegsegger@swiss-it.ch>
* Copyright (c) 2008 Reto Buerki <buerki@swiss-it.ch>
*
* This work is dual-licensed under:
*
* o The terms of the GNU General Public License as published by the Free
* Software Foundation, either version 2 of the License, or (at your option)
* any later version.
*
* o The terms of NetCitadel End User License Agreement
*/
#ifndef __TRANSFER_DEVICE_HH__
#define __TRANSFER_DEVICE_HH__
#include <string>
#include <QString>
#include <QObject>
#include "../../config.h"
#include "fwbuilder/FWException.h"
namespace fwtransfer
{
class DeviceObserver;
/**
* @class TransferDevice
*
* @brief This class represents a device for firewall config transfer.
*
* The TransferDevice class can be used to store information about transfer
* volumes/devices. TransferDevices provide different setter/getter functions
* to set/get information about devices and volumes. TransferDevice objects
* provides a dump() function to dump the currently stored info and also a
* mount() function to actually mount the volume.
*/
class TransferDevice
{
public:
TransferDevice() :
volume_udi(NULL),
volume_fs(NULL),
volume_size(0),
device_udi(NULL),
device_name(NULL),
device_bus(NULL),
mountpoint(NULL),
is_mounted(false),
is_removable(false),
is_hotpluggable(false) {};
/**
* set volume UDI for transfer device.
*
* @param udi volume UDI
*/
void setVolumeUDI(QString udi) { volume_udi = udi; };
/**
* get volume UDI for transfer device.
*
* @return volume UDI
*/
QString getVolumeUDI() const { return volume_udi; };
/**
* set filesystem type for transfer device (e.g. "ext3").
*
* @param fs filesystem type
*/
void setVolumeFS(QString fs) { volume_fs = fs; };
/**
* get filesystem type of transfer device.
*
* @return filesystem type
*/
QString getVolumeFS() const { return volume_fs; };
/**
* set volume size for transfer device.
*
* @param fs filesystem type
*/
void setVolumeSize(qlonglong size) { volume_size = size; };
/**
* get volume size for volume of transfer device as qlonglong.
*
* @return filesystem size in bytes
*/
qlonglong getVolumeSize() const { return volume_size; };
/**
* get volume size for volume of transfer device as QString.
*
* @return filesystem size in human readable string format
*/
QString getVolumeSizeStr() const;
/**
* set device UDI for transfer device.
*
* @param udi device UDI
*/
void setDeviceUDI(QString udi) { device_udi = udi; };
/**
* get device UDI for transfer device.
*
* @return device UDI
*/
QString getDeviceUDI() const { return device_udi; };
/**
* set device name for transfer device (e.g. /dev/sdc1).
*
* @param name device name
*/
void setDeviceName(QString name) { device_name = name; };
/**
* get device name of transfer device.
*
* @return device name
*/
QString getDeviceName() const { return device_name; };
/**
* set bus type used by transfer device (e.g. "usb").
*
* @param bus type of bus device is attached to (pci, usb, ...)
*/
void setDeviceBus(QString bus) { device_bus = bus; };
/**
* get bus type of transfer device.
*
* @return bus type
*/
QString getDeviceBus() const { return device_bus; };
/**
* set transfer device type (e.g. "disk").
*
* @param type transfer device storage type
*/
void setDeviceType(QString type) { device_type = type; };
/**
* get storage type of this transfer device.
*
* @return storage device type
*/
QString getDeviceType() const { return device_type; };
/**
* set mount point for transfer device (e.g. "/media/disk").
*
* @param path mount point of transfer device
*/
void setMountpoint(QString path) { mountpoint = path; };
/**
* get mount point path of transfer device.
*
* @return mount point path
*/
QString getMountpoint() const { return mountpoint; };
/**
* set mounted flag to true or false depending on whether transfer
* device volume is mounted or not.
*
* @param flag mounted status of volume
*/
void setMounted(bool flag) { is_mounted = flag; };
/**
* determines whether transfer device volume is already mounted or not.
*
* @return true if mounted, false if not
*/
bool isMounted() const { return is_mounted; };
/**
* set removable flag to true or false depending on whether device can
* be removed or not.
*
* @param flag removable status flag of device
*/
void setRemovable(bool flag) { is_removable = flag; };
/**
* determines whether device can be removed or not.
*
* @return true if portable, false if not
*/
bool isRemovable() const { return is_removable; };
/**
* set hotpluggable flag to true or false depending on whether device is
* hotpluggable.
*
* @param flag hotpluggable status flag of device
*/
void setHotpluggable(bool flag) { is_hotpluggable = flag; };
/**
* determines whether device is hotpluggable.
*
* @return true if yes, false if not
*/
bool isHotpluggable() const { return is_hotpluggable; };
/**
* debug function to dump transfer device settings.
*/
void dump() const;
/**
* mount transfer device
*
* @throw libfwbuilder::FWException could not mount exception
*/
void mount() throw(libfwbuilder::FWException);
private:
QString volume_udi;
QString volume_fs;
qlonglong volume_size;
QString device_udi;
QString device_name;
QString device_bus;
QString device_type;
QString mountpoint;
bool is_mounted;
bool is_removable;
bool is_hotpluggable;
};
/**
* @class TransferDeviceList
*
* @brief An TransferDeviceList is used to manage transfer devices of a system.
*
* An TransferDeviceList stores all available transfer volumes. It also
* provides a devicesChanged signal which can be used to track list changes.
* This signal is emitted when HAL detects a new device (DeviceAdded) or
* a device has vanished (DeviceRemoved). Users of an TransferDeviceList
* object can connect a slot to this signal to react to this event.
*/
class TransferDeviceList : public QObject, public std::list<TransferDevice>
{
Q_OBJECT
public:
/** TransferDeviceList ctor */
TransferDeviceList(QObject * parent = 0) : QObject(parent) {};
/** TransferDeviceList dtor */
virtual ~TransferDeviceList() {};
/**
* init list of volumes/devices. only usb based, portable volumes
* are added to the list. Previously added transfer devices will be
* cleared from the list before adding new ones.
*
* @throw libfwbuilder::FWException DBus not available exception
*/
void init() throw(libfwbuilder::FWException);
/**
* return specific TransferDevice identified by volume name.
*
* @param volumeid id of volume as QString (e.g. /dev/sdc1)
* @return iterator pointing to requested TransferDevice
*
*/
TransferDeviceList::const_iterator
getDeviceByName(const QString &name) const;
/**
* return specific TransferDevice identified by volume name.
*
* @param volumeid id of volume as string (e.g. /dev/sdc1)
* @return iterator pointing to requested TransferDevice
*
*/
TransferDeviceList::const_iterator
getDeviceByName(const std::string &name) const;
/**
* dump data of all managed transfer devices.
*/
void dump() const;
private:
#ifdef HAVE_QTDBUS
/**
* check DBus availability.
*/
bool checkDBus() const;
/**
* add a new transfer volume with given volume UDI.
*
* @param udi UDI of the volume to add.
* @return true if successfully added, false if not
*/
bool addNewVolume(const QString &udi);
/**
* remove an existing volume identified by UDI from the list.
*
* @param udi UDI of the volume to add.
* @return true if successfully removed, false if not found
*/
bool removeVolume(const QString &udi);
private slots:
void newDeviceDetected(const QString &udi);
void deviceRemovedDetected(const QString &udi);
signals:
void devicesChanged();
#endif
};
/**
* @class PredFindName
*
* @brief Predicate class to find device name in TransferDevice.
*
* PredFindName can be used e.g. as parameter in find_if() function to
* compare TransferDevices in TransferDeviceList with a given device name
* specified by setSearchString().
*/
class PredFindName
{
protected:
QString search_string;
public:
PredFindName() {};
bool operator()(const TransferDevice dev) const
{
return (dev.getDeviceName() == search_string);
}
void setSearchString(const QString &string)
{
search_string = string;
}
};
/**
* @class PredFindVolumeUDI
*
* @brief Predicate class to find volume UDI in TransferDevice.
*
* PredFindVolumeUDI can be used e.g. as parameter in find_if() function to
* compare TransferDevices in TransferDeviceList with a given volume UDI
* specified by setSearchString().
*/
class PredFindVolumeUDI
{
protected:
QString search_string;
public:
PredFindVolumeUDI() {};
bool operator()(const TransferDevice dev) const
{
return (dev.getVolumeUDI() == search_string);
}
void setSearchString(const QString &string)
{
search_string = string;
}
};
}
#endif /* __TRANSFER_DEVICE_HH__ */

View File

@ -0,0 +1,15 @@
#-*- mode: makefile; tab-width: 4; -*-
#
include(../../qmake.inc)
#
TEMPLATE = lib
#
SOURCES = TransferDevice.cpp
HEADERS = TransferDevice.h
CONFIG += staticlib
TARGET = fwtransfer
INSTALLS -= target

View File

@ -211,7 +211,9 @@ void ActionsDialog::applyChanges()
else
ropt->setInt("ipfw_classify_method",DUMMYNETQUEUE);
mw->updateLastModifiedTimestampForAllFirewalls(rule);
emit notify_changes_applied_sign();
// mw->updateLastModifiedTimestampForAllFirewalls(rule);
}
void ActionsDialog::discardChanges()

View File

@ -93,7 +93,8 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif

View File

@ -163,10 +163,9 @@ void AddressRangeDialog::applyChanges()
{
}
mw->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
m_project->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
//apply->setEnabled( false );
mw->updateLastModifiedTimestampForAllFirewalls(obj);
emit notify_changes_applied_sign();
}
void AddressRangeDialog::discardChanges()

View File

@ -68,7 +68,8 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif // ADDRESSRANGEDIALOG_H

View File

@ -150,10 +150,9 @@ void AddressTableDialog::applyChanges()
s->setSourceName( (const char *)cs );
s->setRunTime(m_dialog->r_runtime->isChecked() );
mw->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
m_project->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
//apply->setEnabled( false );
mw->updateLastModifiedTimestampForAllFirewalls(obj);
emit notify_changes_applied_sign();
}
void AddressTableDialog::discardChanges()

View File

@ -69,7 +69,8 @@ signals:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif

232
src/gui/ClusterDialog.cpp Normal file
View File

@ -0,0 +1,232 @@
/*
* ClusterDialog.cpp - Cluster view implementation
*
* Copyright (c) 2008 secunet Security Networks AG
* Copyright (c) 2008 Adrian-Ken Rueegsegger <rueegsegger@swiss-it.ch>
* Copyright (c) 2008 Reto Buerki <buerki@swiss-it.ch>
*
* This work is dual-licensed under:
*
* o The terms of the GNU General Public License as published by the Free
* Software Foundation, either version 2 of the License, or (at your option)
* any later version.
*
* o The terms of NetCitadel End User License Agreement
*/
#include "ClusterDialog.h"
#include "utils.h"
#include "platforms.h"
#include "DialogFactory.h"
#include "FWWindow.h"
#include "ProjectPanel.h"
#include "fwbuilder/Cluster.h"
#include "fwbuilder/StateSyncClusterGroup.h"
#include "fwbuilder/FailoverClusterGroup.h"
#include "fwbuilder/Resources.h"
#include "fwbuilder/Interface.h"
#include <qmessagebox.h>
using namespace std;
using namespace libfwbuilder;
ClusterDialog::~ClusterDialog()
{
delete m_dialog;
}
void ClusterDialog::getHelpName(QString *str)
{
*str = "ClusterDialog";
}
ClusterDialog::ClusterDialog(ProjectPanel *project, QWidget *parent)
: QWidget(parent), m_project(project), config_changed(false)
{
m_dialog = new Ui::ClusterDialog_q;
m_dialog->setupUi(this);
obj = NULL;
}
void ClusterDialog::loadFWObject(FWObject *o)
{
obj = o;
Cluster *s = dynamic_cast<Cluster*>(obj);
assert(s != NULL);
QString platform = obj->getStr("platform").c_str();
// fill in platform
setPlatform(m_dialog->platform, platform);
// fill in host OS
setHostOS(m_dialog->hostOS, platform, obj->getStr("host_OS").c_str());
/*
Management *mgmt = s->getManagementObject();
assert(mgmt != NULL);
*/
m_dialog->obj_name->setText(QString::fromUtf8(s->getName().c_str()));
m_dialog->comment->setText(QString::fromUtf8(s->getComment().c_str()));
m_dialog->inactive->setChecked(s->getInactive());
m_dialog->obj_name->setEnabled(!o->isReadOnly());
setDisabledPalette(m_dialog->obj_name);
m_dialog->platform->setEnabled(!o->isReadOnly());
setDisabledPalette(m_dialog->platform);
m_dialog->hostOS->setEnabled(!o->isReadOnly());
setDisabledPalette(m_dialog->hostOS);
/*
m_dialog->fwAdvanced->setEnabled(!o->isReadOnly());
setDisabledPalette(m_dialog->fwAdvanced);
m_dialog->osAdvanced->setEnabled(!o->isReadOnly());
setDisabledPalette(m_dialog->osAdvanced);
*/
m_dialog->comment->setReadOnly(o->isReadOnly());
setDisabledPalette(m_dialog->comment);
m_dialog->inactive->setEnabled(!o->isReadOnly());
setDisabledPalette(m_dialog->inactive);
}
void ClusterDialog::platformChanged()
{
config_changed = true;
changed();
QString platform = readPlatform(m_dialog->platform);
setHostOS(m_dialog->hostOS, platform, "");
QString pl = readPlatform(m_dialog->platform);
resetClusterGroupTypes();
}
void ClusterDialog::hostOSChanged()
{
if (readHostOS(m_dialog->hostOS).toLatin1().constData() !=
obj->getStr("host_OS"))
{
config_changed = true;
resetClusterGroupTypes();
changed();
}
}
/*
* Check if type of failover and state sync groups matches current
* platform/host os configuration and if not, fix it.
*/
void ClusterDialog::resetClusterGroupTypes()
{
QString host_os = readHostOS(m_dialog->hostOS);
list<QStringPair> state_sync_types;
getStateSyncTypesForOS(host_os, state_sync_types);
for (FWObjectTypedChildIterator it = obj->findByType(StateSyncClusterGroup::TYPENAME);
it != it.end(); ++it)
resetSingleClusterGroupType(*it, state_sync_types);
list<QStringPair> failover_types;
getFailoverTypesForOS(host_os, failover_types);
list<FWObject*> failover_groups = obj->getByTypeDeep(FailoverClusterGroup::TYPENAME);
for (list<FWObject*>::iterator it = failover_groups.begin(); it != failover_groups.end(); ++it)
resetSingleClusterGroupType(*it, failover_types);
}
void ClusterDialog::resetSingleClusterGroupType(FWObject *grp,
list<QStringPair> &allowed_types)
{
string first_allowed_type;
bool match = false;
foreach(QStringPair p, allowed_types)
{
if (first_allowed_type.empty()) first_allowed_type = p.first.toStdString();
if (grp->getStr("type") == p.first.toStdString())
match = true;
}
if (!match) grp->setStr("type", first_allowed_type);
}
void ClusterDialog::changed()
{
emit changed_sign();
}
void ClusterDialog::validate(bool *res)
{
*res = true;
if (!isTreeReadWrite(this, obj))
{
*res = false;
return;
}
if (!validateName(this, obj, m_dialog->obj_name->text()))
{
*res = false;
return;
}
}
void ClusterDialog::libChanged()
{
changed();
}
void ClusterDialog::applyChanges()
{
Cluster *s = dynamic_cast<Cluster*>(obj);
assert(s != NULL);
string oldname = obj->getName();
string newname = string(m_dialog->obj_name->text().toUtf8().constData());
string oldplatform = obj->getStr("platform");
obj->setName(newname);
obj->setComment(string(m_dialog->comment->toPlainText().toUtf8().constData()));
string pl = readPlatform(m_dialog->platform).toLatin1().constData();
obj->setStr("platform", pl);
obj->setStr("host_OS", readHostOS(m_dialog->hostOS).toLatin1().constData());
s->setInactive(m_dialog->inactive->isChecked());
m_project->updateObjName(obj, QString::fromUtf8(oldname.c_str()));
if (oldplatform != pl || oldname != newname)
{
m_project->scheduleRuleSetRedraw();
}
emit notify_changes_applied_sign();
}
void ClusterDialog::discardChanges()
{
loadFWObject(obj);
}
/**
* ObjectEditor class connects its slot to this signal and does all
* the verification for us, then accepts (or not) the event. So we do
* nothing here and defer all the processing to ObjectEditor
*/
void ClusterDialog::closeEvent(QCloseEvent *e)
{
emit close_sign(e);
}

76
src/gui/ClusterDialog.h Normal file
View File

@ -0,0 +1,76 @@
/*
* ClusterDialog.h - Cluster object view
*
* Copyright (c) 2008 secunet Security Networks AG
* Copyright (c) 2008 Adrian-Ken Rueegsegger <rueegsegger@swiss-it.ch>
* Copyright (c) 2008 Reto Buerki <buerki@swiss-it.ch>
*
* This work is dual-licensed under:
*
* o The terms of the GNU General Public License as published by the Free
* Software Foundation, either version 2 of the License, or (at your option)
* any later version.
*
* o The terms of NetCitadel End User License Agreement
*/
#ifndef __CLUSTERDIALOG_H_
#define __CLUSTERDIALOG_H_
#include "../../config.h"
#include <ui_clusterdialog_q.h>
#include <QWidget>
#include "utils.h"
#include "fwbuilder/FWObject.h"
class ProjectPanel;
class ClusterDialog : public QWidget
{
Q_OBJECT
libfwbuilder::FWObject *obj;
Ui::ClusterDialog_q *m_dialog;
ProjectPanel *m_project;
void resetSingleClusterGroupType(libfwbuilder::FWObject *grp,
std::list<QStringPair> &allowed_types);
void resetClusterGroupTypes();
public:
ClusterDialog(ProjectPanel *project, QWidget *parent);
~ClusterDialog();
private:
/** flag to indicate host os, platform changes */
bool config_changed;
public slots:
virtual void changed();
virtual void libChanged();
virtual void applyChanges();
virtual void discardChanges();
virtual void platformChanged();
virtual void hostOSChanged();
virtual void loadFWObject(libfwbuilder::FWObject *obj);
virtual void validate(bool*);
virtual void closeEvent(QCloseEvent *e);
virtual void getHelpName(QString*);
signals:
/**
* This signal is emitted from closeEvent, ObjectEditor connects
* to this signal to make checks before the object editor can be closed
* and to store its position on the screen
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif /* __CLUSTERDIALOG_H_ */

View File

@ -0,0 +1,374 @@
/*
* ClusterGroupDialog.cpp - ClusterGroup view implementation
*
* Copyright (c) 2008 secunet Security Networks AG
* Copyright (c) 2008 Adrian-Ken Rueegsegger <rueegsegger@swiss-it.ch>
* Copyright (c) 2008 Reto Buerki <buerki@swiss-it.ch>
*
* This work is dual-licensed under:
*
* o The terms of the GNU General Public License as published by the Free
* Software Foundation, either version 2 of the License, or (at your option)
* any later version.
*
* o The terms of NetCitadel End User License Agreement
*/
#include "ClusterGroupDialog.h"
#include "utils.h"
#include "platforms.h"
#include "events.h"
#include "ObjectListViewItem.h"
#include "FWWindow.h"
#include "ProjectPanel.h"
#include "DialogFactory.h"
#include "vrrpOptionsDialog.h"
#include "fwbuilder/Cluster.h"
#include "fwbuilder/StateSyncClusterGroup.h"
#include "fwbuilder/FailoverClusterGroup.h"
#include "fwbuilder/Resources.h"
#include "fwbuilder/Interface.h"
#include <qpixmapcache.h>
#include <qmessagebox.h>
#include <qdialog.h>
#include <QCoreApplication>
#include <algorithm>
#include <iostream>
using namespace std;
using namespace libfwbuilder;
ClusterGroupDialog::~ClusterGroupDialog()
{
delete m_dialog;
}
void ClusterGroupDialog::getHelpName(QString *str)
{
*str = "ClusterGroupDialog";
}
ClusterGroupDialog::ClusterGroupDialog(ProjectPanel *project, QWidget *parent)
: QWidget(parent), m_project(project), reload(false)
{
m_dialog = new Ui::ClusterGroupDialog_q;
m_dialog->setupUi(this);
obj = NULL;
}
void ClusterGroupDialog::loadFWObject(FWObject *o)
{
obj = o;
ClusterGroup *g = dynamic_cast<ClusterGroup*>(obj);
assert(g != NULL);
// disable manage members if host OS does not support clustering.
// Parent is either 'Cluster' or 'Interface', call getParent() approprietly
FWObject *parent = obj;
while (parent && !Cluster::isA(parent)) parent = parent->getParent();
if (parent == NULL)
{
throw FWException("ClusterGroupDialog: parent is NULL!");
}
cluster = Cluster::cast(parent);
QString host_os = cluster->getStr("host_OS").c_str();
// Sanity check
// Failover type could be wrong if user changed host OS of the cluster
QString type = obj->getStr("type").c_str();
list<QStringPair> possible_cluster_group_types;
if (StateSyncClusterGroup::isA(o))
getStateSyncTypesForOS(host_os, possible_cluster_group_types);
if (FailoverClusterGroup::isA(o))
getFailoverTypesForOS(host_os, possible_cluster_group_types);
enable_master_column = Resources::os_res[host_os.toStdString()]->getResourceBool(
"/FWBuilderResources/Target/protocols/" + type.toStdString() + "/needs_master");
if (!enable_master_column)
m_dialog->fwMemberTree->hideColumn(2);
bool acceptable_failover_type = false;
for (list<QStringPair>::iterator it=possible_cluster_group_types.begin();
it!=possible_cluster_group_types.end(); ++it)
{
QString t = it->first;
if (t == type)
{
acceptable_failover_type = true;
break;
}
}
if (!acceptable_failover_type && possible_cluster_group_types.size())
obj->setStr(
"type", possible_cluster_group_types.front().first.toStdString());
m_dialog->obj_name->setText(QString::fromUtf8(g->getName().c_str()));
m_dialog->comment->setText(QString::fromUtf8(g->getComment().c_str()));
m_dialog->obj_name->setEnabled(!o->isReadOnly());
setDisabledPalette(m_dialog->obj_name);
m_dialog->comment->setReadOnly(o->isReadOnly());
setDisabledPalette(m_dialog->comment);
QString grp_type = obj->getStr("type").c_str();
m_dialog->type->clear();
int cp = 0;
for (list<QStringPair>::iterator i1=possible_cluster_group_types.begin();
i1!=possible_cluster_group_types.end(); i1++,cp++)
{
m_dialog->type->addItem( i1->second );
if ( grp_type == i1->first ) m_dialog->type->setCurrentIndex(cp);
}
// init link icons, master firewall is colored
m_dialog->fwMemberTree->clear();
std::string master_iface = g->getStr("master_iface");
for (FWObject::iterator it = g->begin(); it != g->end(); it++)
{
FWObject *co = *it;
if (FWReference::cast(co)!=NULL)
{
FWObject *o = FWReference::cast(*it)->getPointer();
if (master_iface == FWObjectDatabase::getStringId(o->getId()))
{
addIcon(o, true);
}
else
{
addIcon(o);
}
}
}
if (!Resources::getTargetCapabilityBool(host_os.toStdString(),
"supports_cluster"))
{
m_dialog->manageMembers->setEnabled(false);
m_dialog->manageMembers->setToolTip("Feature not supported "
"by host OS '" + host_os + "'");
}
else
{
m_dialog->manageMembers->setEnabled(true);
m_dialog->manageMembers->setToolTip("Click here to manage member "
"firewalls of this cluster group.");
}
m_dialog->fwMemberTree->resizeColumnToContents(0);
m_dialog->fwMemberTree->resizeColumnToContents(1);
m_dialog->fwMemberTree->resizeColumnToContents(2);
m_dialog->fwMemberTree->resizeColumnToContents(3);
}
void ClusterGroupDialog::saveGroupType()
{
QString host_os = cluster->getStr("host_OS").c_str();
list<QStringPair> possible_cluster_group_types;
if (StateSyncClusterGroup::isA(obj)) getStateSyncTypesForOS(host_os, possible_cluster_group_types);
if (FailoverClusterGroup::isA(obj)) getFailoverTypesForOS(host_os, possible_cluster_group_types);
QString grp_type = m_dialog->type->currentText();
list<QStringPair>::iterator li =
std::find_if(possible_cluster_group_types.begin(), possible_cluster_group_types.end(), findSecondInQStringPair(grp_type));
if (li != possible_cluster_group_types.end())
obj->setStr("type", li->first.toLatin1().constData() );
}
void ClusterGroupDialog::addIcon(FWObject *o, bool master)
{
FWObject *iface = o;
assert(Interface::cast(iface)!=NULL);
FWObject *fw = Interface::cast(iface)->getParentHost(); // because iface can be subinterface
bool valid = cluster->validateMember(Firewall::cast(fw));
QString iface_name = QString::fromUtf8(iface->getName().c_str());
QString fw_name = QString::fromUtf8(fw->getName().c_str());
QString iface_icn_file = (":/Icons/" + iface->getTypeName() +
"/icon-ref").c_str();
QString fw_icn_file = (":/Icons/" + fw->getTypeName() +
"/icon-ref").c_str();
QPixmap iface_pm;
if (!QPixmapCache::find(iface_icn_file, iface_pm))
{
iface_pm.load(iface_icn_file);
QPixmapCache::insert(iface_icn_file, iface_pm);
}
QPixmap fw_pm;
if (!QPixmapCache::find(fw_icn_file, fw_pm))
{
fw_pm.load(fw_icn_file);
QPixmapCache::insert(fw_icn_file, fw_pm);
}
ObjectListViewItem *item = new ObjectListViewItem(m_dialog->fwMemberTree);
int col = 0;
item->setText(col, fw_name);
item->setIcon(col, QIcon(fw_pm));
col++;
item->setText(col, iface_name);
item->setIcon(col, QIcon(iface_pm));
col++;
// note that if enable_master_column==false, this column is hidden
// but we still need to create an item in this column.
if (master) item->setText(col, tr("Master"));
else item->setText(col, tr(""));
col++;
if (valid)
{
item->setText(col, "OK");
item->setToolTip(
col, tr("Firewall %1 can be used as a member of this cluster").arg(fw->getName().c_str()));
} else
{
item->setText(col, tr("Invalid"));
item->setToolTip(
col, tr("Firewall %1 can not be used as a member of this cluster\n because its host OS or platform does not match those of the cluster.").arg(fw->getName().c_str()));
item->setBackgroundColor(col, QColor(255, 0, 0, 100));
}
item->setProperty("type", iface->getTypeName().c_str());
item->setFWObject(iface);
}
void ClusterGroupDialog::changed()
{
if (!reload)
{
emit changed_sign();
}
}
void ClusterGroupDialog::validate(bool *res)
{
*res = true;
if (!isTreeReadWrite(this, obj))
{
*res = false;
}
if (!validateName(this, obj, m_dialog->obj_name->text()))
{
*res = false;
}
}
void ClusterGroupDialog::applyChanges()
{
ClusterGroup *g = dynamic_cast<ClusterGroup*>(obj);
assert(g != NULL);
QString oldname = obj->getName().c_str();
obj->setName(string(m_dialog->obj_name->text().toUtf8().constData()));
obj->setComment(string(m_dialog->comment->toPlainText().toUtf8().constData()));
saveGroupType();
m_project->updateObjName(obj, oldname);
emit notify_changes_applied_sign();
}
void ClusterGroupDialog::discardChanges()
{
loadFWObject(obj);
}
/*
* This method is connected to the "Edit members" button and opens dialog
* where user chooses cluster member firewalls and interfaces
*/
void ClusterGroupDialog::openClusterConfDialog()
{
try
{
applyChanges();
QWidget *w = DialogFactory::createClusterConfDialog(this, obj);
if (w == NULL)
{
return; // some dialogs may not be implemented yet
}
QDialog *d = dynamic_cast<QDialog*>(w);
assert(d != NULL);
// connect obj changed signal
connect(d, SIGNAL(membersChanged()), this, SLOT(objectChanged()));
d->exec();
delete d;
}
catch (FWException &ex)
{
QMessageBox::critical(
this, "Firewall Builder",
tr("FWBuilder API error: %1").arg(ex.toString().c_str()),
tr("&Continue"), QString::null, QString::null, 0, 1);
return;
}
}
/**
* ObjectEditor class connects its slot to this signal and does all
* the verification for us, then accepts (or not) the event. So we do
* nothing here and defer all the processing to ObjectEditor
*/
void ClusterGroupDialog::closeEvent(QCloseEvent *e)
{
emit close_sign(e);
}
void ClusterGroupDialog::openObject(QTreeWidgetItem *item)
{
ObjectListViewItem *otvi = dynamic_cast<ObjectListViewItem*>(item);
assert(otvi != NULL);
FWObject *o = otvi->getFWObject();
if (o != NULL)
{
QCoreApplication::postEvent(
mw, new showObjectInTreeEvent(o->getRoot()->getFileName().c_str(),
o->getId()));
}
}
void ClusterGroupDialog::objectChanged()
{
reload = true;
loadFWObject(obj);
reload = false;
}
/*
* this method is connected to the "Edit protocol parameters" button
* and opens dialog where user edits state sync and failover
* (heartbeat/openais/vrrp/carp/conntrack/etc) protocol parameters.
*/
void ClusterGroupDialog::openParametersEditor()
{
applyChanges();
FWOptions *gr_opt = ClusterGroup::cast(obj)->getOptionsObject();
QDialog *dlg = dynamic_cast<QDialog*>(
DialogFactory::createClusterGroupOptionsDialog(this, gr_opt));
if (dlg)
{
dlg->exec();
delete dlg;
}
}

View File

@ -0,0 +1,87 @@
/*
* ClusterGroupDialog.h - ClusterGroup object view
*
* Copyright (c) 2008 secunet Security Networks AG
* Copyright (c) 2008 Adrian-Ken Rueegsegger <rueegsegger@swiss-it.ch>
* Copyright (c) 2008 Reto Buerki <buerki@swiss-it.ch>
*
* This work is dual-licensed under:
*
* o The terms of the GNU General Public License as published by the Free
* Software Foundation, either version 2 of the License, or (at your option)
* any later version.
*
* o The terms of NetCitadel End User License Agreement
*/
#ifndef __CLUSTERGROUPDIALOG_H_
#define __CLUSTERGROUPDIALOG_H_
#include "../../config.h"
#include <ui_clustergroupdialog_q.h>
#include "fwbuilder/FWObject.h"
class ProjectPanel;
namespace libfwbuilder {
class Cluster;
}
class ClusterGroupDialog : public QWidget
{
Q_OBJECT
libfwbuilder::FWObject *obj;
libfwbuilder::Cluster *cluster;
Ui::ClusterGroupDialog_q *m_dialog;
bool init;
bool enable_master_column;
ProjectPanel *m_project;
void saveGroupType();
public:
ClusterGroupDialog(ProjectPanel *project, QWidget *parent);
~ClusterGroupDialog();
private:
/** flag to indicate that a reload of the obj takes place */
bool reload;
/**
* add fw/interface link icon to the fwMemberTree
*
* @param o fwobject to add a link for
* @param set_background if true, a different background color is used
*/
void addIcon(libfwbuilder::FWObject *o, bool set_background = false);
public slots:
virtual void changed();
virtual void applyChanges();
virtual void discardChanges();
virtual void validate(bool*);
virtual void loadFWObject(libfwbuilder::FWObject *obj);
virtual void openClusterConfDialog();
virtual void closeEvent(QCloseEvent *e);
virtual void getHelpName(QString*);
void openObject(QTreeWidgetItem *item);
void objectChanged();
void openParametersEditor();
signals:
/**
* This signal is emitted from closeEvent, ObjectEditor connects
* to this signal to make checks before the object editor can be closed
* and to store its position on the screen
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif /* __CLUSTERDIALOG_H_ */

14
src/gui/ColDesc.cpp Executable file
View File

@ -0,0 +1,14 @@
#include "ColDesc.h"
#include "platforms.h"
ColDesc::ColDesc()
{
this->type = Unknown;
}
ColDesc::ColDesc(QString origin, ColumnType type)
{
this->origin = origin;
this->name = getReadableRuleElementName(origin.toStdString());
this->type = type;
}

32
src/gui/ColDesc.h Executable file
View File

@ -0,0 +1,32 @@
#ifndef COLDESC_H
#define COLDESC_H
#include <QMetaType>
class ColDesc
{
public:
enum ColumnType
{
GroupHandle,
RuleOp,
Object,
Action,
Direction,
Options,
Time,
Comment,
Metric,
Unknown
};
ColDesc(QString origin, ColumnType type);
ColDesc();
QString name;
QString origin;
ColumnType type;
};
Q_DECLARE_METATYPE(ColDesc)
#endif // COLDESC_H

View File

@ -115,10 +115,12 @@ void CommentEditorPanel::applyChanges()
{
if (fwbdebug) qDebug("CommentEditorPanel::applyChanges()");
mw->updateLastModifiedTimestampForAllFirewalls(rule);
// mw->updateLastModifiedTimestampForAllFirewalls(rule);
rule->setComment(
string(m_widget->editor->toPlainText().toUtf8().constData())
);
emit notify_changes_applied_sign();
}
void CommentEditorPanel::getHelpName(QString *str)

View File

@ -71,6 +71,7 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif

View File

@ -0,0 +1,57 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "CompilerDriverFactory.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/FWObjectDatabase.h"
#include "CompilerDriver_ipt.h"
#include "CompilerDriver_pf.h"
#include "CompilerDriver_ipf.h"
#include "CompilerDriver_ipfw.h"
#include "CompilerDriver_iosacl.h"
#include "CompilerDriver_pix.h"
#include <string>
using namespace libfwbuilder;
using namespace fwcompiler;
using namespace std;
CompilerDriver* CompilerDriverFactory::createCompilerDriver(Firewall *fw)
{
string platform = fw->getStr("platform");
if (platform == "iptables") return new CompilerDriver_ipt(fw->getRoot());
if (platform == "pf") return new CompilerDriver_pf(fw->getRoot());
if (platform == "ipf") return new CompilerDriver_ipf(fw->getRoot());
if (platform == "ipfw") return new CompilerDriver_ipfw(fw->getRoot());
if (platform == "iosacl") return new CompilerDriver_iosacl(fw->getRoot());
if (platform == "pix") return new CompilerDriver_pix(fw->getRoot());
return NULL;
}

View File

@ -0,0 +1,42 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@vk.crocodile.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef __COMPILER_DRIVER_FACTORY_HH__
#define __COMPILER_DRIVER_FACTORY_HH__
#include "CompilerDriver.h"
namespace libfwbuilder {
class Firewall;
};
class CompilerDriverFactory {
public:
static fwcompiler::CompilerDriver *createCompilerDriver(libfwbuilder::Firewall *fw);
};
#endif

View File

@ -0,0 +1,218 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@fwbuilder.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include "global.h"
#include "CompilerOutputPanel.h"
#include "FWBSettings.h"
#include "ObjectManipulator.h"
#include "FWWindow.h"
#include "ProjectPanel.h"
#include "CompilerDriverFactory.h"
#include "fwbuilder/FWObjectDatabase.h"
#include "fwcompiler/BaseCompiler.h"
#include <QTextFormat>
#include <QStatusBar>
#include <fstream>
using namespace std;
using namespace libfwbuilder;
using namespace fwcompiler;
CompilerOutputPanel::CompilerOutputPanel(ProjectPanel *project, QWidget *parent) :
QWidget(parent)
{
m_project = project;
m_widget = new Ui::CompilerOutputPanel_q;
m_widget->setupUi(this);
}
CompilerOutputPanel::~CompilerOutputPanel()
{
delete m_widget;
}
void CompilerOutputPanel::changed()
{
emit changed_sign();
}
void CompilerOutputPanel::applyChanges()
{
emit notify_changes_applied_sign();
}
void CompilerOutputPanel::discardChanges()
{
}
void CompilerOutputPanel::getHelpName(QString *str)
{
*str = "CompilerOutputPanel";
}
void CompilerOutputPanel::loadFWObject(FWObject *obj)
{
if (fwbdebug)
qDebug("CompilerOutputPanel::loadFWObject obj id=%s",
FWObjectDatabase::getStringId(obj->getId()).c_str());
list<string> err_re;
BaseCompiler::errorRegExp(&err_re);
foreach(string re, err_re)
{
error_re.push_back(QRegExp(re.c_str()));
}
list<string> warn_re;
BaseCompiler::warningRegExp(&warn_re);
foreach(string re, warn_re)
{
warning_re.push_back(QRegExp(re.c_str()));
}
QApplication::setOverrideCursor( QCursor( Qt::WaitCursor) );
QStatusBar *sb = mw->statusBar();
sb->showMessage( tr("Compiling rule...") );
QCoreApplication::processEvents(QEventLoop::ExcludeUserInputEvents);
FWObject *p = obj;
// use Firewall::cast to match both Firewall and Cluster
while (!Firewall::cast(p)) p = p->getParent();
Firewall *fw = Firewall::cast(p);
Rule *rule = Rule::cast(obj);
CompilerDriver *dr = CompilerDriverFactory::createCompilerDriver(fw);
// run in test mode to prevent fatal errors from causing exit
dr->setTestMode();
dr->setEmbeddedMode();
QTextCharFormat format;
QTextCharFormat normal_format;
QTextCharFormat bold_format;
QTextCharFormat error_format;
QTextCharFormat warning_format;
QTextCursor cursor(m_widget->compiler_output_panel->textCursor());
format = cursor.charFormat();
format.setFont(st->getCompilerOutputFont());
normal_format = format;
normal_format.setForeground(QBrush(Qt::black));
bold_format = format;
bold_format.setProperty(QTextFormat::FontWeight, 99);
bold_format.setForeground(QBrush(Qt::black));
error_format = format;
error_format.setForeground(QBrush(Qt::red));
error_format.setProperty(QTextFormat::FontWeight, 99);
warning_format = format;
warning_format.setForeground(QBrush(Qt::blue));
warning_format.setProperty(QTextFormat::FontWeight, 99);
m_widget->compiler_output_panel->clear();
try
{
QMapIterator<QString,QString> it(
dr->compileSingleRule(FWObjectDatabase::getStringId(rule->getId())));
QTextCursor cursor = m_widget->compiler_output_panel->textCursor();
while (it.hasNext())
{
it.next();
QString dbg;
if (fwbdebug)
dbg = QString("(id: %1)").arg(
FWObjectDatabase::getStringId(rule->getId()).c_str());
QString title("%1 / %2 / rule %3 %4\n");
cursor.insertText(title
.arg(it.key())
.arg(rule->getParent()->getName().c_str())
.arg(rule->getPosition())
.arg(dbg), bold_format);
foreach (QString line, it.value().trimmed().split("\n"))
{
format = normal_format;
list<QRegExp>::const_iterator it;
for (it=error_re.begin(); it!=error_re.end(); ++it)
{
if ((*it).indexIn(line) != -1)
{
format = error_format;
break;
}
}
for (it=warning_re.begin(); it!=warning_re.end(); ++it)
{
if ((*it).indexIn(line) != -1)
{
format = warning_format;
break;
}
}
cursor.insertText(line + "\n", format);
}
cursor.insertText("\n");
cursor.insertBlock();
}
} catch (FWException &e)
{
m_widget->compiler_output_panel->append(e.toString().c_str());
m_widget->compiler_output_panel->append("\n");
}
QApplication::restoreOverrideCursor();
sb->clearMessage();
delete dr;
}
void CompilerOutputPanel::validate(bool* b )
{
*b=true;
}
void CompilerOutputPanel::isChanged(bool *)
{
}
void CompilerOutputPanel::closeEvent(QCloseEvent *)
{
}

View File

@ -0,0 +1,81 @@
/*
Firewall Builder
Copyright (C) 2009 NetCitadel, LLC
Author: Vadim Kurland vadim@fwbuilder.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef __COMPILEROUTPUTPANEL_H__
#define __COMPILEROUTPUTPANEL_H__
#include "../../config.h"
#include <ui_compileroutputpanel_q.h>
#include "fwbuilder/FWObject.h"
#include "fwbuilder/Rule.h"
#include "fwbuilder/Firewall.h"
#include <QRegExp>
#include <list>
class ProjectPanel;
class CompilerOutputPanel : public QWidget
{
Q_OBJECT;
libfwbuilder::RoutingRule *rule;
Ui::CompilerOutputPanel_q *m_widget;
ProjectPanel *m_project;
std::list<QRegExp> error_re;
std::list<QRegExp> warning_re;
public:
CompilerOutputPanel(ProjectPanel *project, QWidget* parent);
~CompilerOutputPanel();
public slots:
virtual void changed();
virtual void applyChanges();
virtual void discardChanges();
virtual void loadFWObject(libfwbuilder::FWObject *obj);
virtual void validate(bool*);
virtual void isChanged(bool*);
virtual void getHelpName(QString*);
virtual void closeEvent(QCloseEvent *e);
signals:
/**
* This signal is emitted from closeEvent, ObjectEditor connects
* to this signal to make checks before the object editor can be closed
* and to store its position on the screen
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif

View File

@ -101,7 +101,10 @@ void ConfirmDeleteObjectDialog::findForObject(FWObject *obj)
QPixmapCache::insert( icn_file, pm0);
}
mw->db()->findWhereObjectIsUsed(obj, mw->db(), resset);
FWObjectDatabase *db = obj->getRoot();
assert(db);
db->findWhereObjectIsUsed(obj, db, resset);
FindWhereUsedWidget::humanizeSearchResults(resset);
if (fwbdebug)

View File

@ -230,10 +230,9 @@ void CustomServiceDialog::applyChanges()
int af = (m_dialog->ipv6->isChecked()) ? AF_INET6 : AF_INET;
s->setAddressFamily(af);
mw->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
m_project->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
//apply->setEnabled( false );
mw->updateLastModifiedTimestampForAllFirewalls(obj);
emit notify_changes_applied_sign();
}
void CustomServiceDialog::discardChanges()

View File

@ -78,7 +78,8 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif // CUSTOMSERVICEDIALOG_H

View File

@ -141,10 +141,10 @@ void DNSNameDialog::applyChanges()
s->setSourceName( m_dialog->dnsrec->text().toLatin1().constData() );
s->setRunTime(m_dialog->r_runtime->isChecked() );
mw->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
m_project->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
emit notify_changes_applied_sign();
//apply->setEnabled( false );
mw->updateLastModifiedTimestampForAllFirewalls(obj);
}
void DNSNameDialog::discardChanges()

View File

@ -67,7 +67,8 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif

View File

@ -50,6 +50,8 @@
#include "GroupObjectDialog.h"
#include "HostDialog.h"
#include "FirewallDialog.h"
#include "ClusterDialog.h"
#include "ClusterGroupDialog.h"
#include "InterfaceDialog.h"
#include "TimeDialog.h"
#include "TagServiceDialog.h"
@ -62,6 +64,14 @@
#include "iosaclAdvancedDialog.h"
#include "ipcopAdvancedDialog.h"
#include "secuwallAdvancedDialog.h"
#include "linux24IfaceOptsDialog.h"
#include "secuwallIfaceOptsDialog.h"
#include "vlanOnlyIfaceOptsDialog.h"
#include "openbsdIfaceOptsDialog.h"
#include "clusterMembersDialog.h"
#include "linux24AdvancedDialog.h"
#include "linksysAdvancedDialog.h"
#include "freebsdAdvancedDialog.h"
@ -76,9 +86,18 @@
#include "RoutingRuleOptionsDialog.h"
#include "NATRuleOptionsDialog.h"
#include "vrrpOptionsDialog.h"
#include "carpOptionsDialog.h"
#include "conntrackOptionsDialog.h"
#include "heartbeatOptionsDialog.h"
#include "openaisOptionsDialog.h"
#include "pfsyncOptionsDialog.h"
#include "fwbuilder/Library.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/Cluster.h"
#include "fwbuilder/StateSyncClusterGroup.h"
#include "fwbuilder/FailoverClusterGroup.h"
#include "fwbuilder/Host.h"
#include "fwbuilder/Network.h"
#include "fwbuilder/NetworkIPv6.h"
@ -138,6 +157,12 @@ QWidget *DialogFactory::createDialog(ProjectPanel *project, QWidget *parent,cons
if (objType==Firewall::TYPENAME) return new FirewallDialog(project, parent);
if (objType==Cluster::TYPENAME) return new ClusterDialog(project, parent);
if (objType==StateSyncClusterGroup::TYPENAME) return new ClusterGroupDialog(project, parent);
if (objType==FailoverClusterGroup::TYPENAME) return new ClusterGroupDialog(project, parent);
if (objType==Host::TYPENAME) return new HostDialog(project, parent);
if (objType==Interface::TYPENAME) return new InterfaceDialog(project, parent);
@ -241,6 +266,7 @@ QWidget *DialogFactory::createOSDialog(QWidget *parent,FWObject *o)
if (dlgname=="pix_os") return new pixosAdvancedDialog(parent, o);
if (dlgname=="ios") return new iosAdvancedDialog(parent, o);
if (dlgname=="ipcop") return new ipcoposAdvancedDialog(parent, o);
if (dlgname=="secuwall") return new secuwallAdvancedDialog(parent, o);
cerr << "OS settings dialog for " << dlgname
<< " is not implemented" << endl;
@ -248,4 +274,80 @@ QWidget *DialogFactory::createOSDialog(QWidget *parent,FWObject *o)
return NULL;
}
QWidget *DialogFactory::createIfaceDialog(QWidget *parent,FWObject *o)
throw(FWException)
{
FWObject *h = Interface::cast(o)->getParentHost();
string host_OS = h->getStr("host_OS");
Resources *os = Resources::os_res[host_OS];
if (os==NULL)
throw FWException((const char*)(
QObject::tr("Support module for %1 is not available").
arg(host_OS.c_str()).toLocal8Bit().constData()));
string dlgname = os->Resources::getResourceStr("/FWBuilderResources/Target/interface_dialog");
// add further dlgname support here ...
if (dlgname=="secuwall") return new secuwallIfaceOptsDialog(parent, o);
if (dlgname=="linux24") return new linux24IfaceOptsDialog(parent, o);
if (dlgname=="openbsd") return new openbsdIfaceOptsDialog(parent, o);
if (dlgname=="vlan_only") return new vlanOnlyIfaceOptsDialog(parent, o);
cerr << "Interface settings dialog for OS " << host_OS
<< " is not implemented" << endl;
return NULL;
}
QWidget *DialogFactory::createClusterConfDialog(QWidget *parent, FWObject *o)
throw(FWException)
{
FWObject *objparent = o->getParent();
while (objparent && objparent->getTypeName()!="Cluster")
objparent = objparent->getParent();
assert(objparent);
string host_OS = objparent->getStr("host_OS");
Resources *os = Resources::os_res[host_OS];
string dlgname = os->Resources::getResourceStr("/FWBuilderResources/Target/cluster_dialog");
// add further dlgname support here ...
if (dlgname == "basic") return new clusterMembersDialog(parent, o);
cerr << "Cluster configuration dialog for OS " << host_OS
<< " is not implemented" << endl;
return NULL;
}
/*
* Create cluster group options dialog; dialog class depends on the
* cluster group type. Argument <o> is FWOptions object which is
* a child of ClusterGroup object
*/
QWidget *DialogFactory::createClusterGroupOptionsDialog(QWidget *parent,
FWObject *o)
throw(libfwbuilder::FWException)
{
FWObject *cluster_group = o->getParent();
assert(ClusterGroup::cast(cluster_group)!=NULL);
string type = ClusterGroup::cast(cluster_group)->getStr("type");
if (type == "conntrack") return new conntrackOptionsDialog(parent, o);
if (type == "pfsync") return new pfsyncOptionsDialog(parent, o);
if (type == "vrrp") return new vrrpOptionsDialog(parent, o);
if (type == "carp") return new carpOptionsDialog(parent, o);
if (type == "heartbeat") return new heartbeatOptionsDialog(parent, o);
if (type == "openais") return new openaisOptionsDialog(parent, o);
// Add more cluster group options dialog here
return NULL;
}

View File

@ -23,13 +23,18 @@
*/
#ifndef _DIALOGFACTORY_HH_
#define _DIALOGFACTORY_HH_
#include <qwidget.h>
namespace libfwbuilder {
class FWObject;
class FWException;
};
class ProjectPanel;
class DialogFactory {
public:
@ -39,5 +44,12 @@ class DialogFactory {
throw(libfwbuilder::FWException);
static QWidget *createOSDialog(QWidget *parent,libfwbuilder::FWObject *o)
throw(libfwbuilder::FWException);
static QWidget *createIfaceDialog(QWidget *parent,libfwbuilder::FWObject *o)
throw(libfwbuilder::FWException);
static QWidget *createClusterConfDialog(QWidget *parent, libfwbuilder::FWObject *o)
throw(libfwbuilder::FWException);
static QWidget *createClusterGroupOptionsDialog(QWidget *parent, libfwbuilder::FWObject *o)
throw(libfwbuilder::FWException);
};
#endif

View File

@ -52,11 +52,16 @@
#include <qmessagebox.h>
#include "DiscoveryDruid.h"
#include "ProjectPanel.h"
#include "interfaceProperties.h"
#include "interfacePropertiesObjectFactory.h"
#include <iostream>
#include <map>
#include <vector>
#include <set>
#include <memory>
#include "fwbuilder/HostsFile.h"
#include "fwbuilder/IPv4.h"
@ -135,8 +140,10 @@ DiscoveryDruid::DiscoveryDruid(QWidget *parent, bool start_with_import) :
flt_net = new Filter();
flt_net_d = new FilterDialog(this);
flt_net_d->setFilter(flt_net);
assert(mw->activeProject()->db());
fillLibraries(m_dialog->libs,mw->db());
fillLibraries(m_dialog->libs, mw->activeProject()->db());
m_dialog->libs->setEditable(true);
m_dialog->libs->lineEdit()->setText(mw->getCurrentLib()->getName().c_str());
@ -230,7 +237,7 @@ const char * DISCOVERY_DRUID_SNMPINADDR ="SNMPInAddr";
const char * DISCOVERY_DRUID_SNMPINMASK ="SNMPInMask";
const char * DISCOVERY_DRUID_SNMPRECURSIVE ="SNMPRecursive";
const char * DISCOVERY_DRUID_SNMPFOLLOWP2P ="SNMPFollowP2P";
const char * DISCOVERY_DRUID_SNMPINCLUDEVIRT="SNMPIncludeVirt";
const char * DISCOVERY_DRUID_SNMPINCLUDEUNNUMBERED="SnmpIncludeUnnumbered";
const char * DISCOVERY_DRUID_SNMPDODNS ="SNMPDoDNS";
const char * DISCOVERY_DRUID_SNMPCOMMUNITY ="SNMPCommunity";
const char * DISCOVERY_DRUID_SNMPRETRIES ="SNMPRetries";
@ -273,8 +280,8 @@ void DiscoveryDruid::restore()
QString(DISCOVERY_DRUID_PREFIX) + DISCOVERY_DRUID_SNMPRECURSIVE));
m_dialog->snmpfollowp2p->setChecked(st->getBool(
QString(DISCOVERY_DRUID_PREFIX) + DISCOVERY_DRUID_SNMPFOLLOWP2P));
m_dialog->snmpincludevirt->setChecked(st->getBool(
QString(DISCOVERY_DRUID_PREFIX) + DISCOVERY_DRUID_SNMPINCLUDEVIRT));
m_dialog->snmpincludeunnumbered->setChecked(st->getBool(
QString(DISCOVERY_DRUID_PREFIX) + DISCOVERY_DRUID_SNMPINCLUDEUNNUMBERED));
m_dialog->snmpdodns->setChecked(st->getBool(
QString(DISCOVERY_DRUID_PREFIX) + DISCOVERY_DRUID_SNMPDODNS));
s=st->getStr(QString(DISCOVERY_DRUID_PREFIX) + DISCOVERY_DRUID_SNMPCOMMUNITY);
@ -337,8 +344,8 @@ void DiscoveryDruid::save()
QString(DISCOVERY_DRUID_PREFIX) + DISCOVERY_DRUID_SNMPFOLLOWP2P,
m_dialog->snmpfollowp2p->isChecked());
st->setBool(
QString(DISCOVERY_DRUID_PREFIX) + DISCOVERY_DRUID_SNMPINCLUDEVIRT,
m_dialog->snmpincludevirt->isChecked());
QString(DISCOVERY_DRUID_PREFIX) + DISCOVERY_DRUID_SNMPINCLUDEUNNUMBERED,
m_dialog->snmpincludeunnumbered->isChecked());
st->setBool(
QString(DISCOVERY_DRUID_PREFIX) + DISCOVERY_DRUID_SNMPDODNS,
m_dialog->snmpdodns->isChecked());
@ -1375,7 +1382,6 @@ void DiscoveryDruid::startSNMPScan()
q->init(getSeedHostAddress(),
m_dialog->snmpcommunity->text().toLatin1().constData(),
m_dialog->snmprecursive->isChecked(),
! m_dialog->snmpincludevirt->isChecked(),
false,
m_dialog->snmpfollowp2p->isChecked(),
0,
@ -2024,6 +2030,128 @@ void DiscoveryDruid::typeFirewall()
changeTargetObject(Firewall::TYPENAME);
}
/*
* Guess OS from the sysDescr string returned by the host. Returned OS
* name is always lower case one word, such as "linux", "ios"
*
* Examples of sysDescr strings:
*
* IOS (tm) 3600 Software (C3620-IK9O3S-M), Version 12.2(13), RELEASE SOFTWARE (fc1)
* Linux guardian 2.4.20 #2 Wed Nov 17 11:49:43 CET 2004 mips
* Linux crash 2.6.24-22-server #1 SMP Mon Nov 24 20:06:28 UTC 2008 x86_64
* Apple AirPort - Apple Computer, 2006. All rights Reserved
* Cisco Secure FWSM Firewall Version 2.3(4)
* Cisco PIX Firewall Version 6.2(1)
* Cisco Adaptive Security Appliance Version 8.2(0)227
*/
QString DiscoveryDruid::guessOS(const string &sysDescr)
{
QStringList elements = QString(sysDescr.c_str()).split(" ");
QString first = elements[0].toLower();
if (first == "cisco")
{
if (elements[1].toLower() == "adaptive" &&
elements[2].toLower() == "security" &&
elements[3].toLower() == "appliance") return "pix";
if (elements[1].toLower() == "pix") return "pix";
if (elements[1].toLower() == "secure" &&
elements[2].toLower() == "fwsm") return "pix";
}
if (first == "darwin") return "macosx";
if (first == "apple") return "macosx";
return first;
}
FWObject* DiscoveryDruid::addInterface(FWObject *parent, InterfaceData *in,
bool skip_ip_address_check)
{
ObjectManipulator *om = mw->activeProject()->m_panel->om;
if (!m_dialog->snmpincludeunnumbered->isChecked() && !skip_ip_address_check)
{
if (in->addr_mask.size()==0) return NULL;
if (in->addr_mask.front()->getAddressPtr()->isAny())
return NULL;
}
Interface *itf = NULL;
itf = Interface::cast(
mw->createObject(parent,
QString(Interface::TYPENAME),
QString(in->name.c_str())));
QString iname = om->getStandardName(itf, physAddress::TYPENAME, "mac");
iname = om->makeNameUnique(itf, iname, physAddress::TYPENAME);
physAddress *paddr = physAddress::cast(
mw->createObject(itf, physAddress::TYPENAME, iname)
);
paddr->setPhysAddress(in->mac_addr);
itf->setLabel(in->label);
itf->setSecurityLevel(in->securityLevel);
if (!in->interface_type.empty())
{
itf->getOptionsObject()->setStr("type", in->interface_type);
if (in->interface_type == "8021q")
itf->getOptionsObject()->setInt("vlan_id", in->vlan_id);
}
if (in->addr_mask.size()==0 ||
in->addr_mask.front()->getAddressPtr()->isAny())
{
itf->setUnnumbered(true);
} else
{
list<InetAddrMask*>::iterator n;
for (n=in->addr_mask.begin(); n!=in->addr_mask.end(); ++n)
{
const InetAddr *addr = (*n)->getAddressPtr();
const InetAddr *netm = (*n)->getNetmaskPtr();
if (addr->isV4())
{
try
{
QString iname = om->getStandardName(itf, IPv4::TYPENAME, "ip");
iname = om->makeNameUnique(itf, iname, IPv4::TYPENAME);
IPv4 *ipv4= IPv4::cast(
om->createObject(itf, IPv4::TYPENAME, iname)
);
ipv4->setAddress(*addr);
ipv4->setNetmask(*netm);
} catch (FWException &ex)
{
cerr << "FWException: " << ex.toString() << endl;
}
}
if (addr->isV6())
{
try
{
QString iname = om->getStandardName(itf, IPv6::TYPENAME, "ip");
iname = om->makeNameUnique(itf, iname, IPv6::TYPENAME);
IPv6 *ipv6 = IPv6::cast(
om->createObject(itf, IPv6::TYPENAME, iname)
);
ipv6->setAddress(*addr);
ipv6->setNetmask(*netm);
} catch (FWException &ex)
{
cerr << "FWException: " << ex.toString() << endl;
}
}
}
}
return itf;
}
void DiscoveryDruid::createRealObjects()
{
ObjectDescriptor od;
@ -2061,6 +2189,8 @@ void DiscoveryDruid::createRealObjects()
name = od.sysname;
QString os = guessOS(od.descr);
a = od.addr.toString();
if (od.isSelected)
@ -2072,6 +2202,50 @@ void DiscoveryDruid::createRealObjects()
o = mw->createObject(type.c_str(), name.c_str());
o->setName(name);
if (type==Firewall::TYPENAME)
{
if (os == "linux")
{
o->setStr("platform", "iptables");
o->setStr("host_OS", "linux24");
}
if (os == "freebsd")
{
o->setStr("platform", "pf");
o->setStr("host_OS", "freebsd");
}
if (os == "openbsd")
{
o->setStr("platform", "pf");
o->setStr("host_OS", "openbsd");
}
if (os == "ios")
{
o->setStr("platform", "iosacl");
o->setStr("host_OS", "ios");
}
if (os == "pix" || os == "fwsm")
{
o->setStr("platform", "pix");
o->setStr("host_OS", "pix_os");
}
if (os == "apple")
{
o->setStr("platform", "ipfw");
o->setStr("host_OS", "macosx");
}
if (os == "solaris")
{
o->setStr("platform", "ipf");
o->setStr("host_OS", "solaris");
}
Resources::setDefaultTargetOptions( o->getStr("platform"),
Firewall::cast(o) );
Resources::setDefaultTargetOptions( o->getStr("host_OS"),
Firewall::cast(o) );
}
if (od.interfaces.size()==0)
{
Interface *itf= Interface::cast(
@ -2095,57 +2269,78 @@ void DiscoveryDruid::createRealObjects()
ipv6->setAddress(od.addr);
ipv6->setNetmask(InetAddr());
}
} else
{
map<int,InterfaceData>::const_iterator i;
for (i=od.interfaces.begin(); i!=od.interfaces.end(); ++i)
if (fwbdebug)
{
InterfaceData in = i->second;
if (in.addr_mask.size()==0) continue;
if (in.addr_mask.front()->getAddressPtr()->isAny())
continue;
Interface *itf = Interface::cast(
mw->createObject(o,
QString(Interface::TYPENAME),
QString(i->second.name.c_str())));
itf->setPhysicalAddress(in.mac_addr);
itf->setLabel(in.label);
itf->setExt(in.ext);
itf->setSecurityLevel(in.securityLevel);
list<InetAddrMask*>::iterator n;
for (n=in.addr_mask.begin(); n!=in.addr_mask.end(); ++n)
map<int,InterfaceData>::iterator i;
for (i=od.interfaces.begin(); i!=od.interfaces.end(); ++i)
{
const InetAddr *addr = (*n)->getAddressPtr();
const InetAddr *netm = (*n)->getNetmaskPtr();
if (addr->isV4())
{
IPv4 *ipv4= IPv4::cast(
mw->createObject(itf, IPv4::TYPENAME,
addr->toString().c_str())
);
ipv4->setAddress(*addr);
ipv4->setNetmask(*netm);
mw->autorename(itf, IPv4::TYPENAME, "ip");
}
if (addr->isV6())
{
IPv6 *ipv6 = IPv6::cast(
mw->createObject(itf, IPv6::TYPENAME,
addr->toString().c_str())
);
ipv6->setAddress(*addr);
ipv6->setNetmask(*netm);
mw->autorename(itf, IPv6::TYPENAME, "ip6");
}
InterfaceData *intf = &(i->second);
QString str("Discovered interface %1: %2");
qDebug(
str.arg(intf->name.c_str()).arg(intf->mac_addr.c_str()).toAscii().constData()
);
}
mw->autorename(itf, physAddress::TYPENAME, "mac");
}
list<InterfaceData*> interface_tree;
std::auto_ptr<interfaceProperties> int_prop(
interfacePropertiesObjectFactory::getInterfacePropertiesObject(
o->getStr("host_OS")));
int_prop->rearrangeInterfaces(od.interfaces, interface_tree);
if (interface_tree.size() != od.interfaces.size())
{
// Some interfaces have been converted to subinterfaces
// Show warning
QMessageBox::warning(
this, "Firewall Builder",
tr(
"Some discovered interfaces have been rearranged in "
"fwbuilder objects and recreated as subinterfaces to "
"reflect VLANs, bonding and bridging configurations. "
"The algorithm used to guess correct relationship "
"between interfaces and subinterfaces is imperfect "
"because of the limited information provided by SNMP "
"daemon. Pelase review created objects to make sure "
"generated configuration is accurate. "
"\n"
"\n"
"The program expects MAC addresses of bonding, bridge "
"and vlan interfaces to be the same. It is especially "
"important to review and fix generated objects if you "
"use MAC address spoofing."
),
tr("&Continue"), 0, 0,
0 );
}
list<InterfaceData*>::iterator it;
for (it=interface_tree.begin(); it!=interface_tree.end(); ++it)
{
InterfaceData *in = *it;
// if this interface has subinterfaces, add even if it
// has no ip address (last arg)
FWObject *intf = addInterface(
o, in, in->subinterfaces.size()!=0);
if (intf == NULL) continue;
list<InterfaceData*>::iterator sit;
for (sit=in->subinterfaces.begin();
sit!=in->subinterfaces.end(); ++sit)
{
InterfaceData *subint = *sit;
addInterface(intf, subint, true);
}
}
}
if (!od.descr.empty())
{
FWOptions* opt=(dynamic_cast<Host*>(o))->getOptionsObject();
@ -2153,22 +2348,10 @@ void DiscoveryDruid::createRealObjects()
opt->setStr("snmp_location", od.location);
opt->setStr("snmp_contact", od.contact);
}
mw->moveObject(m_dialog->libs->currentText(), o);
if (type==Firewall::TYPENAME)
{
map<string,string> platforms = Resources::getPlatforms();
map<string,string>::iterator i;
for (i=platforms.begin(); i!=platforms.end(); i++)
Resources::setDefaultTargetOptions( i->first,
Firewall::cast(o) );
map<string,string> OSs = Resources::getOS();
for (i=OSs.begin(); i!=OSs.end(); i++)
Resources::setDefaultTargetOptions( i->first,
Firewall::cast(o) );
}
}else if (type==Network::TYPENAME)
} else if (type==Network::TYPENAME)
{
Network *net=dynamic_cast<Network*>(
mw->createObject(type.c_str(),name.c_str())
@ -2178,7 +2361,7 @@ void DiscoveryDruid::createRealObjects()
net->setAddress(InetAddr(a));
net->setNetmask(InetAddr(InetAddr(a)));
mw->moveObject(m_dialog->libs->currentText(), net);
}else if (type==IPv4::TYPENAME)
} else if (type==IPv4::TYPENAME)
{
IPv4 *obj=dynamic_cast<IPv4*>(
mw->createObject(type.c_str(),name.c_str())
@ -2196,30 +2379,6 @@ void DiscoveryDruid::createRealObjects()
m_dialog->lastprogress->setValue(Objects.size());
}
void DiscoveryDruid::autorename(FWObject *obj,
const string &objtype,
const string &namesuffix)
{
FWObject *hst = obj->getParent();
list<FWObject*> ol = obj->getByType(objtype);
int sfxn = 1;
for (list<FWObject*>::iterator j=ol.begin(); j!=ol.end(); ++j,++sfxn)
{
QString sfx;
if (ol.size()==1) sfx="";
else sfx.setNum(sfxn);
QString nn = QString("%1:%2:%3%4")
.arg(QString::fromUtf8(hst->getName().c_str()))
.arg(QString::fromUtf8(obj->getName().c_str()))
.arg(namesuffix.c_str())
.arg(sfx);
(*j)->setName(string(nn.toUtf8().constData()));
}
ol.clear();
}
void DiscoveryDruid::importPlatformChanged(int cp)
{
if (fwbdebug)

View File

@ -170,6 +170,7 @@ public:
class DiscoveryDruid : public QDialog, public FakeWizard
{
Q_OBJECT
private:
WorkerThread *thread;
BackgroundTask current_task;
@ -213,10 +214,18 @@ private:
void startBackgroundProcess();
void DataFromCrawler();
int monitorOperation();
void autorename(FWObject *obj,const string &objtype,const string &namesuffix);
void restore();
void save();
QString guessOS(const string &sysDescr);
void rearrangeInterfaces(
const QString &os,
std::map<int,libfwbuilder::InterfaceData> &interfaces,
std::list<libfwbuilder::InterfaceData*> &interface_tree);
FWObject* addInterface(libfwbuilder::FWObject *parent,
libfwbuilder::InterfaceData *in,
bool skip_ip_address_check);
public:
DiscoveryDruid(QWidget *parent, bool start_with_import=false);

View File

@ -93,7 +93,7 @@
<addaction name="ObjectLockAction" />
<addaction name="ObjectUnlockAction" />
</widget>
<widget class="QMenu" name="Tools" >
<widget class="QMenu" name="toolsMenu" >
<property name="title" >
<string>Tools</string>
</property>
@ -107,6 +107,7 @@
<addaction name="helpAboutAction" />
<addaction name="debugAction" />
<addaction name="helpAction" />
<addaction name="release_Notes_Action" />
</widget>
<widget class="QMenu" name="RulesMenu" >
<property name="title" >
@ -165,7 +166,7 @@
<addaction name="editMenu" />
<addaction name="ObjectMenu" />
<addaction name="RulesMenu" />
<addaction name="Tools" />
<addaction name="toolsMenu" />
<addaction name="menuWindow" />
<addaction name="helpMenu" />
</widget>
@ -730,6 +731,11 @@
<string>New Object File</string>
</property>
</action>
<action name="release_Notes_Action" >
<property name="text" >
<string>Release Notes</string>
</property>
</action>
</widget>
<layoutdefault spacing="0" margin="11" />
<resources>
@ -1488,8 +1494,25 @@
</hint>
</hints>
</connection>
<connection>
<sender>release_Notes_Action</sender>
<signal>triggered()</signal>
<receiver>FWBMainWindow_q</receiver>
<slot>showReleaseNotes()</slot>
<hints>
<hint type="sourcelabel" >
<x>-1</x>
<y>-1</y>
</hint>
<hint type="destinationlabel" >
<x>370</x>
<y>359</y>
</hint>
</hints>
</connection>
</connections>
<slots>
<slot>clearRecentFilesMenu()</slot>
<slot>showReleaseNotes()</slot>
</slots>
</ui>

View File

@ -94,6 +94,7 @@ const char* iconsInRulesSize = SETTINGS_PATH_PREFIX "/UI/Icons/IconsInRulesSize"
const char* rulesFont = SETTINGS_PATH_PREFIX "/UI/Fonts/RulesFont";
const char* treeFont = SETTINGS_PATH_PREFIX "/UI/Fonts/TreeFont";
const char* uiFont = SETTINGS_PATH_PREFIX "/UI/Fonts/UiFont";
const char* compilerOutputFont = SETTINGS_PATH_PREFIX "/UI/Fonts/CompilerOutputFont";
const char* clipComment = SETTINGS_PATH_PREFIX "/UI/ClipComment";
@ -101,9 +102,10 @@ const char* checkUpdates = SETTINGS_PATH_PREFIX "/UI/CheckUpdates";
const char* checkUpdatesProxy = SETTINGS_PATH_PREFIX "/UI/CheckUpdatesProxy";
const char* newFirewallPlatform = SETTINGS_PATH_PREFIX "/Objects/NewFireallPlatform";
const char* appGUID = SETTINGS_PATH_PREFIX "/ApplicationGUID";
const char* targetStatus = SETTINGS_PATH_PREFIX "/TargetStatus/";
FWBSettings::FWBSettings() :
QSettings(QSettings::UserScope, "netcitadel.com", "Firewall Builder")
{
@ -196,6 +198,15 @@ void FWBSettings::init()
ok = contains(uiFont);
if (!ok) setUiFont(QApplication::font());
ok = contains(compilerOutputFont);
if (!ok)
{
// make compiler output panel font smaller than regular font
QFont compiler_output_font(QApplication::font());
compiler_output_font.setPointSizeF(compiler_output_font.pointSizeF() * 0.75);
setCompilerOutputFont(compiler_output_font);
}
if (fwbdebug)
qDebug("Default application font: %s",
QApplication::font().toString().toLatin1().constData());
@ -324,8 +335,6 @@ void FWBSettings::setSaveFileDir( const QString &d )
void FWBSettings::save()
{
if (mw->db()!=NULL)
setLastEdited( mw->db()->getFileName().c_str() );
}
bool FWBSettings::getRCSLogState() { return value( emptyRCSLog ).toBool(); }
@ -657,7 +666,6 @@ void FWBSettings::setShowDirectionText(bool showText)
setValue(showDirectionText, showText);
}
QFont FWBSettings::getRulesFont()
{
return getFontByType(rulesFont);
@ -688,6 +696,16 @@ void FWBSettings::setUiFont(const QFont &font)
setValue(uiFont, font.toString());
}
QFont FWBSettings::getCompilerOutputFont()
{
return getFontByType(compilerOutputFont);
}
void FWBSettings::setCompilerOutputFont(const QFont &font)
{
setValue(compilerOutputFont, font.toString());
}
QFont FWBSettings::getFontByType(const char *type)
{
QFont font = QFont();
@ -814,3 +832,20 @@ void FWBSettings::setNewFirewallPlatform(const QString &platform)
setValue(newFirewallPlatform, platform);
}
QString FWBSettings::getTargetStatus(const QString &platform,
const QString &default_stat)
{
QString var_path = targetStatus + platform;
bool ok = contains(var_path);
if (!ok) return default_stat;
return value(var_path).toString();
}
void FWBSettings::setTargetStatus(const QString &platform, const QString &status)
{
QString var_path = targetStatus + platform;
setValue(var_path, status);
}

View File

@ -175,12 +175,18 @@ class FWBSettings : public QSettings {
QFont getUiFont();
void setUiFont(const QFont &font);
QFont getCompilerOutputFont();
void setCompilerOutputFont(const QFont &font);
bool getClipComment();
void setClipComment(bool);
bool getCheckUpdates();
void setCheckUpdates(bool);
QString getTargetStatus(const QString &platform, const QString &default_stat);
void setTargetStatus(const QString &plaform, const QString &status);
QString getCheckUpdatesProxy();
void setCheckUpdatesProxy(const QString &proxy_line);

View File

@ -36,6 +36,7 @@
#include "fwbuilder/Library.h"
#include "fwbuilder/Firewall.h"
#include "fwbuilder/Host.h"
#include "fwbuilder/Cluster.h"
#include "fwbuilder/Network.h"
#include "fwbuilder/NetworkIPv6.h"
#include "fwbuilder/IPv4.h"
@ -83,6 +84,7 @@ const char* systemObjects[] = {
"Services/TagServices",
"Services/Users",
"Firewalls",
"Clusters",
"Time",
@ -117,6 +119,7 @@ FWBTree::FWBTree()
systemGroupPaths[TagService::TYPENAME] = "Services/TagServices";
systemGroupPaths[Firewall::TYPENAME] = "Firewalls";
systemGroupPaths[Cluster::TYPENAME] = "Clusters";
systemGroupPaths[Interval::TYPENAME] = "Time";
@ -125,6 +128,9 @@ FWBTree::FWBTree()
systemGroupTypes[Firewall::TYPENAME]= ObjectGroup::TYPENAME;
systemGroupNames[Firewall::TYPENAME]= "Firewalls" ;
systemGroupTypes[Cluster::TYPENAME]= ObjectGroup::TYPENAME;
systemGroupNames[Cluster::TYPENAME]= "Clusters";
systemGroupTypes[Host::TYPENAME]= ObjectGroup::TYPENAME;
systemGroupNames[Host::TYPENAME]= "Hosts" ;
@ -238,6 +244,7 @@ FWBTree::FWBTree()
copyMenuState[""] = false;
copyMenuState["Firewalls"] = false;
copyMenuState["Clusters"] = false;
copyMenuState["Objects"] = false;
copyMenuState["Objects/Addresses"] = false;
copyMenuState["Objects/DNS Names"] = false;
@ -258,6 +265,7 @@ FWBTree::FWBTree()
cutMenuState[""] = true;
cutMenuState["Firewalls"] = false;
cutMenuState["Clusters"] = false;
cutMenuState["Objects"] = false;
cutMenuState["Objects/Addresses"] = false;
cutMenuState["Objects/DNS Names"] = false;
@ -279,6 +287,7 @@ FWBTree::FWBTree()
pasteMenuState[""] = false;
pasteMenuState["Firewalls"] = true;
pasteMenuState["Clusters"] = true;
pasteMenuState["Objects"] = false;
pasteMenuState["Objects/Addresses"] = true;
pasteMenuState["Objects/DNS Names"] = true;
@ -300,6 +309,7 @@ FWBTree::FWBTree()
deleteMenuState[""] = true;
deleteMenuState["Firewalls"] = false;
deleteMenuState["Clusters"] = false;
deleteMenuState["Objects"] = false;
deleteMenuState["Objects/Addresses"] = false;
deleteMenuState["Objects/DNS Names"] = false;
@ -490,6 +500,10 @@ FWObject* FWBTree::createNewLibrary(FWObjectDatabase *db)
o1->setName("Firewalls");
nlib->add(o1);
o1 = db->create(ObjectGroup::TYPENAME);
o1->setName("Clusters");
nlib->add(o1);
o1 = db->create(IntervalGroup::TYPENAME);
o1->setName("Time");
nlib->add(o1);

View File

@ -28,6 +28,7 @@
#include "global.h"
#include "utils.h"
#include "platforms.h"
#include "events.h"
#include "FWObjectDropArea.h"
#include "FWObjectDrag.h"
@ -48,6 +49,7 @@
#include <QDropEvent>
#include <QContextMenuEvent>
#include <QPaintEvent>
#include <QCoreApplication>
#include <iostream>
#include <stdlib.h>
@ -227,7 +229,7 @@ void FWObjectDropArea::pasteObject()
for( i= FWObjectClipboard::obj_clipboard->begin();
i!=FWObjectClipboard::obj_clipboard->end(); ++i)
{
FWObject *co= mw->db()->findInIndex(i->first);
FWObject *co= i->second->db()->findInIndex(i->first);
insertObject(co);
}
@ -238,7 +240,9 @@ void FWObjectDropArea::showInTreeObject()
ProjectPanel * pp = mw->activeProject();
if (pp!=NULL)
{
pp->m_panel->om->openObject(object);
QCoreApplication::postEvent(
pp, new showObjectInTreeEvent(object->getRoot()->getFileName().c_str(),
object->getId()));
}
}
@ -247,8 +251,12 @@ void FWObjectDropArea::editObject()
ProjectPanel * pp = mw->activeProject();
if (pp!=NULL)
{
pp->m_panel->om->openObject(object);
pp->openEditor(object);
QCoreApplication::postEvent(
pp, new showObjectInTreeEvent(object->getRoot()->getFileName().c_str(),
object->getId()));
QCoreApplication::postEvent(
pp, new openObjectInEditorEvent(object->getRoot()->getFileName().c_str(),
object->getId()));
}
}

View File

@ -66,6 +66,9 @@
#include "fwbuilder/UDPService.h"
#include "fwbuilder/UserService.h"
#include "fwbuilder/physAddress.h"
#include "fwbuilder/StateSyncClusterGroup.h"
#include "fwbuilder/FailoverClusterGroup.h"
#include "fwbuilder/Cluster.h"
#include <sstream>
#include <iostream>
@ -121,7 +124,7 @@ QString FWObjectPropertiesFactory::getObjectProperties(FWObject *obj)
str << ar->getRangeStart().toString().c_str();
str << " - ";
str << ar->getRangeEnd().toString().c_str();
} else if (Firewall::isA(obj))
} else if (Firewall::cast(obj))
{
QString platform = obj->getStr("platform").c_str();
QString version = obj->getStr("version").c_str();
@ -172,12 +175,29 @@ QString FWObjectPropertiesFactory::getObjectProperties(FWObject *obj)
str << "/";
str << QString("%1").arg(n->getNetmaskPtr()->getLength());
} else if (ClusterGroup::cast(obj)!=NULL)
{
ClusterGroup *g = ClusterGroup::cast(obj);
str << QObject::tr("type: ") << g->getStr("type").c_str() << "<br>";
FWObjectTypedChildIterator j = obj->findByType(FWObjectReference::TYPENAME);
for ( ; j!=j.end(); ++j)
{
FWObject *obj = FWReference::getObject(*j);
if (Interface::cast(obj))
{
FWObject *fw = obj->getParent();
str << QObject::tr("Group member")
<< " " << fw->getName().c_str()
<< ":" << obj->getName().c_str()
<< "<br>";
}
}
} else if (Group::cast(obj)!=NULL) // just any group
{
Group *g=Group::cast(obj);
str << g->size() << " " << QObject::tr(" objects");
} else if (Firewall::isA(obj))
} else if (Firewall::cast(obj))
{
} else if (Interface::isA(obj))
@ -189,10 +209,12 @@ QString FWObjectPropertiesFactory::getObjectProperties(FWObject *obj)
str << getObjectProperties(*j);
str << "<br>";
}
str << " MAC: ";
physAddress *paddr = intf->getPhysicalAddress();
if (paddr!=NULL)
str << paddr->getPhysAddress().c_str();
str << " MAC: " << paddr->getPhysAddress().c_str() << "<br>";
string intf_type = intf->getOptionsObject()->getStr("type");
if (!intf_type.empty())
str << " Interface Type: " << intf_type.c_str();
} else if (IPService::isA(obj))
{
@ -361,10 +383,26 @@ QString FWObjectPropertiesFactory::getObjectPropertiesDetailed(FWObject *obj,
str += n->getAddressPtr()->toString().c_str();
str += "/";
str += QString("%1").arg(n->getNetmaskPtr()->getLength());
} else if (ClusterGroup::cast(obj)!=NULL)
{
if (showPath && !tooltip) str += "<b>Path: </b>" + path + "<br>\n";
ClusterGroup *g = ClusterGroup::cast(obj);
str += QObject::tr("type: %1<br>").arg(g->getStr("type").c_str());
FWObjectTypedChildIterator j = obj->findByType(FWObjectReference::TYPENAME);
for ( ; j!=j.end(); ++j)
{
FWObject *obj = FWReference::getObject(*j);
if (Interface::cast(obj))
{
FWObject *fw = obj->getParent();
str += QObject::tr("Group member %1:%2<br>").
arg(fw->getName().c_str()).arg(obj->getName().c_str());
}
}
} else if (Group::cast(obj)!=NULL) // just any group
{
if (showPath && !tooltip) str += "<b>Path: </b>" + path + "<br>\n";
Group *g=Group::cast(obj);
Group *g = Group::cast(obj);
str += QObject::tr("%1 objects<br>\n").arg(g->size());
int n = 0;
list<FWObject*> ll = *g;
@ -385,8 +423,9 @@ QString FWObjectPropertiesFactory::getObjectPropertiesDetailed(FWObject *obj,
+ " <b>" + QString::fromUtf8(o1->getName().c_str()) + "</b><br>\n";
}
}
} else if (Firewall::isA(obj))
} else if (Firewall::cast(obj))
{
// Note: Firewall::cast(obj) matched Firewall and Cluster
QString platform = obj->getStr("platform").c_str();
QString version = obj->getStr("version").c_str();
QString readableVersion = getVersionString(platform,version);
@ -430,7 +469,8 @@ QString FWObjectPropertiesFactory::getObjectPropertiesDetailed(FWObject *obj,
str += "</table>";
} else if (Interface::isA(obj))
{
str += QObject::tr("<b>Path:</b> ")+ path +"<br>\n";
Interface *intf = Interface::cast(obj);
//str += QObject::tr("<b>Path:</b> ")+ path +"<br>\n";
FWObjectTypedChildIterator j = obj->findByType(IPv4::TYPENAME);
for ( ; j!=j.end(); ++j)
@ -438,7 +478,21 @@ QString FWObjectPropertiesFactory::getObjectPropertiesDetailed(FWObject *obj,
str += getObjectProperties(*j);
str += "<br>";
}
physAddress *paddr=(Interface::cast(obj))->getPhysicalAddress();
string intf_type = intf->getOptionsObject()->getStr("type");
if (!intf_type.empty())
{
str += "<b>Interface Type: </b>";
str += intf_type.c_str();
if (intf_type == "8021q")
{
int vlan_id = intf->getOptionsObject()->getInt("vlan_id");
str += QString(" VLAN ID=%1").arg(vlan_id);
}
str += "<br>";
}
physAddress *paddr = intf->getPhysicalAddress();
if (paddr!=NULL)
{
str += "MAC: ";
@ -447,22 +501,19 @@ QString FWObjectPropertiesFactory::getObjectPropertiesDetailed(FWObject *obj,
}
QString q;
if (Interface::constcast(obj)->isDyn()) q=" dyn";
if (Interface::constcast(obj)->isUnnumbered()) q=" unnum";
if (Interface::constcast(obj)->isBridgePort()) q=" bridge port";
if (intf->isDyn()) q=" dyn";
if (intf->isUnnumbered()) q=" unnum";
if (intf->isBridgePort()) q=" bridge port";
FWObject *p=obj;
while (p!=NULL && !Firewall::isA(p)) p=p->getParent();
while (p!=NULL && !Firewall::cast(p)) p=p->getParent();
if (p!=NULL && (p->getStr("platform")=="pix" || p->getStr("platform")=="fwsm"))
{
int sl=Interface::constcast(obj)->getSecurityLevel();
int sl = intf->getSecurityLevel();
q=q+QString("sec.level %1").arg(sl);
} else
{
if (Interface::constcast(obj)->isExt()) q=q+" ext";
}
if (Interface::constcast(obj)->isUnprotected()) q=q+" unp";
if (intf->isUnprotected()) q=q+" unp";
if (q!="") str += " (" + q + ")";
str += "<br>\n";
@ -667,7 +718,7 @@ QString FWObjectPropertiesFactory::getRuleActionProperties(PolicyRule *rule)
QString FWObjectPropertiesFactory::getRuleActionPropertiesRich(PolicyRule *rule)
{
FWObject *p=rule;
while (p!=NULL && !Firewall::isA(p)) p=p->getParent();
while (p!=NULL && !Firewall::cast(p)) p=p->getParent();
assert(p!=NULL);
string platform=p->getStr("platform");
QString act = getActionNameForPlatform(rule->getAction(),platform.c_str());

View File

@ -0,0 +1,22 @@
#include "FWObjectSelectionModel.h"
#include "fwbuilder/Firewall.h"
using namespace libfwbuilder;
FWObjectSelectionModel::FWObjectSelectionModel()
{
}
void FWObjectSelectionModel::setSelected(FWObject * so, const QModelIndex &index)
{
this->selectedObjectOld = this->selectedObject;
this->selectedObject = so;
this->index = index;
}
void FWObjectSelectionModel::reset()
{
QModelIndex index;
setSelected(NULL, index);
}

View File

@ -0,0 +1,23 @@
#ifndef FWOBJECTSELECTIONMODEL_H
#define FWOBJECTSELECTIONMODEL_H
#include <QModelIndex>
namespace libfwbuilder
{
class FWObject;
}
class FWObjectSelectionModel
{
public:
libfwbuilder::FWObject *selectedObject;
libfwbuilder::FWObject *selectedObjectOld;
QModelIndex index;
FWObjectSelectionModel();
void setSelected(libfwbuilder::FWObject *, const QModelIndex &index);
void reset();
};
#endif // FWOBJECTSELECTIONMODEL_H

View File

@ -27,7 +27,6 @@
#include "global.h"
#include "check_update_url.h"
#include "../../VERSION.h"
#include "../../build_num"
#include "utils.h"
#include "utils_no_qt.h"
@ -41,7 +40,6 @@
#include "FWBSettings.h"
#include "FWObjectPropertiesFactory.h"
#include "upgradePredicate.h"
#include "listOfLibraries.h"
#include "ObjConflictResolutionDialog.h"
#include "RuleSetView.h"
#include "ObjectEditor.h"
@ -63,6 +61,10 @@
#include "HttpGet.h"
#include "StartTipDialog.h"
#include "transferDialog.h"
#include "events.h"
#include "fwbuilder/FWReference.h"
#include "fwbuilder/Policy.h"
#include "fwbuilder/NAT.h"
@ -181,10 +183,9 @@ FWWindow::FWWindow() : QMainWindow(), // QMainWindow(NULL, Qt::Desktop),
showSub(proj);
setSafeMode(false);
setStartupFileName("");
#ifdef Q_OS_MACX
getMdiArea()->setViewMode(QMdiArea::TabbedView);
m_space->setViewMode(QMdiArea::TabbedView);
#endif
printer = new QPrinter(QPrinter::HighResolution);
@ -200,28 +201,31 @@ FWWindow::FWWindow() : QMainWindow(), // QMainWindow(NULL, Qt::Desktop),
connect( m_mainWindow->newObjectAction, SIGNAL( triggered() ),
this, SLOT(newObject() ) );
this, SLOT(newObject() ) );
connect( m_mainWindow->backAction, SIGNAL( triggered() ),
this, SLOT(back() ) );
this, SLOT(back() ) );
connect( m_mainWindow->findAction, SIGNAL( triggered() ),
this, SLOT(search()) );
this, SLOT(search()) );
connect( m_mainWindow->editMenu, SIGNAL (aboutToShow() ),
this, SLOT( prepareEditMenu() ));
this, SLOT( prepareEditMenu() ));
connect( m_mainWindow->ObjectMenu, SIGNAL (aboutToShow() ),
this, SLOT( prepareObjectMenu() ));
this, SLOT( prepareObjectMenu() ));
connect( m_mainWindow->fileMenu, SIGNAL (aboutToShow() ),
this, SLOT( prepareFileMenu() ));
this, SLOT( prepareFileMenu() ));
connect( m_mainWindow->toolsMenu, SIGNAL (aboutToShow() ),
this, SLOT( prepareToolsMenu() ));
connect( m_mainWindow->menuWindow, SIGNAL (aboutToShow() ),
this, SLOT( prepareWindowsMenu() ));
this, SLOT( prepareWindowsMenu() ));
connect( m_space, SIGNAL(subWindowActivated (QMdiSubWindow *)),
this, SLOT(changeActiveSubwindow()));
connect( m_space, SIGNAL(subWindowActivated(QMdiSubWindow*)),
this, SLOT(subWindowActivated(QMdiSubWindow*)));
disableActions(false);
@ -395,6 +399,13 @@ void FWWindow::startupLoad()
updateOpenRecentMenu(file);
}
QString release_notes_flag = QString("UI/%1/ReleaseNotesShown").arg(VERSION);
// if (!st->getBool(release_notes_flag))
// {
showReleaseNotes();
st->setBool(release_notes_flag, true);
// }
if (! st->getBool("UI/NoStartTip"))
{
StartTipDialog *stdlg = new StartTipDialog();
@ -403,6 +414,8 @@ void FWWindow::startupLoad()
//stdlg->show();
//stdlg->raise();
}
prepareFileMenu();
}
void FWWindow::helpAbout()
@ -417,40 +430,6 @@ void FWWindow::debug()
dd.exec();
}
void FWWindow::info(FWObject *obj, bool forced)
{
if (fwbdebug) qDebug("FWWindow::info called");
if (activeProject()) activeProject()->info(obj, forced);
}
bool FWWindow::saveIfModified()
{
if (activeProject()) return activeProject()->saveIfModified();
return false;
}
QString FWWindow::getDestDir(const QString &fname)
{
if (activeProject()) return activeProject()->getDestDir(fname);
return "";
}
QString FWWindow::chooseNewFileName(const QString &fname, const QString &title)
{
if (activeProject()) return activeProject()->chooseNewFileName(fname,title);
return "";
}
void FWWindow::setFileName(const QString &fname)
{
if (activeProject()) activeProject()->setFileName(fname);
}
void FWWindow::fileProp()
{
if (activeProject()) activeProject()->fileProp();
}
void FWWindow::fileNew()
{
// if the only project panel window that we have shows
@ -465,7 +444,7 @@ void FWWindow::fileNew()
if (proj->fileNew())
{
showSub(proj.get());
//proj->startupLoad();
prepareFileMenu();
proj.release();
}
}
@ -473,51 +452,77 @@ void FWWindow::fileNew()
void FWWindow::fileOpen()
{
QString dir;
QMdiSubWindow *last_active_window = m_space->activeSubWindow();
/*
* Pick default directory where to look for the file to open.
* 1) if "work directory" is configured in preferences, always use it
* 2) if it is blank, use the same directory where currently opened file is
* 3) if this is the first file to be opened, get directory where the user opened
* during last session from settings using st->getOpenFileDir
*/
dir = st->getWDir();
if (fwbdebug) qDebug("Choosing directory for file open 1: %s",
dir.toStdString().c_str());
if (dir.isEmpty() && !mw->getCurrentFileName().isEmpty())
dir = getFileDir(mw->getCurrentFileName());
if (fwbdebug) qDebug("Choosing directory for file open 2: %s",
dir.toStdString().c_str());
if (dir.isEmpty()) dir = st->getOpenFileDir();
if (fwbdebug) qDebug("Choosing directory for file open 3: %s",
dir.toStdString().c_str());
QString fileName = QFileDialog::getOpenFileName(
this,
tr("Open File"),
dir,
"FWB files (*.fwb *.fwl *.xml);;All Files (*)");
if (fileName.isEmpty())
{
m_space->setActiveSubWindow(last_active_window);
return ;
}
if (loadFile(fileName, false))
{
updateOpenRecentMenu(fileName);
// reset actions, including Save() which should now
// be inactive
prepareFileMenu();
} else
m_space->setActiveSubWindow(last_active_window);
}
bool FWWindow::loadFile(const QString &file_name, bool load_rcs_head)
{
ProjectPanel *proj;
// if the only project panel window that we have shows
// default object tree (i.e. its filename is empty), then load file
// into. Otherwise create new project window.
if (activeProject() && activeProject()->getFileName().isEmpty())
{
ProjectPanel *proj = activeProject();
if (proj->fileOpen())
{
proj->readyStatus(true);
proj->loadState(true);
}
proj = activeProject();
if (!proj->loadFile(file_name, load_rcs_head)) return false;
} else
{
std::auto_ptr<ProjectPanel> proj(newProjectPanel());
if (proj->fileOpen())
proj = newProjectPanel();
if (proj->loadFile(file_name, load_rcs_head))
{
showSub(proj.get());
proj->readyStatus(true);
proj->loadState(true);
proj.release();
}
}
}
void FWWindow::loadFile(const QString &filename, bool load_rcs_head)
{
if (activeProject() && activeProject()->getFileName().isEmpty())
{
ProjectPanel *proj = activeProject();
if (proj->loadFile(filename, load_rcs_head))
{
proj->readyStatus(true);
proj->loadState(true);
}
} else
{
std::auto_ptr<ProjectPanel> proj(newProjectPanel());
if (proj->loadFile(filename, load_rcs_head))
{
showSub(proj.get());
proj->readyStatus(true);
proj->loadState(true);
proj.release();
showSub(proj);
} else
{
delete proj;
return false;
}
}
proj->readyStatus(true);
proj->loadState(true);
return true;
}
void FWWindow::fileClose()
@ -537,16 +542,6 @@ void FWWindow::fileClose()
}
void FWWindow::fileSave()
{
if (activeProject()) activeProject()->fileSave();
}
void FWWindow::fileSaveAs()
{
if (activeProject()) activeProject()->fileSaveAs();
}
void FWWindow::fileExit()
{
if (activeProject())
@ -568,31 +563,6 @@ void FWWindow::fileExit()
QCoreApplication::exit(0);
}
void FWWindow::fileCommit()
{
if (activeProject()) activeProject()->fileCommit();
}
/*
* discard changes done to the file and check out clean copy of the
* head revision from RCS
*/
void FWWindow::fileDiscard()
{
if (activeProject()) activeProject()->fileDiscard();
}
void FWWindow::fileAddToRCS()
{
if (activeProject()) activeProject()->fileAddToRCS();
}
bool FWWindow::editingLibrary()
{
if (activeProject()) return activeProject()->editingLibrary();
return false;
}
void FWWindow::toolsDiscoveryDruid()
{
DiscoveryDruid druid(this);
@ -605,102 +575,6 @@ void FWWindow::importPolicy()
druid.exec();
}
void FWWindow::load(QWidget*)
{
if (activeProject()) activeProject()->loadStandardObjects();
}
FWObject* FWWindow::getVisibleFirewalls()
{
if (activeProject()) return activeProject()->getVisibleFirewall();
return 0;
}
void FWWindow::load(QWidget*, RCS *_rcs)
{
if (activeProject()) activeProject()->loadFromRCS(_rcs);
}
bool FWWindow::checkin(bool unlock)
{
if (activeProject()) return activeProject()->checkin(unlock);
return false;
}
void FWWindow::save()
{
if (activeProject()) activeProject()->save();
}
void FWWindow::loadLibrary(const string &libfpath)
{
if (activeProject()) activeProject()->loadLibrary(libfpath);
}
void FWWindow::fileImport()
{
if (activeProject()) activeProject()->fileImport();
}
void FWWindow::fileCompare()
{
if (activeProject()) activeProject()->fileCompare();
}
void FWWindow::findExternalRefs(FWObject *lib,
FWObject *root,
list<FWReference*> &extRefs)
{
if (activeProject()) activeProject()->findExternalRefs(lib, root, extRefs);
}
void FWWindow::setSafeMode(bool f)
{
if (activeProject()) activeProject()->setSafeMode(f);
}
void FWWindow::setStartupFileName(const QString &fn)
{
if (activeProject()) activeProject()->setStartupFileName(fn);
}
bool FWWindow::exportLibraryTest(list<FWObject*> &selectedLibs)
{
/* VERY IMPORTANT: External library file must be self-contained,
* otherwise it can not be exported.
*
* check if selected libraries have references to objects in other
* libraries (not exported to the same file). Exporting such libraries
* pulls in other ones because of these references. This is confusing
* because it means we end up with multiple copies of such objects (in
* exported library file and in user's data file). When user imports
* this library and opens their file, it is impossible to say which
* library an object belongs to.
*
* This is prohibited. We check if exported set of libraries has such
* references and refuse to export it. The user is supposed to clean
* it up by either moving objects into the library they are trying to
* export, or by rearranging objects. The only exception for this is
* library "Standard", which is assumed to be always present so we can
* have references to objects in it.
*/
if (activeProject())
return activeProject()->exportLibraryTest(selectedLibs);
return false;
}
void FWWindow::exportLibraryTo(QString fname,list<FWObject*> &selectedLibs, bool rof)
{
if (activeProject())
activeProject()->exportLibraryTo(fname,selectedLibs, rof);
}
void FWWindow::fileExport()
{
if (activeProject()) activeProject()->fileExport();
}
void FWWindow::setActionsEnabled(bool en)
{
m_mainWindow->insertRuleAction->setEnabled(en);
@ -718,68 +592,6 @@ void FWWindow::setActionsEnabled(bool en)
m_mainWindow->installAction->setEnabled(en );
}
int FWWindow::findFirewallInList(FWObject *f)
{
if (activeProject()) return activeProject()->findFirewallInList(f);
return -1;
}
void FWWindow::ensureObjectVisibleInRules(FWReference *obj)
{
if (activeProject()) activeProject()->ensureObjectVisibleInRules(obj);
}
/*
* Make rule visible and highlight given column
*/
void FWWindow::ensureRuleIsVisible(Rule *rule, int col)
{
if (activeProject()) activeProject()->ensureRuleIsVisible(rule, col);
}
void FWWindow::updateRuleSetViewSelection()
{
if (activeProject()) activeProject()->updateRuleSetViewSelection();
}
void FWWindow::updateTreeViewItemOrder()
{
//this is for case when tree becomes to be resorted
//if we do not reopen parent item, some of child
//items mix incorrectly (maybe bug of QT?)
if (activeProject()) activeProject()->updateTreeViewItemOrder();
}
void FWWindow::updateRuleSetView()
{
if (activeProject()) activeProject()->updateRuleSetView();
}
void FWWindow::updateRuleOptions()
{
if (activeProject()) activeProject()->updateRuleOptions();
}
void FWWindow::updateFirewallName()
{
if (activeProject()) activeProject()->updateFirewallName();
}
void FWWindow::scheduleRuleSetRedraw()
{
if (activeProject()) activeProject()->scheduleRuleSetRedraw();
}
void FWWindow::redrawRuleSets()
{
if (activeProject()) activeProject()->redrawRuleSets();
}
void FWWindow::reopenFirewall()
{
if (activeProject()) activeProject()->reopenFirewall();
}
void FWWindow::setEnabledAfterRF()
{
m_mainWindow->insertRuleAction->setEnabled( true );
@ -816,11 +628,6 @@ void FWWindow::selectRules()
if (activeProject()) activeProject()->selectRules();
}
void FWWindow::unselectRules()
{
if (activeProject()) activeProject()->unselectRules();
}
void FWWindow::disableActions(bool havePolicies)
{
m_mainWindow ->insertRuleAction->setEnabled( havePolicies ); // enabled if there are policies
@ -834,47 +641,15 @@ void FWWindow::disableActions(bool havePolicies)
m_mainWindow ->pasteRuleAboveAction->setEnabled( false );
m_mainWindow ->pasteRuleBelowAction->setEnabled( false );
m_mainWindow ->compileAction->setEnabled( havePolicies );
m_mainWindow ->installAction->setEnabled( havePolicies );
}
void FWWindow::editCopy()
{
if (activeProject()) activeProject()->editCopy();
}
void FWWindow::editCut()
{
if (activeProject())
{
activeProject()->editCut();
reloadAllWindowsWithFile(activeProject());
}
}
void FWWindow::editDelete()
{
if (activeProject())
{
activeProject()->editDelete();
reloadAllWindowsWithFile(activeProject());
}
}
void FWWindow::editPaste()
{
if (activeProject())
{
activeProject()->editPaste();
reloadAllWindowsWithFile(activeProject());
}
m_mainWindow ->compileAction->setEnabled( true );
m_mainWindow ->installAction->setEnabled( true );
}
void FWWindow::compile()
{
std::set<Firewall*> emp;
instd = new instDialog(NULL,BATCH_COMPILE,emp);
instd = new instDialog(NULL, BATCH_COMPILE, emp);
instd->show();
// id->exec();
@ -887,7 +662,7 @@ void FWWindow::compile(set<Firewall*> vf)
qDebug("FWWindow::compile preselected %d firewalls", int(vf.size()));
instDialog *id = new instDialog(NULL,BATCH_COMPILE,vf);
instDialog *id = new instDialog(NULL, BATCH_COMPILE, vf);
instd = id;
instd->show();
@ -898,7 +673,7 @@ void FWWindow::compile(set<Firewall*> vf)
void FWWindow::install(set<Firewall*> vf)
{
instDialog *id=new instDialog(NULL,BATCH_INSTALL, vf);
instDialog *id = new instDialog(NULL, BATCH_INSTALL, vf);
instd = id;
instd->show();
@ -918,70 +693,17 @@ void FWWindow::install()
// delete id;
}
void FWWindow::changeInfoStyle()
void FWWindow::transferfw(set<Firewall*> vf)
{
if (activeProject()) activeProject()->changeInfoStyle();
transferDialog *ed = new transferDialog(NULL, vf);
ed->show();
}
void FWWindow::insertRule()
void FWWindow::transferfw()
{
if (activeProject()) activeProject()->insertRule();
}
void FWWindow::addRuleAfterCurrent()
{
if (activeProject())
activeProject()->addRuleAfterCurrent();
}
void FWWindow::removeRule()
{
if (activeProject()) activeProject()->removeRule();
}
void FWWindow::moveRule()
{
if (activeProject()) activeProject()->moveRule();
}
void FWWindow::moveRuleUp()
{
if (activeProject()) activeProject()->moveRuleUp();
}
void FWWindow::moveRuleDown()
{
if (activeProject()) activeProject()->moveRuleDown();
}
void FWWindow::copyRule()
{
if (activeProject()) activeProject()->copyRule();
}
void FWWindow::cutRule()
{
if (activeProject()) activeProject()->cutRule();
}
void FWWindow::pasteRuleAbove()
{
if (activeProject()) activeProject()->pasteRuleAbove();
}
void FWWindow::pasteRuleBelow()
{
if (activeProject()) activeProject()->pasteRuleBelow();
}
void FWWindow::search()
{
if (activeProject()) activeProject()->search();
}
void FWWindow::findWhereUsed(FWObject * obj)
{
if (activeProject()) activeProject()->findWhereUsed(obj);
std::set<Firewall*> emp;
transferDialog *ed = new transferDialog(NULL, emp);
ed->show();
}
void FWWindow::showEvent(QShowEvent *ev)
@ -996,32 +718,6 @@ void FWWindow::hideEvent(QHideEvent *ev)
QMainWindow::hideEvent(ev);
}
void FWWindow::back()
{
if (activeProject()) activeProject()->back();
}
void FWWindow::newObject()
{
if (activeProject()) activeProject()->newObject();
}
// ObjectManipulator::lockObject calls
// mw->reloadAllWindowsWithFile(activeProject()) to update
// other windows
void FWWindow::lockObject()
{
if (activeProject()) activeProject()->lockObject();
}
// ObjectManipulator::unlockObject calls
// mw->reloadAllWindowsWithFile(activeProject()) to update
// other windows
void FWWindow::unlockObject()
{
if (activeProject()) activeProject()->unlockObject();
}
void FWWindow::prepareEditMenu()
{
if (!activeProject()) return;
@ -1081,14 +777,17 @@ void FWWindow::prepareFileMenu()
bool real_file_opened = (activeProject()->getFileName() != "");
bool in_rcs = (activeProject()->getRCS() != NULL &&
activeProject()->getRCS()->isCheckedOut());
bool needs_saving = (db() && db()->isDirty());
if (fwbdebug)
qDebug("FWWindow::prepareFileMenu(): activeProject()=%p"
" activeProject()->getFileName()='%s'",
" activeProject()->getFileName()='%s'"
" real_file_opened=%d needs_saving=%d",
activeProject(),
activeProject()->getFileName().toAscii().constData());
activeProject()->getFileName().toAscii().constData(),
real_file_opened, needs_saving);
m_mainWindow->fileSaveAction->setEnabled(real_file_opened);
m_mainWindow->fileSaveAction->setEnabled(real_file_opened && needs_saving);
m_mainWindow->fileCloseAction->setEnabled(real_file_opened);
m_mainWindow->filePropAction->setEnabled(real_file_opened);
m_mainWindow->filePrintAction->setEnabled(real_file_opened);
@ -1103,6 +802,11 @@ void FWWindow::prepareFileMenu()
m_mainWindow->fileSaveAsAction->setEnabled(true);
}
void FWWindow::prepareToolsMenu()
{
m_mainWindow->DiscoveryDruidAction->setEnabled(db()!=NULL);
}
void FWWindow::prepareWindowsMenu()
{
windowsPainters.clear();
@ -1128,7 +832,7 @@ void FWWindow::prepareWindowsMenu()
connect(next, SIGNAL(triggered()),m_space, SLOT(activateNextSubWindow()));
connect(previous, SIGNAL(triggered()),m_space, SLOT(activatePreviousSubWindow()));
QList<QMdiSubWindow *> subWindowList = getMdiArea()->subWindowList();
QList<QMdiSubWindow *> subWindowList = m_space->subWindowList();
QActionGroup * ag = new QActionGroup(this);
ag->setExclusive (true);
for (int i = 0 ; i < subWindowList.size(); i++)
@ -1158,41 +862,17 @@ void FWWindow::prepareWindowsMenu()
}
}
void FWWindow::setupAutoSave()
/**
* QMdiArea emits this signal after window has been activated. When
* window is 0, QMdiArea has just deactivated its last active window,
* and there are no active windows on the workspace.
*/
void FWWindow::subWindowActivated(QMdiSubWindow *subwindow)
{
if (activeProject()) activeProject()->setupAutoSave();
}
QString FWWindow::getCurrentFileName()
{
if (activeProject()) return activeProject()->getCurrentFileName();
return "";
}
RCS * FWWindow::getRCS()
{
if (activeProject()) return activeProject()->getRCS();
return 0;
}
void FWWindow::findObject(FWObject *o)
{
if (activeProject()) activeProject()->findObject(o);
}
void FWWindow::closeAuxiliaryPanel()
{
if (activeProject()) activeProject()->closeAuxiliaryPanel();
}
void FWWindow::closeEditorPanel()
{
if (activeProject()) activeProject()->closeEditorPanel();
}
void FWWindow::openEditorPanel()
{
if (activeProject()) activeProject()->openEditorPanel();
if (subwindow==NULL) return;
ProjectPanel *pp = dynamic_cast<ProjectPanel*>(subwindow->widget());
if (pp)
prepareFileMenu();
}
void FWWindow::editPrefs()
@ -1202,37 +882,6 @@ void FWWindow::editPrefs()
}
/*
* reset tab via callback because calling setCurrentPage from
* ruleSetTabChanged causes recursive call to ruleSetTabChanged
*/
void FWWindow::restoreRuleSetTab()
{
if (activeProject()) activeProject()->restoreRuleSetTab();
}
/*
* w - widget that requests editor ownership (ruleset view or tree)
* obj - object to be opened in the editor
* otype - editor type in case obj is a rule
* validate - validate and save editor contents
*
* if w==NULL, then request is done by the same widget that owns editor.
* just need to run validateAndSave and return result
*
* if obj==NULL, then no new object is to be opened in the editor
*
*/
bool FWWindow::requestEditorOwnership(QWidget *w,
FWObject *obj,
ObjectEditor::OptType otype,
bool validate)
{
if (activeProject())
return activeProject()->requestEditorOwnership(w, obj, otype, validate);
return false;
}
void FWWindow::editFind()
{
}
@ -1257,399 +906,11 @@ void FWWindow::helpIndex()
{
}
/*
* find all windows that represent the same file as ProjectPanel pp
* and reload objects (except for the window attached to pp)
*/
void FWWindow::reloadAllWindowsWithFile(ProjectPanel *pp)
{
if (fwbdebug)
qDebug("FWWindow::reloadAllWindowsWithFile pp=%p file=%s",
pp, pp->getRCS()->getFileName().toAscii().constData());
QList<QMdiSubWindow*> subWindowList = getMdiArea()->subWindowList();
QString fileName = pp->getRCS()->getFileName();
for (int i = 0 ; i < subWindowList.size(); i++)
{
ProjectPanel * other_pp = dynamic_cast<ProjectPanel*>(
subWindowList[i]->widget());
if (pp==other_pp) continue;
if (other_pp->getRCS()->getFileName()==fileName)
{
FWObject *obj = other_pp->m_panel->om->getOpened();
if (fwbdebug)
qDebug("FWWindow::reloadAllWindowsWithFile "
"Object %p is opened in the other window", obj);
other_pp->m_panel->om->loadObjects();
if (fwbdebug)
qDebug("FWWindow::reloadAllWindowsWithFile "
"Reopen object %p in the other window", obj);
other_pp->m_panel->om->openObject(obj, false);
other_pp->mdiWindow->update();
}
}
}
void FWWindow::closeRuleSetInAllWindowsWhereOpen(RuleSet *rs)
{
QList<QMdiSubWindow*> subWindowList = getMdiArea()->subWindowList();
for (int i = 0 ; i < subWindowList.size(); i++)
{
ProjectPanel * pp = dynamic_cast<ProjectPanel*>(
subWindowList[i]->widget());
pp->clearFirewallTabs();
pp->closeRuleSet(rs);
}
}
void FWWindow::closeObjectInAllWindowsWhereOpen(FWObject*)
{
QList<QMdiSubWindow*> subWindowList = getMdiArea()->subWindowList();
for (int i = 0 ; i < subWindowList.size(); i++)
{
ProjectPanel * pp = dynamic_cast<ProjectPanel*>(
subWindowList[i]->widget());
pp->m_panel->om->closeObject();
pp->mdiWindow->update();
}
}
//wrapers for some ObjectManipulator functions
FWObject* FWWindow::getOpened()
{
if (activeProject())
return activeProject()->getOpened();
return 0;
}
FWObject* FWWindow::getCurrentLib()
{
if (activeProject())
return activeProject()->getCurrentLib();
return 0;
}
void FWWindow::loadDataFromFw(Firewall *fw)
{
if (activeProject())
activeProject()->loadDataFromFw(fw);
}
void FWWindow::insertObjectInTree(FWObject *parent, FWObject *obj)
{
if (activeProject())
activeProject()->insertObjectInTree(parent, obj);
}
FWObject* FWWindow::createObject(const QString &objType,
const QString &objName,
FWObject *copyFrom)
{
FWObject *res = NULL;
if (activeProject())
{
res = activeProject()->createObject(objType, objName, copyFrom);
reloadAllWindowsWithFile(activeProject());
}
return res;
}
FWObject* FWWindow::createObject(FWObject *parent,
const QString &objType,
const QString &objName,
FWObject *copyFrom)
{
FWObject *res = NULL;
if (activeProject())
{
res = activeProject()->createObject(parent, objType,
objName, copyFrom);
reloadAllWindowsWithFile(activeProject());
}
return res;
}
void FWWindow::moveObject(FWObject *target, FWObject *obj)
{
if (activeProject())
{
activeProject()->moveObject(target, obj);
reloadAllWindowsWithFile(activeProject());
}
}
void FWWindow::moveObject(const QString &targetLibName, FWObject *obj)
{
if (activeProject())
{
activeProject()->moveObject(targetLibName, obj);
reloadAllWindowsWithFile(activeProject());
}
}
void FWWindow::autorename(FWObject *obj,
const std::string &objtype,
const std::string &namesuffix)
{
if (activeProject()) activeProject()->autorename(obj, objtype, namesuffix);
}
void FWWindow::updateLibColor(FWObject *lib)
{
if (activeProject())
{
activeProject()->updateLibColor(lib);
reloadAllWindowsWithFile(activeProject());
}
}
void FWWindow::updateLibName(FWObject *lib)
{
if (activeProject())
{
activeProject()->updateLibName(lib);
reloadAllWindowsWithFile(activeProject());
}
}
void FWWindow::updateObjName(FWObject *obj,
const QString &oldName,
bool askForAutorename)
{
if (activeProject())
{
activeProject()->updateObjName(obj, oldName, askForAutorename);
reloadAllWindowsWithFile(activeProject());
}
}
void FWWindow::updateObjName(FWObject *obj,
const QString &oldName,
const QString &oldLabel,
bool askForAutorename)
{
if (activeProject())
{
activeProject()->updateObjName(obj,
oldName, oldLabel, askForAutorename);
reloadAllWindowsWithFile(activeProject());
}
}
void FWWindow::updateLastModifiedTimestampForOneFirewall(FWObject *o)
{
if (activeProject())
activeProject()->updateLastModifiedTimestampForOneFirewall(o);
}
void FWWindow::updateLastModifiedTimestampForAllFirewalls(FWObject *o)
{
if (activeProject())
activeProject()->updateLastModifiedTimestampForAllFirewalls(o);
}
void FWWindow::updateLastInstalledTimestamp(FWObject *o)
{
if (activeProject()) activeProject()->updateLastInstalledTimestamp(o);
}
void FWWindow::updateLastCompiledTimestamp(FWObject *o)
{
if (activeProject()) activeProject()->updateLastCompiledTimestamp(o);
}
FWObject* FWWindow::pasteTo(FWObject *target, FWObject *obj)
{
if (activeProject()) return activeProject()->pasteTo(target, obj);
return 0;
}
void FWWindow::delObj(FWObject *obj,bool openobj)
{
if (activeProject())
{
activeProject()->delObj(obj, openobj);
reloadAllWindowsWithFile(activeProject());
}
}
ObjectTreeView* FWWindow::getCurrentObjectTree()
{
if (activeProject()) return activeProject()->getCurrentObjectTree();
return 0;
}
void FWWindow::openObject(QTreeWidgetItem *otvi)
{
if (activeProject()) activeProject()->openObject(otvi);
}
void FWWindow::openObject(FWObject *obj)
{
if (activeProject()) activeProject()->openObject(obj);
}
bool FWWindow::editObject(FWObject *obj)
{
if (activeProject()) return activeProject()->editObject(obj);
return false;
}
void FWWindow::findAllFirewalls (std::list<Firewall *> &fws)
{
if (activeProject()) activeProject()->findAllFirewalls (fws);
}
FWObject* FWWindow::duplicateObject(FWObject *target,
FWObject *obj,
const QString &name,
bool askForAutorename)
{
if (activeProject())
return activeProject()->duplicateObject(target,
obj, name, askForAutorename);
return 0;
}
void FWWindow::showDeletedObjects(bool f)
{
if (activeProject()) activeProject()->showDeletedObjects(f);
}
void FWWindow::select()
{
if (activeProject()) activeProject()->select();
}
void FWWindow::unselect()
{
if (activeProject()) activeProject()->unselect();
}
void FWWindow::info()
{
if (activeProject()) info(activeProject()->getSelectedObject(), true);
}
void FWWindow::setManipulatorFocus()
{
if (activeProject()) activeProject()->setManipulatorFocus();
}
void FWWindow::clearManipulatorFocus()
{
if (activeProject()) activeProject()->clearManipulatorFocus();
}
//wrapers for some Object Editor functions
bool FWWindow::isEditorVisible()
{
if (activeProject()) return activeProject()->isEditorVisible();
return false;
}
bool FWWindow::isEditorModified()
{
if (activeProject()) return activeProject()->isEditorModified();
return false;
}
void FWWindow::showEditor()
{
if (activeProject()) activeProject()->showEditor();
}
void FWWindow::hideEditor()
{
if (activeProject()) activeProject()->hideEditor();
}
void FWWindow::closeEditor()
{
if (activeProject()) activeProject()->closeEditor();
}
void FWWindow::openEditor(FWObject *o)
{
if (activeProject()) activeProject()->openEditor(o);
}
void FWWindow::openOptEditor(FWObject *o, ObjectEditor::OptType t)
{
if (activeProject()) activeProject()->openOptEditor(o, t);
}
void FWWindow::blankEditor()
{
if (activeProject()) activeProject()->blankEditor();
}
FWObject* FWWindow::getOpenedEditor()
{
if (activeProject()) return activeProject()->getOpenedEditor();
return 0;
}
ObjectEditor::OptType FWWindow::getOpenedOptEditor()
{
if (activeProject()) return activeProject()->getOpenedOptEditor();
return ObjectEditor::optNone;
}
void FWWindow::selectObjectInEditor(FWObject *o)
{
if (activeProject()) activeProject()->selectObjectInEditor(o);
}
void FWWindow::actionChangedEditor(FWObject *o)
{
if (activeProject()) activeProject()->actionChangedEditor(o);
}
bool FWWindow::validateAndSaveEditor()
{
if (activeProject()) return activeProject()->validateAndSaveEditor();
return false;
}
void FWWindow::setFDObject(FWObject *o)
{
if (activeProject()) activeProject()->setFDObject(o);
}
QPrinter* FWWindow::getPrinter()
{
return printer;
}
FWObjectDatabase* FWWindow::db()
{
if (activeProject()) return activeProject()->db();
return 0;
}
QString FWWindow::printHeader()
{
if (activeProject()) return activeProject()->printHeader();
return "";
}
bool FWWindow::isSystem(FWObject *obj)
{
if (activeProject()) return activeProject()->isSystem(obj);
return false;
}
void FWWindow::closeEvent(QCloseEvent* ev)
{
if (fwbdebug) qDebug("FWWindow::closeEvent");
@ -1676,6 +937,21 @@ void FWWindow::closeEvent(QCloseEvent* ev)
}
}
bool FWWindow::event(QEvent *event)
{
if (event->type() >= QEvent::User)
{
// dispatch event to all projectpanel windows
QList<QMdiSubWindow*> subWindowList = m_space->subWindowList();
for (int i = 0 ; i < subWindowList.size(); i++)
QCoreApplication::sendEvent(subWindowList[i]->widget(), event);
event->accept();
return true;
}
return QMainWindow::event(event);
}
void FWWindow::selectActiveSubWindow (/*const QString & text*/)
{
QObject * sender_ = sender ();
@ -1687,7 +963,7 @@ void FWWindow::selectActiveSubWindow (/*const QString & text*/)
{
if (windowsTitles[i]==text)
{
getMdiArea()->setActiveSubWindow(windowsPainters[i]);
m_space->setActiveSubWindow(windowsPainters[i]);
}
}
}
@ -1718,12 +994,10 @@ void FWWindow::maximize ()
st->setInt("Window/maximized", 1);
}
void FWWindow::changeActiveSubwindow() {}
void FWWindow::updateTreeFont ()
{
QFont font = st->getTreeFont();
QList<QMdiSubWindow *> subWindowList = getMdiArea()->subWindowList();
QList<QMdiSubWindow *> subWindowList = m_space->subWindowList();
for (int i = 0 ; i < subWindowList.size();i++)
{
ProjectPanel * pp = dynamic_cast <ProjectPanel *>(subWindowList[i]->widget());
@ -1740,9 +1014,21 @@ void FWWindow::updateTreeFont ()
void FWWindow::checkForUpgrade(const QString& server_response)
{
disconnect(current_version_http_getter, SIGNAL(done(const QString&)),
this, SLOT(checkForUpgrade(const QString&)));
/*
* getStatus() returns error status if server esponded with 302 or
* 301 redirect. Only "200" is considered success.
*/
if (current_version_http_getter->getStatus())
{
if (!server_response.trimmed().isEmpty())
/*
* server response may be some html or other data in case
* connection goes via proxy, esp. with captive portals. We
* should not interpret that as "new version is available"
*/
if (server_response.trimmed() == "update = 1")
{
QMessageBox::warning(
this,"Firewall Builder",
@ -1772,7 +1058,33 @@ void FWWindow::projectWindowClosed()
void FWWindow::help()
{
Help *h = new Help(this, "main", "Firewall Builder");
Help *h = new Help(this, "Firewall Builder");
h->setSource(QUrl("main.html"));
h->show();
}
void FWWindow::showReleaseNotes()
{
QString file_name = QString("release_notes_%1.html").arg(VERSION);
// Show "release notes" dialog only if corresponding file
// exists.
QString contents;
Help *h = new Help(this, "Important Information About This Release");
if (h->findHelpFile(file_name).isEmpty())
{
// the file does not exist
delete h;
} else
{
// I do not know why, but url "file://file_name" does not seem to work.
// But "file:file_name" works.
h->setSource(QUrl("file:" + file_name));
h->setModal(false);
h->show();
h->exec();
// Class Help uses attribute Qt::WA_DeleteOnClose which
// means the system will delete the object on close. No
// need to delete it explicitly if it was shown.
}
}

View File

@ -31,7 +31,6 @@
#include <ui_pagesetupdialog_q.h>
#include "RCS.h"
#include "ObjectEditor.h"
#include "HttpGet.h"
#include "printerStream.h"
@ -41,6 +40,7 @@
#include <vector>
#include <list>
#include <set>
namespace libfwbuilder {
class FWObjectDatabase;
@ -49,6 +49,7 @@ namespace libfwbuilder {
class RuleSet;
class Rule;
class FWObject;
class FWReference;
};
class ObjectManipulator;
@ -104,14 +105,12 @@ public:
public slots:
void selectActiveSubWindow (/*const QString & text*/);
void subWindowActivated(QMdiSubWindow*);
void minimize();
void maximize();
void changeActiveSubwindow();
virtual void search();
virtual void reopenFirewall();
virtual void redrawRuleSets();
virtual void changeInfoStyle();
virtual void restoreRuleSetTab();
@ -122,6 +121,7 @@ public slots:
virtual void helpContentsAction();
virtual void helpIndex();
virtual void help();
virtual void showReleaseNotes();
virtual void fileNew();
virtual void fileOpen();
@ -155,6 +155,8 @@ public slots:
virtual void compile();
virtual void install(std::set<libfwbuilder::Firewall * > vf);
virtual void install();
virtual void transferfw(std::set<libfwbuilder::Firewall * > vf);
virtual void transferfw();
virtual void insertRule();
virtual void addRuleAfterCurrent();
@ -176,13 +178,12 @@ public slots:
virtual void prepareEditMenu();
virtual void prepareObjectMenu();
virtual void prepareFileMenu();
virtual void prepareToolsMenu();
virtual void prepareWindowsMenu();
virtual void prepareFileOpenRecentMenu();
virtual void toolsDiscoveryDruid();
virtual void closeAuxiliaryPanel();
virtual void closeEditorPanel();
virtual void openEditorPanel();
virtual void killInstDialog();
@ -199,46 +200,25 @@ public slots:
~FWWindow();
QMdiArea* getMdiArea () {return m_space;}
RCS * getRCS();
libfwbuilder::FWObject* getVisibleFirewalls();
void registerAutoOpenDocFile(const QString &file_name,
bool load_from_rcs_head);
void load(QWidget *dialogs_parent,RCS *rcs);
void load(QWidget *dialogs_parent);
void loadLibrary(const std::string &libfpath);
void loadFile(const QString &filename, bool load_rcs_head);
bool loadFile(const QString &filename, bool load_rcs_head);
void save();
bool checkin(bool unlock);
int findFirewallInList(libfwbuilder::FWObject *f);
void updateTreeViewItemOrder();
void reloadAllWindowsWithFile(ProjectPanel *pp);
void closeRuleSetInAllWindowsWhereOpen(libfwbuilder::RuleSet *rs);
void closeObjectInAllWindowsWhereOpen(libfwbuilder::FWObject *obj);
bool editingLibrary();
void ensureObjectVisibleInRules(libfwbuilder::FWReference *obj);
void ensureRuleIsVisible(libfwbuilder::Rule *rule, int col=0);
QString chooseNewFileName(const QString &fname, const QString &title);
void setFileName(const QString &fname);
bool saveIfModified();
void updateFirewallName();
void updateRuleSetView();
void updateRuleOptions();
void updateRuleSetViewSelection();
/**
* unselects whatever is selected in policy
*/
void unselectRules();
/**
* selects whatever is current in rules
*/
@ -249,22 +229,11 @@ public slots:
QString getCurrentFileName();
void info(libfwbuilder::FWObject *o, bool forced = false);
void setupAutoSave();
void findObject(libfwbuilder::FWObject *);
void findWhereUsed(libfwbuilder::FWObject *);
/**
* panel that wants to open an object in the editor
* uses this method to request permission to do so and
* to register itself as an owner of the editor
*/
bool requestEditorOwnership(QWidget *w,
libfwbuilder::FWObject *o,
ObjectEditor::OptType otype,
bool validate = true);
bool exportLibraryTest(std::list<libfwbuilder::FWObject*> &selectedLibs);
void exportLibraryTo(QString fname,std::list<libfwbuilder::FWObject*> &selectedLibs, bool rof);
@ -275,8 +244,6 @@ public slots:
void setSafeMode(bool f);
void setStartupFileName(const QString &fn);
void scheduleRuleSetRedraw();
// semi-intelligent way to guess most appropriate
// destination directory for various file save or file open
// operations. If working directory is configured in
@ -288,9 +255,6 @@ public slots:
QString getDestDir(const QString &filename);
//wrapers for some ObjectManipulator functions
libfwbuilder::FWObject* getOpened();
libfwbuilder::FWObject* getCurrentLib();
void insertObjectInTree(libfwbuilder::FWObject *parent,
@ -311,35 +275,13 @@ public slots:
void moveObject(const QString &targetLibName,
libfwbuilder::FWObject *obj);
void autorename(libfwbuilder::FWObject *obj,
const std::string &objtype,
const std::string &namesuffix);
void updateLibColor(libfwbuilder::FWObject *lib);
void updateLibName(libfwbuilder::FWObject *lib);
void updateObjName(libfwbuilder::FWObject *obj,
const QString &oldName,
bool askForAutorename=true);
void updateObjName(libfwbuilder::FWObject *obj,
const QString &oldName,
const QString &oldLabel,
bool askForAutorename=true);
void updateLastModifiedTimestampForOneFirewall(libfwbuilder::FWObject *o);
void updateLastModifiedTimestampForAllFirewalls(libfwbuilder::FWObject *o);
void updateLastInstalledTimestamp(libfwbuilder::FWObject *o);
void updateLastCompiledTimestamp(libfwbuilder::FWObject *o);
void loadDataFromFw(libfwbuilder::Firewall *fw);
libfwbuilder::FWObject* pasteTo(libfwbuilder::FWObject *target,
libfwbuilder::FWObject *obj);
void delObj(libfwbuilder::FWObject *obj,bool openobj=true);
ObjectTreeView* getCurrentObjectTree();
void openObject(QTreeWidgetItem *otvi);
void openObject(libfwbuilder::FWObject *obj);
bool editObject(libfwbuilder::FWObject *obj);
void findAllFirewalls (std::list<libfwbuilder::Firewall *> &fws);
libfwbuilder::FWObject* duplicateObject(libfwbuilder::FWObject *target,
@ -347,35 +289,9 @@ public slots:
const QString &name = QString::null,
bool askForAutorename=true);
void showDeletedObjects(bool f);
void select();
void unselect();
void info();
void setManipulatorFocus();
void clearManipulatorFocus();
//wrapers for some Object Editor functions
bool isEditorVisible();
bool isEditorModified();
void showEditor();
void hideEditor();
void closeEditor();
void openEditor(libfwbuilder::FWObject *o);
void openOptEditor(libfwbuilder::FWObject *, ObjectEditor::OptType t);
void blankEditor();
libfwbuilder::FWObject* getOpenedEditor();
ObjectEditor::OptType getOpenedOptEditor();
void selectObjectInEditor(libfwbuilder::FWObject *o);
void actionChangedEditor(libfwbuilder::FWObject *o);
bool validateAndSaveEditor();
//find dialog functions wrapers
void setFDObject(libfwbuilder::FWObject *o);
// void select();
// void unselect();
QPrinter* getPrinter();
libfwbuilder::FWObjectDatabase* db();
@ -390,10 +306,10 @@ public slots:
protected:
virtual void showEvent( QShowEvent *ev);
virtual void hideEvent( QHideEvent *ev);
virtual void closeEvent( QCloseEvent * );
virtual void showEvent(QShowEvent *ev);
virtual void hideEvent(QHideEvent *ev);
virtual void closeEvent(QCloseEvent *ev);
virtual bool event(QEvent *event);
};
#endif

View File

@ -0,0 +1,551 @@
/*
Firewall Builder
Copyright (C) 2003, 2006 NetCitadel, LLC
Author: Vadim Kurland vadim@fwbuilder.org
$Id$
This program is free software which we release under the GNU General Public
License. You may redistribute and/or modify this program under the terms
of that license as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
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.
To get a copy of the GNU General Public License, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#include "../../config.h"
#include "global.h"
#include "FWWindow.h"
#include "ProjectPanel.h"
#include "ObjectManipulator.h"
#include "FWObjectClipboard.h"
#include "FWBTree.h"
#include "FWBSettings.h"
#include "RuleSetView.h"
#include "FindObjectWidget.h"
#include "FindWhereUsedWidget.h"
#include "events.h"
#include "fwbuilder/FWReference.h"
#include "fwbuilder/Tools.h"
#include "fwbuilder/Resources.h"
#include "fwbuilder/FWObjectDatabase.h"
#include "fwbuilder/FWException.h"
#include "fwbuilder/Library.h"
#include "fwbuilder/FWObject.h"
/*
#include <qaction.h>
#include <qlistwidget.h>
#include <qmessagebox.h>
#include <qapplication.h>
#include <qfileinfo.h>
#include <qfile.h>
#include <qfiledialog.h>
#include <qpixmap.h>
#include <qpixmapcache.h>
#include <qheaderview.h>
#include <qtabwidget.h>
#include <qcombobox.h>
#include <qcheckbox.h>
#include <qtextedit.h>
#include <qstringlist.h>
#include <qmenu.h>
#include <qtoolbutton.h>
#include <qlayout.h>
#include <qapplication.h>
#include <qcursor.h>
#include <qsplitter.h>
#include <qtimer.h>
#include <qstatusbar.h>
#include <qlabel.h>
#include <qradiobutton.h>
#include <qprinter.h>
#include <qstackedwidget.h>
#include <qlistwidget.h>
#include <qeventloop.h>
#include <qtextstream.h>
#include <QCloseEvent>
#include <QShowEvent>
#include <QList>
#include <QHideEvent>
#include <QMdiArea>
#include <QMdiSubWindow>
#include <QSignalMapper>
#include <QUrl>
*/
/*
* Methods in this module are just wrappers and call the same method
* in the topmost object of the ProjectPanel class (MDI subwindow).
*
* TODO: see if most of these methods can be called directly using
* pointer to the ProjectPanel object. Remove most, if not all,
* wrappers in the FWWindow class.
*/
using namespace libfwbuilder;
using namespace std;
using namespace Ui;
/*************************************************************************/
bool FWWindow::saveIfModified()
{
if (activeProject()) return activeProject()->saveIfModified();
return false;
}
QString FWWindow::getDestDir(const QString &fname)
{
if (activeProject()) return activeProject()->getDestDir(fname);
return "";
}
QString FWWindow::chooseNewFileName(const QString &fname, const QString &title)
{
if (activeProject()) return activeProject()->chooseNewFileName(fname,title);
return "";
}
void FWWindow::setFileName(const QString &fname)
{
if (activeProject()) activeProject()->setFileName(fname);
}
void FWWindow::fileProp()
{
if (activeProject()) activeProject()->fileProp();
}
void FWWindow::fileSave()
{
if (activeProject()) activeProject()->fileSave();
}
void FWWindow::fileSaveAs()
{
if (activeProject()) activeProject()->fileSaveAs();
}
void FWWindow::fileCommit()
{
if (activeProject()) activeProject()->fileCommit();
}
/*
* discard changes done to the file and check out clean copy of the
* head revision from RCS
*/
void FWWindow::fileDiscard()
{
if (activeProject()) activeProject()->fileDiscard();
}
void FWWindow::fileAddToRCS()
{
if (activeProject()) activeProject()->fileAddToRCS();
}
void FWWindow::load(QWidget*)
{
if (activeProject()) activeProject()->loadStandardObjects();
}
void FWWindow::load(QWidget*, RCS *_rcs)
{
if (activeProject()) activeProject()->loadFromRCS(_rcs);
}
void FWWindow::save()
{
if (activeProject()) activeProject()->save();
}
void FWWindow::loadLibrary(const string &libfpath)
{
if (activeProject()) activeProject()->loadLibrary(libfpath);
}
void FWWindow::fileImport()
{
if (activeProject()) activeProject()->fileImport();
}
void FWWindow::fileCompare()
{
if (activeProject()) activeProject()->fileCompare();
}
void FWWindow::findExternalRefs(FWObject *lib,
FWObject *root,
list<FWReference*> &extRefs)
{
if (activeProject()) activeProject()->findExternalRefs(lib, root, extRefs);
}
bool FWWindow::checkin(bool unlock)
{
if (activeProject()) return activeProject()->checkin(unlock);
return false;
}
void FWWindow::setSafeMode(bool f)
{
if (activeProject()) activeProject()->setSafeMode(f);
}
bool FWWindow::exportLibraryTest(list<FWObject*> &selectedLibs)
{
/* VERY IMPORTANT: External library file must be self-contained,
* otherwise it can not be exported.
*
* check if selected libraries have references to objects in other
* libraries (not exported to the same file). Exporting such libraries
* pulls in other ones because of these references. This is confusing
* because it means we end up with multiple copies of such objects (in
* exported library file and in user's data file). When user imports
* this library and opens their file, it is impossible to say which
* library an object belongs to.
*
* This is prohibited. We check if exported set of libraries has such
* references and refuse to export it. The user is supposed to clean
* it up by either moving objects into the library they are trying to
* export, or by rearranging objects. The only exception for this is
* library "Standard", which is assumed to be always present so we can
* have references to objects in it.
*/
if (activeProject())
return activeProject()->exportLibraryTest(selectedLibs);
return false;
}
void FWWindow::exportLibraryTo(QString fname,list<FWObject*> &selectedLibs, bool rof)
{
if (activeProject())
activeProject()->exportLibraryTo(fname,selectedLibs, rof);
}
void FWWindow::fileExport()
{
if (activeProject()) activeProject()->fileExport();
}
int FWWindow::findFirewallInList(FWObject *f)
{
if (activeProject()) return activeProject()->findFirewallInList(f);
return -1;
}
void FWWindow::editCopy()
{
if (activeProject()) activeProject()->editCopy();
}
void FWWindow::editCut()
{
if (activeProject())
{
activeProject()->editCut();
}
}
void FWWindow::editDelete()
{
if (activeProject())
{
activeProject()->editDelete();
}
}
void FWWindow::editPaste()
{
if (activeProject())
{
activeProject()->editPaste();
}
}
void FWWindow::changeInfoStyle()
{
if (activeProject()) activeProject()->changeInfoStyle();
}
void FWWindow::insertRule()
{
if (activeProject()) activeProject()->insertRule();
}
void FWWindow::addRuleAfterCurrent()
{
if (activeProject())
activeProject()->addRuleAfterCurrent();
}
void FWWindow::removeRule()
{
if (activeProject()) activeProject()->removeRule();
}
void FWWindow::moveRule()
{
if (activeProject()) activeProject()->moveRule();
}
void FWWindow::moveRuleUp()
{
if (activeProject()) activeProject()->moveRuleUp();
}
void FWWindow::moveRuleDown()
{
if (activeProject()) activeProject()->moveRuleDown();
}
void FWWindow::copyRule()
{
if (activeProject()) activeProject()->copyRule();
}
void FWWindow::cutRule()
{
if (activeProject()) activeProject()->cutRule();
}
void FWWindow::pasteRuleAbove()
{
if (activeProject()) activeProject()->pasteRuleAbove();
}
void FWWindow::pasteRuleBelow()
{
if (activeProject()) activeProject()->pasteRuleBelow();
}
void FWWindow::search()
{
if (activeProject()) activeProject()->search();
}
void FWWindow::findWhereUsed(FWObject * obj)
{
if (activeProject()) activeProject()->findWhereUsed(obj);
}
void FWWindow::back()
{
if (activeProject()) activeProject()->back();
}
void FWWindow::newObject()
{
if (activeProject()) activeProject()->newObject();
}
// ObjectManipulator::lockObject calls
// mw->reloadAllWindowsWithFile(activeProject()) to update
// other windows
void FWWindow::lockObject()
{
if (activeProject()) activeProject()->lockObject();
}
// ObjectManipulator::unlockObject calls
// mw->reloadAllWindowsWithFile(activeProject()) to update
// other windows
void FWWindow::unlockObject()
{
if (activeProject()) activeProject()->unlockObject();
}
void FWWindow::setupAutoSave()
{
if (activeProject()) activeProject()->setupAutoSave();
}
QString FWWindow::getCurrentFileName()
{
if (activeProject()) return activeProject()->getCurrentFileName();
return "";
}
RCS * FWWindow::getRCS()
{
if (activeProject()) return activeProject()->getRCS();
return 0;
}
void FWWindow::findObject(FWObject *o)
{
if (activeProject()) activeProject()->findObject(o);
}
void FWWindow::closeAuxiliaryPanel()
{
if (activeProject()) activeProject()->closeAuxiliaryPanel();
}
/*
* reset tab via callback because calling setCurrentPage from
* ruleSetTabChanged causes recursive call to ruleSetTabChanged
*/
void FWWindow::restoreRuleSetTab()
{
if (activeProject()) activeProject()->restoreRuleSetTab();
}
FWObject* FWWindow::getCurrentLib()
{
if (activeProject())
return activeProject()->getCurrentLib();
return 0;
}
void FWWindow::loadDataFromFw(Firewall *fw)
{
if (activeProject())
activeProject()->loadDataFromFw(fw);
}
void FWWindow::insertObjectInTree(FWObject *parent, FWObject *obj)
{
if (activeProject())
activeProject()->insertObjectInTree(parent, obj);
}
FWObject* FWWindow::createObject(const QString &objType,
const QString &objName,
FWObject *copyFrom)
{
FWObject *res = NULL;
if (activeProject())
{
res = activeProject()->createObject(objType, objName, copyFrom);
}
return res;
}
FWObject* FWWindow::createObject(FWObject *parent,
const QString &objType,
const QString &objName,
FWObject *copyFrom)
{
FWObject *res = NULL;
if (activeProject())
{
res = activeProject()->createObject(parent, objType,
objName, copyFrom);
}
return res;
}
void FWWindow::moveObject(FWObject *target, FWObject *obj)
{
if (activeProject())
{
activeProject()->moveObject(target, obj);
}
}
void FWWindow::moveObject(const QString &targetLibName, FWObject *obj)
{
if (activeProject())
{
activeProject()->moveObject(targetLibName, obj);
}
}
FWObject* FWWindow::pasteTo(FWObject *target, FWObject *obj)
{
if (activeProject()) return activeProject()->pasteTo(target, obj);
return 0;
}
void FWWindow::delObj(FWObject *obj,bool openobj)
{
if (activeProject())
{
activeProject()->delObj(obj, openobj);
}
}
ObjectTreeView* FWWindow::getCurrentObjectTree()
{
if (activeProject()) return activeProject()->getCurrentObjectTree();
return 0;
}
void FWWindow::findAllFirewalls (std::list<Firewall *> &fws)
{
if (activeProject()) activeProject()->findAllFirewalls (fws);
}
FWObject* FWWindow::duplicateObject(FWObject *target,
FWObject *obj,
const QString &name,
bool askForAutorename)
{
if (activeProject())
return activeProject()->duplicateObject(target,
obj, name, askForAutorename);
return 0;
}
void FWWindow::showDeletedObjects(bool f)
{
if (activeProject()) activeProject()->showDeletedObjects(f);
}
/*
void FWWindow::select()
{
if (activeProject()) activeProject()->select();
}
void FWWindow::unselect()
{
if (activeProject()) activeProject()->unselect();
}
*/
FWObjectDatabase* FWWindow::db()
{
if (activeProject()) return activeProject()->db();
return NULL;
}
QString FWWindow::printHeader()
{
if (activeProject()) return activeProject()->printHeader();
return "";
}
bool FWWindow::isSystem(FWObject *obj)
{
if (activeProject()) return activeProject()->isSystem(obj);
return false;
}
bool FWWindow::editingLibrary()
{
if (activeProject()) return activeProject()->editingLibrary();
return false;
}

View File

@ -39,6 +39,7 @@
#include "RuleSetView.h"
#include "ObjectEditor.h"
#include "ProjectPanel.h"
#include "events.h"
#include "fwbuilder/FWObjectDatabase.h"
#include "fwbuilder/FWReference.h"
@ -68,8 +69,10 @@ using namespace libfwbuilder;
#define MAX_SEARCH_ITEMS_COUNT 10
FindObjectWidget::FindObjectWidget(QWidget*p, const char * n, Qt::WindowFlags f) : QWidget(p,f)
FindObjectWidget::FindObjectWidget(QWidget*p, ProjectPanel *pp,
const char * n, Qt::WindowFlags f) : QWidget(p,f)
{
project_panel = pp;
m_widget = new Ui::findObjectWidget_q;
m_widget->setupUi(this);
@ -123,7 +126,7 @@ void FindObjectWidget::reset()
{
lastFound=NULL;
lastAttrSearch="";
treeSeeker = mw->db()->tree_begin();
treeSeeker = project_panel->db()->tree_begin();
}
@ -286,7 +289,7 @@ void FindObjectWidget::findNext()
// if scope is "policies of opened firewall" then we need to get
// pointer to the currently opened firewall object
RuleSet* current_rule_set = mw->activeProject()->getCurrentRuleSet();
RuleSet* current_rule_set = project_panel->getCurrentRuleSet();
if (current_rule_set)
selectedFirewall = Firewall::cast(current_rule_set->getParent());
else
@ -299,7 +302,7 @@ loop:
QApplication::setOverrideCursor( QCursor( Qt::WaitCursor) );
for (; treeSeeker!=mw->db()->tree_end(); ++treeSeeker)
for (; treeSeeker != project_panel->db()->tree_end(); ++treeSeeker)
{
o = *treeSeeker;
@ -337,7 +340,7 @@ loop:
QApplication::restoreOverrideCursor();
if (treeSeeker==mw->db()->tree_end())
if (treeSeeker == project_panel->db()->tree_end())
{
reset();
if (m_widget->srScope->currentIndex()==3) // scope ==selected firewalls
@ -407,6 +410,7 @@ bool FindObjectWidget::validateReplaceObject()
}
return true;
}
void FindObjectWidget::replace()
{
if(!validateReplaceObject()) return;
@ -419,9 +423,8 @@ void FindObjectWidget::replace()
}
QApplication::setOverrideCursor( QCursor( Qt::WaitCursor) );
FWObject *res=_replaceCurrent();
mw->updateRuleSetView();
mw->info();
FWObject *res = _replaceCurrent();
if (res)
{
showObject(res);
@ -446,7 +449,7 @@ void FindObjectWidget::replaceAll()
QApplication::setOverrideCursor( QCursor( Qt::WaitCursor) );
while (f)
{
for (; treeSeeker!=mw->db()->tree_end(); ++treeSeeker)
for (; treeSeeker != project_panel->db()->tree_end(); ++treeSeeker)
{
o = *treeSeeker;
if( RuleElement::cast(o->getParent())!=NULL)
@ -461,7 +464,7 @@ void FindObjectWidget::replaceAll()
} else if (m_widget->srScope->currentIndex()==0) continue ; // scope == tree only
} else
{
/* if not in rules, then in the tree. */
/* if not in rules, then in the tree. */
if (m_widget->srScope->currentIndex()>1) continue; // scope in (firewalls only , selected firewalls)
}
@ -476,7 +479,7 @@ void FindObjectWidget::replaceAll()
matchID( o->getId() )) break;
}
}
if (treeSeeker==mw->db()->tree_end())
if (treeSeeker == project_panel->db()->tree_end())
{
f=false;
@ -488,14 +491,14 @@ void FindObjectWidget::replaceAll()
_replaceCurrent();
}
}
mw->updateRuleSetView();
mw->info();
QApplication::restoreOverrideCursor();
QMessageBox::information(
this,"Firewall Builder",
this, "Firewall Builder",
tr("Replaced %1 objects.").arg(count));
}
FWObject* FindObjectWidget::_replaceCurrent()
{
FWObject *o=lastFound;
@ -504,13 +507,17 @@ FWObject* FindObjectWidget::_replaceCurrent()
if (p==NULL || o==NULL) return NULL;
if (FWReference::cast(o)==NULL) return NULL;
QCoreApplication::postEvent(
mw, new dataModifiedEvent(project_panel->getFileName(), p->getId()));
p->removeRef(FWReference::cast(o)->getPointer());
//chack for duplicates --------
// check for duplicates --------
FWObject *ro=m_widget->replaceDropArea->getObject();
if (RuleElement::cast(p)==NULL || !RuleElement::cast(p)->isAny())
{
/* avoid duplicates */
// avoid duplicates
int cp_id = ro->getId();
FWObject *oo;
FWReference *ref;
@ -547,7 +554,7 @@ FWObject* FindObjectWidget::_replaceCurrent()
bool FindObjectWidget::inSelectedFirewall( RuleElement* r)
{
FWObject *f=r;
while (f!=NULL && !Firewall::isA(f)) f=f->getParent();
while (f!=NULL && Firewall::cast(f)==NULL) f=f->getParent();
if (f==NULL) return false;
return selectedFirewall==(Firewall::cast(f));
@ -576,26 +583,26 @@ void FindObjectWidget::showObject(FWObject* o)
FWReference* ref=FWReference::cast(o);
if (ref!=NULL && RuleElement::cast(o->getParent())!=NULL)
{
mw->closeEditor();
mw->clearManipulatorFocus();
mw->ensureObjectVisibleInRules( ref );
project_panel->closeEditor();
project_panel->clearManipulatorFocus();
project_panel->ensureObjectVisibleInRules( ref );
return;
}
mw->unselectRules();
project_panel->unselectRules();
if (Group::cast(o->getParent())!=NULL &&
!mw->isSystem(o->getParent()))
!project_panel->isSystem(o->getParent()))
{
mw->openObject( o->getParent() );
mw->editObject( o->getParent() );
mw->selectObjectInEditor( (ref) ? ref->getPointer() : o );
project_panel->openObject( o->getParent() );
project_panel->editObject( o->getParent() );
project_panel->selectObjectInEditor( (ref) ? ref->getPointer() : o );
return;
}
mw->closeEditor();
mw->openObject( o );
mw->select(); // selects an item in the tree and assigns kbd focus to it
project_panel->closeEditor();
project_panel->openObject( o );
project_panel->select(); // selects an item in the tree and assigns kbd focus to it
}
void FindObjectWidget::init()

View File

@ -29,6 +29,7 @@
#include "../../config.h"
#include <ui_findobjectwidget_q.h>
#include "ProjectPanel.h"
#include "fwbuilder/FWObject.h"
#include "fwbuilder/RuleElement.h"
@ -41,13 +42,15 @@ class QWidget;
class FindObjectWidget : public QWidget
{
Q_OBJECT
private:
QString lastAttrSearch;
libfwbuilder::FWObject *lastFound;
libfwbuilder::FWObject::tree_iterator treeSeeker;
private:
QString lastAttrSearch;
libfwbuilder::FWObject *lastFound;
libfwbuilder::FWObject::tree_iterator treeSeeker;
libfwbuilder::Firewall* selectedFirewall;
ProjectPanel *project_panel;
bool matchName(const QString &name);
bool matchID(int id);
bool matchAttr(libfwbuilder::FWObject* obj);
@ -57,7 +60,7 @@ class FindObjectWidget : public QWidget
public:
Ui::findObjectWidget_q *m_widget;
FindObjectWidget(QWidget*p, const char * n = 0, Qt::WindowFlags f = 0);
FindObjectWidget(QWidget*p, ProjectPanel *pp, const char * n = 0, Qt::WindowFlags f = 0);
~FindObjectWidget() { delete m_widget; };
void findObject (libfwbuilder::FWObject *o);

View File

@ -77,10 +77,12 @@ using namespace libfwbuilder;
FindWhereUsedWidget::FindWhereUsedWidget(QWidget *p,
ProjectPanel *pp,
const char * n,
Qt::WindowFlags f,
bool f_mini) : QWidget(p)
{
project_panel = pp;
m_widget = new Ui::findWhereUsedWidget_q;
m_widget->setupUi(this);
@ -139,7 +141,7 @@ void FindWhereUsedWidget::_find(FWObject *obj)
if (fwbdebug) qDebug("FindWhereUsedWidget: initiate search for %s",
obj->getName().c_str());
mw->db()->findWhereObjectIsUsed(obj, mw->db(), resset);
project_panel->db()->findWhereObjectIsUsed(obj, project_panel->db(), resset);
humanizeSearchResults(resset);
set<FWObject*>::iterator i=resset.begin();
@ -184,48 +186,46 @@ void FindWhereUsedWidget::showObject(FWObject* o)
if (RuleElement::cast(o)!=NULL)
{
mw->activeProject()->openRuleSet(o->getParent()->getParent());
mw->clearManipulatorFocus();
RuleSetView *rsv = mw->activeProject()->getCurrentRuleSetView();
project_panel->openRuleSet(o->getParent()->getParent());
project_panel->clearManipulatorFocus();
RuleSetView *rsv = project_panel->getCurrentRuleSetView();
rsv->selectRE(RuleElement::cast(o), object);
rsv->setFocus(Qt::MouseFocusReason);
if (mw->isEditorVisible()) mw->editObject( object );
if (project_panel->isEditorVisible()) project_panel->editObject(object);
} else
{
if (Rule::cast(o)!=NULL)
{
mw->activeProject()->openRuleSet(o->getParent());
mw->clearManipulatorFocus();
RuleSetView *rsv = mw->activeProject()->getCurrentRuleSetView();
rsv->selectRE(Rule::cast(o),rsv->getColByType(RuleSetView::Action));
project_panel->openRuleSet(o->getParent());
project_panel->clearManipulatorFocus();
RuleSetView *rsv = project_panel->getCurrentRuleSetView();
rsv->selectRE(Rule::cast(o),rsv->getColByType(ColDesc::Action));
if (mw->isEditorVisible()) mw->editObject( object );
if (project_panel->isEditorVisible()) project_panel->editObject(object);
} else
{
mw->unselectRules();
project_panel->unselectRules();
if (Group::cast(o)!=NULL)
{
mw->openObject( o );
mw->unselectRules();
project_panel->openObject(o);
project_panel->unselectRules();
if (mw->isEditorVisible())
if (project_panel->isEditorVisible())
{
mw->editObject( o );
mw->selectObjectInEditor( object);
project_panel->editObject(o);
project_panel->selectObjectInEditor(object);
}
} else
{
mw->openObject( object );
mw->unselectRules();
project_panel->openObject( object );
project_panel->unselectRules();
if (mw->isEditorVisible()) mw->editObject( object );
if (project_panel->isEditorVisible()) project_panel->editObject( object );
}
}
}
//mw->closeEditor();
//mw->openObject( o );
}
void FindWhereUsedWidget::humanizeSearchResults(std::set<FWObject *> &resset)
@ -258,13 +258,14 @@ QTreeWidgetItem* FindWhereUsedWidget::createQTWidgetItem(FWObject* o,
RuleSet *rs = NULL;
QPixmap object_icon;
QPixmap parent_icon;
FWBTree tree_format;
if (mw->isSystem(container) || Library::cast(container)) return NULL;
if (tree_format.isSystem(container) || Library::cast(container)) return NULL;
if (RuleElement::cast(container)!=NULL || Rule::cast(container)!=NULL)
{
fw = container;
while (fw!=NULL && !Firewall::isA(fw))
while (fw!=NULL && Firewall::cast(fw)==NULL) // Firewall::cast matches also Cluster
{
if (Rule::cast(fw)) r = Rule::cast(fw);
if (RuleSet::cast(fw)) rs = RuleSet::cast(fw);

View File

@ -29,6 +29,7 @@
#include "../../config.h"
#include <ui_findwhereusedwidget_q.h>
#include "ProjectPanel.h"
#include "fwbuilder/FWObject.h"
#include "fwbuilder/RuleElement.h"
@ -50,6 +51,7 @@ class FindWhereUsedWidget : public QWidget
Q_OBJECT
private:
ProjectPanel *project_panel;
bool flShowObject;
libfwbuilder::FWObject* object;
std::set<libfwbuilder::FWObject *> resset;
@ -58,7 +60,7 @@ private:
void showObject(libfwbuilder::FWObject*);
public:
FindWhereUsedWidget(QWidget*p, const char * n = 0,
FindWhereUsedWidget(QWidget*p, ProjectPanel* pp, const char * n = 0,
Qt::WindowFlags f = 0, bool f_mini=false);
~FindWhereUsedWidget();

View File

@ -148,8 +148,8 @@ void FirewallDialog::fillVersion()
{
m_dialog->version->clear();
list<QStringPair> vl = getVersionsForPlatform(
readPlatform(m_dialog->platform) );
list<QStringPair> vl;
getVersionsForPlatform(readPlatform(m_dialog->platform), vl);
QString v = obj->getStr("version").c_str();
int cp = 0;
for (list<QStringPair>::iterator i1=vl.begin(); i1!=vl.end(); i1++,cp++)
@ -167,8 +167,9 @@ void FirewallDialog::saveVersion()
{
QString pl = readPlatform(m_dialog->platform);
list<QStringPair> vl=getVersionsForPlatform( pl.toLatin1().constData() );
QString v = m_dialog->version->currentText();
list<QStringPair> vl;
getVersionsForPlatform( pl.toLatin1().constData(), vl);
QString v = m_dialog->version->currentText();
list<QStringPair>::iterator li =
std::find_if(vl.begin(),vl.end(),findSecondInQStringPair(v));
if (li!=vl.end())
@ -210,6 +211,31 @@ void FirewallDialog::validate(bool *res)
*res=false;
return;
}
QString platform = readPlatform(m_dialog->platform);
if (platform.isEmpty())
{
*res=false;
QMessageBox::critical(
this, "Firewall Builder",
tr("Platform setting can not be empty"),
tr("&Continue"), 0, 0,
0 );
return;
}
QString ho = readHostOS(m_dialog->hostOS);
if (ho.isEmpty())
{
*res=false;
QMessageBox::critical(
this, "Firewall Builder",
tr("Host OS setting can not be empty"),
tr("&Continue"), 0, 0,
0 );
return;
}
if (!validateName(this,obj,m_dialog->obj_name->text()))
{
*res = false;
@ -258,7 +284,7 @@ void FirewallDialog::applyChanges()
string new_version = obj->getStr("version");
mw->updateObjName(obj,QString::fromUtf8(old_name.c_str()));
m_project->updateObjName(obj, QString::fromUtf8(old_name.c_str()));
if (old_platform!=new_platform || old_host_os!=new_host_os ||
old_name!=new_name || old_version!=new_version)
@ -266,7 +292,7 @@ void FirewallDialog::applyChanges()
if (fwbdebug)
qDebug("FirewallDialog::applyChanges() scheduling call "
"to reopenFirewall()");
mw->scheduleRuleSetRedraw();
m_project->scheduleRuleSetRedraw();
}
if (old_platform!=new_platform)
@ -294,8 +320,10 @@ void FirewallDialog::applyChanges()
Resources::setDefaultTargetOptions(new_host_os, s);
}
mw->updateLastModifiedTimestampForAllFirewalls(s);
// mw->updateLastModifiedTimestampForAllFirewalls(s);
modified = false;
emit notify_changes_applied_sign();
}
void FirewallDialog::discardChanges()

View File

@ -76,6 +76,7 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};

View File

@ -55,10 +55,216 @@
#include <QTextCodec>
#include <QTimer>
#include <QMessageBox>
#include <QTextStream>
using namespace std;
using namespace libfwbuilder;
bool FirewallInstaller::parseManifestLine(const QString &line,
QString *local_file_name,
QString *remote_file_name,
bool *main_script)
{
// generated IOS and PIX scripts use '!' as a comment which places
// manifest marker at offset of 1 char from the beginning of the
// line
if (line.indexOf(MANIFEST_MARKER) == -1) return false;
if (fwbdebug)
qDebug("Manifest line: '%s'", line.toAscii().constData());
int n = QString(MANIFEST_MARKER).length();
QStringList parts = line.mid(n).split(" ", QString::SkipEmptyParts);
if (parts.size() == 0) return false;
if (parts[0] == "*") { *main_script = true; parts.pop_front(); }
if (parts.size() == 0) return false;
*local_file_name = parts[0];
if (parts.size() == 1)
{
*remote_file_name = "";
} else
{
*remote_file_name = parts[1];
}
if (fwbdebug)
qDebug("local_name: '%s' remote_name: '%s' main_script: %d",
local_file_name->toAscii().constData(),
remote_file_name->toAscii().constData(),
*main_script);
return true;
}
/*
* FirewallInstaller::readManifest reads manifest from the generated
* script and applies logic to decide the path and name of all files
* that will be copied to the firewall.
Manifest format:
# files: * local_file_name remote_file_name
the '*' is optional and marks the "main" script, that is, the script
that should be executed on the firewall to activate policy. The part
'# files:' is manifest marker and must be reproduced just so. Parts
are separated by one or more spaces. Remote name is optional, if it is
missing, it is assumed to be equal to the local name. This provides
for backwards compatibility with previous versions where manifest did
not include remote name. Manifest can consit of multiple lines to
describe multiple files, although only one line can have '*'.
Installation process is controlled by several variables that the user
can change in the "advanced" dialog for the firewall platform:
Tab "Compiler":
- output file name
- script name on the firewall
- for PF and ipfilter additionally .conf file name on the firewall
Tab "Installer":
- directory on the firewall where script should be installed
- command that installer should execute on the firewall
These variables have default values if input fields are left blank
in the dialog as follows:
output file name: the name of the firewall object, plus extension
".fw". For PF two files are generated: <firewall>.fw and
<firewall>.conf; for ipfilter files <firewall>.fw, <firewall>-ipf.conf
and <firewall>-nat.conf are generated.
script name on the firewall: the same as the output file name
directory on the firewall: "/etc"
command that installer executes to activate policy: installer runs
script <firewall>.fw
If user enters alternative name in the "script name on the firewall",
it is used when generated script is copied to the firewall. There are
two input fields in the dialogs for PF and ipf where user can enter
alternative name for the .fw script and .conf file. The name can be
relative or absolute path. If it is a relative path or just a file
name, it is treated as a file name in the directory specified by the
"directory on the firewall" input field in the "Installer" tab. If the
name is an absolute path, the directory entered in "directory on the
firewall..." input field is ignored. If user entered alternative name
for the script on the firewall, the command that installer should
execute to activate it must be entered as well. If the alternative
name was entered as an absolute path, activation command should take
this into account and use the same absolute path. The command can
start with "sudo " if user account used to copy and activate policy is
not root.
*/
bool FirewallInstaller::readManifest(const QString &script,
QMap<QString, QString> *all_files)
{
if (fwbdebug)
qDebug("FirewallInstaller::readManifest");
// Read generated config file (cnf->script), find manifest
// and schedule copying of all files listed there.
QFile cf(script);
if (cf.open(QIODevice::ReadOnly ))
{
QTextStream stream(&cf);
QString line;
do
{
line = stream.readLine();
if (line.isNull()) break;
QString local_name;
QString remote_name;
bool main_script = false;
if (parseManifestLine(line, &local_name, &remote_name, &main_script))
{
QFileInfo loc_file_info(local_name);
if (!loc_file_info.isAbsolute())
{
QFileInfo cnf_file_info(cnf->script);
if (cnf_file_info.isAbsolute())
local_name = cnf_file_info.dir().path() + "/" + local_name;
}
if (remote_name.isEmpty())
{
QFileInfo loc_file_info(local_name);
remote_name = cnf->fwdir + "/" + loc_file_info.fileName();
}
// This is the manifest line with "*", it marks the main script
// we should run.
if (main_script)
{
// Override directory variable if remote file name
// is an absolute path. This is used later to
// replace %FWDIR% macro
// Override fwbscript as well
// This is used later to replace %FWSCRIPT% macro
// getDestinationDir() returns corrected directory
// depending on the user (root/regular) and temp install
// flag setting
QFileInfo rem_file_info(remote_name);
if (rem_file_info.isAbsolute())
{
cnf->fwdir = rem_file_info.dir().path();
cnf->remote_script = getDestinationDir(cnf->fwdir) +
rem_file_info.fileName();
} else
{
cnf->remote_script = getDestinationDir(cnf->fwdir) +
remote_name;
}
}
(*all_files)[local_name] = remote_name;
}
} while (!line.isNull());
cf.close();
if (cnf->remote_script.isEmpty())
{
// manifest did not include line with '*'
cnf->remote_script = getDestinationDir(cnf->fwdir) + cnf->script;
}
// Now that we have found the main script and know its
// location (in case user provided absolute path for the
// remote file name variable) we can update remote path for
// all files
QMap<QString, QString>::iterator it;
for (it=all_files->begin(); it!=all_files->end(); ++it)
{
QString local_name = it.key();
QString remote_name = it.value();
QFileInfo rem_file_info(remote_name);
if (rem_file_info.isAbsolute())
(*all_files)[local_name] =
getDestinationDir(rem_file_info.dir().path()) + rem_file_info.fileName();
else
(*all_files)[local_name] =
getDestinationDir(cnf->fwdir) + remote_name;
}
return true;
} else
{
QMessageBox::critical(
inst_dlg, "Firewall Builder",
tr("Generated script file %1 not found.").arg(script),
tr("&Continue") );
return false;
}
}
bool FirewallInstaller::packInstallJobsList(Firewall*)
{
return false;
@ -109,10 +315,11 @@ void FirewallInstaller::packSSHArgs(QStringList &args)
args.push_back(cnf->maddr);
}
void FirewallInstaller::packSCPArgs(const QString &file_name,
void FirewallInstaller::packSCPArgs(const QString &local_name,
const QString &remote_name,
QStringList &args)
{
QString file_with_path = getFullPath(file_name);
QString file_with_path = getFullPath(local_name);
QString scp = st->getSCPPath();
#ifdef _WIN32
@ -167,16 +374,14 @@ void FirewallInstaller::packSCPArgs(const QString &file_name,
}
// bug #2618772: "test install" option does not work. To fix, I
// put macro for the temp dir. in in res/os/host_os.xml XML
// put macro for the temp directory in in res/os/host_os.xml XML
// elements root/test/copy reg_user/test/copy. That macro
// is read and processed by getDestinationDir()
QString dest_dir = getDestinationDir();
if (!cnf->user.isEmpty())
args.push_back(cnf->user + "@" + mgmt_addr + ":" + dest_dir);
args.push_back(cnf->user + "@" + mgmt_addr + ":" + remote_name);
else
args.push_back(mgmt_addr + ":" + dest_dir);
args.push_back(mgmt_addr + ":" + remote_name);
}
/*
@ -198,15 +403,19 @@ void FirewallInstaller::runJobs()
switch (current_job.job)
{
case COPY_FILE:
copyFile(current_job.argument);
copyFile(current_job.argument1, current_job.argument2);
break;
case EXECUTE_COMMAND:
executeCommand(current_job.argument);
executeCommand(current_job.argument1);
break;
case ACTIVATE_POLICY:
activatePolicy();
activatePolicy(current_job.argument1, current_job.argument2);
break;
case RUN_EXTERNAL_SCRIPT:
executeExternalInstallScript(current_job.argument1, current_job.argument2);
break;
}
}
@ -217,25 +426,24 @@ void FirewallInstaller::runJobs()
* commandFinished(). This slot checks termination status of the process
* and if it was successfull, it schedules call to runJobs()
*/
void FirewallInstaller::copyFile(const QString &file_name)
void FirewallInstaller::copyFile(const QString&, const QString&)
{
}
void FirewallInstaller::executeInstallScript()
void FirewallInstaller::executeExternalInstallScript(const QString &command,
const QString &script_args)
{
Management *mgmt = cnf->fwobj->getManagementObject();
assert(mgmt!=NULL);
PolicyInstallScript *pis = mgmt->getPolicyInstallScript();
QString command = pis->getCommand().c_str();
FWObjectDatabase *db = cnf->fwobj->getRoot();
assert(db);
QString wdir = getFileDir( mw->getRCS()->getFileName() );
QStringList args;
//args.push_back(command.trimmed());
QString qs = pis->getArguments().c_str();
args += qs.trimmed().split(" ", QString::SkipEmptyParts);
args += script_args.trimmed().split(" ", QString::SkipEmptyParts);
args.push_back("-f");
args.push_back(mw->db()->getFileName().c_str());
args.push_back(db->getFileName().c_str());
if (wdir!="")
{
@ -270,7 +478,7 @@ void FirewallInstaller::executeCommand(const QString &cmd)
// ************************************************************************
void FirewallInstaller::activatePolicy()
void FirewallInstaller::activatePolicy(const QString&, const QString&)
{
QTimer::singleShot( 0, this, SLOT(runJobs()));
}
@ -353,7 +561,21 @@ QString FirewallInstaller::getActivationCmd()
return inst_dlg->replaceMacrosInCommand(cmd);
}
QString FirewallInstaller::getDestinationDir()
/*
* Takes destination directory defined in the configlet (or XML resource file)
* and substitutes %FWBDIR% macro with @fwdir. Returned directory path
* always ends with separator ("/")
*
* Main purpose of this method is to get the right directory depending
* on the setting of the administration user account and "test
* install" option. In case of test install we copy all files into a
* different directory and run them from there. The directory is
* defined in the resource (or configlet) file. Directory can be
* different depending on combination of the user used to install and
* run the script (root or regular user) and setting of the "test
* install" option.
*/
QString FirewallInstaller::getDestinationDir(const QString &fwdir)
{
QString dir = "";
@ -379,10 +601,14 @@ QString FirewallInstaller::getDestinationDir()
optpath.c_str(),
dir.toAscii().constData(),
cnf->fwdir.toAscii().constData());
// dir can contain macro %FWDIR% which should be replaced with cnf->fwdir
// empty dir is equivalent to just the value of cnf->fwdir
if (dir.isEmpty()) return cnf->fwdir;
if (!dir.endsWith('/')) dir = dir + "/";
return inst_dlg->replaceMacrosInCommand(dir);
if (dir.isEmpty()) return fwdir;
dir.replace("%FWDIR%", fwdir);
if (!dir.endsWith(QDir::separator())) return dir + QDir::separator();
return dir;
}
QString FirewallInstaller::getGeneratedFileFullPath(Firewall *fw)

View File

@ -51,22 +51,23 @@ namespace libfwbuilder
class Firewall;
}
enum instJobType {COPY_FILE, EXECUTE_COMMAND, ACTIVATE_POLICY};
enum instJobType {COPY_FILE, EXECUTE_COMMAND, ACTIVATE_POLICY, RUN_EXTERNAL_SCRIPT};
class instJob
{
public:
instJobType job;
QString argument;
QString argument1;
QString argument2;
instJob(instJobType jt, const QString &a) { job=jt; argument=a; }
instJob(instJobType jt, const QString &a1, const QString &a2)
{ job = jt; argument1 = a1; argument2 = a2; }
};
class FirewallInstaller : public QObject
{
Q_OBJECT
protected:
instDialog *inst_dlg;
@ -80,7 +81,15 @@ protected:
void runSSHSession(SSHSession *s, bool intermediate=false);
QString getFullPath(const QString &file );
void executeInstallScript();
bool parseManifestLine(const QString &line,
QString *local_file_name,
QString *remote_file_name,
bool *main_script);
bool readManifest(const QString &conffie, QMap<QString, QString> *all_files);
void executeExternalInstallScript(const QString &script,
const QString &script_args);
public:
@ -92,14 +101,14 @@ public:
}
void packSSHArgs(QStringList &args);
void packSCPArgs(const QString &file_name, QStringList &args);
void packSCPArgs(const QString &local_name, const QString &remote_name, QStringList &args);
QString getActivationCmd();
QString getDestinationDir();
QString getDestinationDir(const QString &dir);
virtual bool packInstallJobsList(libfwbuilder::Firewall*);
virtual void copyFile(const QString &file_name);
virtual void copyFile(const QString &local_name, const QString &remote_name);
virtual void executeCommand(const QString &cmd);
virtual void activatePolicy();
virtual void activatePolicy(const QString &script, const QString &args);
static QString getGeneratedFileFullPath(libfwbuilder::Firewall *fw);

View File

@ -53,26 +53,29 @@ using namespace libfwbuilder;
bool FirewallInstallerCisco::packInstallJobsList(Firewall*)
{
if (fwbdebug)
qDebug("FirewallInstallerCisco::packInstallJobList conffile=%s",
cnf->conffile.toAscii().constData());
qDebug("FirewallInstallerCisco::packInstallJobList script=%s",
cnf->script.toAscii().constData());
job_list.clear();
job_list.push_back(instJob(ACTIVATE_POLICY, cnf->conffile));
return true;
}
void FirewallInstallerCisco::activatePolicy()
{
// Someone may have external expect script to talk to PIX or a router
// Let them run it too.
Management *mgmt = cnf->fwobj->getManagementObject();
assert(mgmt!=NULL);
PolicyInstallScript *pis = mgmt->getPolicyInstallScript();
if (pis->getCommand()!="" )
if (pis->getCommand()!="")
{
executeInstallScript();
return;
QString cmd = pis->getCommand().c_str();
QString args = pis->getArguments().c_str();
job_list.push_back(
instJob(RUN_EXTERNAL_SCRIPT, cmd, args));
inst_dlg->addToLog(QString("Run script %1 %2\n").arg(cmd).arg(args));
return true;
}
job_list.push_back(instJob(ACTIVATE_POLICY, cnf->script, ""));
return true;
}
void FirewallInstallerCisco::activatePolicy(const QString&, const QString&)
{
QStringList args;
packSSHArgs(args);

View File

@ -52,7 +52,7 @@ public:
FirewallInstaller(_dlg, _cnf, _p) {}
virtual bool packInstallJobsList(libfwbuilder::Firewall*);
virtual void activatePolicy();
virtual void activatePolicy(const QString &script, const QString &args);
};

View File

@ -62,37 +62,33 @@
using namespace std;
using namespace libfwbuilder;
bool FirewallInstallerUnx::packInstallJobsList(Firewall* fw)
{
if (fwbdebug) qDebug("FirewallInstallerUnx::packInstallJobList");
job_list.clear();
inst_dlg->addToLog(QString("Installation plan:\n"));
Management *mgmt = cnf->fwobj->getManagementObject();
assert(mgmt!=NULL);
PolicyInstallScript *pis = mgmt->getPolicyInstallScript();
if (pis->getCommand()!="")
{
job_list.push_back(instJob(ACTIVATE_POLICY, ""));
QString cmd = pis->getCommand().c_str();
QString args = pis->getArguments().c_str();
job_list.push_back(
instJob(RUN_EXTERNAL_SCRIPT, cmd, args));
inst_dlg->addToLog(QString("Run script %1 %2\n").arg(cmd).arg(args));
return true;
}
if (cnf->copyFWB)
{
QFileInfo fwbfile_base(cnf->fwbfile);
if (fwbdebug)
qDebug( QString("Will copy data file: %1").arg(
fwbfile_base.fileName()).toAscii().constData());
job_list.push_back(instJob(COPY_FILE, fwbfile_base.fileName()));
}
/* read manifest from the conf file */
if (fwbdebug)
qDebug("FirewallInstaller::packInstallJobsList read manifest from %s",
cnf->conffile.toAscii().constData());
cnf->script.toAscii().constData());
/*
* Note that if output file is specified in firewall settings dialog,
@ -103,66 +99,70 @@ bool FirewallInstallerUnx::packInstallJobsList(Firewall* fw)
* dir path from the .fw file and if it is not empty, assume that all
* other files are located there as well.
*/
QFileInfo cnf_file_info(cnf->conffile);
QString dir_path = "";
if (cnf_file_info.isAbsolute())
dir_path = cnf_file_info.dir().path() + "/";
// compilers always write file names into manifest in Utf8
QTextCodec::setCodecForCStrings(QTextCodec::codecForName("Utf8"));
QTextCodec::setCodecForLocale(QTextCodec::codecForName("Utf8"));
QFile cf(cnf->conffile);
if (cf.open(QIODevice::ReadOnly ))
{
QTextStream stream(&cf);
QString line;
do
{
line = stream.readLine();
if (line.isNull()) break;
int pos = -1;
if ( (pos=line.indexOf(MANIFEST_MARKER))!=-1 )
{
int n = pos + QString(MANIFEST_MARKER).length();
QString conf_file = line.mid(n+2);
job_list.push_back(instJob(COPY_FILE, dir_path + conf_file));
//key: local_file_name val: remote_file_name
QMap<QString,QString> all_files;
if (fwbdebug)
qDebug("FirewallInstaller: adding %c %s",
line[n].toLatin1(),
line.mid(n+2).toAscii().constData());
}
} while (!line.isNull());
cf.close();
// readManifest() modifies cnf !
if (readManifest(cnf->script, &all_files))
{
QMap<QString, QString>::iterator it;
for (it=all_files.begin(); it!=all_files.end(); ++it)
{
QString local_name = it.key();
QString remote_name = it.value();
job_list.push_back(instJob(COPY_FILE, local_name, remote_name));
inst_dlg->addToLog(QString("Copy file: %1 --> %2\n")
.arg(local_name)
.arg(remote_name).toAscii().constData());
}
} else
{
QMessageBox::critical(
inst_dlg, "Firewall Builder",
tr("Generated script file %1 not found.").arg(cnf->conffile),
tr("&Continue") );
inst_dlg->opError(fw);
return false;
}
if (job_list.size()==0)
job_list.push_back(instJob(COPY_FILE, cnf->conffile));
{
QMessageBox::critical(
inst_dlg, "Firewall Builder",
tr("Incorrect manifest format in generated script. "
"Line with \"*\" is missing, can not find any files "
"to copy to the firewall.\n%1").arg(cnf->script),
tr("&Continue"), QString::null,QString::null,
0, 1 );
return false;
}
job_list.push_back(instJob(ACTIVATE_POLICY, ""));
if (cnf->copyFWB)
{
QString dest_dir = getDestinationDir(cnf->fwdir);
QFileInfo fwbfile_base(cnf->fwbfile);
job_list.push_back(instJob(
COPY_FILE,
fwbfile_base.fileName(),
dest_dir));
inst_dlg->addToLog(QString("Copy data file: %1 --> %2\n")
.arg(fwbfile_base.fileName())
.arg(dest_dir).toAscii().constData());
}
QString cmd = getActivationCmd();
job_list.push_back(instJob(ACTIVATE_POLICY, cmd, ""));
inst_dlg->addToLog(QString("Run script %1\n").arg(cmd));
inst_dlg->addToLog(QString("\n"));
return true;
}
// ************************************************************************
void FirewallInstallerUnx::activatePolicy()
void FirewallInstallerUnx::activatePolicy(const QString &cmd, const QString&)
{
Management *mgmt = cnf->fwobj->getManagementObject();
assert(mgmt!=NULL);
PolicyInstallScript *pis = mgmt->getPolicyInstallScript();
if (pis->getCommand()=="" )
executeSession(getActivationCmd());
else
executeInstallScript();
executeSession(cmd);
}
void FirewallInstallerUnx::executeSession(const QString &cmd)
@ -186,19 +186,20 @@ void FirewallInstallerUnx::executeSession(const QString &cmd)
// ************************************************************************
void FirewallInstallerUnx::copyFile(const QString &file_name)
void FirewallInstallerUnx::copyFile(const QString &local_name,
const QString &remote_name)
{
QString platform = cnf->fwobj->getStr("platform").c_str();
// QTextCodec::setCodecForCStrings(QTextCodec::codecForName("latin1"));
QStringList args;
packSCPArgs(file_name, args);
packSCPArgs(local_name, remote_name, args);
QString file_with_path = getFullPath(file_name);
inst_dlg->addToLog( tr("Copying %1 -> %2:%3\n")
.arg(QString::fromUtf8(file_with_path.toAscii().constData()))
.arg(cnf->maddr).arg(getDestinationDir()));
.arg(QString::fromUtf8(local_name.toAscii().constData()))
.arg(cnf->maddr)
.arg(QString::fromUtf8(remote_name.toAscii().constData())));
if (cnf->verbose) inst_dlg->displayCommand(args);
qApp->processEvents();

View File

@ -46,16 +46,15 @@ class FirewallInstallerUnx : public FirewallInstaller
Q_OBJECT
void executeSession(const QString &cmd);
public:
FirewallInstallerUnx(instDialog *_dlg, instConf *_cnf, const QString &_p) :
FirewallInstaller(_dlg, _cnf, _p) {}
virtual bool packInstallJobsList(libfwbuilder::Firewall*);
virtual void copyFile(const QString &file_name);
virtual void activatePolicy();
virtual void copyFile(const QString &local_name, const QString &remote_name);
virtual void activatePolicy(const QString &script, const QString &args);
};

View File

@ -27,9 +27,9 @@
#include "../../config.h"
#include "global.h"
#include "utils.h"
#include "ProjectPanel.h"
#include "events.h"
#include "FWWindow.h"
#include "ProjectPanel.h"
#include "FWBTree.h"
#include "FWBSettings.h"
#include "FWObjectPropertiesFactory.h"
@ -58,6 +58,7 @@
#include <qtooltip.h>
#include <qscrollarea.h>
#include <qpixmapcache.h>
#include <QCoreApplication>
#include <iostream>
#include <algorithm>
@ -213,7 +214,7 @@ void GroupObjectDialog::iconViewCurrentChanged(QListWidgetItem *itm)
return;
}
int obj_id = itm->data(Qt::UserRole).toInt();
FWObject *o = mw->db()->findInIndex(obj_id);
FWObject *o = m_project->db()->findInIndex(obj_id);
selectedObject = o;
}
@ -226,7 +227,7 @@ void GroupObjectDialog::listViewCurrentChanged(QTreeWidgetItem *itm)
return;
}
int obj_id = itm->data(0, Qt::UserRole).toInt();
FWObject *o = mw->db()->findInIndex(obj_id);
FWObject *o = m_project->db()->findInIndex(obj_id);
selectedObject = o;
}
@ -333,9 +334,11 @@ void GroupObjectDialog::loadFWObject(FWObject *o)
m_dialog->comment->setEnabled( !m_project->isSystem(obj) );
listView->clear();
iconView->clear();
listView->setDB(o->getRoot());
iconView->setDB(o->getRoot());
iconView->setResizeMode( QListWidget::Adjust );
iconView->setGridSize ( QSize(50, 40) );
@ -440,9 +443,9 @@ void GroupObjectDialog::applyChanges()
for (set<int>::iterator k=diff.begin(); k!=diff.end(); ++k)
{
FWObject *o = mw->db()->findInIndex(*k);
FWObject *o = m_project->db()->findInIndex(*k);
if (m_project->isSystem(obj))
mw->delObj(o, false);
m_project->delObj(o, false);
else
obj->removeRef(o);
}
@ -457,17 +460,16 @@ void GroupObjectDialog::applyChanges()
for (set<int>::iterator k1=diff.begin(); k1!=diff.end(); ++k1)
{
FWObject *o = mw->db()->findInIndex(*k1);
FWObject *o = m_project->db()->findInIndex(*k1);
if (m_project->isSystem(o))
mw->pasteTo(obj, o);
m_project->pasteTo(obj, o);
else
obj->addRef(o);
}
mw->updateObjName(obj, QString::fromUtf8(oldname.c_str()));
m_project->updateObjName(obj, QString::fromUtf8(oldname.c_str()));
//apply->setEnabled( false );
mw->updateLastModifiedTimestampForAllFirewalls(obj);
emit notify_changes_applied_sign();
if (fwbdebug) qDebug("GroupObjectDialog::applyChanges done");
}
@ -505,30 +507,33 @@ void GroupObjectDialog::openObject()
{
if (selectedObject!=NULL)
{
mw->openObject( selectedObject );
mw->editObject( selectedObject );
QCoreApplication::postEvent(
m_project, new showObjectInTreeEvent(selectedObject->getRoot()->getFileName().c_str(),
selectedObject->getId()));
}
}
void GroupObjectDialog::openObject(QTreeWidgetItem *itm)
{
int obj_id = itm->data(0, Qt::UserRole).toInt();
FWObject *o = mw->db()->findInIndex(obj_id);
FWObject *o = m_project->db()->findInIndex(obj_id);
if (o!=NULL)
{
mw->openObject( o );
mw->editObject( o );
QCoreApplication::postEvent(
m_project, new showObjectInTreeEvent(o->getRoot()->getFileName().c_str(),
o->getId()));
}
}
void GroupObjectDialog::openObject(QListWidgetItem *itm)
{
int obj_id = itm->data(Qt::UserRole).toInt();
FWObject *o = mw->db()->findInIndex(obj_id);
FWObject *o = m_project->db()->findInIndex(obj_id);
if (o!=NULL)
{
mw->openObject( o );
mw->editObject( o );
QCoreApplication::postEvent(
m_project, new showObjectInTreeEvent(o->getRoot()->getFileName().c_str(),
o->getId()));
}
}
@ -547,7 +552,7 @@ void GroupObjectDialog::dropped(QDropEvent *ev)
// see comment in ObjectTreeView.cpp explaining the purpose of
// flag process_mouse_release_event
ObjectTreeView *otv = mw->getCurrentObjectTree();
ObjectTreeView *otv = m_project->getCurrentObjectTree();
otv->ignoreNextMouseReleaseEvent();
}
@ -561,7 +566,7 @@ void GroupObjectDialog::iconContextMenu(const QPoint & pos)
if (itm)
{
int obj_id = itm->data(Qt::UserRole).toInt();
o = mw->db()->findInIndex(obj_id);
o = m_project->db()->findInIndex(obj_id);
selectedObject = o;
}
setupPopupMenu(iconView->mapToGlobal(pos));
@ -575,7 +580,7 @@ void GroupObjectDialog::listContextMenu(const QPoint & pos)
if (itm)
{
int obj_id = itm->data(0, Qt::UserRole).toInt();
o = mw->db()->findInIndex(obj_id);
o = m_project->db()->findInIndex(obj_id);
selectedObject = o;
}
setupPopupMenu(listView->viewport()->mapToGlobal(pos));
@ -618,7 +623,7 @@ void GroupObjectDialog::copyObj()
for(vector<int>::iterator it=selectedObjects.begin();
it!=selectedObjects.end(); ++it)
{
FWObject* selectedObject = mw->db()->findInIndex(*it);
FWObject* selectedObject = m_project->db()->findInIndex(*it);
if (selectedObject!=NULL && ! m_project->isSystem(selectedObject) )
{
@ -642,7 +647,7 @@ void GroupObjectDialog::pasteObj()
for (i= FWObjectClipboard::obj_clipboard->begin();
i!=FWObjectClipboard::obj_clipboard->end(); ++i)
{
insertObject( mw->db()->findInIndex(i->first) );
insertObject( m_project->db()->findInIndex(i->first) );
}
}
@ -658,7 +663,7 @@ void GroupObjectDialog::deleteObj()
if (fwbdebug)
qDebug("GroupObjectDialog::deleteObj() (*it)=%d", (*it));
FWObject* selectedObject = mw->db()->findInIndex(*it);
FWObject* selectedObject = m_project->db()->findInIndex(*it);
int o_id = selectedObject->getId();
for (int it=0; it<listView->topLevelItemCount(); ++it)

View File

@ -114,7 +114,8 @@ class GroupObjectDialog : public QWidget
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
private:
static enum viewType vt;

View File

@ -30,67 +30,41 @@
#include "Help.h"
#include <QFile>
#include <QDir>
#include <QTextStream>
#include <QLocale>
using namespace std;
Help::Help(QWidget *parent, const QString &help_file, const QString &title) :
SimpleTextView(parent)
Help::Help(QWidget *parent, const QString &title) : SimpleTextView(parent)
{
setAttribute(Qt::WA_DeleteOnClose);
QString locale = QLocale::system().name(); //"en_US";
// Set up path to help qtextBrowser find contents, such as files for <img>
paths.append(QString(respath.c_str()) + "/help/" + locale);
paths.append(QString(respath.c_str()) + "/help/" + "en_US");
m_dialog->textview->setSearchPaths(paths);
m_dialog->textview->setOpenLinks(true);
m_dialog->textview->setOpenExternalLinks(true);
setModal(false);
setName(title);
resize(500, 600);
raise();
QString contents;
getHelpFileContents(help_file, contents);
setText(contents);
};
void Help::scrollToAnchor(const QString &anchor)
{
m_dialog->textview->scrollToAnchor(anchor);
}
bool Help::getHelpFileContents(const QString &help_file, QString &contents)
QString Help::findHelpFile(const QString &file_base_name)
{
QString locale = QLocale::system().name(); //"en_US";
bool res = false;
QFile f;
QTextStream ts;
if (!Help::getFile(help_file, locale, f))
foreach(QString p, paths)
{
// We do not have help file for this locale (including locale "C")
// Show English one as a default
locale = "en_US";
QString try_file_path = p + "/" + file_base_name;
if (fwbdebug) qDebug("Checking help file %s", try_file_path.toLatin1().constData());
if (QFile::exists(try_file_path)) return try_file_path;
}
if (Help::getFile(help_file, locale, f) && f.open(QIODevice::ReadOnly ))
{
ts.setDevice(&f);
contents = ts.readAll();
f.close();
res = true;
} else
{
contents = QString("Help file %1 not found.").arg(f.fileName());
}
return res;
}
bool Help::getFile(const QString &help_file, const QString &locale, QFile &file)
{
file.setFileName(QString(respath.c_str()) + "/help/" + help_file +
"_" + locale + ".html");
return file.exists();
return "";
}

View File

@ -30,25 +30,21 @@
#include "../../config.h"
#include "SimpleTextView.h"
#include <QFile>
#include <QStringList>
#include <QUrl>
class Help : public SimpleTextView
{
QStringList paths;
public:
Help(QWidget *parent, const QString &_file, const QString &title);
Help(QWidget *parent, const QString &title);
virtual ~Help() {};
void scrollToAnchor(const QString &anchor);
static bool getHelpFileContents(const QString &help_file,
QString &contents);
static bool getFile(const QString &help_file, const QString &locale,
QFile &file);
void setSource(const QUrl &url) { m_dialog->textview->setSource(url); }
QString findHelpFile(const QString &file_base_name);
};
#endif

View File

@ -153,11 +153,12 @@ void HostDialog::applyChanges()
// mgmt->getSNMPManagement()->setReadCommunity( snmpCommunity->text().latin1() );
opt->setBool("use_mac_addr_filter", m_dialog->MACmatching->isChecked() );
mw->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
m_project->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
//apply->setEnabled( false );
mw->updateLastModifiedTimestampForAllFirewalls(obj);
modified = false;
emit notify_changes_applied_sign();
}
void HostDialog::discardChanges()

View File

@ -68,6 +68,8 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif // HOSTDIALOG_H

View File

@ -142,10 +142,10 @@ void ICMPServiceDialog::applyChanges()
obj->setInt("type", m_dialog->icmpType->value() );
obj->setInt("code", m_dialog->icmpCode->value() );
mw->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
m_project->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
emit notify_changes_applied_sign();
//apply->setEnabled( false );
mw->updateLastModifiedTimestampForAllFirewalls(obj);
}
void ICMPServiceDialog::discardChanges()

View File

@ -67,7 +67,8 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif // ICMPSERVICEDIALOG_H

View File

@ -197,10 +197,10 @@ void IPServiceDialog::applyChanges()
ip->setDSCPCode("");
}
mw->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
m_project->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
emit notify_changes_applied_sign();
//apply->setEnabled( false );
mw->updateLastModifiedTimestampForAllFirewalls(obj);
}
void IPServiceDialog::discardChanges()

View File

@ -71,7 +71,8 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif // IPSERVICEDIALOG_H

View File

@ -219,10 +219,10 @@ void IPv4Dialog::applyChanges()
} else
s->setNetmask(InetAddr());
mw->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
m_project->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
emit notify_changes_applied_sign();
//apply->setEnabled( false );
mw->updateLastModifiedTimestampForAllFirewalls(obj);
}
void IPv4Dialog::discardChanges()

View File

@ -72,7 +72,8 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif // IPV4DIALOG_H

View File

@ -28,8 +28,7 @@
#include "utils.h"
#include "IPv6Dialog.h"
//#include "ProjectPanel.h"
#include "ProjectPanel.h"
#include "fwbuilder/Library.h"
#include "fwbuilder/IPv6.h"
@ -222,10 +221,10 @@ void IPv6Dialog::applyChanges()
} else
s->setNetmask(InetAddr(AF_INET6, 0));
mw->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
m_project->updateObjName(obj,QString::fromUtf8(oldname.c_str()));
emit notify_changes_applied_sign();
//apply->setEnabled( false );
mw->updateLastModifiedTimestampForAllFirewalls(obj);
}
void IPv6Dialog::discardChanges()

View File

@ -72,7 +72,8 @@ public slots:
*/
void close_sign(QCloseEvent *e);
void changed_sign();
void notify_changes_applied_sign();
};
#endif // IPV6DIALOG_H

Binary file not shown.

Before

Width:  |  Height:  |  Size: 924 B

After

Width:  |  Height:  |  Size: 934 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

After

Width:  |  Height:  |  Size: 1.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 324 B

After

Width:  |  Height:  |  Size: 732 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 519 B

After

Width:  |  Height:  |  Size: 836 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 271 B

After

Width:  |  Height:  |  Size: 834 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 448 B

After

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 395 B

After

Width:  |  Height:  |  Size: 975 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 404 B

After

Width:  |  Height:  |  Size: 883 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 501 B

After

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 397 B

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 320 B

After

Width:  |  Height:  |  Size: 673 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 307 B

After

Width:  |  Height:  |  Size: 891 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 346 B

After

Width:  |  Height:  |  Size: 602 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 348 B

After

Width:  |  Height:  |  Size: 815 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 282 B

After

Width:  |  Height:  |  Size: 796 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 467 B

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 421 B

After

Width:  |  Height:  |  Size: 930 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 333 B

After

Width:  |  Height:  |  Size: 588 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 377 B

After

Width:  |  Height:  |  Size: 774 B

BIN
src/gui/Icons/back_16.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 481 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 499 B

After

Width:  |  Height:  |  Size: 825 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.5 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 788 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.6 KiB

After

Width:  |  Height:  |  Size: 681 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.6 KiB

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 276 B

After

Width:  |  Height:  |  Size: 607 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 457 B

After

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 295 B

After

Width:  |  Height:  |  Size: 602 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 499 B

After

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 380 B

After

Width:  |  Height:  |  Size: 887 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 661 B

After

Width:  |  Height:  |  Size: 1.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 631 B

After

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 407 B

After

Width:  |  Height:  |  Size: 867 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 615 B

After

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 349 B

After

Width:  |  Height:  |  Size: 1011 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 586 B

After

Width:  |  Height:  |  Size: 1.7 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 570 B

After

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 476 B

After

Width:  |  Height:  |  Size: 943 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 562 B

After

Width:  |  Height:  |  Size: 1.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 950 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 820 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 676 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 542 B

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 282 B

After

Width:  |  Height:  |  Size: 767 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 348 B

After

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 251 B

After

Width:  |  Height:  |  Size: 404 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 452 B

After

Width:  |  Height:  |  Size: 503 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 803 B

After

Width:  |  Height:  |  Size: 838 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

After

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 365 B

After

Width:  |  Height:  |  Size: 738 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 618 B

After

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 589 B

After

Width:  |  Height:  |  Size: 1.0 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 427 B

After

Width:  |  Height:  |  Size: 538 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 574 B

After

Width:  |  Height:  |  Size: 985 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 795 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 640 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 373 B

After

Width:  |  Height:  |  Size: 853 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 671 B

After

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 625 B

After

Width:  |  Height:  |  Size: 1.0 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 449 B

After

Width:  |  Height:  |  Size: 632 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 610 B

After

Width:  |  Height:  |  Size: 937 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 803 B

Some files were not shown because too many files have changed in this diff Show More