iControl 101 - #20 - Port Lockdown
A Self IP address is an IP address that you associate with a VLAN, to access hosts in that VLAN. By virtue of its netmask, a self IP address represents an address space, that is, a range of IP addresses spanning the hosts in the VLAN, rather than a single host address. You can associate self IP addresses not only with VLANs, but also with VLAN group. Self IP addresses serve two purposes. First, when sending a message to a destination server, the BIG-IP system uses the self IP addresses of its VLANs to determine the specific VLAN in which a destination server resides. Second, a self IP address serves as the default route for each destination server in the corresponding VLAN. In this case, the self IP address of a VLAN appears as the destination IP address in the packet header when the server sends a response to the BIG-IP system.
Each self IP address has a feature known as port lockdown. Port lockdown is a security feature that allows you to specify particular UDP and TCP protocols and services from which the self IP address can accept traffic. This article will dicuss how to use the iControl API to manage Port Lockdown Access Lists.
Usage
The following code samples will build a PowerShell command line application allowing control over Self IP access lists. This program takes as input the bigip, username, and password as well as a subcommand and optional parameters. Usage is displayed with the Write-Usage function.
param ( $g_bigip = $null, $g_uid = $null, $g_pwd = $null, $g_cmd = $null, $g_selfip = $null, $g_arg1 = $null, $g_arg2 = $null, $g_arg3 = $null, $g_arg4 = $null ); Set-PSDebug -strict; function Write-Usage() { Write-Host @" Usage: SelfIPPortLockdown.ps1 host uid pwd [options] options ------- list - Get a list of Self IPs getaccesslist <selfip> - Gets the access lists for the specified self IP. addaccesslist <selfip> <mode> <protocol> <port> - Adds the list of access methods, with optional protocols/ports, for the specified self IP. deleteaccesslist <selfip> <mode> <protocol> <port> - Deletes protocols and ports from the allow access list for the specified self IP. getdefaccesslist - Gets the default protocol/port access list on which access is allowed. adddefaccesslist <protocol> <port> - Adds to the default list of protocols/ports on which access is allowed. removedefaccesslist <protocol> <port> - Remove protocols and ports from the default list of protocols/ports on which access is allowed. "@; exit; }
Initialization
As is with all of my iControl PowerShell scripts, validation is made as to whether the iControlSnapin is loaded into the current powershell context. The Initialize-F5.iControl cmdlet is then called to setup the connection to the BIG-IP for subsequent calls.
The main application logic checks for the passed in command and then passes control to one of the location functions defined below.
function Do-Initialize() { if ( (Get-PSSnapin | Where-Object { $_.Name -eq "iControlSnapIn"}) -eq $null ) { Add-PSSnapIn iControlSnapIn } $success = Initialize-F5.iControl -HostName $g_bigip -Username $g_uid -Password $g_pwd; return $success; } #------------------------------------------------------------------------- # Main Application Logic #------------------------------------------------------------------------- if ( ($g_bigip -eq $null) -or ($g_uid -eq $null) -or ($g_pwd -eq $null) ) { Write-Usage; } if ( Do-Initialize ) { switch ($g_cmd) { "" { Get-SelfIPList; } "getaccesslist" { Get-AccessList $g_selfip; } "addaccesslist" { Add-AccessList $g_selfip $g_arg1 $g_arg2 $g_arg3 $g_arg4; } "deleteaccesslist" { Delete-AccessList $g_selfip; } "getdefaccesslist" { Get-DefaultAccessList $g_selfip; } "adddefaccesslist" { Add-DefaultAccessList $g_selfip $g_arg1 $g_arg2; } "removedefaccesslist" { Remove-DefaultAccessList $g_selfip $g_arg1 $g_arg2; } default { Write-Usage; } } } else { Write-Error "ERROR: iControl subsystem not initialized" }
Getting a List of Self IP Addresses
If you don't know the configured Self IP addresses on your system, you can retrieve them with the iControl Networking.SelfIP.get_list() method. The Get-SelfIPList function calls this iControl method and prints out the Self IP addresses returned from the iControl call.
function Get-SelfIPList() { $ip_list = (Get-F5.iControl).NetworkingSelfIP.get_list(); Write-Host "Available SelfIPs:"; foreach ($ip in $ip_list) { Write-Host " $ip"; } }
PS C:\> .\SelfIPPortLockdown.ps1 bigip username password Available SelfIPs: 10.10.10.1 20.20.20.1
Querying the Port Lockdown Access Lists for a Self IP
Now that you have the Self IP address you want to work on, you can use the Get-AccessList local function to call the iControl Networking.SelfIPPortLockdown.get_allow_access_list() method This takes as input an array of Self IP addresses and returns the associated Port Lockdown settings. In my example, I do not have a Port Lockdown configured for my Self IP so it returns a Port Lockdown mode of ALLOW_MODE_ALL which means that all traffic is allowed on that Self IP.
function Get-AccessList() { param([string]$selfip = $null); $pld = (Get-F5.iControl).NetworkingSelfIPPortLockdown; $SelfIPAccessA = $pld.get_allow_access_list( (,$selfip) ); foreach ($SelfIPAccess in $SelfIPAccessA) { Write-Host "--------------------------------"; Write-Host "Self IP : " $SelfIPAccess.self_ip; Write-Host "Mode : " $SelfIPAccess.mode; Write-Host "Protocol Ports : "; $pA = $SelfIPAccess.protocol_ports; foreach ($ProtocolPort in $pA) { Write-Host " Protocol : " $ProtocolPort.protocol; Write-Host " Port : " $ProtocolPort.port; } } }
PS C:\> .\SelfIPPortLockdown.ps1 bigip username password getaccesslist 10.10.10.1 -------------------------------------- Self IP : 10.10.10.1 Mode : ALLOW_MODE_ALL Protocol Ports :
Adding a Port Lockdown to a Self IP
The local Add-AccessList function takes as input a Self IP address, a Port Lockdown mode, a Protocol type, and a port to lockdown. The available Allow Modes are:
- ALLOW_MODE_PROTOCOL_PORT - Access to the Self IP is allowed through the specified protocol/port.
- ALLOW_MODE_NONE - Allow no access to the Self IP.
- ALLOW_MODE_DEFAULTS - Allow access ot the Self IP using a pre-determined set of protocols/ports.
- ALLOW_MODE_ALL - Allow full access to the Self IP.
And the Protocol types are:
- PROTOCOL_ANY - Wildcard protocol.
- PROTOCOL_IPV6 - IPv6 header.
- PROTOCOL_ROUTING - Routing header.
- PROTOCOL_NONE - Next header.
- PROTOCOL_FRAGMENT - Fragment header.
- PROTOCOL_DSTOPTS - Destination options.
- PROTOCOL_TCP - TCP protocol.
- PROTOCOL_UDP - UCP protocol.
- PROTOCOL_ICMP - ICMP protcool.
- PROTOCOL_ICMPV6 - ICMPv6 protocol.
- PROTOCOL_OSPF - OSPF protocol.
- PROTOCOL_SCTP - SCTP protocol.
In the below example I'll add a TCP port 44 Allow.
function Add-AccessList() { param( [string]$selfip = $null, [string]$mode = "ALLOW_MODE_NONE", [string]$protocol = "PROTOCOL_ANY", [int]$port = 0); $pld = (Get-F5.iControl).NetworkingSelfIPPortLockdown; $SelfIPAccess = New-Object -TypeName iControl.NetworkingSelfIPPortLockdownSelfIPAccess; $SelfIPAccess.self_ip = $selfip; $SelfIPAccess.mode = $mode; $SelfIPAccess.protocol_ports = New-Object -TypeName iControl.NetworkingSelfIPPortLockdownProtocolPort; $(${SelfIPAccess}.protocol_ports).protocol = $protocol; $(${SelfIPAccess}.protocol_ports).port = $port; $pld.add_allow_access_list( (,$SelfIPAccess) ); Get-AccessList $selfip; }
PS C:\> .\SelfIPPortLockdown.ps1 bigip username password addaccesslist 10.10.10.1 ALLOW_MODE_PROTOCOL_PORT PROTOCOL_TCP 44 -------------------------------------- Self IP : 10.10.10.1 Mode : ALLOW_MODE_PROTOCOL_PORT Protocol Ports : Protocol : PROTOCOL_ANY Port : 0 Protocol : PROTOCOL_TCP Port : 44
Deleting a Port Lockdown From a Self IP
If you want to add a Port Lockdown, you will likely want to delete one as well. The Delete-AccessList list function takes the same parameters as the Add-AccessList function and it calls the iControl Networking.SelfIPPortLockdown.delete_allow_access_list() method to remove the Port Lockdown settings from the specified Self IP. You'll notice that by removing the last Port Lockdown on a Self IP, the mode will be set to ALLOW_MODE_NONE allowing no traffic on the Self IP. To re-enable traffic on the Self IP, you'll need to add another Port Lockdown with the ALLOW_MODE_ALL mode.
function Delete-AccessList() { param( [string]$selfip = $null, [string]$mode = "ALLOW_MODE_NONE", [string]$protocol = "PROTOCOL_ANY", [int]$port = 0); $pld = (Get-F5.iControl).NetworkingSelfIPPortLockdown; $SelfIPAccess = New-Object -TypeName iControl.NetworkingSelfIPPortLockdownSelfIPAccess; $SelfIPAccess.self_ip = $selfip; $SelfIPAccess.mode = $mode; $SelfIPAccess.protocol_ports = New-Object -TypeName iControl.NetworkingSelfIPPortLockdownProtocolPort; $(${SelfIPAccess}.protocol_ports).protocol = $protocol; $(${SelfIPAccess}.protocol_ports).port = $port; $pld.delete_allow_access_list( (,$SelfIPAccess) ); Get-AccessList $selfip; }
PS C:\> .\SelfIPPortLockdown.ps1 bigip username password deleteaccesslist 10.10.10.1 ALLOW_MODE_PROTOCOL_PORT PROTOCOL_TCP 44 -------------------------------------- Self IP : 10.10.10.1 Mode : ALLOW_MODE_NONE PS C:\> .\SelfIPPortLockdown.ps1 bigip username password addaccesslist 10.10.10.1 ALLOW_MODE_ALL PROTOCOL_TCP 0 -------------------------------------- Self IP : 10.10.10.1 Mode : ALLOW_ALL
Querying the Default Port Lockdown Access List
Above, I mentioned that you can configure a Port Lockdown on a Self IP to mode ALLOW_MODE_DEFAULTS. These default settings can be queried with the iControl Networking.SelfIPPortLockdown.get_default_protocol_port_access_list() method. The local Get-DefaultAccessList function calls this iControl command and prints out all the default Protocol Port allow lists.
function Get-DefaultAccessList() { $pld = (Get-F5.iControl).NetworkingSelfIPPortLockdown; $ProtocolPortA = $pld.get_default_protocol_port_access_list(); if ( $ProtocolPortA.Length ) { foreach ($ProtocolPort in $ProtocolPortA) { Write-Host "--------------------------------"; Write-Host "Protocol : " $ProtocolPort.protocol; Write-Host " Port : " $ProtocolPort.port; } } else { Write-Host "No default Protocol Port Access Lists defined"; } }
PS C:\> .\SelfIPPortLockdown.ps1 bigip username password getdefaccesslist No default Protocol Port Access Lists defined.
Adding a Default Port Lockdown Access List
The local Add-DefaultAccessList function takes as input a Protocol Type and Port and then calls the iControl Networking.SelfIPPortLockdown.add_default_protocol_port_access_list() method. In my example I add a default allow list of PROTOCOL_TCP on Port 44.
function Add-DefaultAccessList() { param([string]$protocol = "PROTOCOL_ANY", [int]$port = 0); $pld = (Get-F5.iControl).NetworkingSelfIPPortLockdown; $protocol_port = New-Object -TypeName iControl.NetworkingSelfIPPortLockdownProtocolPort; $protocol_port.protocol = $protocol; $protocol_port.port = $port; $pld.add_default_protocol_port_access_list( (,$protocol_port) ); Get-DefaultAccessList; }
PS C:\> .\SelfIPPortLockdown.ps1 bigip username password adddefaccesslist PROTOCOL_TCP 44 --------------------------------- Protocol : PROTOCOL_TCP Port : 44
Removing a Default Port Lockdown Access List
If you have a default Port Lockdown Access List that you no longer need, you can remove it with the iControl Networking.SelfIPPortLockdown.remove_default_protocol_port_access_list() method.
function Remove-DefaultAccessList() { param([string]$protocol = "PROTOCOL_ANY", [int]$port = 0); $pld = (Get-F5.iControl).NetworkingSelfIPPortLockdown; $protocol_port = New-Object -TypeName iControl.NetworkingSelfIPPortLockdownProtocolPort; $protocol_port.protocol = $protocol; $protocol_port.port = $port; $pld.remove_default_protocol_port_access_list( (,$protocol_port) ); Get-DefaultAccessList; }
PS C:\> .\SelfIPPortLockdown.ps1 bigip username password removedefaccesslist No default Protocol Port Access Lists defined.
Conclusion
Now you have all the tools you need to automate the management of you Port Lockdown Access Lists on your BIG-IP.
The full application can be found in the iControl CodeShare under PsSelfIPPortLockdown.