Automate F5 Backups

tape-bkp

I like to use Solarwinds CatTools to back up my network gear. It’s a great tool that allows you to easily schedule automated backups of network devices–or any command-line device for that matter.

This is where this post come in. There is no inherent template for backing up an F5 device using CatTools (at least right now).

I have a template that I’ve used over the years to create a UCS file based on the hostname and date, store a local copy in the event I need to restore it, as well as TFTP the file to the built-in TFTP server in CatTools for a remote backup.

CatTools Config:

First you’ll need a copy of CatTools somewhere that can reach your F5 via. SSH and have the ability to TFTP from the F5 to the CatTools server. I won’t go over the install or making sure your ACL’s allow this, but make sure you do this first.

  1. Open CatTools Manager
  2. Add your F5 devices under the Devices tab by clicking Add
  3. Select F5 as the vendor and F5.BigIP as the device type (although I don’t think this ultimately matters for much other than reporting).
  4. Pick a name and type in a Host Address (IP address of the F5 management or self IP with ssh permitted inbound)
  5. Pick SSH2 as your method. f5bkp1
  6. Click the Passwords tab, and add a user allocated just to CatTools. It will need to be an administrator with advanced shell. f5bkp2

Now you have your device(s) ready for backup. I like to make sure I have L3/4 connectivity by testing the Telnet/SSH button to make sure a prompt comes up. If not, work on your routing/ACL’s.

  1. Click the Add button under the Activities tab
  2. Under Activity, pick Device.CLI.Send commands option
  3. Add a description that makes sense to you. f5bkp3
  4. Click the Time tab, and set your schedule however you’d like.
  5. Under Devices, pick the F5(s) you added in the first steps.

The Script

Under the Options tab is where the commands will be entered on the device. The script has several lines which I’ll describe below.

export date=`date +"%y%m%d"​`

This sets an environment variable to the current date, year, month and day for file naming. Change this depending on your location or needs.

export filename=$HOSTNAME.$date.ucs

Now we set the filename to the hostname of the F5 and the date we just defined, followed by ucs.

tmsh save /sys ucs /var/local/ucs/$filename

Now we execute the tmsh command to create and save the UCS file to the directory we want.

NOTE: Depending on how frequently you set the backup, you could fill up your F5’s local storage. Although this would take a long time, you can create a script to auto-delete the files if you want, or delete them every 6 months or so when you are in the UI.

cd /var/local/ucs
tftp -m binary 192.168.1.10 -c put $filename

Now we move to that directory, and TFTP the file to the Cattools server. Change the 192 address to your Cattools server.

This is what it will look like in the UI:

f5bkp4

Click OK and run the activity. If you did everything right there should be UCS files in your TFTP directory in CatTools. If not, check ACL’s or routing to make sure you aren’t missing anything.

 

Advertisements
Automate F5 Backups

Configure OCSP Stapling – F5 LTM

The documentation that F5 provides for configuring OCSP stapling is pretty sparse. I decided to write up this quick tutorial to supplement their documentation. What is presented below worked for me in my environment, but may not work in all.

Configure a DNS Resolver

  1. Click Network > DNS Resolvers
  2. Click Create… on the right side
  3. Name it whatever you wish, I called mine resolver.
  4. Leave the rest of the settings as the default.ocsp1
  5. Click Finished

Configure Forward Zones

  1. Once your resolver is created, click its name from the Resolver List page.
  2. Click Forward Zones on the top tab area
  3. Click Add…
  4. In the name area put a period “.”
  5. Place the DNS servers that your F5 will use for lookupsocsp2
  6. Click Finished

Import Certificate Chain

Depending on where the certificate was purchased used by your virtual-server, a chain must be created that matches the server-certificate.

Collect the intermediate certificate(s) related to your certificate from the CA. This will contain the URL the F5 will use to validate the certificate using OCSP.

  1. Click File Management > SSL Certificate List
  2. Click Import…
  3. I like to take the chain and paste it in as text, but you can import the chain however you like.ocsp3
  4. Click Import

