blob: cb1a0dd9f4c4acb2e005bcb80489cc59e01735d8 [file] [log] [blame]
Naveen Joy7ea7ab52021-05-11 10:31:18 -07001#!/usr/bin/env python
2
3# Utility functions for QEMU tests ##
4
5import subprocess
Naveen Joye4168932022-10-04 14:22:05 -07006import sys
Naveen Joy7ea7ab52021-05-11 10:31:18 -07007
8
Andrew Yourtchenko9ba6dcf2023-06-20 14:52:08 +00009def can_create_namespaces():
10 """Check if the environment allows creating the namespaces"""
11
12 try:
13 namespace = "vpp_chk_4212"
14 result = subprocess.run(["ip", "netns", "add", namespace], capture_output=True)
15 if result.returncode != 0:
16 return False
17 result = subprocess.run(["ip", "netns", "del", namespace], capture_output=True)
18 if result.returncode != 0:
19 return False
20 return True
21 except:
22 return False
23
24
Naveen Joy7ea7ab52021-05-11 10:31:18 -070025def create_namespace(ns):
Naveen Joye4168932022-10-04 14:22:05 -070026 """create one or more namespaces.
27
28 arguments:
29 ns -- a string value or an iterable of namespace names
30 """
31 if isinstance(ns, str):
32 namespaces = [ns]
33 else:
34 namespaces = ns
Naveen Joy7ea7ab52021-05-11 10:31:18 -070035 try:
Naveen Joye4168932022-10-04 14:22:05 -070036 for namespace in namespaces:
Andrew Yourtchenko9ba6dcf2023-06-20 14:52:08 +000037 result = subprocess.run(["ip", "netns", "add", namespace])
38 if result.returncode != 0:
39 raise Exception(f"Error while creating namespace {namespace}")
Naveen Joy7ea7ab52021-05-11 10:31:18 -070040 except subprocess.CalledProcessError as e:
41 raise Exception("Error creating namespace:", e.output)
42
43
Naveen Joye4168932022-10-04 14:22:05 -070044def add_namespace_route(ns, prefix, gw_ip):
45 """Add a route to a namespace.
46
47 arguments:
48 ns -- namespace string value
49 prefix -- NETWORK/MASK or "default"
50 gw_ip -- Gateway IP
51 """
52 try:
53 subprocess.run(
54 ["ip", "netns", "exec", ns, "ip", "route", "add", prefix, "via", gw_ip],
55 capture_output=True,
56 )
57 except subprocess.CalledProcessError as e:
58 raise Exception("Error adding route to namespace:", e.output)
59
60
61def delete_host_interfaces(*host_interface_names):
62 """Delete host interfaces.
63
64 arguments:
65 host_interface_names - sequence of host interface names to be deleted
66 """
67 for host_interface_name in host_interface_names:
68 try:
69 subprocess.run(
70 ["ip", "link", "del", host_interface_name], capture_output=True
71 )
72 except subprocess.CalledProcessError as e:
73 raise Exception("Error deleting host interface:", e.output)
74
75
76def create_host_interface(
77 host_interface_name, vpp_interface_name, host_namespace, *host_ip_prefixes
78):
79 """Create a host interface of type veth.
80
81 arguments:
82 host_interface_name -- name of the veth interface on the host side
83 vpp_interface_name -- name of the veth interface on the VPP side
84 host_namespace -- host namespace into which the host_interface needs to be set
85 host_ip_prefixes -- a sequence of ip/prefix-lengths to be set
86 on the host_interface
87 """
88 try:
89 process = subprocess.run(
90 [
91 "ip",
92 "link",
93 "add",
94 "name",
95 vpp_interface_name,
96 "type",
97 "veth",
98 "peer",
99 "name",
100 host_interface_name,
101 ],
102 capture_output=True,
103 )
104 if process.returncode != 0:
105 print(f"Error creating host interface: {process.stderr}")
106 sys.exit(1)
107
108 process = subprocess.run(
109 ["ip", "link", "set", host_interface_name, "netns", host_namespace],
110 capture_output=True,
111 )
112 if process.returncode != 0:
113 print(f"Error setting host interface namespace: {process.stderr}")
114 sys.exit(1)
115
116 process = subprocess.run(
117 ["ip", "link", "set", "dev", vpp_interface_name, "up"], capture_output=True
118 )
119 if process.returncode != 0:
120 print(f"Error bringing up the host interface: {process.stderr}")
121 sys.exit(1)
122
123 process = subprocess.run(
124 [
125 "ip",
126 "netns",
127 "exec",
128 host_namespace,
129 "ip",
130 "link",
131 "set",
132 "dev",
133 host_interface_name,
134 "up",
135 ],
136 capture_output=True,
137 )
138 if process.returncode != 0:
139 print(
140 f"Error bringing up the host interface in namespace: "
141 f"{process.stderr}"
142 )
143 sys.exit(1)
144
145 for host_ip_prefix in host_ip_prefixes:
146 process = subprocess.run(
147 [
148 "ip",
149 "netns",
150 "exec",
151 host_namespace,
152 "ip",
153 "addr",
154 "add",
155 host_ip_prefix,
156 "dev",
157 host_interface_name,
158 ],
159 capture_output=True,
160 )
161 if process.returncode != 0:
162 print(
163 f"Error setting ip prefix on the host interface: "
164 f"{process.stderr}"
165 )
166 sys.exit(1)
167 except subprocess.CalledProcessError as e:
168 raise Exception("Error adding route to namespace:", e.output)
169
170
171def set_interface_mtu(namespace, interface, mtu, logger):
172 """set an mtu number on a linux device interface."""
173 args = ["ip", "link", "set", "mtu", str(mtu), "dev", interface]
174 if namespace:
175 args = ["ip", "netns", "exec", namespace] + args
176 try:
177 logger.debug(
178 f"Setting mtu:{mtu} on linux interface:{interface} "
179 f"in namespace:{namespace}"
180 )
181 subprocess.run(args)
182 except subprocess.CalledProcessError as e:
183 raise Exception("Error updating mtu:", e.output)
184
185
186def enable_interface_gso(namespace, interface):
187 """enable gso offload on a linux device interface."""
188 args = ["ethtool", "-K", interface, "rx", "on", "tx", "on"]
189 if namespace:
190 args = ["ip", "netns", "exec", namespace] + args
191 try:
192 process = subprocess.run(args, capture_output=True)
193 if process.returncode != 0:
194 print(
195 f"Error enabling GSO offload on linux device interface: "
196 f"{process.stderr}"
197 )
198 sys.exit(1)
199 except subprocess.CalledProcessError as e:
200 raise Exception("Error enabling gso:", e.output)
201
202
203def disable_interface_gso(namespace, interface):
204 """disable gso offload on a linux device interface."""
205 args = ["ethtool", "-K", interface, "rx", "off", "tx", "off"]
206 if namespace:
207 args = ["ip", "netns", "exec", namespace] + args
208 try:
209 process = subprocess.run(args, capture_output=True)
210 if process.returncode != 0:
211 print(
212 f"Error disabling GSO offload on linux device interface: "
213 f"{process.stderr}"
214 )
215 sys.exit(1)
216 except subprocess.CalledProcessError as e:
217 raise Exception("Error disabling gso:", e.output)
218
219
220def delete_namespace(namespaces):
221 """delete one or more namespaces.
222
223 arguments:
224 namespaces -- a list of namespace names
225 """
226 try:
227 for namespace in namespaces:
Andrew Yourtchenko9ba6dcf2023-06-20 14:52:08 +0000228 result = subprocess.run(
229 ["ip", "netns", "del", namespace], capture_output=True
230 )
231 if result.returncode != 0:
232 raise Exception(f"Error while deleting namespace {namespace}")
Naveen Joye4168932022-10-04 14:22:05 -0700233 except subprocess.CalledProcessError as e:
234 raise Exception("Error deleting namespace:", e.output)
235
236
Naveen Joy7ea7ab52021-05-11 10:31:18 -0700237def list_namespace(ns):
238 """List the IP address of a namespace"""
239 try:
240 subprocess.run(["ip", "netns", "exec", ns, "ip", "addr"])
241 except subprocess.CalledProcessError as e:
242 raise Exception("Error listing namespace IP:", e.output)