Forum Discussion

jabuens's avatar
jabuens
Icon for Nimbostratus rankNimbostratus
Apr 13, 2022

iRule for SNAT using subnet range rather than host base

Hi,

I'm just a newbie using iRule for SNAT. We have an internal server that being access by our external customer that require us to allow their Company Public IP (i.e /24) rather than single host. Their Company is located from diff country that's why they wanted to some kind of diversity. 

I'm thinking of creating below configuration and want to know if this type of configuration is allowed on F5 and security wise. Is it advisable or there's a better way to of allowing range of subnet from external to access internal resource.

when CLIENT_ACCEPTED {
log local0. "client:"
if { [IP::client_addr] contains "170.42.6.0/24" } {
snat 10.1.147.13
} elseif { [IP::client_addr] contains "70.40.6.0/24" } {
snat 10.1.147.13
} elseif { [IP::client_addr] contains "16.52.171.0/24" } {
snat 10.1.147.13
} elseif { [IP::client_addr] contains "200.52.171.0/22" } {
snat 10.1.147.13
}
}

3 Replies

  • Hello Jabuens.

    I would do it like this

    when CLIENT_ACCEPTED {
    	if { [IP::addr [IP::client_addr] equals 170.42.6.0/24] } {
    		snat 10.1.147.13
    	} elseif { [IP::addr [IP::client_addr] equals 70.40.6.0/24] } {
    		snat 10.1.147.13
    	} elseif { [IP::addr [IP::client_addr] equals 16.52.171.0/24] } {
    		snat 10.1.147.13	
    	} elseif { [IP::addr [IP::client_addr] equals 200.52.171.0/22] } {
    		snat 10.1.147.13
    	}
    }

    Also, there is a chance to group all the conditions in one single statement.

    when CLIENT_ACCEPTED {
    	switch [IP::addr [IP::client_addr] mask 255.255.255.0] {
    		"170.42.6.0" - "70.40.6.0" - "16.52.171.0" - "200.52.168.0" - "200.52.169.0" - "200.52.170.0" - "200.52.171.0" {
    			snat 10.1.147.13
    		}
    	}
    }

     

  • Well I started this as an answer to the real use of SNAT, but after rereading your question, I am not sure why you would use a SNAT in this case. You want to allow different subnets to come into your site? If so, that seems to be a function for a firewall--which the BIG-IP is not. What I wrote below could still apply but for selecting a different pool or node rather than a SNAT. I left what I wrote in case it is of some use to someone.

    Since you are snatting the same IP address, you could use an address class. You just put the subnets into the class and then use a class match statement to see if the [IP::client_addr] is in the class and if so, snat 10.1.147.13

    Something like

    if {[class match [IP::client_addr] equals "mySNATClass"]} {
       snat 10.1.147.13
    }

    Load up an address class named mySNATClass with the following and you are good to go:

    • 170.42.6.0/24
    • 70.40.6.0/24
    • 16.52.171.0/24
    • 200.52.171.0/22

    If you want to vary the address you SNAT (something I believe a future post suggested), you could use a value in the address class and set the address to the subnet, then the value to the IP you want to SNAT. 

    Something like this would work:

    set snatAddr [class match -value [IP::client_addr] equals "mySNATClass"]
    if {$snatAddr ne ""} {
       snat $snatAddr
    }

    For the above, load up the address class the same way, but add a value of the address you want to SNAT.

    • 170.42.6.0/24 - 10.1.147.13
    • 70.40.6.0/24 - 10.1.147.14
    • 16.52.171.0/24 - 10.1.147.15
    • 200.52.171.0/22 - 10.1.147.16

    Error handling of ensuring the value in the class is an exercise left to the reader.

    If you are new to classes, definetly read all the great material on them here on DevCentral.

    Using the class approach makes the process more data-driven planning ahead for the inevitable additions to your If statements.

    Good luck.