From 055e2528720c8e4801ac97d7d48e1358aad87af4 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Harald=20Jens=C3=A5s?= <hjensas@redhat.com>
Date: Tue, 25 Sep 2018 01:06:48 +0200
Subject: [PATCH] Add ctlplane interface routes

For the isolated networks we use the subnets host_routes
to set and get the routes for overcloud node interfaces.

This change add's this to the ctlplane interface.

Partial: blueprint tripleo-routed-networks-templates
Change-Id: Id4cf0cc17bc331ae27f8d0ef8f285050330b7be0
---
 .../net-config-multinode-os-net-config.yaml   |  8 +++++++
 ci/common/net-config-multinode.yaml           |  8 +++++++
 ci/common/net-config-simple-bridge.yaml       |  8 +++++++
 .../nic-configs/ceph-storage.yaml             |  8 +++++++
 .../nic-configs/cinder-storage.yaml           |  8 +++++++
 .../nic-configs/compute.yaml                  |  8 +++++++
 .../nic-configs/controller.yaml               |  8 +++++++
 .../nic-configs/swift-storage.yaml            |  8 +++++++
 .../nic-configs/ceph-storage.yaml             |  8 +++++++
 .../nic-configs/cinder-storage.yaml           |  8 +++++++
 .../multiple-nics/nic-configs/compute.yaml    |  8 +++++++
 .../multiple-nics/nic-configs/controller.yaml |  8 +++++++
 .../nic-configs/swift-storage.yaml            |  8 +++++++
 .../public-bond/nic-configs/ceph-storage.yaml |  8 +++++++
 .../nic-configs/cinder-storage.yaml           |  8 +++++++
 .../public-bond/nic-configs/compute.yaml      |  8 +++++++
 .../public-bond/nic-configs/controller.yaml   |  8 +++++++
 .../nic-configs/swift-storage.yaml            |  8 +++++++
 net-config-bond.j2.yaml                       |  8 +++++++
 net-config-bridge.j2.yaml                     |  8 +++++++
 net-config-linux-bridge.j2.yaml               |  8 +++++++
 net-config-noop.j2.yaml                       |  8 +++++++
 net-config-standalone.j2.yaml                 |  6 ++++-
 ...g-static-bridge-with-external-dhcp.j2.yaml |  8 +++++++
 net-config-static-bridge.j2.yaml              |  8 +++++++
 net-config-static.j2.yaml                     |  8 +++++++
 net-config-undercloud.j2.yaml                 |  6 ++++-
 .../controller-no-external.j2.yaml            | 22 ++++++++++++-----
 .../bond-with-vlans/controller-v6.j2.yaml     | 22 ++++++++++++-----
 .../config/bond-with-vlans/role.role.j2.yaml  |  9 +++++++
 .../config/multiple-nics/compute-dvr.j2.yaml  | 22 ++++++++++++-----
 .../multiple-nics/controller-v6.j2.yaml       | 24 +++++++++++++------
 .../config/multiple-nics/role.role.j2.yaml    | 22 ++++++++++++-----
 .../controller-v6.j2.yaml                     | 22 ++++++++++++-----
 .../role.role.j2.yaml                         | 22 ++++++++++++-----
 .../controller-no-external.j2.yaml            | 22 ++++++++++++-----
 .../single-nic-vlans/controller-v6.j2.yaml    | 22 ++++++++++++-----
 .../config/single-nic-vlans/role.role.j2.yaml | 22 ++++++++++++-----
 puppet/role.role.j2.yaml                      | 16 +++++++++++++
 39 files changed, 396 insertions(+), 63 deletions(-)

diff --git a/ci/common/net-config-multinode-os-net-config.yaml b/ci/common/net-config-multinode-os-net-config.yaml
index e5d51e60df..beb12f2c5c 100644
--- a/ci/common/net-config-multinode-os-net-config.yaml
+++ b/ci/common/net-config-multinode-os-net-config.yaml
@@ -20,6 +20,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   ExternalIpSubnet:
     default: ''
     description: IP address/subnet on the external network
