Tag Archives: JunOS

JNCIP-SEC – Configuring Juniper Enhanced Web Filtering

Two more weeks left to take the JNCIP-SEC exam, or I will lose my JNCIS-SEC credentials. I have a fully loaded SRX320 cluster (with advanced feature licenses) and a vSRX in place so I need to lab up quickly. First feature on the list is Juniper Enhanced Web filtering.

Before you begin the configuration, make sure you meet the following prerequisites:

  • The device has a valid wf_key_websense_ewf license
  • The egress interface has internet connectivity
  • The device has working name-servers defined
  • If you are enabling the feature on a virtual router, be sure to define the VR under [edit security utm feature-profile web-filtering]

To activate the Juniper Enhanced Web Filtering feature, enter the following command:

[edit security utm feature-profile web-filtering]
root@NP-vSRX# show
type juniper-enhanced;

Next, enable the UTM feature profile for Juniper Enhanced Web Filtering and configure the Juniper-managed Websense server URL.

[edit security utm feature-profile web-filtering]
root@NP-vSRX# show
juniper-enhanced {
    server {
        host rp.cloud.threatseeker.com;
        port 80;
    }
}

Before we configure the Websense categories, we should define custom whitelists and blacklists, which can be used to overrule unexpected results from the automated Websense categorization.

Under the UTM custom-objects, we’ll create an URL pattern for one of our favorite networking-related forums and for a blacklisted adult site. These are then addded to custom black/whitelist categories.

