Closed
Description
Using get_netnsid
with a fd
works for IPRoute
instances, calling it on NetNS
does fail.
I've created two (iproute2 netns'ish) network namespaces:
service
tenant1
I need a nsid to create a vlan link inside of tenant1
linked to a physical interface in the service
namespace. To reference the other namespace I need to use the bind mount in /var/run/netns
as there is no pid inside this netns. When calling a netns method of NetNS with the fd
parameter, it will be passed into the proxy NetNS process where the fd is invalid.
Affected NetNS methods:
NetNS.get_netnsid
NetNS.set_netnsid
# python3
Python 3.11.2 (main, Mar 13 2023, 12:18:29) [GCC 12.2.0] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> from pyroute2 import NetNS
>>> n = NetNS('tenant1')
>>> with open('/var/run/netns/service', 'r') as fh:
... n.get_netnsid(fd=fh.fileno())
...
Traceback (most recent call last):
File "<stdin>", line 2, in <module>
File "/home/thomas/src/ifstate/.venv/lib/python3.11/site-packages/pyroute2/iproute/linux.py", line 687, in get_netnsid
response = self.nlm_request(msg, RTM_GETNSID, NLM_F_REQUEST)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/home/thomas/src/ifstate/.venv/lib/python3.11/site-packages/pyroute2/netlink/nlsocket.py", line 870, in nlm_request
return tuple(self._genlm_request(*argv, **kwarg))
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/home/thomas/src/ifstate/.venv/lib/python3.11/site-packages/pyroute2/netlink/nlsocket.py", line 1214, in nlm_request
for msg in self.get(
^^^^^^^^^
File "/home/thomas/src/ifstate/.venv/lib/python3.11/site-packages/pyroute2/netlink/nlsocket.py", line 873, in get
return tuple(self._genlm_get(*argv, **kwarg))
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/home/thomas/src/ifstate/.venv/lib/python3.11/site-packages/pyroute2/netlink/nlsocket.py", line 550, in get
raise msg['header']['error']
pyroute2.netlink.exceptions.NetlinkError: (9, 'Bad file descriptor')
>>> with open('/var/run/netns/service', 'r') as fh:
... n.get_netnsid(fd=fh.fileno())
...
Traceback (most recent call last):
File "<stdin>", line 2, in <module>
File "/home/thomas/src/ifstate/.venv/lib/python3.11/site-packages/pyroute2/iproute/linux.py", line 687, in get_netnsid
response = self.nlm_request(msg, RTM_GETNSID, NLM_F_REQUEST)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/home/thomas/src/ifstate/.venv/lib/python3.11/site-packages/pyroute2/netlink/nlsocket.py", line 870, in nlm_request
return tuple(self._genlm_request(*argv, **kwarg))
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/home/thomas/src/ifstate/.venv/lib/python3.11/site-packages/pyroute2/netlink/nlsocket.py", line 1214, in nlm_request
for msg in self.get(
^^^^^^^^^
File "/home/thomas/src/ifstate/.venv/lib/python3.11/site-packages/pyroute2/netlink/nlsocket.py", line 873, in get
return tuple(self._genlm_get(*argv, **kwarg))
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/home/thomas/src/ifstate/.venv/lib/python3.11/site-packages/pyroute2/netlink/nlsocket.py", line 550, in get
raise msg['header']['error']
pyroute2.netlink.exceptions.NetlinkError: (9, 'Bad file descriptor')
>>>
An strace of the NetNS proxy process shows this output:
# strace -f -p 1019132
strace: Process 1019132 attached
pselect6(8, [5 7], NULL, [5 7], NULL, NULL) = 1 (in [5])
read(5, "\21\1\0\0\0\0\0\0", 8) = 8
read(5, "\200\4\225\376\0\0\0\0\0\0\0}\224(\214\5stage\224\214\vreconstr"..., 265) = 265
sendto(7, [{nlmsg_len=28, nlmsg_type=0x5a /* NLMSG_??? */, nlmsg_flags=NLM_F_REQUEST, nlmsg_seq=256, nlmsg_pid=1018897}, "\x00\x00\x00\x00\x08\x00\x03\x00\x09\x00\x00\x00"], 28, 0, {sa_family=AF_NETLINK, nl_pad=0x1e01, nl_pid=0, nl_groups=00000000}, 12) = 28
write(4, "K\0\0\0\0\0\0\0\200\4\2258\0\0\0\0\0\0\0}\224(\214\5stage\224\214\v"..., 75) = 75
pselect6(8, [5 7], NULL, [5 7], NULL, NULL) = 1 (in [7])
getsockopt(7, SOL_SOCKET, SO_RCVBUF, [425984], [4]) = 0
recvfrom(7, "", 0, MSG_PEEK|MSG_TRUNC|MSG_DONTWAIT, {sa_family=AF_NETLINK, nl_pid=0, nl_groups=00000000}, [12]) = 48
recvfrom(7, [{nlmsg_len=48, nlmsg_type=NLMSG_ERROR, nlmsg_flags=0, nlmsg_seq=256, nlmsg_pid=1019132}, {error=-EBADF, msg=[{nlmsg_len=28, nlmsg_type=0x5a /* NLMSG_??? */, nlmsg_flags=NLM_F_REQUEST, nlmsg_seq=256, nlmsg_pid=1018897}, "\x00\x00\x00\x00\x08\x00\x03\x00\x09\x00\x00\x00"]}], 48, 0, NULL, NULL) = 48
The error is expected as there is no such fd open:
# ls -lha /proc/1019132/fd
total 0
dr-x------ 2 root root 0 Aug 20 11:39 .
dr-xr-xr-x 9 root root 0 Aug 20 11:39 ..
lrwx------ 1 root root 64 Aug 20 12:02 0 -> /dev/pts/3
lrwx------ 1 root root 64 Aug 20 12:02 1 -> /dev/pts/3
lrwx------ 1 root root 64 Aug 20 12:02 2 -> /dev/pts/3
lr-x------ 1 root root 64 Aug 20 12:02 3 -> 'pipe:[1861959]'
l-wx------ 1 root root 64 Aug 20 12:02 4 -> 'pipe:[1858288]'
lr-x------ 1 root root 64 Aug 20 12:02 5 -> 'pipe:[1858289]'
l-wx------ 1 root root 64 Aug 20 12:02 6 -> 'pipe:[1861959]'
lrwx------ 1 root root 64 Aug 20 11:39 7 -> 'socket:[1861960]'
Even if I understand the reason for the exception it is not clear to me how this can be solved 😵💫
Metadata
Metadata
Assignees
Labels
No labels
Activity