diff --git a/ci/common/net-config-multinode.yaml b/ci/common/net-config-multinode.yaml
index 97b668a544..a23a52c47f 100644
--- a/ci/common/net-config-multinode.yaml
+++ b/ci/common/net-config-multinode.yaml
@@ -20,6 +20,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   ExternalIpSubnet:
     default: ''
     description: IP address/subnet on the external network
diff --git a/ci/common/net-config-simple-bridge.yaml b/ci/common/net-config-simple-bridge.yaml
index 762f52f7bc..52bf8c1c58 100644
--- a/ci/common/net-config-simple-bridge.yaml
+++ b/ci/common/net-config-simple-bridge.yaml
@@ -17,6 +17,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   ExternalIpSubnet:
     default: ''
     description: IP address/subnet on the external network
diff --git a/ci/environments/network/multiple-nics-ipv6/nic-configs/ceph-storage.yaml b/ci/environments/network/multiple-nics-ipv6/nic-configs/ceph-storage.yaml
index c42b8b9817..bad7fbc704 100644
--- a/ci/environments/network/multiple-nics-ipv6/nic-configs/ceph-storage.yaml
+++ b/ci/environments/network/multiple-nics-ipv6/nic-configs/ceph-storage.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/multiple-nics-ipv6/nic-configs/cinder-storage.yaml b/ci/environments/network/multiple-nics-ipv6/nic-configs/cinder-storage.yaml
index 5bf8dd253b..0b01f3dabf 100644
--- a/ci/environments/network/multiple-nics-ipv6/nic-configs/cinder-storage.yaml
+++ b/ci/environments/network/multiple-nics-ipv6/nic-configs/cinder-storage.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/multiple-nics-ipv6/nic-configs/compute.yaml b/ci/environments/network/multiple-nics-ipv6/nic-configs/compute.yaml
index 4236212ff8..afb583de19 100644
--- a/ci/environments/network/multiple-nics-ipv6/nic-configs/compute.yaml
+++ b/ci/environments/network/multiple-nics-ipv6/nic-configs/compute.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/multiple-nics-ipv6/nic-configs/controller.yaml b/ci/environments/network/multiple-nics-ipv6/nic-configs/controller.yaml
index 0105cbc3eb..b4e8d99ac6 100644
--- a/ci/environments/network/multiple-nics-ipv6/nic-configs/controller.yaml
+++ b/ci/environments/network/multiple-nics-ipv6/nic-configs/controller.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/multiple-nics-ipv6/nic-configs/swift-storage.yaml b/ci/environments/network/multiple-nics-ipv6/nic-configs/swift-storage.yaml
index 5bf8dd253b..0b01f3dabf 100644
--- a/ci/environments/network/multiple-nics-ipv6/nic-configs/swift-storage.yaml
+++ b/ci/environments/network/multiple-nics-ipv6/nic-configs/swift-storage.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/multiple-nics/nic-configs/ceph-storage.yaml b/ci/environments/network/multiple-nics/nic-configs/ceph-storage.yaml
index 0da7d3b8bd..d55b661161 100644
--- a/ci/environments/network/multiple-nics/nic-configs/ceph-storage.yaml
+++ b/ci/environments/network/multiple-nics/nic-configs/ceph-storage.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/multiple-nics/nic-configs/cinder-storage.yaml b/ci/environments/network/multiple-nics/nic-configs/cinder-storage.yaml
index ef40277560..9087fe07b5 100644
--- a/ci/environments/network/multiple-nics/nic-configs/cinder-storage.yaml
+++ b/ci/environments/network/multiple-nics/nic-configs/cinder-storage.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/multiple-nics/nic-configs/compute.yaml b/ci/environments/network/multiple-nics/nic-configs/compute.yaml
index fcd8f8fe51..84c1576bab 100644
--- a/ci/environments/network/multiple-nics/nic-configs/compute.yaml
+++ b/ci/environments/network/multiple-nics/nic-configs/compute.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/multiple-nics/nic-configs/controller.yaml b/ci/environments/network/multiple-nics/nic-configs/controller.yaml
index 18a977102e..aee95bd289 100644
--- a/ci/environments/network/multiple-nics/nic-configs/controller.yaml
+++ b/ci/environments/network/multiple-nics/nic-configs/controller.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/multiple-nics/nic-configs/swift-storage.yaml b/ci/environments/network/multiple-nics/nic-configs/swift-storage.yaml
index ef40277560..9087fe07b5 100644
--- a/ci/environments/network/multiple-nics/nic-configs/swift-storage.yaml
+++ b/ci/environments/network/multiple-nics/nic-configs/swift-storage.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/public-bond/nic-configs/ceph-storage.yaml b/ci/environments/network/public-bond/nic-configs/ceph-storage.yaml
index b31b917c75..6681302414 100644
--- a/ci/environments/network/public-bond/nic-configs/ceph-storage.yaml
+++ b/ci/environments/network/public-bond/nic-configs/ceph-storage.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/public-bond/nic-configs/cinder-storage.yaml b/ci/environments/network/public-bond/nic-configs/cinder-storage.yaml
index 73a7d4e50f..740109a4b0 100644
--- a/ci/environments/network/public-bond/nic-configs/cinder-storage.yaml
+++ b/ci/environments/network/public-bond/nic-configs/cinder-storage.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/public-bond/nic-configs/compute.yaml b/ci/environments/network/public-bond/nic-configs/compute.yaml
index 0e894cbfed..999285dbf7 100644
--- a/ci/environments/network/public-bond/nic-configs/compute.yaml
+++ b/ci/environments/network/public-bond/nic-configs/compute.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/public-bond/nic-configs/controller.yaml b/ci/environments/network/public-bond/nic-configs/controller.yaml
index 648b0ac74d..83b48ad86e 100644
--- a/ci/environments/network/public-bond/nic-configs/controller.yaml
+++ b/ci/environments/network/public-bond/nic-configs/controller.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/ci/environments/network/public-bond/nic-configs/swift-storage.yaml b/ci/environments/network/public-bond/nic-configs/swift-storage.yaml
index 73a7d4e50f..740109a4b0 100644
--- a/ci/environments/network/public-bond/nic-configs/swift-storage.yaml
+++ b/ci/environments/network/public-bond/nic-configs/swift-storage.yaml
@@ -121,6 +121,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/net-config-bond.j2.yaml b/net-config-bond.j2.yaml
index 642058fdde..d1866c1864 100644
--- a/net-config-bond.j2.yaml
+++ b/net-config-bond.j2.yaml
@@ -27,6 +27,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/net-config-bridge.j2.yaml b/net-config-bridge.j2.yaml
index aa5cff66ac..85eec2d210 100644
--- a/net-config-bridge.j2.yaml
+++ b/net-config-bridge.j2.yaml
@@ -17,6 +17,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/net-config-linux-bridge.j2.yaml b/net-config-linux-bridge.j2.yaml
index e46fb58fde..5fc15fa363 100644
--- a/net-config-linux-bridge.j2.yaml
+++ b/net-config-linux-bridge.j2.yaml
@@ -25,6 +25,14 @@ parameters:
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
     default: 192.168.24.1
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   ControlPlaneSubnetCidr:
     default: ''
     description: >