[edit security utm custom-objects]
root@NP-vSRX# show
url-pattern {
    URL-networking-forumsdotcom {
        value [ http://networking-forums.com 64.90.58.116 ];
    }
    URL-sexdotcom {
        value [ sex.com 206.125.164.82 ];
    }
}
custom-url-category {
    EWF-Blacklist {
        value URL-sexdotcom;
    }
    EWF-Whitelist {
        value URL-networking-forumsdotcom;
    }
}

Our two custom URL categories are added under the global web-filtering configuration.

[edit security utm feature-profile web-filtering]
root@NP-vSRX# show
url-whitelist EWF-Whitelist;
url-blacklist EWF-Blacklist;

As for the Enhanced Web-filtering example, I’ll create one profile for standard internet access called “WF-DefaultInternetAccess”. Adult content and malicious URLs/IP addresses will be blocked by default and some ‘undesirable’ categories will be allowed, yet a security event will be logged. The default action will be set to “permit”.

[edit security utm feature-profile web-filtering juniper-enhanced]
root@NP-vSRX# show
cache;
server {
    host rp.cloud.threatseeker.com;
    port 80;
}
profile WF-DefaultInternetAccess {
    category {
        Enhanced_Adult_Content {
            action block;
        }
        Enhanced_Adult_Material {
            action block;
        }
        Enhanced_Advanced_Malware_Command_and_Control {
            action block;
        }
        Enhanced_Advanced_Malware_Payloads {
            action block;
        }
        Enhanced_Bot_Networks {
            action block;
        }
        Enhanced_Dynamic_DNS {
            action block;
        }
        Enhanced_Emerging_Exploits {
            action block;
        }
        Enhanced_Keyloggers {
            action block;
        }
        Enhanced_Malicious_Embedded_Link {
            action block;
        }
        Enhanced_Malicious_Embedded_iFrame {
            action block;
        }
        Enhanced_Malicious_Web_Sites {
            action block;
        }
        Enhanced_Mobile_Malware {
            action block;
        }
        Enhanced_Parked_Domain {
            action block;
        }
        Enhanced_Phishing_and_Other_Frauds {
            action block;
        }
        Enhanced_Proxy_Avoidance {
            action block;
        }
        Enhanced_Spyware {
            action block;
        }
        Enhanced_Abused_Drugs {
            action log-and-permit;
        }
        Enhanced_Alcohol_and_Tobacco {
            action log-and-permit;
        }
        Enhanced_Drugs {
            action log-and-permit;
        }
        Enhanced_Gambling {
            action log-and-permit;
        }
        Enhanced_Games {
            action log-and-permit;
        }
        Enhanced_Hacking {
            action log-and-permit;
        }
        Enhanced_Illegal_or_Questionable {
            action log-and-permit;
        }
        Enhanced_Nudity {
            action log-and-permit;
        }
        Enhanced_Racism_and_Hate {
            action log-and-permit;
        }
        Enhanced_Sex {
            action log-and-permit;
        }
    }
    default permit;
    fallback-settings {
        default log-and-permit;
        server-connectivity block;
        timeout block;
        too-many-requests block;
    }
}

In case a URL does not have a category assigned but only a Web Reputation Score (WBRS) we can define an action based on that score.

Note – the scores are weighted as follows:

  • 100-90–Site is considered very safe.
  • 80-89–Site is considered moderately safe.
  • 70-79–Site is considered fairly safe.
  • 60-69–Site is considered suspicious.
  • 0-59–Site is considered harmful.
[edit security utm feature-profile web-filtering juniper-enhanced profile WF-DefaultInternetAccess site-reputation-action]
root@NP-vSRX# show
very-safe permit;
moderately-safe permit;
fairly-safe log-and-permit;
suspicious quarantine;
harmful block;

For some special cases, in which the device might not be able to process the HTTP request, we can define fallback options. This basically equates to a fail-open/fail-closed decision.

[edit security utm feature-profile web-filtering juniper-enhanced profile WF-DefaultInternetAccess fallback-settings]
root@NP-vSRX# show
default log-and-permit;
server-connectivity block;
timeout block;
too-many-requests block;

With most pieces in place, the full web-filtering profile looks like this:

[edit security utm feature-profile]
root@NP-vSRX# show
web-filtering {
    url-whitelist EWF-Whitelist;
    url-blacklist EWF-Blacklist;
    type juniper-enhanced;
    juniper-enhanced {
        cache;
        server {
            host rp.cloud.threatseeker.com;
            port 80;
        }
        profile WF-DefaultInternetAccess {
            category {
                Enhanced_Adult_Content {
                    action block;
                }
                Enhanced_Adult_Material {
                    action block;
                }
                Enhanced_Advanced_Malware_Command_and_Control {
                    action block;
                }
                Enhanced_Advanced_Malware_Payloads {
                    action block;
                }
                Enhanced_Bot_Networks {
                    action block;
                }
                Enhanced_Dynamic_DNS {
                    action block;
                }
                Enhanced_Emerging_Exploits {
                    action block;
                }
                Enhanced_Keyloggers {
                    action block;
                }
                Enhanced_Malicious_Embedded_Link {
                    action block;
                }
                Enhanced_Malicious_Embedded_iFrame {
                    action block;
                }
                Enhanced_Malicious_Web_Sites {
                    action block;
                }
                Enhanced_Mobile_Malware {
                    action block;
                }
                Enhanced_Parked_Domain {
                    action block;
                }
                Enhanced_Phishing_and_Other_Frauds {
                    action block;
                }
                Enhanced_Proxy_Avoidance {
                    action block;
                }
                Enhanced_Spyware {
                    action block;
                }
                Enhanced_Abused_Drugs {
                    action log-and-permit;
                }
                Enhanced_Alcohol_and_Tobacco {
                    action log-and-permit;
                }
                Enhanced_Drugs {
                    action log-and-permit;
                }
                Enhanced_Gambling {
                    action log-and-permit;
                }
                Enhanced_Games {
                    action log-and-permit;
                }
                Enhanced_Hacking {
                    action log-and-permit;
                }
                Enhanced_Illegal_or_Questionable {
                    action log-and-permit;
                }
                Enhanced_Nudity {
                    action log-and-permit;
                }
                Enhanced_Racism_and_Hate {
                    action log-and-permit;
                }
                Enhanced_Sex {
                    action log-and-permit;
                }
            }
            site-reputation-action {
                very-safe permit;
                moderately-safe permit;
                fairly-safe log-and-permit;
                suspicious quarantine;
                harmful block;
            }
            default permit;
            fallback-settings {
                default log-and-permit;
                server-connectivity block;
                timeout block;
                too-many-requests block;
            }
        }
    }
}

Next, we need configure a new UTM policy which includes the Enhanced Web Filtering feature. This can be combined with other UTM features such as Sophos anti-virus or content filtering.

[edit security utm]
root@NP-vSRX# set utm-policy UTM-DefaultInternetAccess web-filtering http-profile WF-DefaultInternetAccess

The last step is to attach the UTM profile to a security policy by configuring the application-services action.

[edit security policies from-zone internal-np to-zone internal-transit policy FW-Internal-PermitAll]
root@NP-vSRX# show
match {
    source-address any;
    destination-address any;
    application any;
}
then {
    permit {
        application-services {
            utm-policy UTM-DefaultInternetAccess;
        }
    }
}

Configuring logging

To make webfilter troubleshooting easier, configure the following syslog files, or alternatively send them to a syslog server.

[edit system syslog]
root@NP-vSRX# show
file blocked-sites {
    any any;
    match WEBFILTER_URL_BLOCKED;
}
file allowed-sites {
    any any;
    match WEBFILTER_URL_PERMITTED;
}

Testing

Testing the custom blacklist by browsing to sex.com – HTTPS session was broken (based on destination IP) and the browser returned an error.

Oct 13 14:21:14  NP-vSRX RT_UTM: WEBFILTER_URL_BLOCKED: WebFilter: ACTION="URL Blocked" 10.255.1.13(50278)->206.125.164.82(443) CATEGORY="EWF-Blacklist" REASON="BY_BLACK_LIST" PROFILE="WF-DefaultInternetAccess" URL=206.125.164.82 OBJ=/ username N/A roles N/A

Next, we test the URL in the whitelist (which was actually be blocked by Websense). Networking-forums loads fine now and we have this in the log:

Oct 13 14:23:43  NP-vSRX RT_UTM: WEBFILTER_URL_PERMITTED: WebFilter: ACTION="URL Permitted" 10.255.1.13(50303)->64.90.58.116(443) CATEGORY="EWF-Whitelist" REASON="BY_WHITE_LIST" PROFILE="WF-DefaultInternetAccess" URL=64.90.58.116 OBJ=/ username N/A roles N/A

As a last test, we initiate an HTTP session to http://www.penthouse.com
In the browser, we get the following message:

Juniper Networks Firewall has blocked the URL: 10.255.1.13(62175)->64.59.126.214(80) www.penthouse.com/ CATEGORY: Enhanced_Adult_Content REASON: BY_PRE_DEFINED

And in the syslog file, it looks like this:

Oct 13 14:33:29  NP-vSRX RT_UTM: WEBFILTER_URL_BLOCKED: WebFilter: ACTION="URL Blocked" 10.255.1.13(62175)->64.59.126.214(80) CATEGORY="Enhanced_Adult_Content" REASON="BY_PRE_DEFINED" PROFILE="WF-DefaultInternetAccess" URL=www.penthouse.com OBJ=/ username N/A roles N/A

Verification Commands

To check connectivity between your SRX and the Juniper Websense server:

root@NP-vSRX> show security utm web-filtering status
 UTM web-filtering status:
    Server status: Juniper Enhanced using Websense server UP

Web-filtering statistics – this is useful when the service is not working as expected.

root@NP-vSRX> show security utm web-filtering statistics
 UTM web-filtering statistics:
    Total requests:                     17086
    white list hit:                     20
    Black list hit:                     20
    No license permit:                  0
    Queries to server:                  6472
    Server reply permit:                1868
    Server reply block:                 9
    Server reply quarantine:            0
    Server reply quarantine block:      0
    Server reply quarantine permit:     0
    Custom category permit:             0
    Custom category block:              0
    Custom category quarantine:         0
    Custom category qurantine block:    0
    Custom category quarantine permit:  0
    Site reputation permit:             10597
    Site reputation block:              2495
    Site reputation quarantine:         49
    Site reputation quarantine block:   0
    Site reputation quarantine permit:  1170
    Site reputation by Category         0
    Site reputation by Global           14311
    Cache hit permit:                   847
    Cache hit block:                    11
    Cache hit quarantine:               0
    Cache hit quarantine block:         0
    Cache hit quarantine permit:        0
    Safe-search redirect:               0
    Web-filtering sessions in total:    128000
    Web-filtering sessions in use:      2
    Fallback:                       log-and-permit           block
          Default                                 0               0
          Timeout                                 0               0
     Connectivity                                 0               0
Too-many-requests                                 0               0

That’s pretty much all there is to it for a basic EWF setup. There are many more nerdknobs you can tune but I’ll stick to the basics for my JNCIP-SEC studies.

Bear in mind that the URL filter only works for HTTP traffic and most of the web these day is on SSL and using CDN networks, so it’s very hard to get a good match on SSL traffic. This can be solved by using SSL Forward Proxy or relying more on Layer-7 AppID with custom application signatures.

Sources:

Juniper Enhanced Web Filtering feature guide.

Virtual Chassis on EX2200 switches

The Juniper Virtual Chassis technology allows you to combine multiple physical switches into one logical switch stack, which reduces the management overhead of dealing with many switches. Because all members are acting as a single device, with a proprietary control protocol underneath, there is no need for Spanning Tree and its blocked links. It also has dual routing engine support, albeit with some feature limitations on the EX2200 platform.

Unlike the high-end Juniper switches, the EX2200 does not have dedicated virtual-chassis ports either, so you are limited to using the on-board ethernet ports. The cross-member bandwidth should be OK for basic access deployments though, so here’s how to set it up.

First, gather the serial numbers of all your switches. There are several commands that will show you the serial. I’ve used show chassis hardware

root> show chassis hardware
Hardware inventory:
Item             Version  Part number  Serial number     Description
Chassis                                CW0210160462      EX2200-24T-4G
Routing Engine 0 REV 11   750-026468   CW0210160462      EX2200-24T-4G
FPC 0            REV 11   750-026468   CW0210160462      EX2200-24T-4G
  CPU                     BUILTIN      BUILTIN           FPC CPU
  PIC 0                   BUILTIN      BUILTIN           24x 10/100/1000 Base-T
  PIC 1          REV 11   750-026468   CW0210160462      4x GE SFP
Power Supply 0                                           PS 100W AC
Fan Tray                                                 Fan Tray

Do this for all your switches and copy them to notepad. You will need them later. Mine are indicated on the diagram below.

EX2200 Virtual Chassis Topology

Next, we need to configure our Ethernet ports for virtual-chassis functionality. The EX2200 does not have dedicated VCP ports so we need to convert some ethernet ports. As shown on the drawing, I will use the last four ports on each switch. To activate the ports for VC functionality, enter the following commands.

{master:0}
root> request virtual-chassis vc-port set pic-slot 0 port 20

{master:0}
root> request virtual-chassis vc-port set pic-slot 0 port 21

{master:0}
root> request virtual-chassis vc-port set pic-slot 0 port 22

{master:0}
root> request virtual-chassis vc-port set pic-slot 0 port 23

Rinse and repeat on switch two and three. You can verify the ports were added correctly to the virtual chassis with the following command.

root> show virtual-chassis vc-port
fpc0:
--------------------------------------------------------------------------
Interface   Type              Trunk  Status       Speed        Neighbor
or                             ID                 (mbps)       ID  Interface
PIC / Port
0/20        Configured         -1    Down         1000
0/21        Configured         -1    Down         1000
0/22        Configured         -1    Down         1000
0/23        Configured         -1    Down         1000

Before we can move on to connecting the cables, we have to set up the virtual chassis parameters on our primary routing engine.

We will set up the virtual-chassis in pre-provisioned mode, where we manually tie the serial ids to the member id. The first two switches will be configured as routing engines, one master and one backup, and the last switch will serve as a dumb old line-card. In my case, the virtual chassis configuration on routing engine 0 looks like this:

{master:0}[edit virtual-chassis]
root# show
preprovisioned;
member 0 {
    role routing-engine;
    serial-number CW0210160462;
}
member 1 {
    role routing-engine;
    serial-number CW0210300705;
}
member 2 {
    role line-card;
    serial-number CW0210300694;
}

Now that this is set up, I have connected the cables and the virtual chassis has formed. You can verify VC state and inter-switch connectivity using the show virtual-chassis status command.

root> show virtual-chassis status

Preprovisioned Virtual Chassis
Virtual Chassis ID: fd81.5b7b.172c
Virtual Chassis Mode: Enabled
                                           Mstr           Mixed Neighbor List
Member ID  Status   Serial No    Model     prio  Role      Mode ID  Interface
0 (FPC 0)  Prsnt    CW0210160462 ex2200-24t-4g 129 Master*   NA  1  vcp-255/0/20
                                                                 1  vcp-255/0/21
                                                                 2  vcp-255/0/22
                                                                 2  vcp-255/0/23
1 (FPC 1)  Prsnt    CW0210300705 ex2200-24t-4g 129 Backup    NA  2  vcp-255/0/20
                                                                 2  vcp-255/0/21
                                                                 0  vcp-255/0/22
                                                                 0  vcp-255/0/23
2 (FPC 2)  Prsnt    CW0210300694 ex2200-24t-4g   0 Linecard  NA  0  vcp-255/0/20
                                                                 0  vcp-255/0/21
                                                                 1  vcp-255/0/22
                                                                 1  vcp-255/0/23

This command shows us the IDs, serials and roles of all the members. The far-right columns also show on which ports the neighbours are detected. You can use this to verify everything is properly cabled up.

A quick terse command also shows us all interfaces in the stack are available, except for the ones we dedicated as VCP ports.

root> show interfaces terse | no-more
Interface               Admin Link Proto    Local                 Remote
vcp-255/0/20            up    up
vcp-255/0/20.32768      up    up
vcp-255/0/21            up    up
vcp-255/0/21.32768      up    up
vcp-255/0/22            up    up
vcp-255/0/22.32768      up    up
vcp-255/0/23            up    up
vcp-255/0/23.32768      up    up
ge-0/0/0                up    down
ge-0/0/0.0              up    down eth-switch
ge-0/0/1                up    down
ge-0/0/1.0              up    down eth-switch
ge-0/0/2                up    down
ge-0/0/2.0              up    down eth-switch
ge-0/0/3                up    down
ge-0/0/3.0              up    down eth-switch
ge-0/0/4                up    down
ge-0/0/4.0              up    down eth-switch
ge-0/0/5                up    down
ge-0/0/5.0              up    down eth-switch
ge-0/0/6                up    down
ge-0/0/6.0              up    down eth-switch
ge-0/0/7                up    down
ge-0/0/7.0              up    down eth-switch
ge-0/0/8                up    down
ge-0/0/8.0              up    down eth-switch
ge-0/0/9                up    down
ge-0/0/9.0              up    down eth-switch
ge-0/0/10               up    down
ge-0/0/10.0             up    down eth-switch
ge-0/0/11               up    down
ge-0/0/11.0             up    down eth-switch
ge-0/0/12               up    down
ge-0/0/12.0             up    down eth-switch
ge-0/0/13               up    down
ge-0/0/13.0             up    down eth-switch
ge-0/0/14               up    down
ge-0/0/14.0             up    down eth-switch
ge-0/0/15               up    down
ge-0/0/15.0             up    down eth-switch
ge-0/0/16               up    down
ge-0/0/16.0             up    down eth-switch
ge-0/0/17               up    down
ge-0/0/17.0             up    down eth-switch
ge-0/0/18               up    down
ge-0/0/18.0             up    down eth-switch
ge-0/0/19               up    down
ge-0/0/19.0             up    down eth-switch
ge-1/0/0                up    down
ge-1/0/0.0              up    down eth-switch
ge-1/0/1                up    down
ge-1/0/1.0              up    down eth-switch
ge-1/0/2                up    down
ge-1/0/2.0              up    down eth-switch
ge-1/0/3                up    down
ge-1/0/3.0              up    down eth-switch
ge-1/0/4                up    down
ge-1/0/4.0              up    down eth-switch
ge-1/0/5                up    down
ge-1/0/5.0              up    down eth-switch
ge-1/0/6                up    down
ge-1/0/6.0              up    down eth-switch
ge-1/0/7                up    down
ge-1/0/7.0              up    down eth-switch
ge-1/0/8                up    down
ge-1/0/8.0              up    down eth-switch
ge-1/0/9                up    down
ge-1/0/9.0              up    down eth-switch
ge-1/0/10               up    down
ge-1/0/10.0             up    down eth-switch
ge-1/0/11               up    down
ge-1/0/11.0             up    down eth-switch
ge-1/0/12               up    down
ge-1/0/12.0             up    down eth-switch
ge-1/0/13               up    down
ge-1/0/13.0             up    down eth-switch
ge-1/0/14               up    down
ge-1/0/14.0             up    down eth-switch
ge-1/0/15               up    down
ge-1/0/15.0             up    down eth-switch
ge-1/0/16               up    down
ge-1/0/16.0             up    down eth-switch
ge-1/0/17               up    down
ge-1/0/17.0             up    down eth-switch
ge-1/0/18               up    down
ge-1/0/18.0             up    down eth-switch
ge-1/0/19               up    down
ge-1/0/19.0             up    down eth-switch
ge-2/0/0                up    down
ge-2/0/0.0              up    down eth-switch
ge-2/0/1                up    down
ge-2/0/1.0              up    down eth-switch
ge-2/0/2                up    down
ge-2/0/2.0              up    down eth-switch
ge-2/0/3                up    down
ge-2/0/3.0              up    down eth-switch
ge-2/0/4                up    down
ge-2/0/4.0              up    down eth-switch
ge-2/0/5                up    down
ge-2/0/5.0              up    down eth-switch
ge-2/0/6                up    down
ge-2/0/6.0              up    down eth-switch
ge-2/0/7                up    down
ge-2/0/7.0              up    down eth-switch
ge-2/0/8                up    up
ge-2/0/8.0              up    up   eth-switch
ge-2/0/9                up    down
ge-2/0/9.0              up    down eth-switch
ge-2/0/10               up    down
ge-2/0/10.0             up    down eth-switch
ge-2/0/11               up    down
ge-2/0/11.0             up    down eth-switch
ge-2/0/12               up    down
ge-2/0/12.0             up    down eth-switch
ge-2/0/13               up    down
ge-2/0/13.0             up    down eth-switch
ge-2/0/14               up    down
ge-2/0/14.0             up    down eth-switch
ge-2/0/15               up    down
ge-2/0/15.0             up    down eth-switch
ge-2/0/16               up    down
ge-2/0/16.0             up    down eth-switch
ge-2/0/17               up    down
ge-2/0/17.0             up    down eth-switch
ge-2/0/18               up    down
ge-2/0/18.0             up    down eth-switch
ge-2/0/19               up    down
ge-2/0/19.0             up    down eth-switch
bme0                    up    up
bme0.32768              up    up   inet     128.0.0.1/2
                                            128.0.0.16/2
                                            128.0.0.32/2
                                   tnp      0x10
bme0.32770              down  up   eth-switch
bme0.32771              down  up   eth-switch
dsc                     up    up
gre                     up    up
ipip                    up    up
lo0                     up    up
lo0.16384               up    up   inet     127.0.0.1           --> 0/0
lsi                     up    up
me0                     up    down
me0.0                   up    down inet
mtun                    up    up
pimd                    up    up
pime                    up    up
tap                     up    up
vlan                    up    up
vlan.0                  up    up   inet     192.168.1.1/24
vme                     up    down

We can login to other chassis member for troubleshooting by using the following command. When you log in to a line card JunOS will alert you that it shouldn’t be used for configuration.

root> request session member 2

--- JUNOS 12.3R11.2 built 2015-09-24 11:14:53 UTC
root@:LC:2%
root@:LC:2% cli
warning: This chassis is operating in a non-master role as part of a virtual-chassis (VC) system.
warning: Use of interactive commands should be limited to debugging and VC Port operations.
warning: Full CLI access is provided by the Virtual Chassis Master (VC-M) chassis.
warning: The VC-M can be identified through the show virtual-chassis status command executed at this console.
warning: Please logout and log into the VC-M to use CLI.
{linecard:2}
root>

The out of band management interface, on the back of the switches, can use the same shared IP address across all VC members. To do so, you need to configure the vme interface with the desired management IP. In the background, all member’s management ports (otherwise known as me interfaces) are added to a special management VLAN which is tied to the layer3 vme interface.

{master:0}[edit interfaces]
root# show vme
unit 0 {
    family inet {
        address 10.6.66.25/24;
    }
}

All physical management interfaces can be connected to the OOB management VLAN, and the virtual chassis can respond to ARP requests on all of them.

Note – the VME interface will not work if you already have conflicting configuration on the me interface.

Because we have two routing engines, it’s also recommended to configure the commit synchronize option. When the configuration is committed on the primary routing engine, it will copy over to the backup routing engine. Both routing engines will then validate and activate the new configuration during the commit operation.

{master:0}[edit]
root# set system commit synchronize

Under the hood, the switches are running VCCP, a Juniper proprietary protocol largely based on IS-IS. If you’re interested, you can verify much of the protocol state from the command line, but I won’t go into detail.

root> show virtual-chassis protocol ?
Possible completions:
  adjacency            Show virtual chassis adjacency database
  database             Show virtual chassis link-state database
  interface            Show virtual chassis protocol interface information
  route                Show virtual chassis routing table
  statistics           Show virtual chassis performance statistics

Quoting Juniper here, “most high availability features, including Graceful Routing Engine switchover (GRES), Nonstop bridging (NSB), Nonstop active routing (NSR), and Nonstop software upgrade (NSSU), are not supported on an EX2200 Virtual Chassis.” Therefore, I would not rely an EX2200 virtual chassis as a core switch HA solution.. It does make sense using EX2200 virtual chassis in the access layer though, for simplified management and cross-switch etherchannel connectivity.

Removing Virtual-Chassis Configuration

A switch that was previously member of a virtual chassis may give you some headache when you’re trying to use it as a standard switch again. For example, VC ports can not be returned to their original state, or you might see that it stays in the previous role, even though you’ve removed the configuration. Here’s what seems to work for me.

If you haven’t done so, delete all virtual-chassis configuration

{linecard:2}[edit]
root# delete virtual-chassis
root# commit
warning: Could not connect to fpc0 : Can't assign requested address
warning: Cannot connect to other RE, ignoring it
commit complete

Go into shell mode (start shell) and delete all virtual chassis configuration files.

root@:LC:0% cd /config/vchassis/
root@:LC:0% ls
vc.db                   vc.tlv.db.0             vclocal.conf.tlv
vc.param                vc.tlv.db.1             vclocal.conf.tlv.0
vc.tlv.db               vclocal.conf            vclocal.conf.tlv.1
root@:LC:0% rm *.*

Then, return to operational mode with the cli command and do a system reboot to flush all stale virtual-chassis configuration from memory.

After the reboot, the switch will be in the default state again

Amnesiac (ttyu0)

login: root
Password:

--- JUNOS 12.3R11.2 built 2015-09-24 11:14:53 UTC
root@:RE:0% cli
{master:0}
root> show virtual-chassis

Virtual Chassis ID: 7c29.6cd0.a3b3
Virtual Chassis Mode: Enabled
                                           Mstr           Mixed Neighbor List
Member ID  Status   Serial No    Model     prio  Role      Mode ID  Interface
0 (FPC 0)  Prsnt    CW0210300694 ex2200-24t-4g 128 Master*   NA

Member ID for next new member: 1 (FPC 1)

{master:0}
root> show virtual-chassis vc-port
fpc0:
--------------------------------------------------------------------------

{master:0}

Any questions or comments? Feel free to add them below!

JNCIS-ENT – OSPF LSA types on JunOS

Going through the JNCIS-ENT course, I realized that I had forgotten so much of the details about the different LSA types and all of its intricacies. Next to being able to answer trick exam questions, knowing the LSAs and their working helps a lot when dealing with complex OSPF problems or optimizing your network topologies. As I really needed a refresher for this exam and my upcoming NP refresh I created this simple topology and tried to document as much of my findings as possible.

Lab Topology

OSPF Topology

We have four routers interconnected via OSPF. The area configuration is as follows.

  • vMX1 – RID 1.1.1.1 – connected to area 12
  • vMX2 – RID 2.2.2.2 – connected to area 12 and backbone area 0
  • vMX3 – RID 3.3.3.3 – connected to backbone area 0 and area 34
  • vMX4 – RID 4.4.4.4 – connected to area 34

Below is the standard configuration that is running on router VMX2 – Router ID, area statements and active interfaces. The other routers have similar configuration for their respective interfaces and areas.

[edit]
root@vMX2# show
routing-options {
    router-id 2.2.2.2;
}
protocols {
    ospf {
        area 0.0.0.0 {
            interface ge-0/0/0.0;
            interface lo0.0 {
                passive;
            }
        }
        area 0.0.0.12 {
            interface ge-0/0/1.0;
        }
    }
}

For now, until we move on to the Type 7 LSA, all areas are configured as standard areas. Before we start, here is an output of the LSA database on router VMX2. As it’s connected to two areas, it’s keeping two LSDBs. We’ll be using this router’s database for the first set of LSAs.

root@vMX2> show ospf database

    OSPF database, Area 0.0.0.0
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Router  *2.2.2.2          2.2.2.2          0x80000180  2034  0x22 0x4d8   48
Router   3.3.3.3          3.3.3.3          0x8000017f  2044  0x22 0x1ab6  48
Network  172.16.23.3      3.3.3.3          0x8000017b  1794  0x22 0x7651  32
Summary *1.1.1.1          2.2.2.2          0x80000070  1784  0x22 0x4a76  28
Summary  4.4.4.4          3.3.3.3          0x80000001    53  0x22 0x809f  28
Summary *172.16.12.0      2.2.2.2          0x8000017c  1034  0x22 0x539b  28
Summary  172.16.34.0      3.3.3.3          0x8000017d  1544  0x22 0x4093  28

    OSPF database, Area 0.0.0.12
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Router   1.1.1.1          1.1.1.1          0x80000073   253  0x22 0xd03   48
Router  *2.2.2.2          2.2.2.2          0x80000074   784  0x22 0xe0b   36
Network *172.16.12.2      2.2.2.2          0x80000071   534  0x22 0xda10  32
Summary *2.2.2.2          2.2.2.2          0x80000071   284  0x22 0x10ac  28
Summary *3.3.3.3          2.2.2.2          0x80000071    34  0x22 0xebcb  28
Summary *4.4.4.4          2.2.2.2          0x80000001    52  0x22 0xa87a  28
Summary *172.16.23.0      2.2.2.2          0x80000070  2784  0x22 0xf4fb  28
Summary *172.16.34.0      2.2.2.2          0x80000070  2534  0x22 0x855f  28

LSA Type 1 – Router LSA

The first LSA type is generated by every router participating in OSPF and lists all of the router’s links together with their associated cost, as well the OSPF neigbhours it has inside the area. Every router will flood a Router LSA for each area it is active in.

Looking at our OSPF database from before, router 2.2.2.2 has received a router LSA from router 1.1.1.1 and router 3.3.3.3 (Adv Rtr). Those LSAs are only seen in their respective areas, which demonstrates that a router LSA never leaves an area. We can further drill down to display only routers LSAs with the following command.

root@vMX2> show ospf database router

    OSPF database, Area 0.0.0.0
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Router  *2.2.2.2          2.2.2.2          0x80000181   149  0x22 0x2d9   48
Router   3.3.3.3          3.3.3.3          0x80000180    37  0x22 0x18b7  48

    OSPF database, Area 0.0.0.12
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Router   1.1.1.1          1.1.1.1          0x80000073  1174  0x22 0xd03   48
Router  *2.2.2.2          2.2.2.2          0x80000074  1705  0x22 0xe0b   36

If we want to get more specific and view the contents of the actual LSA, we can do so by specifying the LSA ID and adding the extensive command. Let’s see what router 1.1.1.1 is telling us about itself.

root@vMX2> show ospf database router lsa-id 1.1.1.1 extensive

    OSPF database, Area 0.0.0.12
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Router   1.1.1.1          1.1.1.1          0x80000073  1274  0x22 0xd03   48
  bits 0x0, link count 2
  id 172.16.12.2, data 172.16.12.1, Type Transit (2)
    Topology count: 0, Default metric: 1
  id 1.1.1.1, data 255.255.255.255, Type Stub (3)
    Topology count: 0, Default metric: 0
  Topology default (ID 0)
    Type: Transit, Node ID: 172.16.12.2
      Metric: 1, Bidirectional
  Aging timer 00:38:45
  Installed 00:21:13 ago, expires in 00:38:46, sent 3d 19:45:06 ago
  Last changed 00:21:13 ago, Change count: 4

The router is advertising its two links in the LSA (link count 2). The LSA identifier is the originating router’s RID. The first link is an OSPF type Transit where it has a neighbourship with router 172.16.12.2 (data). If we configured the interface-type to p2p, we would see this as the link type. The router also has a Stub link with prefix 1.1.1.1/32, which means that this network contains only one router.

LSA Type 2 – Network LSA

The second LSA type is the Network LSA, which is generated by the Designated Router on a multi-access (broadcast or non-broadcast) segment. It lists all of the routers connected to the segment. It is generated only by the Designated Router to prevent duplicate LSAs.

Our router 2.2.2.2 has received the following network LSAs in area 12:

root@vMX2> show ospf database area 0.0.0.12 network

    OSPF database, Area 0.0.0.12
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Network *172.16.12.2      2.2.2.2          0x8000001b  2085  0x22 0x87b9  32

Drilling down on this particular LSA, it contains the following information:

root@vMX2> ... 0.0.0.12 network lsa-id 172.16.12.2 extensive

    OSPF database, Area 0.0.0.12
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Network *172.16.12.2      2.2.2.2          0x8000001b  2099  0x22 0x87b9  32
  mask 255.255.255.0
  attached router 2.2.2.2
  attached router 1.1.1.1
  Topology default (ID 0)
    Type: Transit, Node ID: 1.1.1.1
      Metric: 0, Bidirectional
    Type: Transit, Node ID: 2.2.2.2
      Metric: 0, Bidirectional
  Gen timer 00:15:01
  Aging timer 00:25:01
  Installed 00:34:59 ago, expires in 00:25:01, sent 00:34:57 ago
  Last changed 22:03:21 ago, Change count: 1, Ours

From this LSA, we can tell that the network has a /24 mask and that it has router 1.1.1.1 and 2.2.2.2 attached to it. It does not include a cost or metric for the routers, because from the network’s point of view, the cost to the attached routers is zero. If we wanted to know more information about a particular router, we can use the attached router ID which in turn refers to the router LSA we looked at earlier.

LSA Type 3 – Network Summary

This LSA type is generated by Area Border Routers and flooded into a particular area to represent destinations outside of the area. In the opposite direction, the ABR will also advertise prefixes from a non-backbone area back into backbone area 0 with a network LSA. They are flooded into areas where the destination prefix was not found. One thing worth noting is that this only counts for inter-area destinations learned inside the OSPF AS. Routes external to OSPF will use a different LSA type which I’ll cover later.

Again, we will view the contents of router 2.2.2.2’s database for area 12.

root@vMX2> show ospf database area 0.0.0.12 netsummary

    OSPF database, Area 0.0.0.12
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Summary *2.2.2.2          2.2.2.2          0x800000ae  2289  0x22 0x95e9  28
Summary *3.3.3.3          2.2.2.2          0x800000ae  1689  0x22 0x7109  28
Summary *4.4.4.4          2.2.2.2          0x8000003e  1989  0x22 0x2eb7  28
Summary *172.16.23.0      2.2.2.2          0x800000ae  1389  0x22 0x783a  28
Summary *172.16.34.0      2.2.2.2          0x800000ae  1089  0x22 0x99d   28

Router 2.2.2.2, as the area border router, has generated these LSAs itself (*) and flooded them into area 12. Comparing this to the diagram and the full LSA database, we can tell that it has created network summaries for Router, Network and Summary LSAs inside area 0.

root@vMX2>show ospf database area 12 netsummary lsa-id 172.16.34.0 extensive

    OSPF database, Area 0.0.0.12
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Summary *172.16.34.0      2.2.2.2          0x800000ae  1527  0x22 0x99d   28
  mask 255.255.255.0
  Topology default (ID 0) -> Metric: 2
  Gen timer 00:24:33
  Aging timer 00:34:33
  Installed 00:25:27 ago, expires in 00:34:33, sent 00:25:25 ago
  Last changed 5d 22:58:56 ago, Change count: 2, Ours

The LSA ID matches the destination network’s prefix. In this case, router R2 knows about the network 172.16.34.0/24 and added a cost of 2 to reach it. Router 1.1.1.1 will add this value to its own cost to ABR 2.2.2.2 to determine the ultimate cost for the route.

LSA Type 4 – ASBR Summary

When a router is advertising routes from sources external to the OSPF AS, it is called an Autonomous System Border Router (ASBR). Like any other router, it will generate a router LSA for itself (Type 1) into its own area but with a special flag E set. When this LSA is received by the other ABR, the router LSA will be converted into a Type 4 LSA when it is flooded into other areas. The LSA is flooded throughout the entire OSPF Autonomous System and lets other routers know how to reach the ASBR.

To demonstrate, I have configured router 4.4.4.4 to redistribute route 10.4.0.0/24 from its loopback interface as an external route. First, define the export policy as a policy-statement.

root@vMX4# show policy-options
policy-statement redist-direct {
    term term1 {
        from {
            protocol direct;
            interface lo0.0;
        }
        then accept;
    }
}

Then, configure OSPF to use that statement as its export policy.

root@vMX4# show protocols ospf
export redist-direct;
area 0.0.0.34 {
    interface ge-0/0/0.0;
}

We will now see an external route for 10.4.0.0/24, and an ASBR summary for 4.4.4.4 in the database on router 2.2.2.2

root@vMX2> show ospf database area 12

    OSPF database, Area 0.0.0.12
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Router   1.1.1.1          1.1.1.1          0x800000b6  2563  0x22 0x8646  48
Router  *2.2.2.2          2.2.2.2          0x800000b8   559  0x22 0x854f  36
Network *172.16.12.2      2.2.2.2          0x8000001d   259  0x22 0x83bb  32
Summary *2.2.2.2          2.2.2.2          0x800000af  2359  0x22 0x93ea  28
Summary *3.3.3.3          2.2.2.2          0x800000af  1759  0x22 0x6f0a  28
Summary *172.16.23.0      2.2.2.2          0x800000af  1459  0x22 0x763b  28
Summary *172.16.34.0      2.2.2.2          0x800000af  1159  0x22 0x79e   28
ASBRSum *4.4.4.4          2.2.2.2          0x80000001   986  0x22 0x9a87  28
    OSPF AS SCOPE link state database
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Extern   10.4.0.0         4.4.4.4          0x80000001    99  0x22 0xd5be  36

Let’s see what’s inside the ASBR summary…

root@vMX2> ... 12 asbrsummary lsa-id 4.4.4.4 extensive

    OSPF database, Area 0.0.0.12
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
ASBRSum *4.4.4.4          2.2.2.2          0x80000001   177  0x22 0x9a87  28
  mask 0.0.0.0
  Topology default (ID 0) -> Metric: 2
  Gen timer 00:47:03
  Aging timer 00:57:03
  Installed 00:02:57 ago, expires in 00:57:03, sent 00:02:57 ago
  Last changed 00:02:57 ago, Change count: 1, Ours

The LSA ID is the router ID of the ASBR, and router 2.2.2.2 has a cost of 2 to reach it.

For completeness’ sake, the command below shows that the LSA was originally a Type 1 in area 34 before being converted into an ASBR summary by router 3.3.3.3, when flooding it into area 0.

root@vMX3> show ospf database lsa-id 4.4.4.4

    OSPF database, Area 0.0.0.0
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
ASBRSum *4.4.4.4          3.3.3.3          0x80000001  1090  0x22 0x72ac  28

    OSPF database, Area 0.0.0.34
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Router   4.4.4.4          4.4.4.4          0x800000b8  1091  0x22 0x68d   36

LSA Type 5 – AS External LSA

When the ASBR imports routes from outside the Autonomous System, either through static or protocol redistribution, it will flood them into its area as AS External LSAs. This type of LSA is flooded throughout the OSPF topology except for stub areas.

Router 2.2.2.2 has received the external route from ASBR router 4.4.4.4.

root@vMX2> show ospf database area 12 external
    OSPF AS SCOPE link state database
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Extern   10.4.0.0         4.4.4.4          0x80000001   577  0x22 0xd5be  36

The original ASBR’s RID is preserved in the Advertising Router field.

root@vMX2> show ospf database area 12 lsa-id 10.4.0.0 extensive
    OSPF AS SCOPE link state database
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Extern   10.4.0.0         4.4.4.4          0x80000001   675  0x22 0xd5be  36
  mask 255.255.255.0
  Topology default (ID 0)
    Type: 2, Metric: 0, Fwd addr: 0.0.0.0, Tag: 0.0.0.0
  Aging timer 00:48:44
  Installed 00:11:13 ago, expires in 00:48:45, sent 00:11:13 ago
  Last changed 00:11:13 ago, Change count: 1

Router 2.2.2.2 has now learned about the external route 10.4.0.0/24 and will need to recursively use ASBR 4.4.4.4 to reach it. Because the route was injected with the default Type E2, inter-area OSPF link cost is not taken into consideration, and the associated cost is zero as injected by router 4.4.4.4. Before we wrap up on this LSA type, the external route types might need some clarification.

E1 and E2 type routes

External routes or Type 5 LSAs can be imported as either Type 1 or Type 2 routes. When injecting as E2 routes, the autonomous system’s internal cost metrics are not taken into consideration when the LSA is flooded throughout the topology. This the default behaviour and it’s fine in simple stub topologies, but as OSPF is by design a cost-based protocol, using E1 routes makes more sense. This will make the routers combine the route’s original metric with the cost to reach the ASBR (Type 4 LSA), resulting in the total route cost. Let’s demonstrate…

The external route type is configured in the routing-policy. Here’s an example of my export policy before making any changes.

[edit policy-options policy-statement redist-direct]
root@vMX4# show
term term1 {
    from {
        protocol direct;
        interface lo0.0;
    }
    then accept;
}

Now, if we want to set the route as an E1, we define this an action in the policy term. I will import the route with a default cost of 5 and set them as type E1.

[edit policy-options policy-statement redist-direct]
root@vMX4# set term term1 then external type 1

[edit policy-options policy-statement redist-direct]
root@vMX4# set term term1 then metric 5

[edit policy-options policy-statement redist-direct]
root@vMX4# show
term term1 {
    from {
        protocol direct;
        interface lo0.0;
    }
    then {
        metric 5;
        external {
            type 1;
        }
        accept;
    }
}

After a commit, we have the following LSA in our database.

root@vMX2> show ospf database external lsa-id 10.4.0.0 extensive
    OSPF AS SCOPE link state database
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Extern   10.4.0.0         4.4.4.4          0x8000003d    86  0x22 0xcc7   36
  mask 255.255.255.0
  Topology default (ID 0)
    Type: 1, Metric: 5, Fwd addr: 0.0.0.0, Tag: 0.0.0.0
  Aging timer 00:58:33
  Installed 00:01:24 ago, expires in 00:58:34, sent 00:01:24 ago
  Last changed 00:01:24 ago, Change count: 4

The same route is now received as E1 (Type: 1). The cost was injected with a cost of 5 but when we validate in the RIB, we see it has a metric of 7 for the route.

root@vMX2> show route 10.4.0.0 | match metric
10.4.0.0/24        *[OSPF/150] 00:02:09, metric 7, tag 0

This confirms that Total Cost = Cost of Route (5) + Cost to ASBR (2)

LSA Type 7 – NSSA External

When an area is configured as a stub, external routes or Type 5 LSAs will not be allowed in and commonly replaced by one default route. This reduces the LSDB size on the stub routers and keeps the topology simple, but there might be cases where you do need external routes to originate in those stub areas. For these cases, the Not-So-Stubby Area was designed. This allows you to place an ASBR in the stub area and still import external routes, but this time with a special LSA type. When it traverses to the backbone area, the stub-to-backbone ABR will convert the NSSA External LSA into a standard Type-5 External LSA.

To demonstrate, I have converted area 34 to a NSSA on both router 3 and router 4.

root@vMX4# show
export redist-direct;
area 0.0.0.34 {
    nssa;
    interface ge-0/0/0.0;
}

The Type 5 LSA that was previously flooded by router 4.4.4.4 will now be shown as an NSSA External LSA.

root@vMX4> show ospf database

    OSPF database, Area 0.0.0.34
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Router   3.3.3.3          3.3.3.3          0x80000005   227  0x20 0xcc84  36
Router  *4.4.4.4          4.4.4.4          0x80000004   226  0x20 0x8dbc  36
Network *172.16.34.4      4.4.4.4          0x80000002   226  0x20 0x3dee  32
Summary  1.1.1.1          3.3.3.3          0x80000002   227  0x20 0x31fa  28
Summary  2.2.2.2          3.3.3.3          0x80000002   227  0x20 0xf830  28
Summary  3.3.3.3          3.3.3.3          0x80000002   227  0x20 0xc065  28
Summary  172.16.12.0      3.3.3.3          0x80000002   227  0x20 0x5512  28
Summary  172.16.23.0      3.3.3.3          0x80000002   227  0x20 0xd18b  28
NSSA    *10.4.0.0         4.4.4.4          0x80000002   226  0x28 0x2cf7  36

On the last line, we have our Type 7 LSA. Inside it we find the following information…

root@vMX4> show ospf database lsa-id 10.4.0.0 extensive

    OSPF database, Area 0.0.0.34
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
NSSA    *10.4.0.0         4.4.4.4          0x80000002   262  0x28 0x2cf7  36
  mask 255.255.255.0
  Topology default (ID 0)
    Type: 1, Metric: 5, Fwd addr: 172.16.34.4, Tag: 0.0.0.0
  Gen timer 00:45:37
  Aging timer 00:55:37
  Installed 00:04:22 ago, expires in 00:55:38, sent 00:04:22 ago
  Last changed 00:04:22 ago, Change count: 2, Ours

The LSA contents are almost identical to the previous one, except that the router’s LAN IP is now in the Fwd address field.

Hopping back to router 2, we see the same prefix has been received as an External, Type 5, LSA.

root@vMX2> show ospf database lsa-id 10.4.0.0 extensive
    OSPF AS SCOPE link state database
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
Extern   10.4.0.0         3.3.3.3          0x80000002   715  0x22 0xc06f  36
  mask 255.255.255.0
  Topology default (ID 0)
    Type: 1, Metric: 5, Fwd addr: 172.16.34.4, Tag: 0.0.0.0
  Aging timer 00:48:05
  Installed 00:11:52 ago, expires in 00:48:05, sent 00:11:50 ago
  Last changed 00:12:16 ago, Change count: 1

Interestingly, the advertising router is no longer 4.4.4.4 but 3.3.3.3, as this was the one that generated the Type 5 LSA. Because this router is now also acting as an ASBR, it advertised its own Router LSA with the E bit set which is into an ASBR summary LSA by router 2.2.2.2 when it is sent into area 12.

root@vMX2> show ospf database asbrsummary

    OSPF database, Area 0.0.0.12
 Type       ID               Adv Rtr           Seq      Age  Opt  Cksum  Len
ASBRSum *3.3.3.3          2.2.2.2          0x80000001  1006  0x22 0xbe68  28

From the perspective of the other routers, this device is now the source of the external route and the same logic we saw earlier is applied.

There you go, some of the things I’ve learned labbing LSAs. If you have anything to add, or spotted some inaccuracy, I’m always happy to hear in the comments!

Consistent software versions on dual-partition JunOS devices

Modern Junos devices have dual boot partitions, each with their own copy of the operating system. This ensures that the device will boot if storage or other boot-related issues are detected on the primary boot partition.

However, when you manually update the software, it is only updated on one of the partitions which is then set as the boot partition. The second, original, partition will keep running on the previous version until it is manually updated as well. This might be an advantage if you are testing a new software version and want to quickly roll back to the old one. It could also wreak havoc if you are inadvertently falling back to a pre-historic software version that is missing or not compatible with some of the features you’ve since enabled. If you have found a stable software version, it’s best to keep both partitions in sync. Here’s how to do it…

Identifying a software mismatch

The first hint is given at boot time. Right before the login prompt and banner, the console will alert you of the software version disparity.

kern.securelevel: -1 -> 1
Creating JAIL MFS partition...
JAIL MFS partition created
Boot media /dev/ad0 has dual root support


WARNING: JUNOS versions running on dual partitions are not same


** /dev/ad0s1a
FILE SYSTEM CLEAN; SKIPPING CHECKS
clean, 242154 free (34 frags, 30265 blocks, 0.0% fragmentation)

You can also find out from operational mode. The command below will show you the software versions on both of the partitions.

netprobe@netfilter> show system snapshot media internal
Information for snapshot on       internal (/dev/ad0s1a) (backup)
Creation date: Jul 31 11:13:12 2014
JUNOS version on snapshot:
  junos  : 12.1X44-D35.5-domestic
Information for snapshot on       internal (/dev/ad0s2a) (primary)
Creation date: Mar 4 19:53:11 2016
JUNOS version on snapshot:
  junos  : 12.1X46-D40.2-domestic

As you can see from the output, we are currently running on partition /dev/ad0s2a, which has a newer software version than the first partition /dev/ad0s1a.

Cloning the primary partition

To get the software version from our now-primary partition over to the backup, the system will first format the backup partition and then clone the contents. This process is initiated with the command below.

netprobe@netfilter> request system snapshot slice alternate
Formatting alternate root (/dev/ad0s1a)...
Copying '/dev/ad0s2a' to '/dev/ad0s1a' .. (this may take a few minutes)
The following filesystems were archived: /

After the cloning process you might need to reboot the device, depending on the model. If all went well, you will no longer see the warning prompt for version mismatch:

Creating JAIL MFS partition...
JAIL MFS partition created
Boot media /dev/ad0 has dual root support
** /dev/ad0s1a
FILE SYSTEM CLEAN; SKIPPING CHECKS

And voila, the snapshot command will now show the same SW version on both partitions.

netprobe@netfilter> show system snapshot media internal
Information for snapshot on       internal (/dev/ad0s1a) (backup)
Creation date: Mar 4 21:45:37 2016
JUNOS version on snapshot:
  junos  : 12.1X46-D40.2-domestic
Information for snapshot on       internal (/dev/ad0s2a) (primary)
Creation date: Mar 4 21:48:51 2016
JUNOS version on snapshot:
  junos  : 12.1X46-D40.2-domestic

On EX switches, you can alternate between boot partitions by entering this command.

request system reboot slice alternate media internal

Unfortunately this doesn’t seem to work on SRX devices, at least not on the branch devices I’ve worked with so far. If anyone knows how to make this work on these SRXs I would love to hear about it!

JNCIS-SEC – Juniper SRX100 Cluster Configuration

In this post I will go through the basics of cluster configuration on the SRX. I still have a couple of SRX100s laying around, which is perfect to cover the clustering topics of the JNCIS-SEC blueprint!

Before you start configuring the cluster, always verify that both your boxes are on the same software version.

root@FW01A> show system software
Information for junos:

Comment:
JUNOS Software Release [12.1X44-D40.2]

Physical Wiring

Here is how the cluster will be cabled up. Because there’s a lot to remember during the configuration, it’s best to make this sort of diagram before you begin.

SRX100B Cluster Wiring

Connect the fxp1 and Fab ports

The Control link (fxp1) is used to synchronize configuration and performs cluster health checks by sending heartbeat messages. The physical port location depends on the SRX model, and can also be configurable on the high-end models. In my case, on the branch SRX100B, the fe0/0/07 interfaces are predetermined as fxp1.

The fab interface is used to exchange all the session state information between both devices. This provides a stateful failover if anything happens to the primary cluster node. You can choose which interface to assign. I will use fe/0/0/5 so all the first ports stay available.

Setting the Cluster-ID and Node ID

First, wipe all the old configuration and put both devices in cluster mode. Some terminology:

  • The cluster ID ranges from 1 to 15 and uniquely identifies the cluster if you have multiple clusters across the network. I will use Cluster ID 1
  • The node ID identifies both members in the cluster. A cluster will only have two members ever, so the options are 0 and 1

The commands below are entered in operational mode:

root@FW01A> set chassis cluster cluster-id 1 node 0 reboot
Successfully enabled chassis cluster. Going to reboot now
root@FW01B> set chassis cluster cluster-id 1 node 1 reboot
Successfully enabled chassis cluster. Going to reboot now

Keep attention when you enter the commands above. Make sure you are actually enabling the cluster, not disabling it. That would return the following message:

 Successfully disabled chassis cluster. Going to reboot now

Configuring the management interfaces

Once the devices have restarted we can move on to the configuration part.

To get out-of-band access to your firewalls, you really should configure both the members with a managment IP on the fxp0 interface.
All member-specific configuration is applied under the groups node-memmbers stanza. This is also where the hostnames are configured.

{primary:node0}[edit groups]
root@FW01A# show
node0 {
    system {
        host-name FW01A;
    }
    interfaces {
        fxp0 {
            unit 0 {
                family inet {
                    address 192.168.1.1/24;
                }
            }
        }
    }
}
node1 {
    system {
        host-name FW01B;
    }
    interfaces {
        fxp0 {
            unit 0 {
                family inet {
                    address 192.168.1.2/24;
                }
            }
        }
    }
}

On the SRX100B, the fxp0 interface is automatically mapped to the fe0/0/6 interface. Be sure to check the documentation for your specific model.

Apply Group

Before committing, don’t forget to include the command below . This ensures that node-specific config is only applied to that particular node.

{primary:node0}[edit]
root@FW01A# set apply-groups "${node}"

Configuring the fabric interface

The next step is to configure your fabric links, which are used to exchange the session state. Node0 has the fab0 interface and Node1 has the fab1 interface.

{primary:node0}[edit interfaces]
root@FW01A# show
fab0 {
    fabric-options {
        member-interfaces {
            fe-0/0/5;
        }
    }
}
fab1 {
    fabric-options {
        member-interfaces {
            fe-1/0/5;
        }
    }
}

After a commit, we can see both the control and fabric links are up.

root@FW01A# run show chassis cluster interfaces
Control link status: Up

Control interfaces:
    Index   Interface        Status
    0       fxp1             Up

Fabric link status: Up

Fabric interfaces:
    Name    Child-interface    Status
                               (Physical/Monitored)
    fab0    fe-0/0/5           Up   / Up
    fab0
    fab1    fe-1/0/5           Up   / Up
    fab1

Redundant-pseudo-interface Information:
    Name         Status      Redundancy-group
    lo0          Up          0

Configuring the Redundancy Groups

The redundancy group is where you configure the cluster’s failover properties relating to a collection of interfaces or other objects. RG0 is configured by default when you activate the cluster, and manages the redundancy for the routing engines. Let’s create a new RG 1 for our interfaces.

{secondary:node0}[edit chassis]
root@FW01A# show
cluster {
    redundancy-group 0 {
        node 0 priority 100;
        node 1 priority 1;
    }
    redundancy-group 1 {
        node 0 priority 100;
        node 1 priority 1;
    }
}

Configuring Redundant Ethernet interfaces

The reth interfaces are bundles of physical ports across both cluster members. The child interfaces inherit the configuration from the overlying reth interface – think of it as being similar to an 802.3ad Etherchannel. In fact, you can use an Etherchannel to use more than one physical port on each node.

{secondary:node0}[edit chassis cluster]
root@FW01A# set reth-count 2

After entering this command, you can do a quick commit, which will make the reth interfaces visible in the terse command.

root@FW01A# run show interfaces terse | match reth
reth0                   up    down
reth1                   up    down

Now you can configure the reth interfaces as you would with any other interface, give them an IP and assign them to the Redundancy Group.

reth0 is our outside interface, and reth1 is the inside.

{secondary:node0}[edit interfaces]
root@FW01A# show reth0
redundant-ether-options {
    redundancy-group 1;
}
unit 0 {
    family inet {
        address 1.1.1.1/24;
    }
}
{secondary:node0}[edit interfaces]
root@FW01A# show reth1
redundant-ether-options {
    redundancy-group 1;
}
unit 0 {
    family inet {
        address 10.0.0.1/24;
    }
}

When our reths are configured, we can add our physical ports. The fe-0/0/0 (node0) and fe-1/0/0 (node1) will join reth0, fe-0/0/1 and fe-1/0/1 will join reth1.

{secondary:node0}[edit interfaces]
root@FW01A# show
fe-0/0/0 {
    fastether-options {
        redundant-parent reth0;
    }
}
fe-0/0/1 {
    fastether-options {
        redundant-parent reth1;
    }
}
fe-1/0/0 {
    fastether-options {
        redundant-parent reth0;
    }
}
fe-1/0/1 {
    fastether-options {
        redundant-parent reth1;
    }
}

Interface monitoring

We can use interface monitoring to subtract a predetermined priority value off our redundancy group priority, when a link goes physically down.

For example, node0 is primary for RG1 with a priority of 100. If we add an interface-monitor value of anything higher than 100 to the physical interface, the link-down event will cause to priority to drop to zero and trigger the failover. Configuration is applied at the redundancy-groups:

{primary:node0}[edit chassis cluster]
root@FW01A# show
reth-count 2;
redundancy-group 0 {
    node 0 priority 100;
    node 1 priority 1;
}
redundancy-group 1 {
    node 0 priority 100;
    node 1 priority 1;
    preempt;
    gratuitous-arp-count 5;
    interface-monitor {
        fe-0/0/0 weight 255;
        fe-0/0/1 weight 255;
        fe-1/0/0 weight 255;
        fe-1/0/1 weight 255;
    }
}

Finally, we add the interfaces to security zones.

root@FW01A# show security zones
security-zone untrust {
    interfaces {
        reth0.0;
    }
}
security-zone trust {
    host-inbound-traffic {
        system-services {
            ping;
        }
    }
    interfaces {
        reth1.0;
    }
}

Verification

After cabling it up, we can verify that the cluster is fully operational.

root@FW01A> show chassis cluster status
Cluster ID: 1
Node                  Priority          Status    Preempt  Manual failover

Redundancy group: 0 , Failover count: 0
    node0                   100         primary        no       no
    node1                   1           secondary      no       no

Redundancy group: 1 , Failover count: 0
    node0                   100         primary        yes      no
    node1                   1           secondary      yes      no
root@FW01A> show chassis cluster interfaces
Control link status: Up

Control interfaces:
    Index   Interface        Status
    0       fxp1             Up

Fabric link status: Up

Fabric interfaces:
    Name    Child-interface    Status
                               (Physical/Monitored)
    fab0    fe-0/0/5           Up   / Up
    fab0
    fab1    fe-1/0/5           Up   / Up
    fab1

Redundant-ethernet Information:
    Name         Status      Redundancy-group
    reth0        Up          1
    reth1        Up          1

Redundant-pseudo-interface Information:
    Name         Status      Redundancy-group
    lo0          Up          0

Interface Monitoring:
    Interface         Weight    Status    Redundancy-group
    fe-1/0/1          255       Up        1
    fe-1/0/0          255       Up        1
    fe-0/0/1          255       Up        1
    fe-0/0/0          255       Up        1

Let’s see how long the failover takes, by unplugging one of the links in the trust zone.

Pinging from the inside switch to the reth1 address 10.0.0.1

theswitch#ping 10.0.0.1 repeat 10000

Type escape sequence to abort.
Sending 10000, 100-byte ICMP Echos to 10.0.0.1, timeout is 2 seconds:
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!!!!!!.!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

Excellent, only lost one ping while failing over to node1 which would be 2 seconds.

We can see that node1 is now the primary for redundancy group 1, which holds our interfaces:

root@FW01A> show chassis cluster status redundancy-group 1
Cluster ID: 1
Node                  Priority          Status    Preempt  Manual failover

Redundancy group: 1 , Failover count: 3
    node0                   0           secondary      yes      no
    node1                   1           primary        yes      no

{primary:node0}

In the next article, I will dive a bit deeper and integrate the SRX cluster in a real-world topology.

JNCIS-SEC – Custom IDP policies on the Juniper SRX

Activating Intrusion Detection and Prevention (or IPS, as all the cool kids call it) on the SRX is quite straightforward in itself, but turning it on and relying solely on the default IDP policies is not going to cut it. While doing my own tests, running some scriptkiddie attacks against a virtual machine, I was expecting lots of sirens but unfortunately, the SRX stayed silent. No detection and definitely no prevention. As I quickly gathered, you actually need to put some thought in the services you are exposing and the kind of attacks you can expect, and then craft your own policies with the specific signatures.

For this one, I’ll be creating a custom IDP rule on the vSRX. I’m assuming you have already set up the vSRX, activated the advanced features license and set up IDP. If not, here are some links that will put you on the right path.

Scenario

  • We are hosting an SSH/SFTP server on my public IP address of 1.1.1.10/32. Every day, there are hundreds of brute-force login attempts. Obviously, the server admin has not implemented protective measures so we will try to reduce the impact by enabling IDP.
  • Destination NAT has been configured and is translating 1.1.1.10 to internal DMZ server 10.0.4.10.

Here is the firewall configuration. IDP has already been enabled on this policy.

[edit security policies from-zone untrust to-zone dmz policy FW-SFTP-Servers]
root@NP-vSRX-01# show
match {
    source-address any;
    destination-address Grp-SFTP-Servers;
    application junos-ssh;
}
then {
    permit {
        application-services {
            idp;
        }
    }
    log {
        session-init;
    }
}

Server setup and brute-force script

I’m using this script which runs a txt file of common passwords against the username specified.

On the linux server, let’s create a user, aptly named “admin”, with one of the passwords from the text files

lab@V104-10:~$ sudo useradd admin
lab@V104-10:~$ sudo passwd admin
Enter new UNIX password:
Retype new UNIX password:
passwd: password updated successfully

First, running the script with the standard IDP policy of Server-Protection-1G

lab@V120-10:/tmp/brutessh$ python brutessh.py -h 1.1.1.10 -u admin -d passlist.txt

*************************************
*SSH Bruteforcer Ver. 0.2           *
*Coded by Christian Martorella      *
*Edge-Security Research             *
*laramies@gmail.com                 *
*************************************

HOST: 1.1.1.10 Username: admin Password file: passlist.txt
===========================================================================
Trying password...
miller


Auth OK ---> Password Found: changeme
tiger

Times -- > Init: 0.032772 End: 6.861204

The SRX was not paying attention during the attack -nothing in the attack table- and the server got owned.

root@NP-vSRX-01> show security idp attack table
root@NP-vSRX-01>

Rolling your own IDP rules

Unfortunately, the server guy had to be let go and we are now looking for a way to be prevent these kinds of attacks. Of course, the first thing to do would be to harden the server and enforce strong credentials, but it does help if you are notified of an ongoing attack. Even better if the SRX could also prevent or slow down the attack.

For our scenario, we are specifically looking for SSH Brute-force attacks. A good way to find out if the SRX has an on-board signature for this is to browse the attack database. You can find all these signatures in operational mode.

root@NP-vSRX-01# run show security idp attack description SSH?
Possible completions:
          Attack name
  SSH:AUDIT:SSH-V1
  SSH:AUDIT:UNEXPECTED-HEADER
  SSH:BRUTE-LOGIN
  SSH:ERROR:COOKIE-MISMATCH
  SSH:ERROR:INVALID-HEADER
  SSH:ERROR:INVALID-PKT-TYPE
  SSH:ERROR:MSG-TOO-LONG
  SSH:ERROR:MSG-TOO-SHORT
  SSH:MISC:EXPLOIT-CMDS-UNIX
  SSH:MISC:MAL-VERSION
  SSH:MISC:UNIX-ID-RESP
  SSH:NON-STD-PORT
  SSH:OPENSSH-MAXSTARTUP-DOS
  SSH:OPENSSH:BLOCK-DOS
  SSH:OPENSSH:GOODTECH-SFTP-BOF
  SSH:OPENSSH:NOVEL-NETWARE
  SSH:OVERFLOW:FREESSHD-KEY-OF
  SSH:OVERFLOW:PUTTY-VER
  SSH:OVERFLOW:SECURECRT-BOF
  SSH:PRAGMAFORT-KEY-OF
  SSH:SYSAX-MULTI-SERVER-DOS
  SSH:SYSAX-SERVER-DOS

root@NP-vSRX-01# run show security idp attack description SSH:BRUTE-LOGIN
Description: This signature detects attempts by remote attackers to log in to an SSH server by brute-forcing the password.

Another great resource for finding the right signature is this page.

If you are using one of the predefined IDP policy sets, navigate down and edit the configuration. I am using Server-Protection-1G on mine.

The policy below will detect SSH brute-force attempts and, by using the ip-action, block the source IP for 30 minutes. That should slow ’em down.

[edit security idp idp-policy Server-Protection-1G rulebase-ips]
root@NP-vSRX-01# show rule SSH-SFTP-Services
match {
    from-zone any;
    source-address any;
    to-zone any;
    destination-address any;
    application default;
    attacks {
        predefined-attacks SSH:BRUTE-LOGIN;
    }
}
then {
    action {
        close-client;
    }
    ip-action {
        ip-block;
        target source-address;
        timeout 1800;
    }
    notification {
        log-attacks;
    }
}

You can rearrange the rules by using the insert policy before

Testing the policy

Running the script for a second time, it only took a small number of brute-force attempts until the alarm triggered. After a minute or two of time-outs, the script gave up and started spawning python errors.

lab@V120-10:/tmp/brutessh$ python brutessh.py -h 1.1.1.10 -u admin -d passlist.txt

*************************************
*SSH Bruteforcer Ver. 0.2           *
*Coded by Christian Martorella      *
*Edge-Security Research             *
*laramies@gmail.com                 *
*************************************

HOST: 1.1.1.10 Username: admin Password file: passlist.txt
===========================================================================
Trying password...
abc123
Exception in thread carmen
:
Traceback (most recent call last):
  File "/usr/lib/python2.7/threading.py", line 810, in __bootstrap_inner
    self.run()
  File "brutessh.py", line 44, in run
    t = paramiko.Transport(hostname)
  File "/tmp/brutessh/paramiko/transport.py", line 235, in __init__
    sock.connect((hostname, port))
  File "/usr/lib/python2.7/socket.py", line 224, in meth
    return getattr(self._sock,name)(*args)
error: [Errno 110] Connection timed out
Exception in thread test
:
Traceback (most recent call last):
  File "/usr/lib/python2.7/threading.py", line 810, in __bootstrap_inner
    self.run()
  File "brutessh.py", line 44, in run
    t = paramiko.Transport(hostname)
  File "/tmp/brutessh/paramiko/transport.py", line 235, in __init__
    sock.connect((hostname, port))
  File "/usr/lib/python2.7/socket.py", line 224, in meth
    return getattr(self._sock,name)(*args)
error: [Errno 110] Connection timed out
Exception in thread password1
:

Some verification commands on the SRX itself.

root@NP-vSRX-01> show security log | match IDP:
2015-09-17 19:22:45 UTC  IDP: at 1442517764, SIG Attack log <2.2.2.1/6768->1.1.1.10/22> for TCP protocol and service SERVICE_IDP application NONE by rule 6 of rulebase IPS in policy Server-Protection-1G. attack: repeat=0, action=CLOSE_CLIENT, threat-severity=MEDIUM, name=SSH:BRUTE-LOGIN, NAT <0.0.0.0:0->10.0.4.10:0>, time-elapsed=0, inbytes=0, outbytes=0, inpackets=0, outpackets=0, intf:untrust:ge-0/0/0.0->dmz:ge-0/0/2.0, packet-log-id: 0, alert=no, username=N/A, roles=N/A and misc-message -

The SRX detected three login attempts through before shunning the remote IP

root@NP-vSRX-01> show security idp attack table
IDP attack statistics:

  Attack name                                  #Hits
  SSH:BRUTE-LOGIN                              3
root@NP-vSRX-01> show security idp attack detail SSH:BRUTE-LOGIN
Display Name: SSH: Brute Force Login Attempt
Severity: Minor
Category: SSH
Recommended: true
Recommended Action: Drop
Type: signature
Direction: CTS
False Positives: rarely
Service: SSH
Shellcode: no
Flow: control
Context: first-data-packet
Negate: false
TimeBinding:
        Scope: peer
        Count: 10
Hidden Pattern: False
Pattern: \[SSH\].*
root@NP-vSRX-01> show security idp counters action
IDP counters:

  IDP counter type                                                      Value
 None                                                                    0
 Recommended                                                             0
 Ignore                                                                  0
 Diffserv                                                                0
 Drop packet                                                             0
 Drop                                                                    0
 Close                                                                   0
 Close server                                                            0
 Close client                                                            3
 IP action rate limit                                                    0
 IP action drop                                                          3
 IP action close                                                         0
 IP action nofity                                                        0
 IP action failed                                                        0

Wrapping up

Although very basic, this example demonstrated that it absolutely pays off to invest some time in crafting your own IDP rules. Keeping a detailed inventory of the services you are hosting and matching it against the associated application-level attack signatures will greatly increase your security posture. Combined with the Screen Options, which protect against some of the L3/L4 attacks, this makes the SRX well worth considering 🙂

Route-based IPsec tunnels on the SRX

Expanding on the basic branch setup from my previous labs, I added another virtual SRX to the topology to exercise the VPN stuff. As the “ISP” router, I first tried adding a CSR-1000V to the lab but found out the hard way that it’s bandwidth throttled at 100kbps. With six virtual machines behind it sporadically fetching stuff off the internet, the entire lab came to a grinding halt. 🙂

As a quick workaround, I settled on a VyOS appliance , which was surprisingly easy to work with. It’s very similar to JunOS so I had it up and running in just a couple of minutes.

Anyway, enough about that. Here’s the network I’ll be working off to build some VPNs…

Topology

VPN Topology

Before you configure VPN tunnels, make sure that your public interface is listening for IKE traffic. This is defined on the zone or interface level.

[edit security zones security-zone untrust]
root@NP-vSRX-01# show
host-inbound-traffic {
    system-services {
        ssh;
        ping;
        ike;
    }
}
interfaces {
    ge-0/0/0.0;
}

Tunnel interface, routing and security zone

First, define a Secure Tunnel interface with IPv4 support by adding the inet family. If you forget the family inet statement, your tunnel will not pass traffic.

For simple tunnels without dynamic routing protocols, assigning an IP address is not required.

[edit interfaces]
root@NP-vSRX-01# show st0
unit 1 {
    description "Branch1 Tunnel Interface";
    family inet;
}

Create a static route for the peer subnet(s) and point it to the tunnel interface.

[edit]
root@NP-vSRX-01# set routing-options static route 10.2.0.0/24 next-hop st0.1

One thing I tend to forget is to add the st0 interface to the right security zone. Rather than putting it in the untrust zone, I will create a separate zone for VPN and put the tunnel there.

[edit security zones security-zone vpn]
root@NP-vSRX-01# show
interfaces {
    st0.1;
}

Once that is done, we can start configuring the actual VPN policy. There are a lot of components to configure, but once you know how they intertwine it’s pretty straightforward.

Configuring Phase 1

First, configure an IKE proposal. You could choose one of the JunOS templates, but where’s the fun in that, right? 🙂

[edit security ike]
root@NP-vSRX-01# show
proposal P1-Proposal-Branch1 {
    description "Branch1 Phase1 Proposal";
    authentication-method pre-shared-keys;
    authentication-algorithm sha-256;
    encryption-algorithm aes-256-cbc;
    lifetime-seconds 43200;
}

Once we have the P1 proposal, we define the phase 1 policy which in turn refers to the proposal. Unless your peer has a dynamic IP, main mode is what you need. This is also where you specify the preshared key.

[edit security ike policy P1-Policy-Branch1]
root@NP-vSRX-01# show
mode main;
description "Branch1 Phase1 Policy";
proposals P1-Proposal-Branch1;
pre-shared-key ascii-text "$9$DDH.f9CuB1hqMORhcle4aZGjq"; ## SECRET-DATA

Third and last for Phase 1 template, configure the gateway peer IP address with the corresponding policy. If possible, always use IKE version 2. The external interface is where the SRX can expect the UDP/500 packets.

[edit security ike gateway P1-Peer-Branch1]
root@NP-vSRX-01# show
ike-policy P1-Policy-Branch1;
address 2.2.2.1;
external-interface ge-0/0/0;
version v2-only;

Now that Phase1 is set, we can move on to the IPsec configuration.

Phase 2 – IPsec

Just as we did before, we first define a proposal. Choose your most secure option for encryption and hashing, and a reasonably short keying lifetime.

[edit security ipsec proposal P2-Proposal-Branch1]
root@NP-vSRX-01# show
description "Branch1 Phase2 Proposal";
protocol esp;
authentication-algorithm hmac-sha-256-128;
encryption-algorithm aes-256-cbc;
lifetime-seconds 3600;

Configure the IPsec policy that again refers to the proposal. Unless the peer does not support it, always turn on PFS.

[edit security ipsec policy P2-Policy-Branch1]
root@NP-vSRX-01# show
description "Branch1 Phase2 Policy";
perfect-forward-secrecy {
    keys group5;
}
proposals P2-Proposal-Branch1;

The final step is where the Phase 1 and 2 components are glued together. For route-based tunnels, don’t forget to bind your st interface. I prefer to negotiate the tunnels immediately rather than waiting for traffic.

[edit security ipsec vpn P2-IPsec-Branch1]
root@NP-vSRX-01# show
bind-interface st0.1;
ike {
    gateway P1-Peer-Branch1;
    ipsec-policy P2-Policy-Branch1;
}
establish-tunnels immediately;

Security Policies

From a VPN point of view, we are ready to accept IPsec connections on this box. We are listening for IKE traffic, we have a route pointing to our tunnel interface and VPN policies are configured. The only thing we need to do is configure the firewall policies.

For this one, I will be allowing traffic from the remote sites to one of the machines on the trust zone. I already created some objects in the global address book.

From VPN to Trust:

[edit security policies from-zone vpn to-zone trust]
root@NP-vSRX-01# show
policy FW-Allow-VPN-Branch {
    match {
        source-address Host-10.2.0.10;
        destination-address Host-10.0.0.10;
        application any;
    }
    then {
        permit;
        count;
    }
}

From Trust to VPN:

[edit security policies]
root@NP-vSRX-01# show from-zone trust to-zone vpn
policy FW-Allow-VPN-Branch {
    match {
        source-address Host-10.0.0.10;
        destination-address Host-10.2.0.10;
        application any;
    }
    then {
        permit;
        count;
    }
}

Configuring the Branch site SRX

The benefit of having two SRX’s is that you can easily copy-paste, edit and mirror the config.

### PHASE 1 ### 

set security ike proposal P1-Proposal-HQ description "HQ Phase1 Proposal"
set security ike proposal P1-Proposal-HQ authentication-method pre-shared-keys
set security ike proposal P1-Proposal-HQ authentication-algorithm sha-256
set security ike proposal P1-Proposal-HQ encryption-algorithm aes-256-cbc
set security ike proposal P1-Proposal-HQ lifetime-seconds 43200
set security ike policy P1-Policy-HQ mode main
set security ike policy P1-Policy-HQ description "HQ Phase1 Policy"
set security ike policy P1-Policy-HQ proposals P1-Proposal-HQ
set security ike policy P1-Policy-HQ pre-shared-key ascii-text "$9$DDH.f9CuB1hqmORhcle4aZGjq"
set security ike gateway P1-Peer-HQ ike-policy P1-Policy-HQ
set security ike gateway P1-Peer-HQ address 1.1.1.1
set security ike gateway P1-Peer-HQ external-interface ge-0/0/0

### PHASE 2 ####

set security ipsec proposal P2-Proposal-HQ description "HQ Phase2 Proposal"
set security ipsec proposal P2-Proposal-HQ protocol esp
set security ipsec proposal P2-Proposal-HQ authentication-algorithm hmac-sha-256-128
set security ipsec proposal P2-Proposal-HQ encryption-algorithm aes-256-cbc
set security ipsec proposal P2-Proposal-HQ lifetime-seconds 3600
set security ipsec policy P2-Policy-HQ description "HQ Phase2 Policy"
set security ipsec policy P2-Policy-HQ perfect-forward-secrecy keys group5
set security ipsec policy P2-Policy-HQ proposals P2-Proposal-HQ
set security ipsec vpn P2-IPsec-HQ bind-interface st0.1
set security ipsec vpn P2-IPsec-HQ ike gateway P1-Peer-HQ
set security ipsec vpn P2-IPsec-HQ ike ipsec-policy P2-Policy-HQ

#### TUNNEL INTERFACE ### 

set interfaces st0 unit 1 description "HQ Tunnel Interface"
set interfaces st0 unit 1 family inet

### HOST INBOUND TRAFFIC ### 

set security zones security-zone untrust host-inbound-traffic system-services ike

### ADD TUNNEL TO ZONE ###

set security zones security-zone untrust interfaces st0.1

### ADD ROUTE ###

set routing-options static route 10.0.0.0/24 next-hop st0.1
set routing-options static route 10.0.4.0/24 next-hop st0.1

### SECURITY POLICIES ### 

set security policies from-zone vpn to-zone branch policy FW-Allow-VPN-HQ-In match source-address Host-10.0.0.10
set security policies from-zone vpn to-zone branch policy FW-Allow-VPN-HQ-In match destination-address Host-10.2.0.10
set security policies from-zone vpn to-zone branch policy FW-Allow-VPN-HQ-In match application any
set security policies from-zone vpn to-zone branch policy FW-Allow-VPN-HQ-In then permit
set security policies from-zone vpn to-zone branch policy FW-Allow-VPN-HQ-In then count
set security policies from-zone branch to-zone vpn policy FW-Allow-VPN-HQ-Server match source-address Host-10.2.0.10
set security policies from-zone branch to-zone vpn policy FW-Allow-VPN-HQ-Server match destination-address Host-10.0.0.10
set security policies from-zone branch to-zone vpn policy FW-Allow-VPN-HQ-Server match application any
set security policies from-zone branch to-zone vpn policy FW-Allow-VPN-HQ-Server then permit
set security policies from-zone branch to-zone vpn policy FW-Allow-VPN-HQ-Server then count

Verification

On the HQ SRX, we already have a phase 1 tunnel up using IKEv2 as the exchange protocol.

root@NP-vSRX-01> show security ike security-associations
Index   State  Initiator cookie  Responder cookie  Mode           Remote Address
2441630 UP     2fb27eba88550b6b  e8b7c6a94c94f8d2  IKEv2          2.2.2.1

We also have a Phase 2 tunnel, with just under one hour of lifetime left.

root@NP-vSRX-01> show security ipsec security-associations
  Total active tunnels: 1
  ID    Algorithm       SPI      Life:sec/kb  Mon lsys Port  Gateway
  <131073 ESP:aes-cbc-256/sha256 14b32bcb 3433/ unlim - root 500 2.2.2.1
  >131073 ESP:aes-cbc-256/sha256 fef69f20 3433/ unlim - root 500 2.2.2.1

Some more details about the IPsec parameters, like Proxy IDs (0.0.0.0/0) and encryption/authentication standards.

root@NP-vSRX-01> show security ipsec security-associations index 131073 detail
  ID: 131073 Virtual-system: root, VPN Name: P2-IPsec-Branch1
  Local Gateway: 1.1.1.1, Remote Gateway: 2.2.2.1
  Local Identity: ipv4_subnet(any:0,[0..7]=0.0.0.0/0)
  Remote Identity: ipv4_subnet(any:0,[0..7]=0.0.0.0/0)
  Version: IKEv2
    DF-bit: clear
    Bind-interface: st0.1

  Port: 500, Nego#: 32, Fail#: 0, Def-Del#: 0 Flag: 0x600a29
  Last Tunnel Down Reason: Delete payload received
    Direction: inbound, SPI: 14b32bcb, AUX-SPI: 0
                              , VPN Monitoring: -
    Hard lifetime: Expires in 3339 seconds
    Lifesize Remaining:  Unlimited
    Soft lifetime: Expires in 2752 seconds
    Mode: Tunnel(0 0), Type: dynamic, State: installed
    Protocol: ESP, Authentication: hmac-sha256-128, Encryption: aes-cbc (256 bits)
    Anti-replay service: counter-based enabled, Replay window size: 64

    Direction: outbound, SPI: fef69f20, AUX-SPI: 0
                              , VPN Monitoring: -
    Hard lifetime: Expires in 3339 seconds
    Lifesize Remaining:  Unlimited
    Soft lifetime: Expires in 2752 seconds
    Mode: Tunnel(0 0), Type: dynamic, State: installed
    Protocol: ESP, Authentication: hmac-sha256-128, Encryption: aes-cbc (256 bits)
    Anti-replay service: counter-based enabled, Replay window size: 64

A good way to verify that there’s two-way communication is to inspect the IPsec counters

root@NP-vSRX-01> show security ipsec statistics index 131073
ESP Statistics:
  Encrypted bytes:        140965904
  Decrypted bytes:       3342178434
  Encrypted packets:        1132200
  Decrypted packets:        2245688
AH Statistics:
  Input bytes:                    0
  Output bytes:                   0
  Input packets:                  0
  Output packets:                 0
Errors:
  AH authentication failures: 0, Replay errors: 251
  ESP authentication failures: 0, ESP decryption failures: 0
  Bad headers: 0, Bad trailers: 0

The ultimate test is to verify on the internal machines. Note the asterisks on the tunnel segment. If there’s an address assigned to the st interface, this one would show in the trace results.

root@Branch-vSRX-01> ssh lab@10.2.0.10
lab@10.2.0.10's password:
Welcome to Ubuntu 14.10 (GNU/Linux 3.16.0-23-generic x86_64)

 * Documentation:  https://help.ubuntu.com/

Last login: Thu Sep 10 22:27:33 2015
lab@V120-10:~$ ping 10.0.0.10
PING 10.0.0.10 (10.0.0.10) 56(84) bytes of data.
64 bytes from 10.0.0.10: icmp_seq=1 ttl=62 time=10.3 ms
64 bytes from 10.0.0.10: icmp_seq=2 ttl=62 time=13.5 ms
64 bytes from 10.0.0.10: icmp_seq=3 ttl=62 time=11.6 ms
^C
--- 10.0.0.10 ping statistics ---
3 packets transmitted, 3 received, 0% packet loss, time 2003ms
rtt min/avg/max/mdev = 10.370/11.869/13.567/1.318 ms

lab@V120-10:~$ traceroute 10.0.0.10
traceroute to 10.0.0.10 (10.0.0.10), 30 hops max, 60 byte packets
 1  10.2.0.1 (10.2.0.1)  3.864 ms  3.912 ms  4.003 ms
 2  * * *
 3  10.0.0.10 (10.0.0.10)  13.682 ms  13.679 ms  13.666 ms
lab@V120-10:~$

That’s it, a fully functional, although very basic, route-based VPN.

JNCIS-SEC – SRX Static NAT Configuration

I already went into source and destination NAT in the last few posts. The last one I wanted to lab up is Static NAT, which creates a one-to-one mapping between two addresses. The translation is bidirectional and ports are not translated. On the downside, it does require you to sacrifice one public IP per internal server which is not always the most cost-efficient method.

Here’s what I’ll be working on:

SRX NAT topology

The following Static NAT entries will be configured:

  • Server 10.0.100.10 will be translated to 1.1.1.10
  • Server 10.0.100.11 will be translated to 1.1.1.11

Using the Global Address Book

Instead of using regular IP prefixes as matching conditions, I will be using address book entries in the NAT config. Referring to the same names in both security policy and NAT makes interpreting and troubleshooting the config much more straightforward.

First, navigate over to the global address book under Security, and enter addresses as you would under the zones. I am creating objects for both the public and private addresses:

[edit security address-book global]
root@NP-vSRX-01# show
address Host-Private-10.0.100.10 10.0.100.10/32;
address Host-Private-10.0.100.11 10.0.100.11/32;
address Host-Public-1.1.1.10 1.1.1.10/32;
address Host-Public-1.1.1.11 1.1.1.11/32;

Caution, when you start adding entries to the global address book, the SRX will start spawning this error when trying a commit:

[edit security zones security-zone untrust]
root@NP-vSRX-01# show
##
## Warning: Zone specific address books are not allowed when there are global address books defined
##

From the looks of it, you will need to move all your zone address books over to the global one, so make sure you start off right on a new SRX. Worst case, you can still match on regular IP prefixes for NAT.

Next will be to define a ruleset, and create some rules. One thing to keep in mind is that you configure the NAT rule to match on the destination address to perform the NAT. Implicitly, the SRX will then create a reverse source-NAT mapping. Just imagine the traffic entering your network, and to what address it should be translated, and the SRX will take care of the reverse traffic for you.

Here is the configuration for the first host, referencing the object name by using destination-address-name:

[edit security nat static]
root@NP-vSRX-01# show
rule-set Static-From-Untrust {
    from zone untrust;
    rule NAT-DMZ-10 {
        match {
            destination-address-name Host-Public-1.1.1.10;
        }
        then {
            static-nat {
                prefix-name {
                    Host-Private-10.0.100.10;
                }
            }
        }
    }
}

Copy paste for the second host:

rule NAT-DMZ-11 {
    match {
        destination-address-name Host-Public-1.1.1.11;
    }
    then {
        static-nat {
            prefix-name {
                Host-Private-10.0.100.11;
            }
        }
    }
}

Verification

The most useful command for Static NAT verification is show security nat static rule, which shows you both a config overview and a hit count.

root@NP-vSRX-01> show security nat static rule all
Total static-nat rules: 2
Total referenced IPv4/IPv6 ip-prefixes: 4/0

Static NAT rule: NAT-DMZ-10           Rule-set: Static-From-Untrust
  Rule-Id                    : 1
  Rule position              : 1
  From zone                  : untrust
  Destination addresses      : Host-Public-1.1.1.10
  Host addresses             : Host-Private-10.0.100.10
  Netmask                    : 32
  Host routing-instance      : N/A
  Translation hits           : 40
    Successful sessions      : 34
    Failed sessions          : 6
  Number of sessions         : 0

Static NAT rule: NAT-DMZ-11           Rule-set: Static-From-Untrust
  Rule-Id                    : 2
  Rule position              : 2
  From zone                  : untrust
  Destination addresses      : Host-Public-1.1.1.11
  Host addresses             : Host-Private-10.0.100.11
  Netmask                    : 32
  Host routing-instance      : N/A
  Translation hits           : 112
    Successful sessions      : 112
    Failed sessions          : 0
  Number of sessions         : 0

To emphasize that no PAT is performed, here is an output of the session table. We are using port 50973 on both ends of the firewall.

Session ID: 15148, Policy name: FW-PermitWeb/7, Timeout: 4, Valid
  In: 10.0.100.11/50973 --> 91.189.92.200/80;tcp, If: ge-0/0/1.0, Pkts: 26, Bytes: 5673
  Out: 91.189.92.200/80 --> 1.1.1.11/50973;tcp, If: ge-0/0/0.0, Pkts: 25, Bytes: 5863

JNCIS-SEC – Port forwarding on the SRX

A common technique to obscure services from network probing is to host them on ports outside of the well-known ports range. This might help as a first defense, but in reality the ports are still there for anyone who steps out of the defaults. It also makes life harder for other firewall engineers 🙂 On the other hand, if your ISP is blocking services hosted in the well-known range, it might be your only option.

As in all the NAT examples, here is the topology:

SRX NAT topology

We are hosting an SFTP server, but are fed up with all the bruteforce attacks, so decide to host it on a different port. Traffic coming from the untrust zone, destined for 1.1.1.11 and arriving at TCP port 2222, will be translated to port 22 on the inside.

First, we define the real, internal port at the DNAT pool, together with the internal IP.

[edit security nat destination]
root@NP-vSRX-01# show pool DNAT-Host100-11
address 10.0.100.11/32 port 22;

Then, we go to our rule set, which defined the traffic direction (from untrust) and enter the address and port on which it should be listening, plus the pool to translate to:

[edit security nat destination rule-set DNAT-From-Untrust]
root@NP-vSRX-01# show
from zone untrust;
rule DNAT-Host100-11 {
    match {
        destination-address 1.1.1.11/32;
        destination-port {
            2222;
        }
    }
    then {
        destination-nat {
            pool {
                DNAT-Host100-11;
            }
        }
    }
}

That’s it. After doing a telnet to port 2222, we see the following flow in the table:

Session ID: 167059, Policy name: FW-SSH-Server/6, Timeout: 1778, Valid
  In: 10.6.60.68/62340 --> 1.1.1.11/2222;tcp, If: ge-0/0/0.0, Pkts: 3, Bytes: 132
  Out: 10.0.100.11/22 --> 10.6.60.68/62340;tcp, If: ge-0/0/1.0, Pkts: 2, Bytes: 126

Port forwarding with a dynamic IP

If you are running a dynamic IP address, it won’t be possible to define one IP as a match condition. Unless your ISP is always handing out addresses in one specific range, the only option is to define the destination-address as 0.0.0.0/0

All config stays the same, but the DNAT rule looks like this:

[edit security nat destination rule-set DNAT-From-Untrust rule DNAT-Host100-11]
root@NP-vSRX-01# show
match {
    destination-address 0.0.0.0/0;
    destination-port {
        2222;
    }
}
then {
    destination-nat {
        pool {
            DNAT-Host100-11;
        }
    }
}

JNCIS-SEC Lab – Destination NAT

In this lab, we will look at configuring the SRX to translate the destination field for incoming traffic, which is widely used for public servers in a DMZ.

As with all the NAT examples, I’ll be using the following topology:

SRX NAT topology

These are the requirements for the translations:

  • Only applies to traffic coming from the internet (untrust zone)
  • Destination 1.1.1.10/32 will be translated to DMZ IP 10.0.100.10/32
  • Destination 1.1.1.11/32 will be translated to DMZ IP 10.0.100.11/32

First, I will configure security policies for the following services:

  • Server 10.0.100.10 is hosting a Telnet server
  • Server 10.0.100.11 is an SSH/SFTP server

Because DNAT happens before policy lookup, we always refer to the address as it will be after translation.

[edit security policies from-zone untrust to-zone dmz]
root@NP-vSRX-01# show
policy FW-Telnet-Server {
    match {
        source-address any;
        destination-address Host-10.0.100.10-32;
        application junos-telnet;
    }
    then {
        permit;
        log {
            session-close;
        }
    }
}
policy FW-SSH-Server {
    match {
        source-address any;
        destination-address Host-10.0.100.11-32;
        application junos-ssh;
    }
    then {
        permit;
        log {
            session-close;
        }
    }
}

As this is a fresh config, we will first define a rule-set that specifies the traffic direction. Destination NAT does not give you the option to specify the to-zone, just the source zone.

[edit security nat destination]
root@NP-vSRX-01# show
rule-set DNAT-From-Untrust {
    from zone untrust;
}

Now, let’s add the two pools:

[edit security nat destination]
root@NP-vSRX-01# show
pool DNAT-Host100-11 {
    address 10.0.100.11/32;
}
pool DNAT-Host100-10 {
    address 10.0.100.10/32;
}

And here are the NAT rules themselves:

[edit security nat destination rule-set DNAT-From-Untrust]
rule DNAT-Host100-10 {
    match {
        destination-address 1.1.1.10/32;
    }
    then {
        destination-nat {
            pool {
                DNAT-Host100-10;
            }
        }
    }
}
rule DNAT-Host100-11 {
    match {
        destination-address 1.1.1.11/32;
    }
    then {
        destination-nat {
            pool {
                DNAT-Host100-11;
            }
        }
    }
}

Because the upstream router is in the same segment as our firewall, we will also need to add ProxyARP to the global NAT config.

[edit security nat]
root@NP-vSRX-01# set proxy-arp interface ge-0/0/0.0 address 1.1.1.10/32 to 1.1.1.11/32

Verification

After starting a telnet and SSH session from my PC, this is the session table:

Session ID: 166748, Policy name: FW-SSH-Server/6, Timeout: 1792, Valid
  In: 10.6.66.68/59016 --> 1.1.1.11/22;tcp, If: ge-0/0/0.0, Pkts: 3, Bytes: 132
  Out: 10.0.100.11/22 --> 10.6.66.68/59016;tcp, If: ge-0/0/1.0, Pkts: 2, Bytes: 126
Session ID: 166759, Policy name: FW-Telnet-Server/5, Timeout: 1798, Valid
  In: 10.6.66.68/60731 --> 1.1.1.10/23;tcp, If: ge-0/0/0.0, Pkts: 11, Bytes: 510
  Out: 10.0.100.10/23 --> 10.6.66.68/60731;tcp, If: ge-0/0/1.0, Pkts: 14, Bytes: 652
root@NP-vSRX-01> show security nat destination summary
Total pools: 2
Pool name            Address                           Routing        Port  Total
                     Range                             Instance             Address
DNAT-Host100-11      10.0.100.11    - 10.0.100.11                     0     1
DNAT-Host100-10      10.0.100.10    - 10.0.100.10                     0     1

Total rules: 2
Rule name            Rule set       From                               Action
DNAT-Host100-11      DNAT-From-Untrust untrust                         DNAT-Host100-11
DNAT-Host100-10      DNAT-From-Untrust untrust                         DNAT-Host100-10
root@NP-vSRX-01> show security nat destination pool all
Total destination-nat pools: 2

Pool name       : DNAT-Host100-11
Pool id         : 3
Total address   : 1
Translation hits: 1
Address range                        Port
    10.0.100.11 - 10.0.100.11           0

Pool name       : DNAT-Host100-10
Pool id         : 4
Total address   : 1
Translation hits: 8
Address range                        Port
    10.0.100.10 - 10.0.100.10           0