Create OCSP Profile

  1. Click Profiles > SSL > OCSP Stapling
  2. Click Add…
  3. Click the Advanced drop-down
  4. Pick a name that makes sense to you
  5. In the DNS Resolver section pick the resolver we made above
  6. Under Trusted CA and Trusted Responders pick the chain we created above
  7. I use Comodo certificates, so the settings beginning at Sign Hash and below that are highlighted in yellow were changed to match Comodo’s and F5’s recommendations. These may or may not work for you.ocsp4

Create SSL Profile with OCSP Responder

  1. Go to Local Traffic > Profiles > SSL > Client
  2. Click Create…
  3. Name it whatever makes sense to you
  4. Pick the Certificate, Key and Chain that you have imported already.
  5. In the OCSP Stapling Parameters pick the profile we created in the previous step
  6. Click Add for each certificate the profile will provide.
    • Optional – To create a more secure profile:
      1. Change your Ciphers to; ECDHE+AES-GCM:ECDHE+AES
      2. Disable Renegotiation
    • Click Finished

Testing

There are a few ways to test your profile to see whether OCSP responses are being sent from your virtual-server or not. I prefer to run a capture but you can check using the tool at SSL-labs also.

  1. Capture a SSL handshake between you and the virtual server
    • Go to the packet where the vs responds with the Certificate
    • Drill down to the Certificate Status Record Layer
    • Expand until you see OCSP response with a responseStatus of Successful (0)ocsp5
  2. Run a test using SSL-Labs
    • Go to https://www.ssllabs.com/ssltest/analyze.html and enter your domain if it is pubic
    • Wait for the test to complete and check for the OCSP Stapling line and make sure it says Yesocsp6
    • I like this site to check for potential issues with your configuration, save it and use it in the future if you don’t already.

Important Note about Default Route

Initially I had an issue with lookups and the OCSP status check using the OCSP Resolver profile I configured. I use Auto-Last Hop on our F5, so my configuration has no default route.

When you have no default route, the default behavior of the F5 is to perform DNS lookups and pull the OCSP status from the virtual-server(s) VLAN self-IP with the OCSP profile assigned to it. If you are firewalling and don’t have a rule permitting this, you may see that OCSP is not working.

As of this version (11.6.0 HF5), the F5 will not use the MGMT interface which typically has its own IP with a gateway. You must have a self-IP assigned elsewhere and configure a default route for it.

There are a few solutions to this:

  • Add a default route for an interface you want to perform lookups (syslog, snmp interface, etc.) and allow that IP to perform DNS lookups and pull the OCSP status from the Internet. The self IP(s) of the F5 on this VLAN must have Internet access.
  • Add ACL’s to allow each virtual-servers VLAN self-IP to perform DNS lookups and pull the OCSP status. These IPs will all require Internet access.
  • Change the OCSP profile to use proxy to perform lookups and pull status.
Configure OCSP Stapling – F5 LTM

F5 Persistence Mirroring w/ iRules

img_1926

In a failover pair of devices, mirroring persistence records is important. When one LTM fails, we need the other to know which server a user’s session was “stuck” to. If a device failed and the other device was not aware of these records, the decision process would start again and a user could lose their session (wait for the tickets to roll in…) We want our HA pair of F5’s to failover seamlessly so they can be updated without impacting users, as well as transparency to end-users when a device fails.

The problem with the F5 is when you are using multiple persistence methodologies, mirroring does not function for each type you are using in the iRule, only the type in the ‘Default Persistence Profile’ chosen in the virtual-server. This is a problem when you are using a few different types in one iRule. For example; persist cookie, persist source_addr, persist uie, etc. all in one iRule.

So what do I do? The solution to this is difficult if not impossible to find in dev-central. I had to open a support case to even find this out. Use universal persistence!! In almost all cases when I opened support tickets the engineer would state that when I was using ‘persist cookie’ that it was unusual. I always thought to myself, “What, this is crazy!! Why even offer me a persistence type if it is not recommended to be used by the manufacturers of the device themselves!!”