diff --git a/net-config-noop.j2.yaml b/net-config-noop.j2.yaml
index 2ac51db424..5417761135 100644
--- a/net-config-noop.j2.yaml
+++ b/net-config-noop.j2.yaml
@@ -20,6 +20,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/net-config-standalone.j2.yaml b/net-config-standalone.j2.yaml
index ecfcfb0eae..69c9224db4 100644
--- a/net-config-standalone.j2.yaml
+++ b/net-config-standalone.j2.yaml
@@ -34,7 +34,11 @@ parameters:
     type: string
   ControlPlaneStaticRoutes:
     default: []
-    description: A list of static routes
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
     type: json
   DnsServers: # Override this via parameter_defaults
     default: []
diff --git a/net-config-static-bridge-with-external-dhcp.j2.yaml b/net-config-static-bridge-with-external-dhcp.j2.yaml
index f43cc47c64..2752f2c72c 100644
--- a/net-config-static-bridge-with-external-dhcp.j2.yaml
+++ b/net-config-static-bridge-with-external-dhcp.j2.yaml
@@ -32,6 +32,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/net-config-static-bridge.j2.yaml b/net-config-static-bridge.j2.yaml
index 5d67c3e091..363a790abd 100644
--- a/net-config-static-bridge.j2.yaml
+++ b/net-config-static-bridge.j2.yaml
@@ -32,6 +32,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/net-config-static.j2.yaml b/net-config-static.j2.yaml
index 334ed32e93..46037415ba 100644
--- a/net-config-static.j2.yaml
+++ b/net-config-static.j2.yaml
@@ -31,6 +31,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   DnsServers: # Override this via parameter_defaults
     default: []
     description: >
