This post is written by Leonardo Solano, Senior Hybrid Cloud Solution Architect and Chris Lunsford, Senior Specialist Solutions Architect, AWS Outposts.
AWS Outposts lets customers use the same Amazon Virtual Private Cloud (VPC) security mechanisms, such as security groups and network access control lists, to control traffic flows for on-premises applications running on Outposts. Some customers, desiring additional security or consistency with on-premises systems, want the ability to inspect and filter incoming application traffic as it enters the Outpost. Ideally, they would like to deploy virtual appliances in front of the workloads running on Outposts.
Today, we are announcing a new feature called Outposts local lateway (LGW) ingress routing. This lets you create LGW inbound routes to redirect incoming traffic to an Amazon Elastic Compute Cloud (EC2) Elastic Network Interface (ENI) associated with an EC2 instance running on Outposts rack. The traffic is redirected for inspection before it reaches the workloads running on Outposts rack. Moreover, it lets the EC2 virtual appliance inspect, filter, or optimize the traffic in a similar way as VPC ingress routing in the Region.
Use case
A common use case for this feature is deploying a customer-preferred third-party virtual network appliance. The appliance can inspect, modify, or monitor the incoming traffic for policy compliance and forward compliant traffic on to the workloads running on the Outpost. A typical virtual appliance could be a firewall, intrusion detection system (IDS), or intrusion prevention system (IPS). The features provided by the virtual appliances vary, and they may include deep packet inspection, traffic optimization, and flow monitoring. This new Outposts rack feature modifies the default behavior of the local gateway routing table (LGW-RTB), and it lets customers redirect traffic coming into an Outposts deployment to the virtual appliance.
The new behavior?
Now you can create static routes in the LGW-RTB that target a specific ENI on the Outpost as the next hop. These static routes are propagated toward the customer network through the Border Gateway Protocol (BGP) peering sessions with the Customer Networking Devices. The on-premises network will route traffic to the specified Classless Inter-Domain Routing (CIDR) prefixes, as defined in the static routes, toward the Outposts Network Devices.
In the preceeding diagram, the static route 198.19.33.248/29 has a longer prefix length than 198.19.33.240/28, and both routes will be propagated toward the customer network via BGP. The incoming traffic for the 198.19.33.248/29 prefix will be directed toward the ENI eni-1234example0. The architecture looks like the following diagram, where the security virtual appliance is seated between the LGW and a set of EC2 instances in Outposts.
As ingress traffic is routed through the virtual appliance for inspection and filtering, the destination addresses of packets arriving at the ENI of the virtual appliance won’t match its ENI’s private IP address (the packets are transiting the instance). By default, the ENI will drop the inbound traffic unless you disable source/destination checking on the virtual appliance instance ENI settings. The following screenshot shows how you can disable the EC2 instance source/destination checking in the AWS console.
Considerations for LGW ingress routing
Consider the following requirements when preparing to deploy LGW ingress routing:
- The ENIs used as the next-hop target must be deployed in an Outposts Subnet.
- The subnets must belong to a VPC associated with the LGW-RTB.
- Routes with the longest matches are prioritized. If there are two with the same destination CIDR, then static routes are preferred over propagated ones.
Working with Outposts LGW ingress routing
The following output shows what the LGW route table looks like before applying the ingress routing feature:
{ "Routes": [ { "DestinationCidrBlock": "0.0.0.0/0", "LocalGatewayVirtualInterfaceGroupId": "lgw-vif-grp-XXX", "Type": "static", "State": "active", "LocalGatewayRouteTableId": "lgw-rtb-XXX", "LocalGatewayRouteTableArn": "arn:aws:ec2:>AWS-REGION>:<account-id>:local-gateway-route-table/lgw-rtb-XXX", "OwnerId": "<account-id>" }, { "DestinationCidrBlock": "198.19.33.16/28", "CoipPoolId": "coip-pool-0000aaaabbbbcccc1111", "Type": "propagated", "State": "active", "LocalGatewayRouteTableId": "lgw-rtb-XXX", "LocalGatewayRouteTableArn": "arn:aws:ec2:<AWS-REGION>:<account-id>:local-gateway-route-table/lgw-XXX", "OwnerId": "<account-id>" }, { "DestinationCidrBlock": "198.19.33.240/28", "CoipPoolId": "coip-pool-0000aaaabbbbcccc2222", "Type": "propagated", "State": "active", "LocalGatewayRouteTableId": "lgw-rtb-XXX", "LocalGatewayRouteTableArn": "arn:aws:ec2:<AWS-REGION>:<account-id>:local-gateway-route-table/lgw-XXX", "OwnerId": "<account-id>" } ] }The relevant change under an LGW-RTB before to add a local-gateway-route is the presence of the “propagated routes”. This represents the Outposts Subnets that can’t be deleted or modified with Next-Hop as specific ENIs present in Outposts. In the following section, we will cover how it will look after the creation of a local-gateway-route.
Configuring LGW ingress routing
To configure LGW ingress routing, you must provide the LGW route table ID, the ENI ID that will be utilized as a next-hop, and the destination CIDR block. Once you have identified those three parameters, you can configure LGW ingress routing via the This is shown in the following example, where the prefix 198.19.33.248/29 is routed to an Outpost. If the route points to an ENI attached to an instance, then the route will show as active. If the route points to an ENI that isn’t attached to an EC2 instance, then the route will show a blackhole state.
$ aws ec2 create-local-gateway-route \ --local-gateway-route-table-id <lgw-rtb-id> \ --network-interface-id <eni-id> \ --destination-cidr-block 198.19.33.248/29 { "Route": { "DestinationCidrBlock": "198.19.33.248/29", "NetworkInterfaceId": "eni-id", "Type": "static", "State": "active", "LocalGatewayRouteTableId": "lgw-rtb-id", "LocalGatewayRouteTableArn": "arn:aws:ec2:<AWS-REGION>:<account-id>:local-gateway-route-table/<lgw-rtb-id>", "OwnerId": "<account-id>" } }Once LGW ingress routing has been configured, the LGW will route traffic destined to the 198.19.33.248/29 prefix to the target ENI. This must be present as part of the Outposts subnets. Note that the segment 198.19.33.248/29 is part of the Outposts CIDR range of 198.19.33.240/28. This belongs, in this case, to the Outposts customer-owned IP address (CoIP) CIDRs. When traffic follows a static route to an ENI, the packet destination address is preserved and isn’t translated to the private address of the ENI.
In this case, the new LGW-RTB will look like the following:
{ "Routes": [ { "DestinationCidrBlock": "0.0.0.0/0", "LocalGatewayVirtualInterfaceGroupId": "lgw-vif-grp-XXX", "Type": "static", "State": "active", "LocalGatewayRouteTableId": "lgw-rtb-XXX", "LocalGatewayRouteTableArn": "arn:aws:ec2:<AWS-REGION>:<account-id>:local-gateway-route-table/lgw-rtb-XXX", "OwnerId": "<account-id>" }, { "DestinationCidrBlock": "198.19.33.16/28", "CoipPoolId": "coip-pool-0000aaaabbbbcccc1111", "Type": "propagated", "State": "active", "LocalGatewayRouteTableId": "lgw-rtb-XXX", "LocalGatewayRouteTableArn": "arn:aws:ec2:<AWS-REGION>:<account-id>:local-gateway-route-table/lgw-XXX", "OwnerId": "<account-id>" }, { "DestinationCidrBlock": "198.19.33.240/28", "CoipPoolId": "coip-pool-0000aaaabbbbcccc1111", "Type": "propagated", "State": "active", "LocalGatewayRouteTableId": "lgw-rtb-XXX", "LocalGatewayRouteTableArn": "arn:aws:ec2:<AWS-REGION>:<account-id>:local-gateway-route-table/lgw-XXX", "OwnerId": "<account-id>" }, { "DestinationCidrBlock": "198.19.33.248/29", "NetworkInterfaceId": "eni-XXX", "Type": "static", "State": "active", "LocalGatewayRouteTableId": "lgw-rtb-XXX", "LocalGatewayRouteTableArn": "arn:aws:ec2:<AWS-REGION>:<account-id>:local-gateway-route-table/lgw-rtb-XXX", "OwnerId": "<account-id>" } ] }In the AWS console, the LGW-RTB will show the new ingress routing route:
Modifying LGW ingress routing
Utilize a similar AWS CLI command to the one that we used previously to create the LGW ingress routing route to modify existing routes. In this case, the command will be aws ec2 modify-local-gateway-route, and the arguments are the same as with the create command. Use this command when you want to shift inbound traffic from one EC2 instance to another – perhaps from an active to a standby network appliance while you perform required maintenance on the primary instance.
$ aws ec2 modify-local-gateway-route \ --local-gateway-route-table-id <lgw-rtb-id> \ --network-interface-id <new-eni-id> \ --destination-cidr-block 198.19.33.248/29 { "Route": { "DestinationCidrBlock": "198.19.33.248/29", "NetworkInterfaceId": "new-eni-id", "Type": "static", "State": "active", "LocalGatewayRouteTableId": "lgw-rtb-id", "LocalGatewayRouteTableArn": "arn:aws:ec2:<AWS-REGION>:<account-id>:local-gateway-route-table/<lgw-rtb-id>", "OwnerId": "<account-id>" } }Conclusion
AWS Outposts LGW ingress routing allows AWS customers and partners to deploy virtual appliances on Outposts rack and direct inbound traffic through those appliances. The virtual appliance can inspect, filter, and optimize the ingress traffic before forwarding it on to the workloads running on Outposts rack, creating fine-grained network and security policies for your workloads. To learn more about AWS Outposts rack, visit the product overview page.