The solution to this problem is to convert your existing iRule that uses a few different types of persistence to all use universal. The syntax may not be as simple, but universal persistence can do everything the other types can and more. Unfortunately F5 doesn’t have universal persistence documented very well (common theme), but this is a good start.

Let’s go over a simple example iRule. In this example I’m examining URI (virtual directory) and making decisions based on that value. I am using source IP and cookie hash stickiness. Different apps require different types of persistence. A normal person would offer what F5 provides, but that is not recommended by F5.

when HTTP_REQUEST {
 switch -glob [string tolower [HTTP::uri]] {
 "/app1*" {
 pool POOL-APP1
 persist source_addr 255.255.255.255
 }
 "/app2*" -
 "/app3*" {
 pool POOL-APP23
 persist cookie hash "ASP.NET_SessionId"
 }
 "/app4*" {
 pool POOL-APP4
 persist none
 }
 default {
 HTTP::redirect https://[getfield [HTTP::host] ":" 1][HTTP::uri]
 }
 }
 }

Unfortunately I can only pick one default persistence type in my virtual-server so not every record will fail over to the second node. We need to fix this by converting the syntax to universal and pick UIE as the default type.

when HTTP_REQUEST {
 switch -glob [string tolower [HTTP::uri]] {
 "/app1*" {
 pool POOL-APP1
 persist uie [IP::client_addr]
 }
 "/app2*" -
 "/app3*" {
 pool POOL-APP23
 persist uie [HTTP::cookie "ASP.NET_SessionId"]
 }
 "/app4*" {
 pool POOL-APP4
 persist none
 }
 default {
 HTTP::redirect https://[getfield [HTTP::host] ":" 1][HTTP::uri]
 }
 }
 }

Pretty simple, no? Now I assign my universal persistence profile with the ‘Mirror Persistence’ option checked.

uie1

Persistence records will now mirror to the passive device. View the records on each device by running ‘tmsh show ltm persistence persist-records’ to validate that the records are on each F5.

Aside: I think by now you all know how big of a fan I am of the Cisco ACE. Guess how easy this is with the ACE? Add ‘replicate sticky’ to your sticky group configuration. Way too simple…

F5 Persistence Mirroring w/ iRules

Poodle Vulnerability: Who’s Using SSLv3?

poodle

There are a ton of different articles on devcentral about certain iRules for changing the encryption that users are using, dropping them, etc. I found it difficult to find any code specific to just logging who is using SSLv3 so I can track them down and try to contact the customer. Managers found the reports that I generated useful to make a business decision instead of simply shutting of SSLv3 on the F5.

All this rule does is define a high-speed-logging server and send a message to the logging server so you can run reports against the logs. It logs source IP and URI (virtual-directory) from the request. Apply this to whichever virtual-server you need to log these requests from.

when CLIENT_ACCEPTED {
   set logpub [HSL::open -publisher /Common/HSL-SERVER]
}
when HTTP_REQUEST {
   set cipher [SSL::cipher version]
   set uri [HTTP::uri]
   if { $cipher equals "SSLv3" } {
      HSL::send $logpub "$cipher encryption used from client; [IP::client_addr] to $uri"
   }
}
Poodle Vulnerability: Who’s Using SSLv3?

iRule – IP Restrict Internal Applications

Fork in the road

In some scenarios it is necessary to limit access to applications behind the F5. Lets say you are hosting an application that is load balanced and is publicly and privately accessible on the same virtual-server. This can be accomplished by using an iRule.

In my scenario I need to limit access to applications running on an HTTP (non-SSL/TLS) virtual-server so that internal clear-text calls are permitted on the LAN, but users on the Internet are redirected to the same resource on HTTPS. My private networks all start with 10.* so it was fairly easy for me to write a rule to accomplish this. The rule can be customized to fit many different scenarios.