diff --git a/net-config-undercloud.j2.yaml b/net-config-undercloud.j2.yaml
index e4f43edee9..e106dfb5ad 100644
--- a/net-config-undercloud.j2.yaml
+++ b/net-config-undercloud.j2.yaml
@@ -34,7 +34,11 @@ parameters:
     type: string
   ControlPlaneStaticRoutes:
     default: []
-    description: A list of static routes
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
     type: json
   DnsServers: # Override this via parameter_defaults
     default: []
diff --git a/network/config/bond-with-vlans/controller-no-external.j2.yaml b/network/config/bond-with-vlans/controller-no-external.j2.yaml
index 957bfdf493..6b81706232 100644
--- a/network/config/bond-with-vlans/controller-no-external.j2.yaml
+++ b/network/config/bond-with-vlans/controller-no-external.j2.yaml
@@ -21,6 +21,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -90,12 +98,14 @@ resources:
                     - - get_param: ControlPlaneIp
                       - get_param: ControlPlaneSubnetCidr
                 routes:
-                - ip_netmask: 169.254.169.254/32
-                  next_hop:
-                    get_param: EC2MetadataIp
-                - default: true
-                  next_hop:
-                    get_param: ControlPlaneDefaultRoute
+                  list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
+                    - - ip_netmask: 169.254.169.254/32
+                        next_hop:
+                          get_param: EC2MetadataIp
+                      - default: true  # NOTE(hjensas): This is the IPv4 default route
+                        next_hop:
+                        get_param: ControlPlaneDefaultRoute
               - type: ovs_bridge
                 name: bridge_name
                 use_dhcp: true
diff --git a/network/config/bond-with-vlans/controller-v6.j2.yaml b/network/config/bond-with-vlans/controller-v6.j2.yaml
index d6086c08a3..39c347c347 100644
--- a/network/config/bond-with-vlans/controller-v6.j2.yaml
+++ b/network/config/bond-with-vlans/controller-v6.j2.yaml
@@ -19,6 +19,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -88,12 +96,14 @@ resources:
                     - - get_param: ControlPlaneIp
                       - get_param: ControlPlaneSubnetCidr
                 routes:
-                - ip_netmask: 169.254.169.254/32
-                  next_hop:
-                    get_param: EC2MetadataIp
-                - default: true  # NOTE(hjensas): This is the IPv4 default route
-                  next_hop:
-                    get_param: ControlPlaneDefaultRoute
+                  list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
+                    - - ip_netmask: 169.254.169.254/32
+                        next_hop:
+                          get_param: EC2MetadataIp
+                      - default: true  # NOTE(hjensas): This is the IPv4 default route
+                        next_hop:
+                        get_param: ControlPlaneDefaultRoute
               - type: ovs_bridge
                 name: bridge_name
                 dns_servers:
