sni
5 TopicsSNI Routing with BIG-IP
In the previous article, The Three HTTP Routing Patterns, Lori MacVittie covers 3 methods of routing. Today we will look at Server Name Indication (SNI) routing as an additional method of routing HTTPS or any protocol that uses TLS and SNI. Using SNI we can route traffic to a destination without having to terminate the SSL connection. This enables several benefits including: Reduced number of Public IPs Simplified configuration More intelligent routing of TLS traffic Terminating SSL Connections When you havea SSL certificate and key you can perform the cryptographic actions required to encrypt traffic using TLS. This is what I refer to as “terminating the SSL connection” throughout this article. When you want to route traffic this is a chickenand an egg problem, becausefor TLS traffic you want to be able to route the traffic by being able to inspect the contents, but this normally requires being able to “terminate the SSL connection”. The goal of this article is to layer in traffic routing for TLS traffic without having to require having/knowing the original SSL certificate and key. Server Name Indication (SNI) SNI is a TLS extension that makes it possible to "share" certificates on a single IP address. This is possible due to a client using a TLS extension that requests a specific name before the server responds with a SSL certificate. Prior to SNI, the other options would be a wildcard certificate or Subject Alternative Name (SAN) that allows you to specify multiple names with a single certificate. SNI with Virtual Servers It has been possible to use SNI on F5 BIG-IP since TMOS 11.3.0. The following KB13452 outlines how it can be configured. In this scenario (from the KB article) the BIG-IP is terminating the SSL connection. Not all clients support SNI and you will always need to specify a “fallback” profile that will be used if a SNI name is not used or matched. The next example will look at how to use SNI without terminating the SSL connection. SNI Routing Occasionally you may have the need to have a hybrid configuration of terminating SSL connections on the BIG-IP and sending connections without terminating SSL. One method is to create two separate virtual servers, one for SSL connections that the BIG-IP will handle (using clientssl profile) and one that it will not handle SSL (just TCP). This works OK for a small number of backends, but does not scale well if you have many backends (run out of Public IP addresses). Using SNI Routing we can handle everything on a single virtual server / Public IP address. There are 3 methods for performing SNI Routing with BIG-IP iRule with binary scan a. Article by Colin Walker code attribute to Joel Moses b. Code Share by Stanislas Piron iRule with SSL::extensions Local Traffic Policy Option #1 is for folks that prefer complete control of the TLS protocol. It only requires the use of a TCP profile. Options #2 and #3 only require the use of a SSL persistence profile and TCP profile. SNI Routing with Local Traffic Policy We will skip option #1 and #2 in this article and look at using a Local Traffic Policy for SNI Routing. For a review of Local Traffic Policies check out the following DevCentral articles: LTM Policy Jan 2015 Simplifying Local Traffic Policies in BIG-IP 12.1 June 2016 In previous articles about Local Traffic Policiesthe focus was on routing HTTP traffic, but today we will use it to route SSL connections using SNI. In the following example, using a Local Traffic Policy named “sni_routing”, we are setting a condition on the SSL Extension “servername” and sending the traffic to a pool without terminating the SSL connection. The pool member could be another server or another BIG-IP device. The next example will forward the traffic to another virtual server that is configured with a clientssl profile. This uses VIP targeting to send traffic to another virtual server on the same device. In both examples it is important to note that the “condition”/“action” has been changed from occurring on “request” (that maps to a HTTP L7 request) to “ssl client hello”. By performing the action prior to any L7 functions occurring, we can forward the traffic without terminating the SSL connection. The previous example policy, “sni_routing”, can be attached to a Virtual Server that only has a TCP profile and SSL persistence profile. No HTTP or clientssl profile is required! This method can also be used to solve the issue of how to consolidate multiple SSL virtual servers behind a single virtual server that have different APM and/or ASM policies. This is similar to the architecture that is used by the Container Connector for Cloud Foundry; in creating a two-tier load balancing solution on a single device. Routed Correctly? TLS 1.3 has interesting proposals on how to obscure the servername (TLS in TLS?), but for now this is a useful and practical method of handling multiple SSL certs on a single IP. In the future this may still be possible as well with TLS 1.3. For example the use of a HTTP Fronting service could be a tier 1 virtual server (this is just my personal speculation, I have not tried, at the time of publishing this was still a draft proposal). In other news it has been demonstrated that a combination of using SNI and a different host header can be used for “domain fronting”. A method to enforce consistent policy (prevent domain fronting) would be to layer in additional conditions that match requested SNI servername (TLS extension) with requested HOST header (L7 HTTP header). This would help enforce that a tenant is using a certificate that is associated with their application and not “borrowing” the name and certificate that is being used by an adjacent service. We don’t think of a TLS extension as an attribute that can be used to route application traffic, but it is useful and possible on BIG-IP.24KViews0likes16CommentsSSL Orchestrator Use Case: Inbound SNI Switching with version 9.1
Introduction SSLO will generate a single set of SSL profiles for use in a topology. It may be useful, especially in an inbound gateway mode, to process traffic to multiple sites, requiring different server certificates. The use case is to employ native BIG-IP SNI switching in SSLO, such that an SSLO topology can select a correct client SSL profile and server certificate based on the incoming SNI. In this example we have a single web server with multiple IP addresses hosting different web site domains: en.appserverone.com resides on 10.1.10.90 en.appservertwo.com resides on 10.1.10.91 When an external client requests https://en.appserverone.com we want the SSL Orchestrator to use a specific keypair for the sessions and direct the traffic to 10.1.10.90.When an external client requests https://en.appservertwo.com we want the SSL Orchestrator to use a different keypair for the sessions and direct the traffic to 10.1.10.91. Configuration Steps Import Private Keys and Certificates Create Client SSL Profiles Create New SSL Configurations Add the Client SSL Profiles to the Interception Rule Import the Private Key and Certificate for the different web site domains From the BIG-IP Configuration Utility go to SSL Orchestrator > Certificates Management > Certificates and Keys. Click Import on the right. For the Import Type select Key. Give it a name, en.appserverone.com in this example.For the Key Source you can upload a file or paste in the text.We’ll use the Paste option which you can see below.Click Import when done. Click on the Key Name created in the previous step. Click Import. For the Certificate Source you can upload a file or paste in the text.We’ll use the Paste option which you can see below.Click Import when done. Repeat these steps for other web site domains.In this example we will add one more, en.appservertwo.com as you can see below. Create a Client SSL Profile for each certificate/key pair From the BIG-IP Configuration Utility go to SSL Orchestrator > Components > Profiles > Client SSL. Click Create on the right. Give it a name, en.appserverone.com in this example.Select the Custom box on the far right then click Add for the Certificate Key Chain. Select the Certificate and Key created previously and click Add.A Passphrase and Chain can be specified if needed.Click Add when done. Select the Advanced option next to Configuration. Scroll down and find the Server Name field.Enter the FQDN that external clients will request, en.appserverone.com in this example. Note: when an external client requests https://en.appserverone.com their TLS Client Hello will contain an extension value for ‘server_name’ field with a value of ‘en.appserverone.com’.We’re instructing SSL Orchestrator to use this Client SSL Profile when it receives this type of request from a client. Scroll to the bottom and click Finished when done. Repeat these steps for other web site domains.In this example we will add one more, en.appservertwo.com as you can see below. Create New SSL Configurations In this example an Incoming L3 Topology already exists.From the Configuration Utility select SSL Orchestrator > Configuration > SSL Configurations. Click Add Give it a name, appserverone in this example.Deselect the check boxes for Forward Proxy and Default SNI. For the SNI Server Name enter the FQDN, en.appserverone.com in this example For Client-side SSL select the pencil icon to edit the Certificate Key Chains. Use the Drop Down menu to choose the correct Certificate and Key, en.appserverone.com in this example. Click Done Click Save & Next at the bottom. Click Deploy Click OK to the Success message Repeat this step as needed.In this example another SSL Configuration is added for en.appservertwo.com. Add the Client SSL Profiles to the Interception Rule From the Configuration Utility select SSL Orchestrator > Configuration > Interceptions Rules. sslo_L3_inbound. Select the correct rule, sslo_L3_inbound in this example. Click the pencil icon to edit the rule. Scroll down to the Server SSL Profiles.Select the Server SSL Profiles created previously and click the arrow to move them from Available to Selected. At the bottom click Save & Next. Click Deploy Click OK to the Success message Summary Congratulations! The configuration is now complete810Views1like0CommentsSSL Orchestrator Use Case: Inbound SNI Switching
Introduction SSLO will generate a single set of SSL profiles for use in a topology. It may be useful, especially in an inbound gateway mode, to process traffic to multiple sites, requiring different server certificates. The use case is to employ native BIG-IP SNI switching in SSLO, such that an SSLO topology can select a correct client SSL profile and server certificate based on the incoming SNI. In this example we have a single web server with multiple IP addresses hosting different web site domains: en.appserverone.com resides on 10.1.10.90 en.appservertwo.com resides on 10.1.10.91 When an external client requests https://en.appserverone.com we want the SSL Orchestrator to use a specific keypair for the sessions and direct the traffic to 10.1.10.90.When an external client requests https://en.appservertwo.com we want the SSL Orchestrator to use a different keypair for the sessions and direct the traffic to 10.1.10.91. Configuration Steps Import Private Keys and Certificates Create Client SSL Profiles Create a String Data Group* Import iRules Attach iRule to existing Topology Attach iRule to Existing Application Topology Attach iRule to existing Topology Interception Rule (alternative) *Note: You can either use an iRule and Data Group to match SNI to a Profile, or a static SNI-to-profile mapping in an iRule.The advantage of using a Data Group is all management is done at the Data Group. Import the Private Key and Certificate for the different web site domains From the BIG-IP Configuration Utility go to SSL Orchestrator > Certificates Management > Certificates and Keys. Click Import on the right. For the Import Type select Key. Give it a name, en.appserverone.com in this example.For the Key Source you can upload a file or paste in the text.We’ll use the Paste option which you can see below.Click Import when done. Click on the Key Name created in the previous step. Click Import. For the Certificate Source you can upload a file or paste in the text.We’ll use the Paste option which you can see below.Click Import when done. Repeat these steps for other web site domains.In this example we will add one more, en.appservertwo.com as you can see below. Create a Client SSL Profile for each certificate/key pair From the BIG-IP Configuration Utility go to SSL Orchestrator > Components > Profiles > Client SSL. Click Create on the right. Give it a name, en.appserverone.com in this example.Select the Custom box on the far right then click Add for the Certificate Key Chain. Select the Certificate and Key created previously and click Add.A Passphrase and Chain can be specified if needed.Click Add when done. Select the Advanced option next to Configuration. Scroll down and find the Server Name field.Enter the FQDN that external clients will request, en.appserverone.com in this example. Note: when an external client requests https://en.appserverone.com their TLS Client Hello will contain an extension value for ‘server_name’ field with a value of ‘en.appserverone.com’.We’re instructing SSL Orchestrator to use this Client SSL Profile when it receives this type of request from a client. Scroll to the bottom and click Finished when done. Repeat these steps for other web site domains.In this example we will add one more, en.appservertwo.com as you can see below. Create a String Data Group that maps the SNI to the Client SSL Profile. This step is only required if using the ‘in-t-rule-datagroup’ iRule. From the BIG-IP Configuration Utility go to Local Traffic > iRules > Data Group List. Click Create over on the right. Give it a name, SNI_switcher in this example and select String next to Type. Create a String that maps the SNI to the Client SSL Profile name created previously.Click Add. Note: If creating these profiles in other partitions, or if the VIP runs in another partition, it’s useful to prepend the partition name to avoid confusion. So, in this case, the client SSL profile would be: /Common/en.appserverone.com Repeat this step for as many mappings as you require.We’re doing two in this example and it should look like the following.Click Finished when done. Import iRules We will create two iRules from the following 1.library-rule: This rule is required. The next two iRules will make calls to the Library iRule to check the TCP payload for the ‘server_name’ field in the TLS Client Hello. 2.in-t-rule-datagroup: This iRule depends upon a ‘Data Group’ to map the SNI to the Client SSL Profile 3.in-t-rule-static: This is a static iRule does not depend upon a ‘Data Group’.This iRule contains the mapping of theSNI(s) to the Client SSL Profile(s) Note: Rules 2 and 3 perform the same function in a slightly different manner.We will cover both options but you can pick whichever one you want to use. Note: Using a data group or static iRule to switch the client SSL profile, requires a binary-scanning TCP iRule that may have an impact on performance Click Create over on the Right. Give it the name library-rule . Copy and paste the following into the Definition field: proc getSNI { payload } { set detect_handshake 1 binary scan ${payload} H* orig if { [binary scan [TCP::payload] cSS tls_xacttype tls_version tls_recordlen] < 3 } { reject return } ## 768 SSLv3.0 ## 769 TLSv1.0 ## 770 TLSv1.1 ## 771 TLSv1.2 switch $tls_version { "769" - "770" - "771" { if { ($tls_xacttype == 22) } { binary scan ${payload} @5c tls_action if { not (($tls_action == 1) && ([string length ${payload}] > $tls_recordlen)) } { set detect_handshake 0 } } } "768" { set detect_handshake 0 } default { set detect_handshake 0 } } if { ($detect_handshake) } { ## skip past the session id set record_offset 43 binary scan ${payload} @${record_offset}c tls_sessidlen set record_offset [expr {$record_offset + 1 + $tls_sessidlen}] ## skip past the cipher list binary scan ${payload} @${record_offset}S tls_ciphlen set record_offset [expr {$record_offset + 2 + $tls_ciphlen}] ## skip past the compression list binary scan ${payload} @${record_offset}c tls_complen set record_offset [expr {$record_offset + 1 + $tls_complen}] ## check for the existence of ssl extensions if { ([string length ${payload}] > $record_offset) } { ## skip to the start of the first extension binary scan ${payload} @${record_offset}S tls_extenlen set record_offset [expr {$record_offset + 2}] ## read all the extensions into a variable binary scan ${payload} @${record_offset}a* tls_extensions ## for each extension for { set ext_offset 0 } { $ext_offset < $tls_extenlen } { incr ext_offset 4 } { binary scan $tls_extensions @${ext_offset}SS etype elen if { ($etype == 0) } { ## if it's a servername extension read the servername set grabstart [expr {$ext_offset + 9}] set grabend [expr {$elen - 5}] binary scan $tls_extensions @${grabstart}A${grabend} tls_servername_orig set tls_servername [string tolower ${tls_servername_orig}] set ext_offset [expr {$ext_offset + $elen}] break } else { ## skip over other extensions set ext_offset [expr {$ext_offset + $elen}] } } } } if { ![info exists tls_servername] } { ## This isn't TLS so we can't decrypt it anyway return "null" } else { return ${tls_servername} } TCP::release } Click Finished when Done From the BIG-IP Configuration Utility go to Local Traffic > iRules > iRule List. Click Create over on the Right. Give it a name, in-t-rule-datagroup in this example.Copy and paste the following into the Definition field: ## SSLO SNI Switching Rule ## Date: July 2020 ## Purpose: Useful in SSLO versions 8.x and below to switch the client SSL profile based on ClientHello SNI ## in inbound SSLO topologies. This would be practical for L3 inbound gateway mode or L2 inbound topologies. ## Instructions: ## - Import server certificates and private keys ## - Create a separate client SSL profile for each cert/key pair ## - Create a string data group that maps the SNI to the client SSL profile name (ex. test0.f5labs.com := test0-clientssl) ## - Add the library-rule iRule to LTM (name "library-rule") ## - Add the SNI-switching-rule to LTM (name is arbitrary) ## - Create an L3 inbound gateway mode SSLO topology. Define a server cert/key to be used as the "default" (when no SNI matches) ## - Edit the L3 inbound Interception Rule and add the SNI switching rule. Deploy and test. when CLIENT_ACCEPTED priority 250 { TCP::collect } when CLIENT_DATA priority 250 { ## call the external procedure set sni [call library-rule::getSNI [TCP::payload]] ## lookup SSL profile in data group set sslprofile [class lookup ${sni} sni-switching-dg] if { ${sslprofile} ne "" } { set cmd "SSL::profile /Common/${sslprofile}" ; eval $cmd } TCP::release } Click Finished when done. Click Create over on the Right. Give it a name, in-t-rule-static in this example.Copy and paste the following into the Definition field: when CLIENT_ACCEPTED priority 250 { TCP::collect } when CLIENT_DATA priority 250 { ## call the external procedure set sni [call library-rule::getSNI [TCP::payload]] switch [string tolower ${sni}] { "en.appserverone.com" { set cmd1 "SSL::profile /Common/en.appserverone.com" ; eval $cmd1 } "en.appservertwo.com" { set cmd2 "SSL::profile /Common/en.appservertwo.com" ; eval $cmd2 } } TCP::release } Note: this iRule requires customization.The items in Blue are the Server Names that external clients will request.The items above in Red are the names of the Client SSL Profiles created previously. Click Finished when done Attach iRule to existing Inbound Topology If you have an existing Topology you can attach the iRule to that Topology.To do this you will need to disable Strictness on the Topology.From the BIG-IP Configuration Utility select SSL Orchestrator > Configuration.Click the padlock on the right to Unprotect the Configuration. Click OK when presented with the following message. Note: Disabling Strictness on the Topology is needed to modify it and add multiple client-ssl profiles. Select Local Traffic > Virtual Servers.Click the name of your Topology, sslo_Inbound_Topology in this example. Scroll down to the SSL Profile (Client).Add the SSL Profiles created previously, 10.1.10.90 and 10.1.10.91 in this example.You also need a default SNI SSL Profile in case no SNI matches.We’re using clientssl in this example.Your screen should look similar to the following. Click Update at the bottom when done. Select Resources so we can attach the iRule. In the iRule section select Manage. Locate the iRule in the Available field.Select the one you want to use, in-t-rule-static in this example, then click the << to move it to Enabled.Click Finished when done. The configuration is now complete.When external clients request en.appserverone.com or en.appservertwo.com the correct Client SSL profile will be used. Existing Application Topology SSL Orchestrator manages the services and service policies for existing applications while an existing ADC application manages its own SSL settings and application delivery, consuming the SSL Orchestrator service policy information. The Existing Application topology is available for SSL Orchestrator addon licensed devices. ·Traffic flows into the BIG-IP. (This is configured outside of this topology.) ·Traffic is decrypted and sent to security devices. ·Traffic is re-encrypted and sent out to the applications. (This is configured outside of this flow.) From the BIG-IP Configuration Utility select SSL Orchestrator > Configuration. Scroll down and click Next. Give it a name, Inbound in this example.Choose the Existing Application option and click Save & Next. On the Services List screen you can Add Services now or do so later.In this example we’ll have a Generic L3 Inline Service.Click Save & Next. On the Services Chain List screen you can Add or Edit a Service Chain.In this example it’s named ServiceChain.Click Save & Next. On the Security Policy screen click the pencil icon on the right to edit the Rule. Select the Service Chain and click OK. Click Save & Next. Review the configuration summary and make any changes as needed.Otherwise click Deploy. Add iRule and SSL Profiles to the Virtual Server From the BIG-IP Configuration Utility select Local Traffic > Virtual Servers.Click the name of the Virtual Server you want to configure, SNI in this example. Scroll down to the SSL Profile (Client) section.Highlight the SSL Profiles created previously and click << to move them to Selected. Scroll to the bottom and click Update. Select Resources to attach the iRule. Click Manage to the right of iRules. Select the iRule you want to use, in-t-rule-static in this example.Click << to move it to Enabled.Click Finished. The configuration is now complete. Attach iRule to existing Topology Interception Rule (alternative) Assign an iRule to the Interception Rule ·This incurs a performance hit without the SSL profiles attached to a VIP, but doesn’t require default-for-sni to be configured and does not require Strictness to be disabled on the Topology. From the BIG-IP Configuration Utility select SSL Orchestrator > Configuration. Select Interception Rules then click on the name of your Interception Rule, sslo_Inbound_App in this example. Click the pencil icon to edit the rule. Scroll down until you get to the section on iRules.Select the iRule you want to use, in-t-rule-static in this example and click the arrow to move it to Selected. Click Save & Next at the bottom. Click Deploy to complete the configuration. The configuration is now complete.2KViews0likes5CommentsHTTPS SNI Monitoring How-to
Hi, You may or may not already have encountered a webserver that requires the SNI (Server Name Indication) extension in order to know which website it needs to serve you. It comes down to "if you don't tell me what you want, I'll give you a default website or even simply reset the connection". A typical IIS8.5 will do this, even with the 'Require SNI' checkbox unchecked. So you have your F5, with its HTTPS monitors. Those monitors do not yet support SNI, as they have no means of specifying the hostname you want to use for SNI. In comes a litle script, that will do exactly that. Here's a few quick steps to get you started: Download the script from this article (it's posted on pastebin: http://pastebin.com/hQWnkbMg). Import it under 'System' > 'File Management' > 'External Monitor Program File List'. Create a monitor of type 'External' and select the script from the picklist under 'External Program'. Add your specific variables (explanation below). Add the monitor to a pool and you are good to go. A quick explanation of the variables: METHOD (GET, POST, HEAD, OPTIONS, etc. - defaults to 'GET') URI ("the part after the hostname" - defaults to '/') HTTPSTATUS (the status code you want to receive from the server - defaults to '200') HOSTNAME (the hostname to be used for SNI and the Host Header - defaults to the IP of the node being targetted) TARGETIP and TARGETPORT (same functionality as the 'alias' fields in the original monitors - defaults to the IP of the node being targetted and port 443) DEBUG (set to 0 for nothing, set to 1 for logs in /var/log/ltm - defaults to '0') RECEIVESTRING (the string that needs to be present in the server response - default is empty, so not checked) HEADERX (replace the X by a number between 1 and 50, the value for this is a valid HTTP header line, i.e. "User-Agent: Mozilla" - no defaults) EXITSTATUS (set to 0 to make the monitor always mark te pool members as up; it's fairly useless, but hey... - defaults to 1) There is a small thing you need to know though: due to the nature of the openssl binary (more specifically the s_client), we are presented with a "stdin redirection problem". The bottom line is that your F5 cannot be "slow" and by slow I mean that if it requires more than 3 seconds to pipe a string into openssl s_client, the script will always fail. This limit is defined in the variable "monitor_stdin_sleeptime" and defaults to '3'. You can set it to something else by adding a variable named 'STDIN_SLEEPTIME' and giving it a value. From my experience, anything above 3 stalls the "F5 script executer", anything below 2 is too fast for openssl to read the request from stdin, effectively sending nothing and thus yielding 'down'. When you enable debugging (DEBUG=1), you can see what I mean for yourself: no more log entries for the script when STDIN_SLEEPTIME is set too high; always down when you set it too low. I hope this script is useful for you, Kind regards, Thomas Schockaert6.2KViews0likes22CommentsLightboard Lessons: TLS Server Name Indication
Server Name Indication (SNI) is an extension to the TLS protocol that allows the client to include the requested hostname in the first message of the SSL handshake (Client Hello). Prior to the introduction of SNI, the client could not easily establish secure connections to multiple servers hosted on a single IP address. Because SNI lets the client identify the intended secure server during the initial part of the TLS handshake, it allows the server to host more than one secure website on a single IP address. In this Lightboard Lesson video, John explains the details of SNI and how you can configure it on your BIG-IP. Enjoy! Related Resources: SSL Profiles: Server Name Indication Configuring a Virtual Server for SNI SNI via iRules (used in versions prior to 11.1) TLS SNI Compatible Browsers1.4KViews0likes3Comments