For more information regarding the security incident at F5, the actions we are taking to address it, and our ongoing efforts to protect our customers, click here.

Forum Discussion

jokragly's avatar
jokragly
Icon for Nimbostratus rankNimbostratus
Feb 22, 2016

iRule patter based encrypted cookie

I have been trying to figure out a way that I can use a single iRule to apply to many Virtual Servers to encrypt my cookie.

I have tried following the a couple KB articles and they do not seem to work. When i apply the following iRule to my Virtual Server it breaks it and doesn't load the page. Any suggestions on how to accomplish this?

when RULE_INIT {

 Cookie name prefix
set static::ck_pattern "BIGipServer*"

 Log debug to /var/log/ltm? 1=yes, 0=no)
set static::ck_debug 1

 Cookie encryption passphrase
 Change this to a custom string!
set static::ck_pass "Test123"

} when HTTP_REQUEST {

if {$static::ck_debug}{log local0. "Request cookie names: [HTTP::cookie names]"}

 Check if the cookie names in the request match our string glob pattern
if {[set cookie_names [lsearch -all -inline [HTTP::cookie names] $static::ck_pattern]] ne ""}{

     We have at least one match so loop through the cookie(s) by name
    if {$static::ck_debug}{log local0. "Matching cookie names: [HTTP::cookie names]"}
    foreach cookie_name $cookie_names {

         Decrypt the cookie value and check if the decryption failed (null return value)
        if {[HTTP::cookie decrypt $cookie_name $static::ck_pass] eq ""}{

             Cookie wasn't encrypted, delete it
            if {$static::ck_debug}{log local0. "Removing cookie as decryption failed for $cookie_name"}
            HTTP::cookie remove $cookie_name
        }
    }
    if {$static::ck_debug}{log local0. "Cookie header(s): [HTTP::header values Cookie]"}
}

} when HTTP_RESPONSE {

if {$static::ck_debug}{log local0. "Response cookie names: [HTTP::cookie names]"}

 Check if the cookie names in the request match our string glob pattern
if {[set cookie_names [lsearch -all -inline [HTTP::cookie names] $static::ck_pattern]] ne ""}{

     We have at least one match so loop through the cookie(s) by name
    if {$static::ck_debug}{log local0. "Matching cookie names: [HTTP::cookie names]"}
    foreach cookie_name $cookie_names {

         Encrypt the cookie value
        HTTP::cookie encrypt $cookie_name $static::ck_pass
    }
    if {$static::ck_debug}{log local0. "Set-Cookie header(s): [HTTP::header values Set-Cookie]"}
}

}

1 Reply

  • Hi Jokragly,

    the iRule below is at least working for me...

    when RULE_INIT {
         Cookie name prefix
        set static::ck_pattern "BIGipServer*"
    
         Log debug to /var/log/ltm? 1=yes, 0=no)
        set static::ck_debug 1
    
         Cookie encryption passphrase
         Change this to a custom string!
        set static::ck_pass "Test123"
    } 
    
    when HTTP_REQUEST {
        if {$static::ck_debug}{log local0. "Request cookie names: [HTTP::cookie names]"}
    
         Check if the cookie names in the request match our string glob pattern
        if {[set cookie_names [lsearch -all -inline [HTTP::cookie names] $static::ck_pattern]] ne ""}{
    
             We have at least one match so loop through the cookie(s) by name
            if {$static::ck_debug}{log local0. "Matching cookie names: $cookie_names"}
            foreach cookie_name $cookie_names {
    
                 Decrypt the cookie value and check if the decryption failed (null return value)
                if {[HTTP::cookie decrypt $cookie_name $static::ck_pass] eq ""}{
    
                     Cookie wasn't encrypted, delete it
                    if {$static::ck_debug}{log local0. "Removing cookie as decryption failed for $cookie_name"}
                    HTTP::cookie remove $cookie_name
                }
            }
            if {$static::ck_debug}{log local0. "Cookie header(s): [HTTP::header values Cookie]"}
        }
    } 
    when HTTP_RESPONSE {
        if {$static::ck_debug}{log local0. "Response cookie names: [HTTP::cookie names]"}
    
         Check if the cookie names in the request match our string glob pattern
        if {[set cookie_names [lsearch -all -inline [HTTP::cookie names] $static::ck_pattern]] ne ""}{
    
             We have at least one match so loop through the cookie(s) by name
            if {$static::ck_debug}{log local0. "Matching cookie names: [HTTP::cookie names]"}
            foreach cookie_name $cookie_names {
    
                 Encrypt the cookie value
                HTTP::cookie encrypt $cookie_name $static::ck_pass
            }
            if {$static::ck_debug}{log local0. "Set-Cookie header(s): [HTTP::header values Set-Cookie]"}
        }
    }
    

    Note: Checked corrected some formatings and changed the "Matching cookie names"

    [log]
    line.

    Mon Feb 22 22:40:23 CET 2016     info    f5-02   tmm[2649]       Rule /Common/iRule_2_Delete : Set-Cookie header(s): {BIGipServerwww.itacs.de=!CGOtVQL7P+nj19+TSJ8pqJQSLtu5dFey0o2aYmp8+zLRyY2cUVC18DA2xdis4A4LWyZe97t2HR419/DaFZkLsQrfuZ7iRbTOg7ji8Ohm; path=/; Httponly; Secure}
    Mon Feb 22 22:40:23 CET 2016     info    f5-02   tmm[2649]       Rule /Common/iRule_2_Delete : Matching cookie names: BIGipServerwww.itacs.de
    Mon Feb 22 22:40:23 CET 2016     info    f5-02   tmm[2649]       Rule /Common/iRule_2_Delete : Response cookie names: BIGipServerwww.itacs.de
    Mon Feb 22 22:40:23 CET 2016     info    f5-02   tmm[2649]       Rule /Common/iRule_2_Delete : Cookie header(s): {ASP.NET_SessionId=jdkq3zcgwi22yx3ai1cotaqb; ASP.NET_SessionId_HMAC=0CEsmi1j37fbUwv27pg0TKoGy3HYeIFnDWOrqUF4sOI=; BIGipServerwww.itacs.de=rd1o00000000000000000000ffffd96e6c98o443}
    Mon Feb 22 22:40:23 CET 2016     info    f5-02   tmm[2649]       Rule /Common/iRule_2_Delete : Matching cookie names: BIGipServerwww.itacs.de
    Mon Feb 22 22:40:23 CET 2016     info    f5-02   tmm[2649]       Rule /Common/iRule_2_Delete : Request cookie names: ASP.NET_SessionId BIGipServerwww.itacs.de ASP.NET_SessionId_HMAC
    

    Cheers, Kai