diff --git a/network/config/bond-with-vlans/role.role.j2.yaml b/network/config/bond-with-vlans/role.role.j2.yaml
index a7c072a398..2c5027a770 100644
--- a/network/config/bond-with-vlans/role.role.j2.yaml
+++ b/network/config/bond-with-vlans/role.role.j2.yaml
@@ -17,6 +17,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -93,6 +101,7 @@ resources:
                       - get_param: ControlPlaneSubnetCidr
                 routes:
                   list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
                     - - ip_netmask: 169.254.169.254/32
                         next_hop:
                           get_param: EC2MetadataIp
diff --git a/network/config/multiple-nics/compute-dvr.j2.yaml b/network/config/multiple-nics/compute-dvr.j2.yaml
index 34c087021c..15d32fdc12 100644
--- a/network/config/multiple-nics/compute-dvr.j2.yaml
+++ b/network/config/multiple-nics/compute-dvr.j2.yaml
@@ -19,6 +19,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -84,12 +92,14 @@ resources:
                     - - get_param: ControlPlaneIp
                       - get_param: ControlPlaneSubnetCidr
                 routes:
-                - ip_netmask: 169.254.169.254/32
-                  next_hop:
-                    get_param: EC2MetadataIp
-                - default: true
-                  next_hop:
-                    get_param: ControlPlaneDefaultRoute
+                  list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
+                    - - ip_netmask: 169.254.169.254/32
+                        next_hop:
+                          get_param: EC2MetadataIp
+                      - default: true
+                        next_hop:
+                          get_param: ControlPlaneDefaultRoute
               - type: interface
                 name: nic2
                 use_dhcp: false
diff --git a/network/config/multiple-nics/controller-v6.j2.yaml b/network/config/multiple-nics/controller-v6.j2.yaml
index 1f5c7f8ffb..ab04bf6403 100644
--- a/network/config/multiple-nics/controller-v6.j2.yaml
+++ b/network/config/multiple-nics/controller-v6.j2.yaml
@@ -18,6 +18,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -83,13 +91,15 @@ resources:
                     - - get_param: ControlPlaneIp
                       - get_param: ControlPlaneSubnetCidr
                 routes:
-                - ip_netmask: 169.254.169.254/32
-                  next_hop:
-                    get_param: EC2MetadataIp
-                # IPv4 Default Route
-                - default: true  # NOTE(hjensas): This is the IPv4 default route
-                  next_hop:
-                    get_param: ControlPlaneDefaultRoute
+                  list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
+                    - - ip_netmask: 169.254.169.254/32
+                        next_hop:
+                          get_param: EC2MetadataIp
+                      # IPv4 Default Route
+                      - default: true  # NOTE(hjensas): This is the IPv4 default route
+                        next_hop:
+                          get_param: ControlPlaneDefaultRoute
               - type: interface
                 name: nic2
                 use_dhcp: false
diff --git a/network/config/multiple-nics/role.role.j2.yaml b/network/config/multiple-nics/role.role.j2.yaml
index 1191e747da..9bb347ee7b 100644
--- a/network/config/multiple-nics/role.role.j2.yaml
+++ b/network/config/multiple-nics/role.role.j2.yaml
@@ -17,6 +17,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -88,13 +96,15 @@ resources:
                     - - get_param: ControlPlaneIp
                       - get_param: ControlPlaneSubnetCidr
                 routes:
-                - ip_netmask: 169.254.169.254/32
-                  next_hop:
-                    get_param: EC2MetadataIp
+                  list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
+                    - - ip_netmask: 169.254.169.254/32
+                        next_hop:
+                          get_param: EC2MetadataIp
 {%- if role.default_route_networks is not defined or 'ControlPlane' in role.default_route_networks %}
-                - default: true
-                  next_hop:
-                    get_param: ControlPlaneDefaultRoute
+                      - default: true
+                        next_hop:
+                          get_param: ControlPlaneDefaultRoute
 {%- endif %}
 {%- set nics_used = [1] %}
 {%- for network in networks if network.enabled|default(true) and network.name not in role.networks_skip_config|default([]) %}
