Chapter 10. Creating the data plane for SR-IOV and DPDK environments
You can deploy Red Hat OpenStack Services on OpenShift (RHOSO) environments that take advantage of the performance and throughput advantages of SR-IOV and DPDK.
The Red Hat OpenStack Services on OpenShift (RHOSO) data plane consists of RHEL 9.4 or 9.6 nodes. Use the OpenStackDataPlaneNodeSet custom resource definition (CRD) to create the custom resources (CRs) that define the nodes and the layout of the data plane. After you have defined your OpenStackDataPlaneNodeSet CRs, you create an OpenStackDataPlaneDeployment CR that deploys each of your OpenStackDataPlaneNodeSet CRs.
An OpenStackDataPlaneNodeSet CR is a logical grouping of nodes of a similar type. A data plane typically consists of multiple OpenStackDataPlaneNodeSet CRs to define groups of nodes with different configurations and roles. You can use pre-provisioned or unprovisioned nodes in an OpenStackDataPlaneNodeSet CR:
- Pre-provisioned node: You have used your own tools to install the operating system on the node before adding it to the data plane.
- Unprovisioned node: The node does not have an operating system installed before you add it to the data plane. The node is provisioned by using the Cluster Baremetal Operator (CBO) as part of the data plane creation and deployment process.
You cannot include both pre-provisioned and unprovisioned nodes in the same OpenStackDataPlaneNodeSet CR.
To create and deploy a data plane, you must perform the following tasks:
-
Create a
SecretCR for each node set for Ansible to use to run commands on the data plane nodes. -
Create the
OpenStackDataPlaneNodeSetCRs that define the nodes and layout of the data plane. -
Create the
OpenStackDataPlaneDeploymentCR that triggers the Ansible execution that deploys and configures the software for the specified list ofOpenStackDataPlaneNodeSetCRs.
The following procedures create two simple node sets, one with pre-provisioned nodes, and one with bare-metal nodes that must be provisioned during the node set deployment. The procedures aim to get you up and running quickly with a data plane environment that you can use to troubleshoot issues and test the environment before adding all the customizations you require. You can add additional node sets to a deployed environment, and you can customize your deployed environment by updating the common configuration in the default ConfigMap CR for the service, and by creating custom services.
10.1. Prerequisites Copy linkLink copied to clipboard!
- A functional control plane, created with the OpenStack Operator.
-
You are logged on to a workstation that has access to the Red Hat OpenShift Container Platform (RHOCP) cluster as a user with
cluster-adminprivileges.
10.2. Creating the data plane secrets Copy linkLink copied to clipboard!
Create the Secret custom resources (CRs) that the data plane requires to operate. The Secret CRs secure access between nodes, register the operating systems with the Red Hat Customer Portal, enable node repositories, and provide Compute nodes with access to libvirt.
To enable secure access between nodes, you must generate two SSH keys and create an SSH key Secret CR for each key:
An SSH key to enable Ansible to manage the RHEL nodes on the data plane. Ansible executes commands with this user and key. You can create an SSH key for each
OpenStackDataPlaneNodeSetCR in your data plane.- An SSH key to enable migration of instances between Compute nodes.
Prerequisites
-
Pre-provisioned nodes are configured with an SSH public key in the
$HOME/.ssh/authorized_keysfile for a user with passwordlesssudoprivileges. For more information, see Managing sudo access in the RHEL Configuring basic system settings guide.
Procedure
For unprovisioned nodes, create the SSH key pair for Ansible:
$ ssh-keygen -f <key_file_name> -N "" -t rsa -b 4096-
Replace
<key_file_name>with the name to use for the key pair.
-
Replace
Create the
SecretCR for Ansible and apply it to the cluster:$ oc create secret generic dataplane-ansible-ssh-private-key-secret \ --save-config \ --dry-run=client \ --from-file=ssh-privatekey=<key_file_name> \ --from-file=ssh-publickey=<key_file_name>.pub \ [--from-file=authorized_keys=<key_file_name>.pub] -n openstack \ -o yaml | oc apply -f --
Replace
<key_file_name>with the name and location of your SSH key pair file. -
Optional: Only include the
--from-file=authorized_keysoption for bare-metal nodes that must be provisioned when creating the data plane.
-
Replace
If you are creating Compute nodes, create a secret for migration.
Create the SSH key pair for instance migration:
$ ssh-keygen -f ./nova-migration-ssh-key -t ecdsa-sha2-nistp521 -N ''Create the
SecretCR for migration and apply it to the cluster:$ oc create secret generic nova-migration-ssh-key \ --save-config \ --from-file=ssh-privatekey=nova-migration-ssh-key \ --from-file=ssh-publickey=nova-migration-ssh-key.pub \ -n openstack \ -o yaml | oc apply -f -
For nodes that have not been registered to the Red Hat Customer Portal, create the
SecretCR for subscription-manager credentials to register the nodes:$ oc create secret generic subscription-manager \ --from-literal rhc_auth='{"login": {"username": "<subscription_manager_username>", "password": "<subscription_manager_password>"}}'-
Replace
<subscription_manager_username>with the username you set forsubscription-manager. -
Replace
<subscription_manager_password>with the password you set forsubscription-manager.
-
Replace
Create a
SecretCR that contains the Red Hat registry credentials:$ oc create secret generic redhat-registry --from-literal edpm_container_registry_logins='{"registry.redhat.io": {"<username>": "<password>"}}'Replace
<username>and<password>with your Red Hat registry username and password credentials.For information about how to create your registry service account, see the Knowledge Base article Creating Registry Service Accounts.
If you are creating Compute nodes, create a secret for libvirt.
Create a file on your workstation named
secret_libvirt.yamlto define the libvirt secret:apiVersion: v1 kind: Secret metadata: name: libvirt-secret namespace: openstack type: Opaque data: LibvirtPassword: <base64_password>Replace
<base64_password>with a base64-encoded string with maximum length 63 characters. You can use the following command to generate a base64-encoded password:$ echo -n <password> | base64TipIf you do not want to base64-encode the username and password, you can use the
stringDatafield instead of thedatafield to set the username and password.
Create the
SecretCR:$ oc apply -f secret_libvirt.yaml -n openstack
Verify that the
SecretCRs are created:$ oc describe secret dataplane-ansible-ssh-private-key-secret $ oc describe secret nova-migration-ssh-key $ oc describe secret subscription-manager $ oc describe secret redhat-registry $ oc describe secret libvirt-secret
10.3. Creating a custom SR-IOV Compute service Copy linkLink copied to clipboard!
You must create a custom SR-IOV Compute service for NFV in a RHOSO environment.
This SR-IOV Compute service is an Ansible service that runs on the data plane. This custom service performs the following tasks on the SR-IOV Compute nodes:
- Applies CPU pinning parameters.
- Performs PCI passthrough.
To create the SR-IOV custom service, you must perform these actions:
-
Create a
ConfigMapfor CPU pinning that maps a CPU pinning configuration to a specified set of SR-IOV Compute nodes. -
Create a
ConfigMapfor PCI passthrough that maps a PCI passthrough configuration to a specified set of SR-IOV Compute nodes. -
Create the actual SR-IOV custom service that will implement the
configMapson your data plane.
Prerequisites
-
You have the
occommand line tool installed on your workstation. -
You are logged on to a workstation that has access to the RHOSO control plane as a user with
cluster-adminprivileges.
Procedure
Create a
ConfigMapCR that defines configurations for CPU pinning and PCI passthrough, and save it to a YAML file on your workstation, for example,pinning-passthrough.yaml.Change the values (in boldface) as appropriate for your environment:
--- apiVersion: v1 kind: ConfigMap metadata: name: cpu-pinning-nova data: 25-cpu-pinning-nova.conf: | [DEFAULT] reserved_host_memory_mb = 4096 [compute] cpu_shared_set = 0-3,24-27 cpu_dedicated_set = 8-23,32-47 [neutron] physnets = <network_name1>, <network_name2> [neutron_physnet_<network_name1>] numa_nodes = <ID list> [neutron_physnet_<network_name2>] numa_nodes = <ID list> [neutron_tunnel] numa_nodes = <ID list> --- apiVersion: v1 kind: ConfigMap metadata: name: sriov-nova data: 26-sriov-nova.conf: | [libvirt] cpu_power_management=false [pci] passthrough_whitelist = {"address": "0000:05:00.2", "physical_network":"sriov-1", "trusted":"true"} passthrough_whitelist = {"address": "0000:05:00.3", "physical_network":"sriov-2", "trusted":"true"} ----
cpu_shared_set: enter a comma-separated list or range of physical host CPU numbers used to provide vCPU inventory, determine the host CPUs that unpinned instances can be scheduled to, and determine the host CPUs that instance emulator threads should be offloaded to for instances configured with the share emulator thread policy. -
cpu_dedicated_set: enter a comma-separated list or range of physical host CPU numbers to which processes for pinned instance CPUs can be scheduled. For example,4-12,^8,15reserves cores from 4-12 and 15, excluding 8. -
<network_name_n_>: replace<network_name1>and<network_name2>with the names of the physical networks that your gateways are on. (This network is set in the neutron networkprovider:*namefield.) numa_nodes = <ID list>: replace<ID list>with a comma-separated list of IDs of the NUMA nodes associated with this physnet. For example:0,1. For example:[neutron] physnets = foo,bar [neutron_physnet_foo] numa_nodes = 0 [neutron_physnet_bar] numa_nodes = 2, 3This configuration ensures that instances using one or more L2-type networks with
provider:physical_network=foomust be scheduled on host cores from NUMA node 0, while instances using one or more networks withprovider:physical_network=barmust be scheduled on host cores from both NUMA nodes 2 and 3. For the latter case, it will be necessary to split the guest across two or more host NUMA nodes using thehw:numa_nodes extraspec.-
passthrough_whitelist: specify valid NIC addresses and names for"address"and"physical_network".
-
Create the
ConfigMapobject, using theConfigMapCR file:- Example
$ oc create -f sriov-pinning-passthru.yaml -n openstack
Create an
OpenStackDataPlaneServiceCR that defines the SR-IOV custom service, and save it to a YAML file on your workstation, for examplenova-custom-sriov.yaml:apiVersion: dataplane.openstack.org/v1beta1 kind: OpenStackDataPlaneService metadata: name: nova-custom-sriovAdd the
ConfigMapCRs to the custom service, and specify theSecretCR for the cell that the node set that runs this service connects to:apiVersion: dataplane.openstack.org/v1beta1 kind: OpenStackDataPlaneService metadata: name: nova-custom-sriov spec: label: dataplane-deployment-nova-custom-sriov dataSources: - configMapRef: name: cpu-pinning-nova - configMapRef: name: sriov-nova - secretRef: name: nova-cell1-compute-config - secretRef: name: nova-migration-ssh-key tlsCerts: default: contents: - dnsnames - ips networks: - ctlplane issuer: osp-rootca-issuer-internal caCerts: combined-ca-bundleSpecify the Ansible commands to create the custom service, by referencing an Ansible Playbook or by including the Ansible play in the
playbookContentsfield:apiVersion: dataplane.openstack.org/v1beta1 kind: OpenStackDataPlaneService metadata: name: nova-custom-sriov spec: label: dataplane-deployment-nova-custom-sriov edpmServiceType: nova dataSources: - configMapRef: name: cpu-pinning-nova - configMapRef: name: sriov-nova - secretRef: name: nova-cell1-compute-config - secretRef: name: nova-migration-ssh-key playbook: osp.edpm.nova tlsCerts: default: contents: - dnsnames - ips networks: - ctlplane issuer: osp-rootca-issuer-internal caCerts: combined-ca-bundleplaybook: identifies the default playbook available for your service.In this case, it is the Compute service (nova). To see the listing of default playbooks, see https://openstack-k8s-operators.github.io/edpm-ansible/playbooks.html.
Create the
custom-nova-sriovservice:$ oc apply -f nova-custom-sriov.yaml -n openstackVerify that the custom service is created:
$ oc get openstackdataplaneservice nova-custom-sriov -o yaml -n openstack
10.4. Create a custom OVS-DPDK Compute service Copy linkLink copied to clipboard!
You must create a custom OVS-DPDK Compute service for NFV in a RHOSO environment.
The OVS-DPDK Compute service is an Ansible service that is run on the data plane. This custom service applies various parameters on the OVS-DPDK Compute nodes, including CPU pinning parameters, a block migration parameter, and a NUMA-aware vswitch feature that allows instances to create in the NUMA node that is connected to the NIC used by the OVS bridge.
To create the OVS-DPDK custom service, you must perform these actions:
-
Create a
ConfigMapthat maps the configurations to a specified set of OVS-DPDK Compute nodes. -
Create the actual OVS-DPDK custom service that will implement the
ConfigMapon your data plane.
Prerequisites
-
You have the
occommand line tool installed on your workstation. -
You are logged on to a workstation that has access to the RHOSO control plane as a user with
cluster-adminprivileges.
Procedure
Create a
ConfigMapCR that defines a configuration for the parameters, and save it to a YAML file on your workstation, for example,dpdk-custom.yaml.Change the values (in boldface) as appropriate for your environment:
--- apiVersion: v1 kind: ConfigMap metadata: name: dpdk-custom-nova namespace: openstack data: 25-dpdk-custom-nova.conf: | [DEFAULT] reserved_host_memory_mb = 4096 [compute] cpu_shared_set = 0-3,24-27 cpu_dedicated_set = 8-23,32-47 [neutron] physnets = <network_name1>, <network_name2> [neutron_physnet_<network_name1>] numa_nodes = <ID list> [neutron_physnet_<network_name2>] numa_nodes = <ID list> [neutron_tunnel] numa_nodes = <ID list> [libvirt] live_migration_permit_post_copy=false ----
cpu_shared_set: enter a comma-separated list or range of physical host CPU numbers used to provide vCPU inventory, determine the host CPUs that unpinned instances can be scheduled to, and determine the host CPUs that instance emulator threads should be offloaded to for instances configured with the share emulator thread policy. -
cpu_dedicated_set: enter a comma-separated list or range of physical host CPU numbers to which processes for pinned instance CPUs can be scheduled. For example,4-12,^8,15reserves cores from 4-12 and 15, excluding 8. -
<network_name_n_>: replace<network_name1>and<network_name2>with the names of the physical networks that your gateways are on, for which you need to configure NUMA affinity. (This network is set in the neutron networkprovider:*namefield.) <ID list>: replace<ID list>with a comma-separated list of IDs of the NUMA nodes associated with this physnet. For example:0,1. For example:[neutron] physnets = foo,bar [neutron_physnet_foo] numa_nodes = 0 [neutron_physnet_bar] numa_nodes = 2, 3This configuration ensures that instances using one or more L2-type networks with
provider:physical_network=foo`must be scheduled on host cores from NUMA node 0, while instances using one or more networks withprovider:physical_network=bar`must be scheduled on host cores from both NUMA nodes 2 and 3. For the latter case, it will be necessary to split the guest across two or more host NUMA nodes using thehw:numa_nodes extra`spec.-
live_migration_permit_post_copy=false: necessary for successful block live migration of instances attached to a Geneve network with DPDK.
-
Create the
ConfigMapobject, using theConfigMapCR file:- Example
$ oc create -f dpdk-custom.yaml -n openstack
Create an
OpenStackDataPlaneServiceCR that defines the OVS-DPDK custom service, and save it to a YAML file on your workstation, for examplenova-custom-ovsdpdk.yaml:apiVersion: dataplane.openstack.org/v1beta1 kind: OpenStackDataPlaneService metadata: name: nova-custom-ovsdpdk namespace: openstackAdd the
ConfigMapCR to the custom service, and specify theSecretCR for the cell that the node set that runs this service connects to:apiVersion: dataplane.openstack.org/v1beta1 kind: OpenStackDataPlaneService metadata: name: nova-custom-ovsdpdk namespace: openstack spec: label: dataplane-deployment-nova-custom-ovsdpdk edpmServiceType: nova dataSources: - configMapRef: name: dpdk-custom-nova - secretRef: name: nova-cell1-compute-config - secretRef: name: nova-migration-ssh-key tlsCerts: default: contents: - dnsnames - ips networks: - ctlplane issuer: osp-rootca-issuer-internal caCerts: combined-ca-bundleSpecify the Ansible commands to create the custom service, by referencing an Ansible Playbook or by including the Ansible play in the
playbookContentsfield:apiVersion: dataplane.openstack.org/v1beta1 kind: OpenStackDataPlaneService metadata: name: nova-custom-ovsdpdk namespace: openstack spec: label: dataplane-deployment-nova-custom-ovsdpdk edpmServiceType: nova dataSources: - configMapRef: name: dpdk-custom-nova - secretRef: name: nova-cell1-compute-config - secretRef: name: nova-migration-ssh-key playbook: osp.edpm.nova tlsCerts: default: contents: - dnsnames - ips networks: - ctlplane issuer: osp-rootca-issuer-internal caCerts: combined-ca-bundleplaybook: identifies the default playbook available for your service.In this case, it is the Compute service (nova). To see the listing of default playbooks, see https://openstack-k8s-operators.github.io/edpm-ansible/playbooks.html.
Create the
nova-custom-ovsdpdkservice:$ oc apply -f nova-custom-ovsdpdk.yaml -n openstackVerify that the custom service is created:
$ oc get openstackdataplaneservice nova-custom-ovsdpdk -o yaml -n openstack
10.5. Create a set of data plane nodes with pre-provisioned nodes Copy linkLink copied to clipboard!
Define an OpenStackDataPlaneNodeSet custom resource (CR) for each logical grouping of pre-provisioned nodes in your data plane, for example, nodes grouped by hardware, location, or networking.
You can define as many node sets as necessary for your deployment. Each node can be included in only one OpenStackDataPlaneNodeSet CR. Each node set can be connected to only one Compute cell. By default, node sets are connected to cell1. If you customize your control plane to include additional Compute cells, you must specify the cell to which the node set is connected. For more information on adding Compute cells, see Connecting an OpenStackDataPlaneNodeSet CR to a Compute cell in the Customizing the Red Hat OpenStack Services on OpenShift deployment guide.
You use the nodeTemplate field to configure the properties that all nodes in an OpenStackDataPlaneNodeSet CR share, and the nodeTemplate.nodes field for node-specific properties. Node-specific configurations override the inherited values from the nodeTemplate.
Procedure
Create a file on your workstation named
openstack_preprovisioned_node_set.yamlto define theOpenStackDataPlaneNodeSetCR:apiVersion: dataplane.openstack.org/v1beta1 kind: OpenStackDataPlaneNodeSet metadata: name: openstack-data-plane namespace: openstack spec: env: - name: ANSIBLE_FORCE_COLOR value: "True"-
name- TheOpenStackDataPlaneNodeSetCR name must be unique, contain only lower case alphanumeric characters and-(hyphens) or.(periods), start and end with an alphanumeric character, and have a maximum length of 53 characters. Update the name in this example to a name that reflects the nodes in the set. -
env- Optional: a list of environment variables to pass to the pod.
-
Specify that the nodes in this set are pre-provisioned:
preProvisioned: trueAdd the SSH key secret that you created to enable Ansible to connect to the data plane nodes:
nodeTemplate: ansibleSSHPrivateKeySecret: <secret-key>-
Replace
<secret-key>with the name of the SSH keySecretCR you created for this node set in Creating the data plane secrets, for example,dataplane-ansible-ssh-private-key-secret.
-
Replace
-
Create a Persistent Volume Claim (PVC) in the
openstacknamespace on your Red Hat OpenShift Container Platform (RHOCP) cluster to store logs. Set thevolumeModetoFilesystemandaccessModestoReadWriteOnce. Do not request storage for logs from a PersistentVolume (PV) that uses the NFS volume plugin. NFS is incompatible with FIFO and theansible-runnercreates a FIFO file to write to store logs. For information about PVCs, see Understanding persistent storage in the RHOCP Storage guide and Red Hat OpenShift Container Platform cluster requirements in Planning your deployment. Enable persistent logging for the data plane nodes:
nodeTemplate: ansibleSSHPrivateKeySecret: <secret-key> extraMounts: - extraVolType: Logs volumes: - name: ansible-logs persistentVolumeClaim: claimName: <pvc_name> mounts: - name: ansible-logs mountPath: "/runner/artifacts"-
Replace
<pvc_name>with the name of the PVC storage on your RHOCP cluster.
-
Replace
-
Add the common configuration for the set of nodes in this group under the
nodeTemplatesection. Each node in thisOpenStackDataPlaneNodeSetinherits this configuration. For information about the properties you can use to configure common node attributes, seeOpenStackDataPlaneNodeSetCRspecproperties. Register the operating system of the nodes that are not registered to the Red Hat Customer Portal, and enable repositories for your nodes. The following steps demonstrate how to register your nodes to CDN. For details on how to register your nodes with Red Hat Satellite 6.13, see Managing Hosts.
Create a
SecretCR that contains thesubscription-managercredentials:apiVersion: v1 kind: Secret metadata: name: subscription-manager data: username: <base64_encoded_username> password: <base64_encoded_password>Create a
SecretCR that contains the Red Hat registry credentials:$ oc create secret generic redhat-registry --from-literal edpm_container_registry_logins='{"registry.redhat.io": {"<username>": "<password>"}}'-
Replace
<username>and<password>with your Red Hat registry username and password credentials.
-
Replace
For information about how to create your registry service account, see the Red Hat Knowledgebase article Creating Registry Service Accounts.
Specify the
SecretCRs to use to source the usernames and passwords:nodeTemplate: ansible: ... ansibleVarsFrom: - prefix: subscription_manager_ secretRef: name: subscription-manager - secretRef: name: redhat-registry ansibleVars: rhc_release: 9.4 rhc_repositories: - {name: "*", state: disabled} - {name: "<repository_name1>", state: enabled} - {name: "<repository_name2>", state: enabled} - {name: "<repository_name3>", state: enabled} - {name: "<repository_name4>", state: enabled} - {name: "<repository_name5>", state: enabled} - {name: "<repository_name6>", state: enabled}where:
<repository_name1>,<repository_name2>,<repository_name3>,<repository_name4>,<repository_name5>,<repository_name6>- Specifies the name of the repository to enable. For more information about which repositories are required, see Required repositories for Red Hat OpenStack Services on OpenShift 18.0.
Define each node in this node set:
nodes: edpm-compute-0: hostName: edpm-compute-0 networks: - name: ctlplane subnetName: subnet1 defaultRoute: true fixedIP: 192.168.122.100 - name: internalapi subnetName: subnet1 fixedIP: 172.17.0.100 - name: storage subnetName: subnet1 fixedIP: 172.18.0.100 - name: tenant subnetName: subnet1 fixedIP: 172.19.0.100 ansible: ansibleHost: 192.168.122.100 ansibleUser: cloud-admin ansibleVars: fqdn_internal_api: edpm-compute-0.example.com edpm_network_config_nmstate: true edpm-compute-1: hostName: edpm-compute-1 networks: - name: ctlplane subnetName: subnet1 defaultRoute: true fixedIP: 192.168.122.101 - name: internalapi subnetName: subnet1 fixedIP: 172.17.0.101 - name: storage subnetName: subnet1 fixedIP: 172.18.0.101 - name: tenant subnetName: subnet1 fixedIP: 172.19.0.101 ansible: ansibleHost: 192.168.122.101 ansibleUser: cloud-admin ansibleVars: fqdn_internal_api: edpm-compute-1.example.com-
edpm-compute-0- The node definition reference, for example,edpm-compute-0. Each node in the node set must have a node definition. -
networks- Defines the IPAM and the DNS records for the node. -
fixedIP- Specifies a predictable IP address for the network that must be in the allocation range defined for the network in theNetConfigCR. ansibleVars- Node-specific Ansible variables that customize the node.Note-
Nodes defined within the
nodessection can configure the same Ansible variables that are configured in thenodeTemplatesection. Where an Ansible variable is configured for both a specific node and within thenodeTemplatesection, the node-specific values override those from thenodeTemplatesection. -
You do not need to replicate all the
nodeTemplateAnsible variables for a node to override the default and set some node-specific values. You only need to configure the Ansible variables you want to override for the node. -
When you define the networkData Secret for an individual node (such as
edpm-compute-0), it acts as a complete override rather than a supplemental configuration. Because node-specific configurations override the inherited default values from thenodeTemplatesection, you must ensure that your node-specificnetworkDataSecret contains the full set of required network configurations for that node, not just the unique values. -
Many
ansibleVarsincludeedpmin the name, which stands for "External Data Plane Management".
-
Nodes defined within the
edpm_network_config_nmstate- Sets theos-net-configprovider tonmstate. The default value istrue. Change it tofalseonly if a specific limitation of thenmstateprovider requires you to use theifcfgprovider. For more information on advantages and limitations of thenmstateprovider, see https://docs.redhat.com/en/documentation/red_hat_openstack_services_on_openshift/18.0/html/planning_your_deployment/plan-networks_planning#plan-os-net-config_plan-network in Planning your deployment.For more information, see:
-
OpenStackDataPlaneNodeSetCR properties - Network interface configuration options
- Example custom network interfaces for NFV
-
In the
servicessection, add the list of services that will run on the data plane node. Ensure that you replacenovawithnova-custom-sriov, ornova-custom-ovsdpdk, or both:... services: - bootstrap - download-cache - reboot-os - configure-ovs-dpdk - configure-network - validate-network - install-os - configure-os - ssh-known-hosts - run-os - install-certs - ovn - neutron-ovn - neutron-ovn-igmp - neutron-metadata - libvirt - nova-custom-sriov - nova-custom-ovsdpdk - telemetry ...-
Save the
openstack_preprovisioned_node_set.yamldefinition file. Create the data plane resources:
$ oc create -f openstack_preprovisioned_node_set.yaml -n openstackVerify that the data plane resources have been created:
$ oc get openstackdataplanenodeset -n openstack- Sample output
NAME STATUS MESSAGE openstack-data-plane False Deployment not started
For information about the meaning of the returned status, see Data plane conditions and states.
Verify that the
Secretresource was created for the node set:$ oc get secret | grep openstack-data-planeSample output
dataplanenodeset-openstack-data-plane Opaque 1 3m50sVerify the services were created:
$ oc get openstackdataplaneservice -n openstackSample output
NAME AGE configure-network 6d7h configure-os 6d6h install-os 6d6h run-os 6d6h validate-network 6d6h ovn 6d6h libvirt 6d6h nova 6d6h telemetry 6d6h
10.5.1. Example OpenStackDataPlaneNodeSet CR for pre-provisioned nodes with a single NIC Copy linkLink copied to clipboard!
Review examples to learn how to create a node set from pre-provisioned Compute nodes.
The following example OpenStackDataPlaneNodeSet CR creates a node set from pre-provisioned Compute nodes with some node-specific configuration. The example includes optional fields. Review the example and update the optional fields to the correct values for your environment or remove them before using the example in your Red Hat OpenStack Services on OpenShift (RHOSO) deployment.
The example that follows for an OpenStackDataPlaneNodeSet CR assumes that the node contains a single NIC.
Update the name of the OpenStackDataPlaneNodeSet CR in this example to a name that reflects the nodes in the set. The OpenStackDataPlaneNodeSet CR name must be unique, contain only lower case alphanumeric characters and - (hyphens) or . (periods), start and end with an alphanumeric character, and have a maximum length of 53 characters.
The following variables are autogenerated from IPAM and DNS and are not provided by the user:
-
ctlplane_dns_nameservers -
dns_search_domains -
ctlplane_host_routes
apiVersion: dataplane.openstack.org/v1beta1
kind: OpenStackDataPlaneNodeSet
metadata:
name: openstack-data-plane
namespace: openstack
spec:
env:
- name: ANSIBLE_FORCE_COLOR
value: "True"
networkAttachments:
- ctlplane
preProvisioned: true
nodeTemplate:
ansibleSSHPrivateKeySecret: dataplane-ansible-ssh-private-key-secret
extraMounts:
- extraVolType: Logs
volumes:
- name: ansible-logs
persistentVolumeClaim:
claimName: <pvc_name>
mounts:
- name: ansible-logs
mountPath: "/runner/artifacts"
managementNetwork: ctlplane
ansible:
ansibleUser: cloud-admin
ansiblePort: 22
ansibleVarsFrom:
- secretRef:
name: subscription-manager
- secretRef:
name: redhat-registry
ansibleVars:
timesync_ntp_servers:
- hostname: ntp.example.com
iburst: true
- hostname: ntp2.example.com
iburst: false
rhc_release: 9.4
rhc_repositories:
- {name: "*", state: disabled}
- {name: "<repository_name1>", state: enabled}
- {name: "<repository_name2>", state: enabled}
- {name: "<repository_name3>", state: enabled}
- {name: "<repository_name4>", state: enabled}
- {name: "<repository_name5>", state: enabled}
- {name: "<repository_name6>", state: enabled}
edpm_bootstrap_release_version_package: []
edpm_network_config_os_net_config_mappings:
edpm-compute-0:
nic1: 52:54:04:60:55:22
neutron_physical_bridge_name: br-ex
neutron_public_interface_name: eth0
edpm_network_config_template: |
---
{% set mtu_list = [ctlplane_mtu] %}
{% for network in nodeset_networks %}
{{ mtu_list.append(lookup('vars', networks_lower[network] ~ '_mtu')) }}
{%- endfor %}
{% set min_viable_mtu = mtu_list | max %}
network_config:
- type: ovs_bridge
name: {{ neutron_physical_bridge_name }}
mtu: {{ min_viable_mtu }}
use_dhcp: false
dns_servers: {{ ctlplane_dns_nameservers }}
domain: {{ dns_search_domains }}
addresses:
- ip_netmask: {{ ctlplane_ip }}/{{ ctlplane_cidr }}
routes: {{ ctlplane_host_routes }}
members:
- type: interface
name: nic1
mtu: {{ min_viable_mtu }}
# force the MAC address of the bridge to this interface
primary: true
{% for network in nodeset_networks %}
- type: vlan
mtu: {{ lookup('vars', networks_lower[network] ~ '_mtu') }}
vlan_id: {{ lookup('vars', networks_lower[network] ~ '_vlan_id') }}
addresses:
- ip_netmask:
{{ lookup('vars', networks_lower[network] ~ '_ip') }}/{{ lookup('vars', networks_lower[network] ~ '_cidr') }}
routes: {{ lookup('vars', networks_lower[network] ~ '_host_routes') }}
{% endfor %}
nodes:
edpm-compute-0:
hostName: edpm-compute-0
networks:
- name: ctlplane
subnetName: subnet1
defaultRoute: true
fixedIP: 192.168.122.100
- name: internalapi
subnetName: subnet1
fixedIP: 172.17.0.100
- name: storage
subnetName: subnet1
fixedIP: 172.18.0.100
- name: tenant
subnetName: subnet1
fixedIP: 172.19.0.100
ansible:
ansibleHost: 192.168.122.100
ansibleUser: cloud-admin
ansibleVars:
fqdn_internal_api: edpm-compute-0.example.com
edpm-compute-1:
hostName: edpm-compute-1
networks:
- name: ctlplane
subnetName: subnet1
defaultRoute: true
fixedIP: 192.168.122.101
- name: internalapi
subnetName: subnet1
fixedIP: 172.17.0.101
- name: storage
subnetName: subnet1
fixedIP: 172.18.0.101
- name: tenant
subnetName: subnet1
fixedIP: 172.19.0.101
ansible:
ansibleHost: 192.168.122.101
ansibleUser: cloud-admin
ansibleVars:
fqdn_internal_api: edpm-compute-1.example.com
services:
- bootstrap
- download-cache
- reboot-os
- configure-ovs-dpdk
- configure-network
- validate-network
- install-os
- configure-os
- ssh-known-hosts
- run-os
- install-certs
- ovn
- neutron-ovn
- neutron-ovn-igmp
- neutron-metadata
- libvirt
- nova-custom-sriov
- nova-custom-ovsdpdk
- telemetry
where:
<repository_name1>,<repository_name2>,<repository_name3>,<repository_name4>,<repository_name5>,<repository_name6>- Specifies the name of the repository to enable. For more information about which repositories are required, see Required repositories for Red Hat OpenStack Services on OpenShift 18.0.
10.6. Creating a set of data plane nodes with unprovisioned nodes Copy linkLink copied to clipboard!
Define an OpenStackDataPlaneNodeSet custom resource (CR) for each logical grouping of unprovisioned nodes in your data plane, for example, nodes grouped by hardware, location, or networking.
You can define as many node sets as necessary for your deployment. Each node can be included in only one OpenStackDataPlaneNodeSet CR. Each node set can be connected to only one Compute cell. By default, node sets are connected to cell1. If you customize your control plane to include additional Compute cells, you must specify the cell to which the node set is connected. For more information on adding Compute cells, see Connecting an OpenStackDataPlaneNodeSet CR to a Compute cell in the Customizing the Red Hat OpenStack Services on OpenShift deployment guide.
You use the nodeTemplate field to configure the properties that all nodes in an OpenStackDataPlaneNodeSet CR share, and the nodeTemplate.nodes field for node-specific properties. Node-specific configurations override the inherited values from the nodeTemplate.
For more information about provisioning bare-metal nodes, see Planning provisioning for bare-metal data plane nodes in Planning your deployment.
Prerequisites
- Cluster Baremetal Operator (CBO) is installed and configured for provisioning. For more information, see Planning provisioning for bare-metal data plane nodes in Planning your deployment.
-
A
BareMetalHostCR is registered and inspected for each bare-metal data plane node. Each bare-metal node must be in theAvailablestate after inspection.
Procedure
Create a file on your workstation named
openstack_unprovisioned_node_set.yamlto define theOpenStackDataPlaneNodeSetCR:apiVersion: dataplane.openstack.org/v1beta1 kind: OpenStackDataPlaneNodeSet metadata: name: openstack-data-plane namespace: openstack spec: tlsEnabled: true env: - name: ANSIBLE_FORCE_COLOR value: "True"-
name- TheOpenStackDataPlaneNodeSetCR name must be unique, contain only lower case alphanumeric characters and-(hyphens) or.(periods), start and end with an alphanumeric character, and have a maximum length of 53 characters. Update the name in this example to a name that reflects the nodes in the set. -
env- Optional: a list of environment variables to pass to the pod.
-
Define the
baremetalSetTemplatefield to describe the configuration of the bare-metal nodes:preProvisioned: false baremetalSetTemplate: deploymentSSHSecret: dataplane-ansible-ssh-private-key-secret bmhNamespace: <bmh_namespace> cloudUserName: <ansible_ssh_user> bmhLabelSelector: app: <bmh_label> ctlplaneInterface: <interface>-
Replace
<bmh_namespace>with the namespace defined in the correspondingBareMetalHostCR for the node. -
Replace
<ansible_ssh_user>with the username of the Ansible SSH user. -
Replace
<bmh_label>with the metadata label defined in the correspondingBareMetalHostCR for the node, for example,openstack. Metadata labels, such asapp,workload, andnodeNameare key-value pairs for labelling nodes. Set thebmhLabelSelectorfield to select data plane nodes based on one or more labels that match the labels in the correspondingBareMetalHostCR. -
Replace
<interface>with the control plane interface the node connects to, for example,enp6s0.
-
Replace
The BMO manages
BareMetalHostCRs in theopenshift-machine-apinamespace by default. You must update theProvisioningCR to watch all namespaces:$ oc patch provisioning provisioning-configuration --type merge -p '{"spec":{"watchAllNamespaces": true }}'Add the SSH key secret that you created to enable Ansible to connect to the data plane nodes:
nodeTemplate: ansibleSSHPrivateKeySecret: <secret-key>-
Replace
<secret-key>with the name of the SSH keySecretCR you created in Creating the data plane secrets, for example,dataplane-ansible-ssh-private-key-secret.
-
Replace
-
Create a Persistent Volume Claim (PVC) in the
openstacknamespace on your RHOCP cluster to store logs. Set thevolumeModetoFilesystemandaccessModestoReadWriteOnce. Do not request storage for logs from a PersistentVolume (PV) that uses the NFS volume plugin. NFS is incompatible with FIFO and theansible-runnercreates a FIFO file to write to store logs. For information about PVCs, see Understanding persistent storage in the RHOCP Storage guide and Red Hat OpenShift Container Platform cluster requirements in Planning your deployment. Enable persistent logging for the data plane nodes:
nodeTemplate: ansibleSSHPrivateKeySecret: <secret-key> extraMounts: - extraVolType: Logs volumes: - name: ansible-logs persistentVolumeClaim: claimName: <pvc_name> mounts: - name: ansible-logs mountPath: "/runner/artifacts"-
Replace
<pvc_name>with the name of the PVC storage on your RHOCP cluster.
-
Replace
Add the common configuration for the set of nodes in this group under the
nodeTemplatesection. Each node in thisOpenStackDataPlaneNodeSetinherits this configuration.For more information, see:
Define each node in this node set:
nodes: edpm-compute-0: hostName: edpm-compute-0 networks: - name: ctlplane subnetName: subnet1 defaultRoute: true fixedIP: 192.168.122.100 - name: internalapi subnetName: subnet1 - name: storage subnetName: subnet1 - name: tenant subnetName: subnet1 ansible: ansibleHost: 192.168.122.100 ansibleUser: cloud-admin ansibleVars: fqdn_internal_api: edpm-compute-0.example.com edpm_network_config_nmstate: true edpm-compute-1: hostName: edpm-compute-1 networks: - name: ctlplane subnetName: subnet1 defaultRoute: true fixedIP: 192.168.122.101 - name: internalapi subnetName: subnet1 - name: storage subnetName: subnet1 - name: tenant subnetName: subnet1 ansible: ansibleHost: 192.168.122.101 ansibleUser: cloud-admin ansibleVars: fqdn_internal_api: edpm-compute-1.example.com-
edpm-compute-0- The node definition reference, for example,edpm-compute-0. Each node in the node set must have a node definition. -
networks- Defines the IPAM and the DNS records for the node. -
fixedIP- Specifies a predictable IP address for the network that must be in the allocation range defined for the network in theNetConfigCR. ansibleVars- Node-specific Ansible variables that customize the node.Note-
Nodes defined within the
nodessection can configure the same Ansible variables that are configured in thenodeTemplatesection. Where an Ansible variable is configured for both a specific node and within thenodeTemplatesection, the node-specific values override those from thenodeTemplatesection. -
You do not need to replicate all the
nodeTemplateAnsible variables for a node to override the default and set some node-specific values. You only need to configure the Ansible variables you want to override for the node. -
When you define the networkData Secret for an individual node (such as
edpm-compute-0), it acts as a complete override rather than a supplemental configuration. Because node-specific configurations override the inherited default values from thenodeTemplatesection, you must ensure that your node-specificnetworkDataSecret contains the full set of required network configurations for that node, not just the unique values. -
Many
ansibleVarsincludeedpmin the name, which stands for "External Data Plane Management".
-
Nodes defined within the
edpm_network_config_nmstate- Sets theos-net-configprovider tonmstate. The default value istrue. Change it tofalseonly if a specific limitation of thenmstateprovider requires you to use theifcfgprovider. For more information on advantages and limitations of thenmstateprovider, see https://docs.redhat.com/en/documentation/red_hat_openstack_services_on_openshift/18.0/html/planning_your_deployment/plan-networks_planning#plan-os-net-config_plan-network in Planning your deployment.For information about the properties you can use to configure node attributes, see
OpenStackDataPlaneNodeSetCR properties.
-
In the
servicessection, add the list of services that will run on the data plane node. Ensure that you replacenovawithnova-custom-sriov, ornova-custom-ovsdpdk, or both:... services: - bootstrap - download-cache - reboot-os - configure-ovs-dpdk - configure-network - validate-network - install-os - configure-os - ssh-known-hosts - run-os - install-certs - ovn - neutron-ovn - neutron-ovn-igmp - neutron-metadata - libvirt - nova-custom-sriov - nova-custom-ovsdpdk - telemetry ...-
Save the
openstack_unprovisioned_node_set.yamldefinition file. Create the data plane resources:
$ oc create -f openstack_unprovisioned_node_set.yaml -n openstackVerify that the data plane resources have been created:
$ oc get openstackdataplanenodeset -n openstack NAME STATUS MESSAGE openstack-data-plane False Deployment not startedFor information on the meaning of the returned status, see Data plane conditions and states.
Verify that the
Secretresource was created for the node set:$ oc get secret -n openstack | grep openstack-data-plane dataplanenodeset-openstack-data-plane Opaque 1 3m50sVerify the services were created:
$ oc get openstackdataplaneservice -n openstack NAME AGE configure-network 6d7h configure-os 6d6h install-os 6d6h run-os 6d6h validate-network 6d6h ovn 6d6h libvirt 6d6h nova 6d6h telemetry 6d6h
10.6.1. Example OpenStackDataPlaneNodeSet CR for unprovisioned nodes Copy linkLink copied to clipboard!
Review examples to learn how to create a node set from unprovisioned Compute nodes.
The following example OpenStackDataPlaneNodeSet CR creates a node set from unprovisioned Compute nodes with some node-specific configuration. The unprovisioned Compute nodes are provisioned when the node set is created. The example includes optional fields. Review the example and update the optional fields to the correct values for your environment or remove them before using the example in your Red Hat OpenStack Services on OpenShift (RHOSO) deployment.
Update the name of the OpenStackDataPlaneNodeSet CR in this example to a name that reflects the nodes in the set. The OpenStackDataPlaneNodeSet CR name must be unique, contain only lower case alphanumeric characters and - (hyphens) or . (periods), start and end with an alphanumeric character, and have a maximum length of 53 characters.
The following variables are autogenerated from IPAM and DNS and are not provided by the user:
-
ctlplane_dns_nameservers -
dns_search_domains -
ctlplane_host_routes
apiVersion: dataplane.openstack.org/v1beta1
kind: OpenStackDataPlaneNodeSet
metadata:
name: openstack-data-plane
namespace: openstack
spec:
env:
- name: ANSIBLE_FORCE_COLOR
value: "True"
networkAttachments:
- ctlplane
preProvisioned: false
baremetalSetTemplate:
deploymentSSHSecret: dataplane-ansible-ssh-private-key-secret
bmhNamespace: openstack
cloudUserName: cloud-admin
bmhLabelSelector:
app: openstack
ctlplaneInterface: enp1s0
nodeTemplate:
ansibleSSHPrivateKeySecret: dataplane-ansible-ssh-private-key-secret
extraMounts:
- extraVolType: Logs
volumes:
- name: ansible-logs
persistentVolumeClaim:
claimName: <pvc_name>
mounts:
- name: ansible-logs
mountPath: "/runner/artifacts"
managementNetwork: ctlplane
ansible:
ansibleUser: cloud-admin
ansiblePort: 22
ansibleVarsFrom:
- secretRef:
name: subscription-manager
- secretRef:
name: redhat-registry
ansibleVars:
timesync_ntp_servers:
- hostname: ntp.example.com
iburst: true
- hostname: ntp2.example.com
iburst: false
rhc_release: 9.4
rhc_repositories:
- {name: "*", state: disabled}
- {name: "<repository_name1>", state: enabled}
- {name: "<repository_name2>", state: enabled}
- {name: "<repository_name3>", state: enabled}
- {name: "<repository_name4>", state: enabled}
- {name: "<repository_name5>", state: enabled}
- {name: "<repository_name6>", state: enabled}
edpm_bootstrap_release_version_package: []
edpm_network_config_os_net_config_mappings:
edpm-compute-0:
nic1: 52:54:04:60:55:22
edpm-compute-1:
nic1: 52:54:04:60:55:22
neutron_physical_bridge_name: br-ex
neutron_public_interface_name: eth0
edpm_network_config_template: |
---
{% set mtu_list = [ctlplane_mtu] %}
{% for network in nodeset_networks %}
{{ mtu_list.append(lookup('vars', networks_lower[network] ~ '_mtu')) }}
{%- endfor %}
{% set min_viable_mtu = mtu_list | max %}
network_config:
- type: ovs_bridge
name: {{ neutron_physical_bridge_name }}
mtu: {{ min_viable_mtu }}
use_dhcp: false
dns_servers: {{ ctlplane_dns_nameservers }}
domain: {{ dns_search_domains }}
addresses:
- ip_netmask: {{ ctlplane_ip }}/{{ ctlplane_cidr }}
routes: {{ ctlplane_host_routes }}
members:
- type: interface
name: nic1
mtu: {{ min_viable_mtu }}
# force the MAC address of the bridge to this interface
primary: true
{% for network in nodeset_networks %}
- type: vlan
mtu: {{ lookup('vars', networks_lower[network] ~ '_mtu') }}
vlan_id: {{ lookup('vars', networks_lower[network] ~ '_vlan_id') }}
addresses:
- ip_netmask:
{{ lookup('vars', networks_lower[network] ~ '_ip') }}/{{ lookup('vars', networks_lower[network] ~ '_cidr') }}
routes: {{ lookup('vars', networks_lower[network] ~ '_host_routes') }}
{% endfor %}
nodes:
edpm-compute-0:
hostName: edpm-compute-0
networks:
- name: ctlplane
subnetName: subnet1
defaultRoute: true
fixedIP: 192.168.122.100
- name: internalapi
subnetName: subnet1
- name: storage
subnetName: subnet1
- name: tenant
subnetName: subnet1
ansible:
ansibleHost: 192.168.122.100
ansibleUser: cloud-admin
ansibleVars:
fqdn_internal_api: edpm-compute-0.example.com
bmhLabelSelector:
nodeName: edpm-compute-0
edpm-compute-1:
hostName: edpm-compute-1
networks:
- name: ctlplane
subnetName: subnet1
defaultRoute: true
fixedIP: 192.168.122.101
- name: internalapi
subnetName: subnet1
- name: storage
subnetName: subnet1
- name: tenant
subnetName: subnet1
ansible:
ansibleHost: 192.168.122.101
ansibleUser: cloud-admin
ansibleVars:
fqdn_internal_api: edpm-compute-1.example.com
bmhLabelSelector:
nodeName: edpm-compute-1
services:
- bootstrap
- download-cache
- reboot-os
- configure-ovs-dpdk
- configure-network
- validate-network
- install-os
- configure-os
- ssh-known-hosts
- run-os
- install-certs
- ovn
- neutron-ovn
- neutron-ovn-igmp
- neutron-metadata
- libvirt
- nova-custom-sriov
- nova-custom-ovsdpdk
- telemetry
where:
<repository_name1>,<repository_name2>,<repository_name3>,<repository_name4>,<repository_name5>,<repository_name6>- Specifies the name of the repository to enable. For more information about which repositories are required, see Required repositories for Red Hat OpenStack Services on OpenShift 18.0.
10.7. OpenStackDataPlaneNodeSet CR spec properties Copy linkLink copied to clipboard!
The following sections detail the OpenStackDataPlaneNodeSet CR spec properties you can configure.
10.7.1. nodeTemplate Copy linkLink copied to clipboard!
Defines the common attributes for the nodes in this OpenStackDataPlaneNodeSet. You can override these common attributes in the definition for each individual node.
| Field | Description |
|---|---|
|
| Name of the private SSH key secret that contains the private SSH key for connecting to nodes. Secret name format: Secret.data.ssh-privatekey For more information, see Creating an SSH authentication secret.
Default: |
|
|
Name of the network to use for management (SSH/Ansible). Default: |
|
|
Network definitions for the |
|
|
Ansible configuration options. For more information, see |
|
| The files to mount into an Ansible Execution Pod. |
|
|
UserData configuration for the |
|
|
NetworkData configuration for the |
10.7.2. nodes Copy linkLink copied to clipboard!
Defines the node names and node-specific attributes for the nodes in this OpenStackDataPlaneNodeSet. Overrides the common attributes defined in the nodeTemplate.
| Field | Description |
|---|---|
|
|
Ansible configuration options. For more information, see |
|
| The files to mount into an Ansible Execution Pod. |
|
| The node name. |
|
| Name of the network to use for management (SSH/Ansible). |
|
| NetworkData configuration for the node. |
|
| Instance networks. |
|
| Node-specific user data. |
10.7.3. ansible Copy linkLink copied to clipboard!
Defines the group of Ansible configuration options.
| Field | Description |
|---|---|
|
|
The user associated with the secret you created in Creating the data plane secrets. Default: |
|
| SSH host for the Ansible connection. |
|
| SSH port for the Ansible connection. |
|
|
The Ansible variables that customize the set of nodes. You can use this property to configure any custom Ansible variable, including the Ansible variables available for each Note
The |
|
|
A list of sources to populate Ansible variables from. Values defined by an |
10.7.4. ansibleVarsFrom Copy linkLink copied to clipboard!
Defines the list of sources to populate Ansible variables from.
| Field | Description |
|---|---|
|
|
An optional identifier to prepend to each key in the |
|
|
The |
|
|
The |
10.7.5. Overriding network defaults with `networkData Copy linkLink copied to clipboard!
When configuring your data plane nodes, you can provide node-specific network configurations using the networkData parameter, which refers to a Secret that contains the configuration. You can define networkData at two levels within the OpenStackDataPlaneNodeSet CR: under the nodeTemplate properties and under the individual nodes properties. The nodeTemplate field is used to configure the common baseline properties applied to all nodes in the node set. However, if you apply the networkData property to a specific node within the nodes section, this node-specific configuration overrides the inherited default values from the nodeTemplate. This override mechanism allows you to establish a broad default network configuration for a group of nodes, while safely overriding those defaults for specific nodes that require unique, node-specific network setups.
10.8. Network interface configuration options Copy linkLink copied to clipboard!
You have many options for configuring network interfaces.
Most of these options can be sorted into the following categories:
Linux bridges are not supported in RHOSO. Instead, use methods such as Linux bonds and dedicated NICs for RHOSO traffic.
10.8.1. interface Copy linkLink copied to clipboard!
Defines a single network interface. The network interface name uses either the actual interface name (eth0, eth1, enp0s25) or a set of numbered interfaces (nic1, nic2, nic3). The network interfaces of hosts within a role do not have to be exactly the same when you use numbered interfaces such as nic1 and nic2, instead of named interfaces such as eth0 and eno2. For example, one host might have interfaces em1 and em2, while another has eno1 and eno2, but you can refer to the NICs of both hosts as nic1 and nic2.
The order of numbered interfaces corresponds to the order of named network interface types:
ethXinterfaces, such aseth0,eth1, and so on.Names appear in this format when consistent device naming is turned off in
udev.enoXandemXinterfaces, such aseno0,eno1,em0,em1, and so on.These are usually on-board interfaces.
enXand any other interfaces, sorted alpha numerically, such asenp3s0,enp3s1,ens3, and so on.These are usually add-on interfaces.
The numbered NIC scheme includes only live interfaces, for example, if the interfaces have a cable attached to the switch. If you have some hosts with four interfaces and some with six interfaces, use nic1 to nic4 and attach only four cables on each host.
| Option | Default | Description |
|---|---|---|
|
|
Name of the interface. The network interface | |
|
| False | Use DHCP to get an IP address. |
|
| False | Use DHCP to get a v6 IP address. |
|
| A list of IP addresses assigned to the interface. | |
|
| A list of routes assigned to the interface. For more information, see Section 10.8.7, “routes”. | |
|
| 1500 | The maximum transmission unit (MTU) of the connection. |
|
| False |
Defines the interface as the primary interface. Required only when the |
|
| False | Write the device alias configuration instead of the system names. |
|
| None | Arguments that you want to pass to the DHCP client. |
|
| None | List of DNS servers that you want to use for the interface. |
|
|
Set this option to |
- Example
... edpm_network_config_template: | --- {% set mtu_list = [ctlplane_mtu] %} {% for network in nodeset_networks %} {{ mtu_list.append(lookup('vars', networks_lower[network] ~ '_mtu')) }} {%- endfor %} {% set min_viable_mtu = mtu_list | max %} network_config: - type: interface name: nic2 ...
10.8.2. vlan Copy linkLink copied to clipboard!
Defines a VLAN. Use the VLAN ID and subnet passed from the parameters section.
vlanoptions
| Option | Default | Description |
|---|---|---|
| vlan_id | The VLAN ID. | |
| device | The parent device to attach the VLAN. Use this parameter when the VLAN is not a member of an OVS bridge. For example, use this parameter to attach the VLAN to a bonded interface device. | |
| use_dhcp | False | Use DHCP to get an IP address. |
| use_dhcpv6 | False | Use DHCP to get a v6 IP address. |
| addresses | A list of IP addresses assigned to the VLAN. | |
| routes | A list of routes assigned to the VLAN. For more information, see Section 10.8.7, “routes”. | |
| mtu | 1500 | The maximum transmission unit (MTU) of the connection. |
| primary | False | Defines the VLAN as the primary interface. |
| persist_mapping | False | Write the device alias configuration instead of the system names. |
| dhclient_args | None | Arguments that you want to pass to the DHCP client. |
| dns_servers | None | List of DNS servers that you want to use for the VLAN. |
- Example
... edpm_network_config_template: | --- {% set mtu_list = [ctlplane_mtu] %} {% for network in nodeset_networks %} {{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }} {%- endfor %} {% set min_viable_mtu = mtu_list | max %} network_config: ... - type: vlan device: nic{{ loop.index + 1 }} mtu: {{ lookup(vars, networks_lower[network] ~ _mtu) }} vlan_id: {{ lookup(vars, networks_lower[network] ~ _vlan_id) }} addresses: - ip_netmask: {{ lookup(vars, networks_lower[network] ~ _ip) }}/{{ lookup(vars, networks_lower[network] ~ _cidr) }} routes: {{ lookup(vars, networks_lower[network] ~ _host_routes) }} ...- Example - creating a VLAN on an
ovs_bridge To create a VLAN on an
ovs_bridge, you must place the VLAN configuration under thememberssection:... network_config: - type: ovs_bridge name: br0 use_dhcp: false members: - type: interface name: nic5 - type: vlan vlan_id: 138 use_dhcp: false ...- Example - creating a VLAN on an
ovs_user_bridge To create a VLAN on an
ovs_user_bridge, you must place the VLAN configuration under thememberssection. The members must be either anovs_dpdk_bondor andovs_dpdk_port:... network_config: -type: ovs_user_bridge name: br-link members: -type: ovs_dpdk_bond name: dpdkbond0 mtu: 9000 rx_queue: 4 members: -type: ovs_dpdk_port name: dpdk0 members: -type: interface name: nic2 -type: ovs_dpdk_port name: dpdk1 members: -type: interface name: nic3 -type: vlan vlan_id:138 use_dhcp: false ...
10.8.3. ovs_bridge Copy linkLink copied to clipboard!
Defines a bridge in Open vSwitch (OVS), which connects multiple interface, ovs_bond, and vlan objects together.
The network interface type, ovs_bridge, takes a parameter name.
Placing Control group networks on the ovs_bridge interface can cause downtime. The OVS bridge connects to the Networking service (neutron) server to obtain configuration data. If the OpenStack control traffic, typically the Control Plane and Internal API networks, is placed on an OVS bridge, then connectivity to the neutron server is lost whenever you upgrade OVS, or the OVS bridge is restarted by the admin user or process. If downtime is not acceptable in these circumstances, then you must place the Control group networks on a separate interface or bond rather than on an OVS bridge:
- You can achieve a minimal setting when you put the Internal API network on a VLAN on the provisioning interface and the OVS bridge on a second interface.
- To implement bonding, you need at least two bonds (four network interfaces). Place the control group on a Linux bond. If the switch does not support LACP fallback to a single interface for PXE boot, then this solution requires at least five NICs.
If you have multiple bridges, you must use distinct bridge names other than accepting the default name of bridge_name. If you do not use distinct names, then during the converge phase, two network bonds are placed on the same bridge.
ovs_bridgeoptions
| Option | Default | Description |
|---|---|---|
| name | Name of the bridge. | |
| use_dhcp | False | Use DHCP to get an IP address. |
| use_dhcpv6 | False | Use DHCP to get a v6 IP address. |
| addresses | A list of IP addresses assigned to the bridge. | |
| routes | A list of routes assigned to the bridge. For more information, see Section 10.8.7, “routes”. | |
| mtu | 1500 | The maximum transmission unit (MTU) of the connection. |
| members | A sequence of interface, VLAN, and bond objects that you want to use in the bridge. | |
| ovs_options | A set of options to pass to OVS when creating the bridge. | |
| ovs_extra | A set of options to set as the OVS_EXTRA parameter in the network configuration file of the bridge. | |
| defroute | True |
Use a default route provided by the DHCP service. Only applies when you enable |
| persist_mapping | False | Write the device alias configuration instead of the system names. |
| dhclient_args | None | Arguments that you want to pass to the DHCP client. |
| dns_servers | None | List of DNS servers that you want to use for the bridge. |
- Example
... edpm_network_config_template: | --- {% set mtu_list = [ctlplane_mtu] %} {% for network in nodeset_networks %} {{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }} {%- endfor %} {% set min_viable_mtu = mtu_list | max %} network_config: - type: ovs_bridge name: br-bond dns_servers: {{ ctlplane_dns_nameservers }} domain: {{ dns_search_domains }} members: - type: ovs_bond name: bond1 mtu: {{ min_viable_mtu }} ovs_options: {{ bound_interface_ovs_options }} members: - type: interface name: nic2 mtu: {{ min_viable_mtu }} primary: true - type: interface name: nic3 mtu: {{ min_viable_mtu }} ...
10.8.4. Network interface bonding Copy linkLink copied to clipboard!
You can bundle multiple physical NICs together to form a single logical channel known as a bond. You can configure bonds to provide redundancy for high availability systems or increased throughput.
Red Hat OpenStack Platform supports Open vSwitch (OVS) kernel bonds, OVS-DPDK bonds, and Linux kernel bonds.
| Bond type | Type value | Allowed bridge types | Allowed members |
|---|---|---|---|
| OVS kernel bonds |
|
|
|
| OVS-DPDK bonds |
|
|
|
| Linux kernel bonds |
|
|
|
Do not combine ovs_bridge and ovs_user_bridge on the same node.
ovs_bondDefines a bond in Open vSwitch (OVS) to join two or more
interfacestogether. This helps with redundancy and increases bandwidth.Expand Table 10.7. ovs_bond options Option Default Description name
Name of the bond.
use_dhcp
False
Use DHCP to get an IP address.
use_dhcpv6
False
Use DHCP to get a v6 IP address.
addresses
A list of IP addresses assigned to the bond.
routes
A list of routes assigned to the bond. For more information, see Section 10.8.7, “routes”.
mtu
1500
The maximum transmission unit (MTU) of the connection.
primary
False
Defines the interface as the primary interface.
members
A sequence of interface objects that you want to use in the bond.
ovs_options
A set of options to pass to OVS when creating the bond. For more information, see Table 10.8, “
ovs_optionsparameters for OVS bonds”.ovs_extra
A set of options to set as the OVS_EXTRA parameter in the network configuration file of the bond.
defroute
True
Use a default route provided by the DHCP service. Only applies when you enable
use_dhcporuse_dhcpv6.persist_mapping
False
Write the device alias configuration instead of the system names.
dhclient_args
None
Arguments that you want to pass to the DHCP client.
dns_servers
None
List of DNS servers that you want to use for the bond.
Expand Table 10.8. ovs_options parameters for OVS bonds ovs_optionDescription bond_mode=balance-slbSource load balancing (slb) balances flows based on source MAC address and output VLAN, with periodic rebalancing as traffic patterns change. When you configure a bond with the
balance-slbbonding option, there is no configuration required on the remote switch. The Networking service (neutron) assigns each source MAC and VLAN pair to a link and transmits all packets from that MAC and VLAN through that link. A simple hashing algorithm based on source MAC address and VLAN number is used, with periodic rebalancing as traffic patterns change. Thebalance-slbmode is similar to mode 2 bonds used by the Linux bonding driver. You can use this mode to provide load balancing even when the switch is not configured to use LACP.bond_mode=active-backupWhen you configure a bond using
active-backupbond mode, the Networking service keeps one NIC in standby. The standby NIC resumes network operations when the active connection fails. Only one MAC address is presented to the physical switch. This mode does not require switch configuration, and works when the links are connected to separate switches. This mode does not provide load balancing.lacp=[active | passive | off]Controls the Link Aggregation Control Protocol (LACP) behavior. Only certain switches support LACP. If your switch does not support LACP, use
bond_mode=balance-slborbond_mode=active-backup.other-config:lacp-fallback-ab=trueSet active-backup as the bond mode if LACP fails.
other_config:lacp-time=[fast | slow]Set the LACP heartbeat to one second (fast) or 30 seconds (slow). The default is slow.
other_config:bond-detect-mode=[miimon | carrier]Set the link detection to use miimon heartbeats (miimon) or monitor carrier (carrier). The default is carrier.
other_config:bond-miimon-interval=100If using miimon, set the heartbeat interval (milliseconds).
bond_updelay=1000Set the interval (milliseconds) that a link must be up to be activated to prevent flapping.
other_config:bond-rebalance-interval=10000Set the interval (milliseconds) that flows are rebalancing between bond members. Set this value to zero to disable flow rebalancing between bond members.
- Example - OVS bond
... edpm_network_config_template: | --- {% set mtu_list = [ctlplane_mtu] %} {% for network in nodeset_networks %} {{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }} {%- endfor %} {% set min_viable_mtu = mtu_list | max %} network_config: ... members: - type: ovs_bond name: bond1 mtu: {{ min_viable_mtu }} ovs_options: {{ bond_interface_ovs_options }} members: - type: interface name: nic2 mtu: {{ min_viable_mtu }} primary: true - type: interface name: nic3 mtu: {{ min_viable_mtu }}- Example - OVS DPDK bond
In this example, a bond is created as part of an OVS user space bridge:
edpm_network_config_template: | --- {% set mtu_list = [ctlplane_mtu] %} {% for network in nodeset_networks %} {{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }} {%- endfor %} {% set min_viable_mtu = mtu_list | max %} network_config: ... members: - type: ovs_user_bridge name: br-dpdk0 members: - type: ovs_dpdk_bond name: dpdkbond0 rx_queue: {{ num_dpdk_interface_rx_queues }} members: - type: ovs_dpdk_port name: dpdk0 members: - type: interface name: nic4 - type: ovs_dpdk_port name: dpdk1 members: - type: interface name: nic5
10.8.5. LACP with OVS bonding modes Copy linkLink copied to clipboard!
You can use Open vSwitch (OVS) bonds with the optional Link Aggregation Control Protocol (LACP). LACP is a negotiation protocol that creates a dynamic bond for load balancing and fault tolerance.
Use the following table to understand support compatibility for OVS kernel and OVS-DPDK bonded interfaces in conjunction with LACP options.
Do not use OVS bonds on control and storage networks. Instead, use Linux bonds with VLAN and LACP.
If you use OVS bonds, and restart the OVS or the neutron agent for updates, hot fixes, and other events, the control plane can be disrupted.
| Objective | OVS bond mode | Compatible LACP options | Notes |
| High availability (active-passive) |
|
| |
| Increased throughput (active-active) |
|
|
|
|
|
|
|
10.8.6. linux_bond Copy linkLink copied to clipboard!
Defines a Linux bond that joins two or more interfaces together. This helps with redundancy and increases bandwidth. Ensure that you include the kernel-based bonding options in the bonding_options parameter.
| Option | Default | Description |
|---|---|---|
| name | Name of the bond. | |
| use_dhcp | False | Use DHCP to get an IP address. |
| use_dhcpv6 | False | Use DHCP to get a v6 IP address. |
| addresses | A list of IP addresses assigned to the bond. | |
| routes | A list of routes assigned to the bond. See Section 10.8.7, “routes”. | |
| mtu | 1500 | The maximum transmission unit (MTU) of the connection. |
| members | A sequence of interface objects that you want to use in the bond. | |
| bonding_options |
A set of options when creating the bond. See | |
| defroute | True |
Use a default route provided by the DHCP service. Only applies when you enable |
| persist_mapping | False | Write the device alias configuration instead of the system names. |
| dhclient_args | None | Arguments that you want to pass to the DHCP client. |
| dns_servers | None | List of DNS servers that you want to use for the bond. |
bonding_optionsparameters for Linux bonds-
The
bonding_optionsparameter sets the specific bonding options for the Linux bond. See the Linux bonding examples that follow this table:
bonding_options | Description |
|---|---|
|
|
Sets the bonding mode, which in the example is |
|
| Defines whether LACP packets are sent every 1 second, or every 30 seconds. |
|
| Defines the minimum amount of time that an interface must be active before it is used for traffic. This minimum configuration helps to mitigate port flapping outages. |
|
| The interval in milliseconds that is used for monitoring the port state using the MIIMON functionality of the driver. |
- Example - Linux bond
... edpm_network_config_template: | --- {% set mtu_list = [ctlplane_mtu] %} {% for network in nodeset_networks %} {{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }} {%- endfor %} {% set min_viable_mtu = mtu_list | max %} network_config: - type: linux_bond name: bond1 mtu: {{ min_viable_mtu }} bonding_options: "mode=802.3ad lacp_rate=fast updelay=1000 miimon=100 xmit_hash_policy=layer3+4" members: type: interface name: ens1f0 mtu: {{ min_viable_mtu }} primary: true type: interface name: ens1f1 mtu: {{ min_viable_mtu }} ...- Example - Linux bond: bonding two interfaces
... edpm_network_config_template: | --- {% set mtu_list = [ctlplane_mtu] %} {% for network in nodeset_networks %} {{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }} {%- endfor %} {% set min_viable_mtu = mtu_list | max %} network_config: - type: linux_bond name: bond1 members: - type: interface name: nic2 - type: interface name: nic3 bonding_options: "mode=802.3ad lacp_rate=[fast|slow] updelay=1000 miimon=100" ...- Example - Linux bond set to
active-backupmode with one VLAN .... edpm_network_config_template: | --- {% set mtu_list = [ctlplane_mtu] %} {% for network in nodeset_networks %} {{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }} {%- endfor %} {% set min_viable_mtu = mtu_list | max %} network_config: - type: linux_bond name: bond_api bonding_options: "mode=active-backup" use_dhcp: false dns_servers: get_param: DnsServers members: - type: interface name: nic3 primary: true - type: interface name: nic4 - type: vlan vlan_id: {{ lookup(vars, networks_lower[network] ~ _vlan_id) }} device: bond_api addresses: - ip_netmask: get_param: InternalApiIpSubnet- Example - Linux bond on OVS bridge
In this example, the bond is set to
802.3adwith LACP mode and one VLAN:... edpm_network_config_template: | --- {% set mtu_list = [ctlplane_mtu] %} {% for network in nodeset_networks %} {{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }} {%- endfor %} {% set min_viable_mtu = mtu_list | max %} network_config: - type: ovs_bridge name: br-tenant use_dhcp: false mtu: 9000 members: - type: linux_bond name: bond_tenant bonding_options: "mode=802.3ad updelay=1000 miimon=100" use_dhcp: false dns_servers: get_param: DnsServers members: - type: interface name: p1p1 primary: true - type: interface name: p1p2 - type: vlan vlan_id: {get_param: TenantNetworkVlanID} addresses: - ip_netmask: {get_param: TenantIpSubnet} ...
10.8.7. routes Copy linkLink copied to clipboard!
Defines a list of routes to apply to a network interface, VLAN, bridge, or bond.
| Option | Default | Description |
|---|---|---|
| ip_netmask | None | IP and netmask of the destination network. |
| default | False |
Sets this route to a default route. Equivalent to setting |
| next_hop | None | The IP address of the router used to reach the destination network. |
- Example - routes
... edpm_network_config_template: | --- {% set mtu_list = [ctlplane_mtu] %} {% for network in nodeset_networks %} {{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }} {%- endfor %} {% set min_viable_mtu = mtu_list | max %} network_config: - type: ovs_bridge name: br-tenant ... routes: {{ [ctlplane_host_routes] | flatten | unique }} ...
10.9. edpm-ansible variables for SR-IOV and OVS-DPDK Copy linkLink copied to clipboard!
Use edpm-ansible variables to to optimize CPU and memory performance for OVS-DPDK and SR-IOV workloads on Red Hat OpenStack Services on OpenShift (RHOSO) data plane nodes.
Always pair CPU sibling threads, or logical CPUs, together in the physical core when allocating CPU cores.
Use the variables to align your hardware configuration with host, guest instance, and OVS-DPDK process needs.
10.9.2. Data plane (EDPM) Ansible variables Copy linkLink copied to clipboard!
You can use a set of Ansible variables to optimize CPU and memory parameters for performance on data plane nodes with OVS-DPDK and SR-IOV.
You can use the following Ansible roles variables in a custom resource (CR).
- edpm_ovs_dpdk
-
Enables you to add, modify, and delete OVS-DPDK configurations, by using values defined in the OVS-DPDK
edpmAnsible variables. - edpm_ovs_dpdk_pmd_core_list
- Provides the CPU cores that are used for the DPDK poll mode drivers (PMD). Choose CPU cores that are associated with the local NUMA nodes of the DPDK interfaces.
- edpm_ovs_dpdk_enable_tso
-
Enables (
true) or disables (false) the TCP segmentation offloading (TSO) for DPDK feature. The default isfalse. - edpm_tuned_profile
-
Name of the custom TuneD profile. The default value is
throughput-performance. - edpm_tuned_isolated_cores
- A set of CPU cores isolated from the host processes.
- edpm_ovs_dpdk_socket_memory
Specifies the amount of memory in MB to pre-allocate from the hugepage pool, per NUMA node.
dpm_ovs_dpdk_socket_memoryis theother_config:dpdk-socket-memvalue in OVS:- Provide as a comma-separated list.
- For a NUMA node without a DPDK NIC, use the static value of 1024MB (1GB).
Calculate the edpm_ovs_dpdk_socket_memory value from the MTU value of each NIC on the NUMA node. The following equation approximates the value:
MEMORY_REQD_PER_MTU = (ROUNDUP_PER_MTU + 800) * (4096 * 64) Bytes-
800is the overhead value. -
4096 * 64is the number of packets in the mempool.
-
-
Add the
MEMORY_REQD_PER_MTUfor each of the MTU values set on the NUMA node and add another512MBas buffer. Round the value up to a multiple of1024.
- edpm_ovs_dpdk_memory_channels
Maps memory channels in the CPU per NUMA node. edpm_ovs_dpdk_memory_channels is the other_config:dpdk-extra="-n <value>" value in OVS:
-
Use
dmidecode -t memoryor your hardware manual to determine the number of memory channels available. -
Use
ls /sys/devices/system/node/node* -dto determine the number of NUMA nodes. - Divide the number of memory channels available by the number of NUMA nodes.
-
Use
- edpm_ovs_dpdk_vhost_postcopy_support
-
Enable or disable OVS-DPDK vhost post-copy support. Setting this to
trueenables post-copy support for all vhost user client ports. - edpm_nova_libvirt_qemu_group
-
Set
edpm_nova_libvirt_qemu_grouptohugetlbfs`so that the `ovs-vswitchdandqemuprocesses can access the shared huge pages and UNIX socket that configures thevirtio-net device. This value is role-specific and should be applied to any role leveraging OVS-DPDK. - edpm_ovn_bridge_mappings
List of bridge and DPDK ports mappings.
Example:
edpm_ovn_bridge_mappings: - "datacentre:br-ex"- edpm_kernel_args
-
Provides multiple kernel arguments to
/etc/default/grubfor the compute nodes at boot time.
10.9.3. Configuration map parameters Copy linkLink copied to clipboard!
You can set various parameters in the ConfigMap section of a custom resource (CR) to configure the CPU and memory for optimum performance on data plane nodes for OVS-DPDK and SR-IOV.
- cpu_shared_set
-
List or range of host CPU cores used to determine the host CPUs that instance emulator threads should be offloaded to for instances configured with the share emulator thread policy (
hw::emulator_threads_policy=share). - cpu_dedicated_set
A comma-separated list or range of physical host CPU numbers to which processes for pinned instance CPUs can be scheduled.
-
Exclude all cores from the
edpm_ovs_dpdk_pmd_core_list. - Include all remaining cores.
- Pair the sibling threads together.
-
Exclude all cores from the
- reserved_host_memory_mb
-
Reserves memory in MB for tasks on the host. Use the static value of
4096MB.
10.10. Example custom network interfaces for NFV Copy linkLink copied to clipboard!
Example templates demonstrate how to customize network interfaces for NFV in RHOSO environments.
10.10.1. Example template - non-partitioned NIC Copy linkLink copied to clipboard!
This template example configures the RHOSO networks on a NIC that is not partitioned.
apiVersion: v1
data:
25-igmp.conf: |
[ovs]
igmp_snooping_enable = True
kind: ConfigMap
metadata:
name: neutron-igmp
namespace: openstack
---
apiVersion: v1
data:
25-cpu-pinning-nova.conf: |
[DEFAULT]
reserved_host_memory_mb = 4096
[compute]
cpu_shared_set = "0,20,1,21"
cpu_dedicated_set = "8-19,28-39"
[neutron]
physnets = dpdkdata1
[neutron_physnet_dpdkdata1]
numa_nodes = 1
[libvirt]
cpu_power_management=false
kind: ConfigMap
metadata:
name: ovs-dpdk-sriov-cpu-pinning-nova
namespace: openstack
---
apiVersion: v1
data:
03-sriov-nova.conf: |
[pci]
device_spec = {"address": "0000:05:00.2", "physical_network":"sriov-1", "trusted":"true"}
device_spec = {"address": "0000:05:00.3", "physical_network":"sriov-2", "trusted":"true"}
device_spec = {"address": "0000:07:00.0", "physical_network":"sriov-3", "trusted":"true"}
device_spec = {"address": "0000:07:00.1", "physical_network":"sriov-4", "trusted":"true"}
kind: ConfigMap
metadata:
name: sriov-nova
namespace: openstack
---
apiVersion: v1
data:
NodeRootPassword: cmVkaGF0Cg==
kind: Secret
metadata:
name: baremetalset-password-secret
namespace: openstack
type: Opaque
---
apiVersion: v1
data:
authorized_keys: ZWNkc2Etc2hhMi1uaXN0cDUyMSBBQUFBRTJWalpITmhMWE5vWVRJdGJtbHpkSEExTWpFQUFBQUlibWx6ZEhBMU1qRUFBQUNGQkFBVFdweE5LNlNYTEo0dnh2Y0F4N0t4c3FLenI0a3pEalRpT0dQa3pyZWZnTjdVcmo2RUZPUXlBRWk5cXNnYkRVYXp0MktpdzJqc3djbG5TYW1zUDE0V2x3RkN2a1NuU1o4cTZwWGJTbGpNa3Z1R3FiVXZoSTVxTVlMTDNlRWpyU21nNDlWcTBWZkdFQmxIWUx6TGFncVBlN1FKR0NCMGlWTVk5b3N0TFdPM1NKbXVuZz09IGNpZm13X3JlcHJvZHVjZXJfa2V5Cg==
ssh-privatekey: LS0tLS1CRUdJTiBPUEVOU1NIIFBSSVZBVEUgS0VZLS0tLS0KYjNCbGJuTnphQzFyWlhrdGRqRUFBQUFBQkc1dmJtVUFBQUFFYm05dVpRQUFBQUFBQUFBQkFBQUFyQUFBQUJObFkyUnpZUwoxemFHRXlMVzVwYzNSd05USXhBQUFBQ0c1cGMzUndOVEl4QUFBQWhRUUFFMXFjVFN1a2x5eWVMOGIzQU1leXNiS2lzNitKCk13NDA0amhqNU02M240RGUxSzQraEJUa01nQkl2YXJJR3cxR3M3ZGlvc05vN01ISlowbXByRDllRnBjQlFyNUVwMG1mS3UKcVYyMHBZekpMN2hxbTFMNFNPYWpHQ3k5M2hJNjBwb09QVmF0Rlh4aEFaUjJDOHkyb0tqM3UwQ1JnZ2RJbFRHUGFMTFMxagp0MGlacnA0QUFBRVl0cGNtdHJhWEpyWUFBQUFUWldOa2MyRXRjMmhoTWkxdWFYTjBjRFV5TVFBQUFBaHVhWE4wY0RVeU1RCkFBQUlVRUFCTmFuRTBycEpjc25pL0c5d0RIc3JHeW9yT3ZpVE1PTk9JNFkrVE90NStBM3RTdVBvUVU1RElBU0wycXlCc04KUnJPM1lxTERhT3pCeVdkSnFhdy9YaGFYQVVLK1JLZEpueXJxbGR0S1dNeVMrNGFwdFMrRWptb3hnc3ZkNFNPdEthRGoxVwpyUlY4WVFHVWRndk10cUNvOTd0QWtZSUhTSlV4ajJpeTB0WTdkSW1hNmVBQUFBUWdHTWZobWFSblZFcnhjZ2Z6aVRpdzFnClBjYXBBV21TMHh5dDNyclhoSnExd0pRMys3ZFp0Y3l0alg5VVVuNnh0NlE1M0JTT1ZvaWR2L2pZK2krYytNVVhUZ0FBQUIKUmphV1p0ZDE5eVpYQnliMlIxWTJWeVgydGxlUUVDQXdRRkJnPT0KLS0tLS1FTkQgT1BFTlNTSCBQUklWQVRFIEtFWS0tLS0tCg==
ssh-publickey: ZWNkc2Etc2hhMi1uaXN0cDUyMSBBQUFBRTJWalpITmhMWE5vWVRJdGJtbHpkSEExTWpFQUFBQUlibWx6ZEhBMU1qRUFBQUNGQkFBVFdweE5LNlNYTEo0dnh2Y0F4N0t4c3FLenI0a3pEalRpT0dQa3pyZWZnTjdVcmo2RUZPUXlBRWk5cXNnYkRVYXp0MktpdzJqc3djbG5TYW1zUDE0V2x3RkN2a1NuU1o4cTZwWGJTbGpNa3Z1R3FiVXZoSTVxTVlMTDNlRWpyU21nNDlWcTBWZkdFQmxIWUx6TGFncVBlN1FKR0NCMGlWTVk5b3N0TFdPM1NKbXVuZz09IGNpZm13X3JlcHJvZHVjZXJfa2V5Cg==
kind: Secret
metadata:
name: dataplane-ansible-ssh-private-key-secret
namespace: openstack
type: Opaque
---
apiVersion: v1
data:
LibvirtPassword: MTIzNDU2Nzg=
kind: Secret
metadata:
name: libvirt-secret
namespace: openstack
type: Opaque
---
apiVersion: v1
data:
ssh-privatekey: LS0tLS1CRUdJTiBPUEVOU1NIIFBSSVZBVEUgS0VZLS0tLS0KYjNCbGJuTnphQzFyWlhrdGRqRUFBQUFBQkc1dmJtVUFBQUFFYm05dVpRQUFBQUFBQUFBQkFBQUFyQUFBQUJObFkyUnpZUwoxemFHRXlMVzVwYzNSd05USXhBQUFBQ0c1cGMzUndOVEl4QUFBQWhRUUFwWTlSRzV5a2pLR3p2c295dWlDZm1zakEwZkFYCmkvS0hQT3R3Zm9NZjRQZXpRSFFNOHFJZ0pGc0svaVlwNVJIWmNVQlcwVVBCNnBpazQ1L3k0QVF4bmVBQWRrN0JQbTc0dG8KSkxoVjY2U3pzV2pHR1NFdzVXVFBwVUVpaXdQMlNiL1l4dXloNWlLbUJyTE5SRWpYTEJvbjJJZWRBbEJMaC9FaGpkdFZjUwo5ZzczQ0tvQUFBRVFoeS9PODRjdnp2TUFBQUFUWldOa2MyRXRjMmhoTWkxdWFYTjBjRFV5TVFBQUFBaHVhWE4wY0RVeU1RCkFBQUlVRUFLV1BVUnVjcEl5aHM3N0tNcm9nbjVySXdOSHdGNHZ5aHp6cmNINkRIK0QzczBCMERQS2lJQ1JiQ3Y0bUtlVVIKMlhGQVZ0RkR3ZXFZcE9PZjh1QUVNWjNnQUhaT3dUNXUrTGFDUzRWZXVrczdGb3hoa2hNT1ZrejZWQklvc0Q5a20vMk1icwpvZVlpcGdheXpVUkkxeXdhSjlpSG5RSlFTNGZ4SVkzYlZYRXZZTzl3aXFBQUFBUWdEQ0lEdHFqZ0JNam8rbG1rRnhzV3NvCkxKOGxBSWF0a0ZTdDkxcGJHWWIrVFRnS0NSOGhqbXdjalNoRzFlNlRaZWZNTkc5TklzVlRYYjNjTkYvaThJTHV1UUFBQUEKNXViM1poSUcxcFozSmhkR2x2YmdFQ0F3UT0KLS0tLS1FTkQgT1BFTlNTSCBQUklWQVRFIEtFWS0tLS0tCg==
ssh-publickey: ZWNkc2Etc2hhMi1uaXN0cDUyMSBBQUFBRTJWalpITmhMWE5vWVRJdGJtbHpkSEExTWpFQUFBQUlibWx6ZEhBMU1qRUFBQUNGQkFDbGoxRWJuS1NNb2JPK3lqSzZJSitheU1EUjhCZUw4b2M4NjNCK2d4L2c5N05BZEF6eW9pQWtXd3IrSmlubEVkbHhRRmJSUThIcW1LVGpuL0xnQkRHZDRBQjJUc0UrYnZpMmdrdUZYcnBMT3hhTVlaSVREbFpNK2xRU0tMQS9aSnY5akc3S0htSXFZR3NzMUVTTmNzR2lmWWg1MENVRXVIOFNHTjIxVnhMMkR2Y0lxZz09IG5vdmEgbWlncmF0aW9uCg==
kind: Secret
metadata:
name: nova-migration-ssh-key
namespace: openstack
type: kubernetes.io/ssh-auth
---
apiVersion: dataplane.openstack.org/v1beta1
kind: OpenStackDataPlaneNodeSet
metadata:
name: openstack-edpm
namespace: openstack
spec:
baremetalSetTemplate:
bmhLabelSelector:
app: openstack
cloudUserName: cloud-admin
ctlplaneInterface: enp130s0f0
passwordSecret:
name: baremetalset-password-secret
namespace: openstack
provisioningInterface: enp5s0
env:
- name: ANSIBLE_FORCE_COLOR
value: "True"
networkAttachments:
- ctlplane
nodeTemplate:
ansible:
ansiblePort: 22
ansibleUser: cloud-admin
ansibleVars:
dns_search_domains: []
rhc_release: 9.4
rhc_repositories:
- {name: "*", state: disabled}
- {name: "<repository_name1>", state: enabled}
- {name: "<repository_name2>", state: enabled}
- {name: "<repository_name3>", state: enabled}
- {name: "<repository_name4>", state: enabled}
- {name: "<repository_name5>", state: enabled}
- {name: "<repository_name6>", state: enabled}
edpm_fips_mode: check
edpm_kernel_args: default_hugepagesz=1GB hugepagesz=1G hugepages=64 iommu=pt
intel_iommu=on tsx=off isolcpus=2-19,22-39
edpm_network_config_hide_sensitive_logs: false
edpm_network_config_os_net_config_mappings:
edpm-compute-0:
dmiString: system-product-name
id: PowerEdge R730
nic1: eno1
nic2: eno2
nic3: enp130s0f0
nic4: enp130s0f1
nic5: enp130s0f2
nic6: enp130s0f3
nic7: enp5s0f0
nic8: enp5s0f1
nic9: enp5s0f2
nic10: enp5s0f3
nic11: enp7s0f0np0
nic12: enp7s0f1np1
edpm-compute-1:
dmiString: system-product-name
id: PowerEdge R730
nic1: eno1
nic2: eno2
nic3: enp130s0f0
nic4: enp130s0f1
nic5: enp130s0f2
nic6: enp130s0f3
nic7: enp5s0f0
nic8: enp5s0f1
nic9: enp5s0f2
nic10: enp5s0f3
nic11: enp7s0f0np0
nic12: enp7s0f1np1
edpm_network_config_template: |
---
{% set mtu_list = [ctlplane_mtu] %}
{% for network in nodeset_networks %}
{{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }}
{%- endfor %}
{% set min_viable_mtu = mtu_list | max %}
network_config:
- type: interface
name: nic1
use_dhcp: false
- type: interface
name: nic2
use_dhcp: false
- type: linux_bond
name: bond_api
use_dhcp: false
bonding_options: "mode=active-backup"
dns_servers: {{ ctlplane_dns_nameservers }}
members:
- type: interface
name: nic3
primary: true
addresses:
- ip_netmask: {{ ctlplane_ip }}/{{ ctlplane_cidr }}
routes:
- default: true
next_hop: {{ ctlplane_gateway_ip }}
- type: vlan
vlan_id: {{ lookup(vars, networks_lower[internalapi] ~ _vlan_id) }}
device: bond_api
addresses:
- ip_netmask: {{ lookup(vars, networks_lower[internalapi] ~ _ip) }}/{{ lookup(vars, networks_lower[internalapi] ~ _cidr) }}
- type: vlan
vlan_id: {{ lookup(vars, networks_lower[storage] ~ _vlan_id) }}
device: bond_api
addresses:
- ip_netmask: {{ lookup(vars, networks_lower[storage] ~ _ip) }}/{{ lookup(vars, networks_lower[storage] ~ _cidr) }}
- type: ovs_user_bridge
name: br-link0
use_dhcp: false
ovs_extra: "set port br-link0 tag={{ lookup(vars, networks_lower[tenant] ~ _vlan_id) }}"
addresses:
- ip_netmask: {{ lookup(vars, networks_lower[tenant] ~ _ip) }}/{{ lookup(vars, networks_lower[tenant] ~ _cidr) }}
mtu: {{ lookup(vars, networks_lower[tenant] ~ _mtu) }}
members:
- type: ovs_dpdk_bond
name: dpdkbond0
mtu: 9000
rx_queue: 2
ovs_extra: "set port dpdkbond0 bond_mode=balance-slb"
members:
- type: ovs_dpdk_port
name: dpdk0
members:
- type: interface
name: nic7
- type: ovs_dpdk_port
name: dpdk1
members:
- type: interface
name: nic8
- type: ovs_user_bridge
name: br-dpdk0
mtu: 9000
use_dhcp: false
members:
- type: ovs_dpdk_bond
name: dpdkbond1
mtu: 9000
rx_queue: 3
ovs_options: "bond_mode=balance-tcp lacp=active other_config:lacp-time=fast other-config:lacp-fallback-ab=true other_config:lb-output-action=true"
members:
- type: ovs_dpdk_port
name: dpdk2
members:
- type: interface
name: nic5
- type: ovs_dpdk_port
name: dpdk3
members:
- type: interface
name: nic6
- type: ovs_user_bridge
name: br-dpdk1
mtu: 9000
use_dhcp: false
members:
- type: ovs_dpdk_port
name: dpdk4
mtu: 9000
rx_queue: 3
members:
- type: interface
name: nic4
- type: sriov_pf
name: nic9
numvfs: 10
mtu: 9000
use_dhcp: false
promisc: true
- type: sriov_pf
name: nic10
numvfs: 10
mtu: 9000
use_dhcp: false
promisc: true
- type: sriov_pf
name: nic11
numvfs: 5
mtu: 9000
use_dhcp: false
promisc: true
- type: sriov_pf
name: nic12
numvfs: 5
mtu: 9000
use_dhcp: false
promisc: true
edpm_neutron_sriov_agent_SRIOV_NIC_physical_device_mappings: sriov-1:enp5s0f2,sriov-2:enp5s0f3,sriov-3:enp7s0f0np0,sriov-4:enp7s0f1np1
edpm_nodes_validation_validate_controllers_icmp: false
edpm_nodes_validation_validate_gateway_icmp: false
edpm_nova_libvirt_qemu_group: hugetlbfs
edpm_ovn_bridge_mappings:
- dpdkmgmt:br-link0
- dpdkdata0:br-dpdk0
- dpdkdata1:br-dpdk1
edpm_ovs_dpdk_memory_channels: "4"
edpm_ovs_dpdk_pmd_auto_lb: "true"
edpm_ovs_dpdk_pmd_core_list: 2,3,4,5,6,7,22,23,24,25,26,27
edpm_ovs_dpdk_pmd_improvement_threshold: "25"
edpm_ovs_dpdk_pmd_load_threshold: "70"
edpm_ovs_dpdk_pmd_rebal_interval: "2"
edpm_ovs_dpdk_socket_memory: 4096,4096
edpm_ovs_dpdk_vhost_postcopy_support: "true"
edpm_selinux_mode: enforcing
edpm_sshd_allowed_ranges:
- 192.168.122.0/24
edpm_sshd_configure_firewall: true
edpm_tuned_isolated_cores: 2-19,22-39
edpm_tuned_profile: cpu-partitioning-powersave
enable_debug: false
gather_facts: false
neutron_physical_bridge_name: br-access
neutron_public_interface_name: nic1
service_net_map:
nova_api_network: internalapi
nova_libvirt_network: internalapi
timesync_ntp_servers:
- hostname: clock.redhat.com
ansibleSSHPrivateKeySecret: dataplane-ansible-ssh-private-key-secret
managementNetwork: ctlplane
networks:
- defaultRoute: true
name: ctlplane
subnetName: subnet1
- name: internalapi
subnetName: subnet1
- name: storage
subnetName: subnet1
- name: tenant
subnetName: subnet1
nodes:
edpm-compute-0:
hostName: compute-0
edpm-compute-1:
hostName: compute-1
preProvisioned: false
services:
- redhat
- bootstrap
- download-cache
- reboot-os
- configure-ovs-dpdk
- configure-network
- validate-network
- install-os
- configure-os
- ssh-known-hosts
- run-os
- install-certs
- ovn
- neutron-ovn-igmp
- neutron-metadata
- neutron-sriov
- libvirt
- nova-custom-ovsdpdksriov
- telemetry
---
apiVersion: dataplane.openstack.org/v1beta1
kind: OpenStackDataPlaneService
metadata:
name: neutron-ovn-igmp
namespace: openstack
spec:
caCerts: combined-ca-bundle
dataSources:
- configMapRef:
name: neutron-igmp
- secretRef:
name: neutron-ovn-agent-neutron-config
edpmServiceType: neutron-ovn
label: neutron-ovn-igmp
playbook: osp.edpm.neutron_ovn
tlsCerts:
default:
contents:
- dnsnames
- ips
issuer: osp-rootca-issuer-ovn
keyUsages:
- digital signature
- key encipherment
- client auth
networks:
- ctlplane
---
apiVersion: dataplane.openstack.org/v1beta1
kind: OpenStackDataPlaneService
metadata:
name: nova-custom-ovsdpdksriov
namespace: openstack
spec:
caCerts: combined-ca-bundle
dataSources:
- configMapRef:
name: ovs-dpdk-sriov-cpu-pinning-nova
- configMapRef:
name: sriov-nova
- secretRef:
name: nova-cell1-compute-config
- secretRef:
name: nova-migration-ssh-key
edpmServiceType: nova
label: nova-custom-ovsdpdksriov
playbook: osp.edpm.nova
tlsCerts:
default:
contents:
- dnsnames
- ips
issuer: osp-rootca-issuer-internal
networks:
- ctlplane
-
edpm-compute-n- Defines theedpm_network_config_os_net_config_mappingsvariable to map the actual NICs. You identify each NIC by specifying the MAC address or the device name on each compute node to the NIC ID that the RHOSOos-net-configtool uses which is typically, `nic`n. -
linux_bond- Creates a control-plane Linux bond for an isolated network. In this example, a Linux bond is created with mode active-backup onnic3andnic4. -
type: vlan- Assigns VLANs to Linux bonds. In this example, the VLAN ID of theinternalapiandstoragenetworks is assigned tobond-api. -
ovs_user_bridge- Sets a bridge with OVS-DPDK ports. In this example, an OVS user bridge is created with a DPDK bond that has two DPDK ports that correspond tonic7andnic8for the tenant network. A GENEVE tunnel is used. -
sriov_pf- Creates SR-IOV VFs. In this example, an interface type ofsriov_pfis configured as a physical function that the host can use. -
numvfs- Sets the number of VFs that are required. -
<repository_name1>,<repository_name2>,<repository_name3>,<repository_name4>,<repository_name5>,<repository_name6>: Specifies the name of the repository to enable. For more information about which repositories are required, see Required repositories for Red Hat OpenStack Services on OpenShift 18.0.
10.10.2. Example template - partitioned NIC Copy linkLink copied to clipboard!
This template example configures the RHOSO networks on a NIC that is partitioned. This example only shows the portion of the custom resource (CR) definition where the NIC is partitioned.
edpm_network_config_os_net_config_mappings:
dellr750:
dmiString: system-product-name
id: PowerEdge R750
nic1: eno8303
nic2: ens1f0
nic3: ens1f1
nic4: ens1f2
nic5: ens1f3
nic6: ens2f0np0
nic7: ens2f1np1
edpm_network_config_template: |
---
{% set mtu_list = [ctlplane_mtu] %}
{% for network in nodeset_networks %}
{{ mtu_list.append(lookup(vars, networks_lower[network] ~ _mtu)) }}
{%- endfor %}
{% set min_viable_mtu = mtu_list | max %}
network_config:
- type: interface
name: nic1
use_dhcp: false
- type: interface
name: nic2
use_dhcp: false
addresses:
- ip_netmask: {{ ctlplane_ip }}/{{ ctlplane_cidr }}
routes:
- default: true
next_hop: {{ ctlplane_gateway_ip }}
- type: sriov_pf
name: nic3
mtu: 9000
numvfs: 5
use_dhcp: false
defroute: false
nm_controlled: true
hotplug: true
- type: sriov_pf
name: nic4
mtu: 9000
numvfs: 5
use_dhcp: false
defroute: false
nm_controlled: true
hotplug: true
- type: linux_bond
name: bond_api
use_dhcp: false
bonding_options: "mode=active-backup"
dns_servers: {{ ctlplane_dns_nameservers }}
members:
- type: sriov_vf
device: nic3
vfid: 0
vlan_id: {{ lookup(vars, networks_lower[internalapi] ~ _vlan_id) }}
- type: sriov_vf
device: nic4
vfid: 0
vlan_id: {{ lookup(vars, networks_lower[internalapi] ~ _vlan_id) }}
addresses:
- ip_netmask: {{ lookup(vars, networks_lower[internalapi] ~ _ip) }}/{{ lookup(vars, networks_lower[internalapi] ~ _cidr) }}
- type: linux_bond
name: storage_bond
use_dhcp: false
bonding_options: "mode=active-backup"
dns_servers: {{ ctlplane_dns_nameservers }}
members:
- type: sriov_vf
device: nic3
vfid: 1
vlan_id: {{ lookup(vars, networks_lower[storage] ~ _vlan_id) }}
- type: sriov_vf
device: nic4
vfid: 1
vlan_id: {{ lookup(vars, networks_lower[storage] ~ _vlan_id) }}
addresses:
- ip_netmask: {{ lookup(vars, networks_lower[storage] ~ _ip) }}/{{ lookup(vars, networks_lower[storage] ~ _cidr) }}
- type: linux_bond
name: mgmtst_bond
use_dhcp: false
bonding_options: "mode=active-backup"
dns_servers: {{ ctlplane_dns_nameservers }}
members:
- type: sriov_vf
device: nic3
vfid: 2
vlan_id: {{ lookup(vars, networks_lower[storagemgmt] ~ _vlan_id) }}
- type: sriov_vf
device: nic4
vfid: 2
vlan_id: {{ lookup(vars, networks_lower[storagemgmt] ~ _vlan_id) }}
addresses:
- ip_netmask: {{ lookup(vars, networks_lower[storagemgmt] ~ _ip) }}/{{ lookup(vars, networks_lower[storagemgmt] ~ _cidr) }}
- type: ovs_user_bridge
name: br-link0
use_dhcp: false
mtu: 9000
ovs_extra: "set port br-link0 tag={{ lookup(vars, networks_lower[tenant] ~ _vlan_id) }}"
addresses:
- ip_netmask: {{ lookup(vars, networks_lower[tenant] ~ _ip) }}/{{ lookup(vars, networks_lower[tenant] ~ _cidr) }}
members:
- type: ovs_dpdk_bond
name: dpdkbond0
mtu: 9000
rx_queue: 1
members:
- type: ovs_dpdk_port
name: dpdk0
members:
- type: sriov_vf
device: nic3
vfid: 3
- type: ovs_dpdk_port
name: dpdk1
members:
- type: sriov_vf
device: nic4
vfid: 3
- type: ovs_user_bridge
name: br-dpdk0
use_dhcp: false
mtu: 9000
rx_queue: 1
members:
- type: ovs_dpdk_port
name: dpdk2
members:
- type: interface
name: nic5
- type: sriov_pf
name: nic6
mtu: 9000
numvfs: 5
use_dhcp: false
defroute: false
- type: sriov_pf
name: nic7
mtu: 9000
numvfs: 5
use_dhcp: false
defroute: false
10.11. Deploying the data plane Copy linkLink copied to clipboard!
Use the OpenStackDataPlaneDeployment CRD and custom resources (CRs) to configure the services on the data plane nodes and deploy the data plane.
You control the execution of Ansible on the data plane by creating OpenStackDataPlaneDeployment custom resources (CRs). Each OpenStackDataPlaneDeployment CR models a single Ansible execution.
When the OpenStackDataPlaneDeployment successfully completes execution, it does not automatically run the Ansible again, even if the OpenStackDataPlaneDeployment or related OpenStackDataPlaneNodeSet resources are changed. To start another Ansible execution, you must create another OpenStackDataPlaneDeployment CR.
Create an OpenStackDataPlaneDeployment (CR) that deploys each of your OpenStackDataPlaneNodeSet CRs.
Procedure
Create a file on your workstation named
openstack_data_plane_deploy.yamlto define theOpenStackDataPlaneDeploymentCR:apiVersion: dataplane.openstack.org/v1beta1 kind: OpenStackDataPlaneDeployment metadata: name: openstack-data-plane-
name- TheOpenStackDataPlaneDeploymentCR name must be unique, must consist of lower case alphanumeric characters,-(hyphen) or.(period), and must start and end with an alphanumeric character. Update the name in this example to a name that reflects the node sets in the deployment.
-
Add all the
OpenStackDataPlaneNodeSetCRs that you want to deploy.spec: nodeSets: - openstack-data-plane - <nodeSet_name> - ... - <nodeSet_name> services: ...-
Replace
<nodeSet_name>with the names of theOpenStackDataPlaneNodeSetCRs that you want to include in your data plane deployment, for example,openstack_preprovisioned_node_set.yamloropenstack_unprovisioned_node_set.yaml.
-
Replace
-
Save the
openstack_data_plane_deploy.yamldeployment file. Deploy the data plane:
$ oc create -f openstack_data_plane_deploy.yaml -n openstackYou can view the Ansible logs while the deployment executes:
$ oc get pod -l app=openstackansibleee -w $ oc logs -l app=openstackansibleee -f --max-log-requests 10Confirm that the data plane is deployed:
$ oc get openstackdataplanedeployment -n openstack- Sample output
NAME STATUS MESSAGE openstack-data-plane True Setup Complete
Repeat the
oc getcommand until you see theNodeSet Readymessage:$ oc get openstackdataplanenodeset -n openstack- Sample output
NAME STATUS MESSAGE openstack-data-plane True NodeSet ReadyFor information about the meaning of the returned status, see Data plane conditions and states.
If the status indicates that the data plane has not been deployed, then troubleshoot the deployment. For information, see Troubleshooting the data plane creation and deployment.
Map the Compute nodes to the Compute cell that they are connected to:
$ oc rsh nova-cell0-conductor-0 nova-manage cell_v2 discover_hosts --verboseIf you did not create additional cells, this command maps the Compute nodes to
cell1.
Verification
Access the remote shell for the
openstackclientpod and confirm that the deployed Compute nodes are visible on the control plane:$ oc rsh -n openstack openstackclient $ openstack hypervisor list
10.12. Data plane conditions and states Copy linkLink copied to clipboard!
Each data plane resource has a series of conditions within their status subresource that indicates the overall state of the resource, including its deployment progress.
For an OpenStackDataPlaneNodeSet, until an OpenStackDataPlaneDeployment has been started and finished successfully, the Ready condition is False. When the deployment succeeds, the Ready condition is set to True. A subsequent deployment sets the Ready condition to False until the deployment succeeds, when the Ready condition is set to True.
| Condition | Description |
|---|---|
|
|
|
|
| "True": All setup tasks for a resource are complete. Setup tasks include verifying the SSH key secret, verifying other fields on the resource, and creating the Ansible inventory for each resource. Each service-specific condition is set to "True" when that service completes deployment. You can check the service conditions to see which services have completed their deployment, or which services failed. |
|
| "True": The NodeSet has been successfully deployed. |
|
| "True": The required inputs are available and ready. |
|
| "True": DNSData resources are ready. |
|
| "True": The IPSet resources are ready. |
|
| "True": Bare-metal nodes are provisioned and ready. |
| Status field | Description |
|---|---|
|
|
|
|
| |
|
|
| Condition | Description |
|---|---|
|
|
|
|
| "True": The data plane is successfully deployed. |
|
| "True": The required inputs are available and ready. |
|
|
"True": The deployment has succeeded for the named |
|
|
"True": The deployment has succeeded for the named |
| Status field | Description |
|---|---|
|
|
|
| Condition | Description |
|---|---|
|
| "True": The service has been created and is ready for use. "False": The service has failed to be created. |
10.13. Troubleshooting data plane creation and deployment Copy linkLink copied to clipboard!
To troubleshoot a deployment when services are not deploying or operating correctly, you can check the job condition message for the service, and you can check the logs for a node set.
10.13.1. Checking the job condition message for a service Copy linkLink copied to clipboard!
Each data plane deployment has associated services with a job condition message that reflects the current AnsibleEE job status. You can use this information to troubleshoot services that are not deploying or operating correctly.
Procedure
Determine the name and status of all deployments:
$ oc get openstackdataplanedeploymentThe following example output shows two deployments currently in progress:
$ oc get openstackdataplanedeployment NAME NODESETS STATUS MESSAGE edpm-compute ["openstack-edpm-ipam"] False Deployment in progressRetrieve and inspect Ansible execution jobs.
The Kubernetes jobs are labeled with the name of the
OpenStackDataPlaneDeployment. You can list jobs for eachOpenStackDataPlaneDeploymentby using the label:$ oc get job -l openstackdataplanedeployment=edpm-compute NAME STATUS COMPLETIONS DURATION AGE bootstrap-edpm-compute-openstack-edpm-ipam Complete 1/1 78s 25h configure-network-edpm-compute-openstack-edpm-ipam Complete 1/1 37s 25h configure-os-edpm-compute-openstack-edpm-ipam Complete 1/1 66s 25h download-cache-edpm-compute-openstack-edpm-ipam Complete 1/1 64s 25h install-certs-edpm-compute-openstack-edpm-ipam Complete 1/1 46s 25h install-os-edpm-compute-openstack-edpm-ipam Complete 1/1 57s 25h libvirt-edpm-compute-openstack-edpm-ipam Complete 1/1 2m37s 25h neutron-metadata-edpm-compute-openstack-edpm-ipam Complete 1/1 61s 25h nova-edpm-compute-openstack-edpm-ipam Complete 1/1 3m20s 25h ovn-edpm-compute-openstack-edpm-ipam Complete 1/1 78s 25h run-os-edpm-compute-openstack-edpm-ipam Complete 1/1 33s 25h ssh-known-hosts-edpm-compute Complete 1/1 19s 25h telemetry-edpm-compute-openstack-edpm-ipam Complete 1/1 2m5s 25h validate-network-edpm-compute-openstack-edpm-ipam Complete 1/1 16s 25hYou can check logs by using
oc logs -f job/<job-name>, for example, if you want to check the logs from the configure-network job:$ oc logs -f jobs/configure-network-edpm-compute-openstack-edpm-ipam | tail -n2 PLAY RECAP ********************************************************************* edpm-compute-0 : ok=22 changed=0 unreachable=0 failed=0 skipped=17 rescued=0 ignored=0
10.13.1.1. Job condition messages Copy linkLink copied to clipboard!
AnsibleEE jobs have an associated condition message that indicates the current state of the service job. This condition message is displayed in the MESSAGE field of the oc get job <job_name> command output. Jobs return one of the following conditions when queried:
-
Job not started: The job has not started. -
Job not found: The job could not be found. -
Job is running: The job is currently running. -
Job complete: The job execution is complete. -
Job error occurred <error_message>: The job stopped executing unexpectedly. The<error_message>is replaced with a specific error message.
To further investigate a service that is displaying a particular job condition message, view its logs by using the command oc logs job/<service>. For example, to view the logs for the repo-setup-openstack-edpm service, use the command oc logs job/repo-setup-openstack-edpm.
10.13.2. Checking the logs for a node set Copy linkLink copied to clipboard!
You can access the logs for a node set to check for deployment issues.
Procedure
Retrieve pods with the
OpenStackAnsibleEElabel:$ oc get pods -l app=openstackansibleee configure-network-edpm-compute-j6r4l 0/1 Completed 0 3m36s validate-network-edpm-compute-6g7n9 0/1 Pending 0 0s validate-network-edpm-compute-6g7n9 0/1 ContainerCreating 0 11s validate-network-edpm-compute-6g7n9 1/1 Running 0 13sSSH into the pod you want to check:
Pod that is running:
$ oc rsh validate-network-edpm-compute-6g7n9Pod that is not running:
$ oc debug configure-network-edpm-compute-j6r4l
List the directories in the
/runner/artifactsmount:$ ls /runner/artifacts configure-network-edpm-compute validate-network-edpm-computeView the
stdoutfor the required artifact:$ cat /runner/artifacts/configure-network-edpm-compute/stdout