In summary my logic first inspects the IP address of the clients request. If it starts with 10., process the request by looking at URI (virtual-directory). If there is a successful match, send to the appropriate server. If not, redirect the full HOST and URI request from the client to HTTPS.

Secondarily if the clients IP does not match my public range, drop requests to certain resources that are not accessible at all from the Internet and redirect the rest to HTTPS as we did before.

 when HTTP_REQUEST {
    if { [IP::client_addr] starts_with 10. } {
       switch -glob [string tolower [HTTP::uri]] {
          "/app1*" -
          "/app2*" {
                pool POOL-APP-HTTP
                persist none
          }
          "/fs*" {
                pool POOL-FS-HTTP
                persist none
          }
          default {
                HTTP::redirect https://[getfield [HTTP::host] ":" 1][HTTP::uri]
          }
      }
 }
 else {
    switch -glob [string tolower [HTTP::uri]] {
       "/internal1*" {
          drop
       }
       default {
          HTTP::redirect https://[getfield [HTTP::host] ":" 1][HTTP::uri]
       }
    }
 }
}
iRule – IP Restrict Internal Applications

Language Aware Maintenance Page

It seems to be an expectation now that web-applications are language and location-aware. When a web application fails, the F5 can present a ‘sorry’ page using a variety of methods. I’ve found that the iFile presentation of HTML files using iRules to be the easiest for me.

In addition to detecting the health of members in a pool, this iRule includes the detection of the users browser Accept-language to forward them to the correct language sorry page. Assign this iRule to your virtual server and it will start working once a pool has zero healthy nodes in it.

The following iRule checks to see if there are less than one member in a pool. If this is the case–the header in request is then checked to check the Accept-Language and present the correct HTML page based on that field. I check for French, Japanese and the default is English. Add additional languages as needed and their respective HTML page to present to users. Of course you will need to create and import your maintenance page into the F5 and then add it to the iRule iFile list.

when HTTP_REQUEST {
 if {[active_members [LB::server pool]] < 1} {
 log local0.crit "Server Pool: [LB::server pool] has failed"
 switch -glob [HTTP::header "Accept-Language"] {
 "fr*" {
 HTTP::respond 200 content [ifile get maintenance.fr.html] "Content-Type" "text/html"
 }
 "ja*" {
 HTTP::respond 200 content [ifile get maintenance.jp.html] "Content-Type" "text/html"
 }
 default {
 HTTP::respond 200 content [ifile get maintenance.en.html] "Content-Type" "text/html"
 }
 }
 }
}
Language Aware Maintenance Page

Rewriting IIS Server Response Content from HTTP to HTTPS

eraser-paper

This may seem like an unusual post, but this may apply to “load-balancer gurus” who do SSL termination. In certain cases web-applications that you host have embedded code that reference http links. This can be resolved with F5 iRules, but it can be tricky with Cisco ACE.

Instead of reinventing the wheel, here’s how to do it with the URL Rewrite module in IIS. A good reference link can be found here.

Lets say your webserver keeps responding with image referrer links with http instead of https. This will give users on the web errors about mixed content. IIS can rewrite those responses for you without spending tons of man-hours fixing your code or bothering developers.

What this is doing is looking for any content that starts with HTTP and grabs any content after the star as a back-reference to basically plop into use in the next portion. {R:2} is that reference in the rewrite value.  I’m looking for http patterns after img, link and script tags. You can customize to your specific application.

 <rule name="Content-Rewrite" preCondition="" enabled="true" patternSyntax="Wildcard">
  <match filterByTags="Img, Link, Script" pattern="*http://*" />
   <conditions />
    <action type="Rewrite" value="https://{R:2}" />
  </rule>
  <preConditions>
  <preCondition name="http" logicalGrouping="MatchAny" patternSyntax="Wildcard">
  <add input="{RESPONSE_CONTENT_TYPE}" pattern="http:" />

Rewriting IIS Server Response Content from HTTP to HTTPS