diff --git a/network/config/single-nic-linux-bridge-vlans/controller-v6.j2.yaml b/network/config/single-nic-linux-bridge-vlans/controller-v6.j2.yaml
index e51e7eee5b..1562b82eaa 100644
--- a/network/config/single-nic-linux-bridge-vlans/controller-v6.j2.yaml
+++ b/network/config/single-nic-linux-bridge-vlans/controller-v6.j2.yaml
@@ -18,6 +18,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -83,12 +91,14 @@ resources:
                     - - get_param: ControlPlaneIp
                       - get_param: ControlPlaneSubnetCidr
                 routes:
-                - ip_netmask: 169.254.169.254/32
-                  next_hop:
-                    get_param: EC2MetadataIp
-                - default: true  # NOTE(hjensas): This is the IPv4 default route
-                  next_hop:
-                    get_param: ControlPlaneDefaultRoute
+                  list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
+                    - - ip_netmask: 169.254.169.254/32
+                        next_hop:
+                          get_param: EC2MetadataIp
+                      - default: true  # NOTE(hjensas): This is the IPv4 default route
+                        next_hop:
+                          get_param: ControlPlaneDefaultRoute
                 members:
                 - type: interface
                   name: interface_name
diff --git a/network/config/single-nic-linux-bridge-vlans/role.role.j2.yaml b/network/config/single-nic-linux-bridge-vlans/role.role.j2.yaml
index c1e688ed18..e3a4a96bba 100644
--- a/network/config/single-nic-linux-bridge-vlans/role.role.j2.yaml
+++ b/network/config/single-nic-linux-bridge-vlans/role.role.j2.yaml
@@ -17,6 +17,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -86,13 +94,15 @@ resources:
                     - - get_param: ControlPlaneIp
                       - get_param: ControlPlaneSubnetCidr
                 routes:
-                - ip_netmask: 169.254.169.254/32
-                  next_hop:
-                    get_param: EC2MetadataIp
+                  list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
+                    - - ip_netmask: 169.254.169.254/32
+                        next_hop:
+                          get_param: EC2MetadataIp
 {%- if role.default_route_networks is not defined or 'ControlPlane' in role.default_route_networks %}
-                - default: true
-                  next_hop:
-                    get_param: ControlPlaneDefaultRoute
+                      - default: true
+                        next_hop:
+                          get_param: ControlPlaneDefaultRoute
 {%- endif %}
                 members:
                 - type: interface
diff --git a/network/config/single-nic-vlans/controller-no-external.j2.yaml b/network/config/single-nic-vlans/controller-no-external.j2.yaml
index bc559908e2..96a642921c 100644
--- a/network/config/single-nic-vlans/controller-no-external.j2.yaml
+++ b/network/config/single-nic-vlans/controller-no-external.j2.yaml
@@ -21,6 +21,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -86,12 +94,14 @@ resources:
                     - - get_param: ControlPlaneIp
                       - get_param: ControlPlaneSubnetCidr
                 routes:
-                - ip_netmask: 169.254.169.254/32
-                  next_hop:
-                    get_param: EC2MetadataIp
-                - default: true
-                  next_hop:
-                    get_param: ControlPlaneDefaultRoute
+                  list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
+                    - - ip_netmask: 169.254.169.254/32
+                        next_hop:
+                          get_param: EC2MetadataIp
+                      - default: true
+                        next_hop:
+                          get_param: ControlPlaneDefaultRoute
                 members:
                 - type: interface
                   name: nic1
diff --git a/network/config/single-nic-vlans/controller-v6.j2.yaml b/network/config/single-nic-vlans/controller-v6.j2.yaml
index 39fc32b292..5125a72bce 100644
--- a/network/config/single-nic-vlans/controller-v6.j2.yaml
+++ b/network/config/single-nic-vlans/controller-v6.j2.yaml
@@ -18,6 +18,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -83,12 +91,14 @@ resources:
                     - - get_param: ControlPlaneIp
                       - get_param: ControlPlaneSubnetCidr
                 routes:
-                - ip_netmask: 169.254.169.254/32
-                  next_hop:
-                    get_param: EC2MetadataIp
-                - default: true  # NOTE(hjensas): This is the IPv4 default route
-                  next_hop:
-                    get_param: ControlPlaneDefaultRoute
+                  list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
+                    - - ip_netmask: 169.254.169.254/32
+                        next_hop:
+                          get_param: EC2MetadataIp
+                      - default: true  # NOTE(hjensas): This is the IPv4 default route
+                        next_hop:
+                          get_param: ControlPlaneDefaultRoute
                 members:
                 - type: interface
                   name: nic1
diff --git a/network/config/single-nic-vlans/role.role.j2.yaml b/network/config/single-nic-vlans/role.role.j2.yaml
index 9188e9e9ef..0f02e1a574 100644
--- a/network/config/single-nic-vlans/role.role.j2.yaml
+++ b/network/config/single-nic-vlans/role.role.j2.yaml
@@ -17,6 +17,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
 {% for network in networks %}
   {{network.name}}IpSubnet:
     default: ''
@@ -86,13 +94,15 @@ resources:
                     - - get_param: ControlPlaneIp
                       - get_param: ControlPlaneSubnetCidr
                 routes:
-                - ip_netmask: 169.254.169.254/32
-                  next_hop:
-                    get_param: EC2MetadataIp
+                  list_concat_unique:
+                    - get_param: ControlPlaneStaticRoutes
+                    - - ip_netmask: 169.254.169.254/32
+                        next_hop:
+                          get_param: EC2MetadataIp
 {%- if role.default_route_networks is not defined or 'ControlPlane' in role.default_route_networks %}
-                - default: true
-                  next_hop:
-                    get_param: ControlPlaneDefaultRoute
+                      - default: true
+                        next_hop:
+                          get_param: ControlPlaneDefaultRoute
 {%- endif %}
                 members:
                 - type: interface
diff --git a/puppet/role.role.j2.yaml b/puppet/role.role.j2.yaml
index e59f1ddb18..a9f47651ba 100644
--- a/puppet/role.role.j2.yaml
+++ b/puppet/role.role.j2.yaml
@@ -249,6 +249,14 @@ parameters:
     description: The default route of the control plane network. (The parameter
       is automatically resolved from the ctlplane subnet's gateway_ip attribute.)
     type: string
+  ControlPlaneStaticRoutes:
+    default: []
+    description: >
+      Routes for the ctlplane network traffic.
+      JSON route e.g. [{'destination':'10.0.0.0/16', 'nexthop':'10.0.0.1'}]
+      Unless the default is changed, the parameter is automatically resolved
+      from the subnet host_routes attribute.
+    type: json
   EC2MetadataIp:
     default: ''
     description: The IP address of the EC2 metadata server. (The parameter
@@ -353,6 +361,9 @@ conditions:
   ctlplane_default_route_set:
     not:
       equals: [{get_param: ControlPlaneDefaultRoute}, '']
+  ctlplane_static_routes_set:
+    not:
+        equals: [{get_param: ControlPlaneStaticRoutes}, []]
   ec2metadaip_set:
     not:
       equals: [{get_param: EC2MetadataIp}, '']
@@ -504,6 +515,11 @@ resources:
           - ctlplane_default_route_set
           - {get_param: ControlPlaneDefaultRoute}
           - {get_attr: [{{server_resource_name}}, addresses, ctlplane, 0, subnets, 0, gateway_ip]}
+      ControlPlaneStaticRoutes:
+        if:
+          - ctlplane_static_routes_set
+          - {get_param: ControlPlaneStaticRoutes}
+          - {get_attr: [{{server_resource_name}}, addresses, ctlplane, 0, subnets, 0, host_routes]}
       EC2MetadataIp:
         if:
           - ec2metadaip_set