diff options
author | Mattias Jernberg <mattiasj@axis.com> | 2022-09-29 18:37:13 +0200 |
---|---|---|
committer | Richard Purdie <richard.purdie@linuxfoundation.org> | 2022-09-29 21:26:04 +0100 |
commit | 0d317209d4234c5f05a9fcdc13c52f502f104018 (patch) | |
tree | 0474370065750fc6ec58c3e1023b1e4c5bec8a7a | |
parent | c014281f72f4f54ec8e681ef2b8e1080de9ab5cf (diff) | |
download | bitbake-contrib-0d317209d4234c5f05a9fcdc13c52f502f104018.tar.gz |
utils: Add enable_loopback_networking()
It can be used to enable the loopback interface, typically after calling
disable_network().
Also correct a typo in a debug message.
Signed-off-by: Mattias Jernberg <mattias.jernberg@axis.com>
Signed-off-by: Peter Kjellerstedt <peter.kjellerstedt@axis.com>
Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org>
-rw-r--r-- | lib/bb/utils.py | 42 |
1 files changed, 41 insertions, 1 deletions
diff --git a/lib/bb/utils.py b/lib/bb/utils.py index 92d44c526..e6e21e20f 100644 --- a/lib/bb/utils.py +++ b/lib/bb/utils.py @@ -29,6 +29,8 @@ import collections import copy import ctypes import random +import socket +import struct import tempfile from subprocess import getstatusoutput from contextlib import contextmanager @@ -1603,6 +1605,44 @@ def set_process_name(name): except: pass +def enable_loopback_networking(): + # From bits/ioctls.h + SIOCGIFFLAGS = 0x8913 + SIOCSIFFLAGS = 0x8914 + SIOCSIFADDR = 0x8916 + SIOCSIFNETMASK = 0x891C + + # if.h + IFF_UP = 0x1 + IFF_RUNNING = 0x40 + + # bits/socket.h + AF_INET = 2 + + # char ifr_name[IFNAMSIZ=16] + ifr_name = struct.pack("@16s", b"lo") + def netdev_req(fd, req, data = b""): + # Pad and add interface name + data = ifr_name + data + (b'\x00' * (16 - len(data))) + # Return all data after interface name + return fcntl.ioctl(fd, req, data)[16:] + + with socket.socket(socket.AF_INET, socket.SOCK_DGRAM, socket.IPPROTO_IP) as sock: + fd = sock.fileno() + + # struct sockaddr_in ifr_addr { unsigned short family; uint16_t sin_port ; uint32_t in_addr; } + req = struct.pack("@H", AF_INET) + struct.pack("=H4B", 0, 127, 0, 0, 1) + netdev_req(fd, SIOCSIFADDR, req) + + # short ifr_flags + flags = struct.unpack_from('@h', netdev_req(fd, SIOCGIFFLAGS))[0] + flags |= IFF_UP | IFF_RUNNING + netdev_req(fd, SIOCSIFFLAGS, struct.pack('@h', flags)) + + # struct sockaddr_in ifr_netmask + req = struct.pack("@H", AF_INET) + struct.pack("=H4B", 0, 255, 0, 0, 0) + netdev_req(fd, SIOCSIFNETMASK, req) + def disable_network(uid=None, gid=None): """ Disable networking in the current process if the kernel supports it, else @@ -1624,7 +1664,7 @@ def disable_network(uid=None, gid=None): ret = libc.unshare(CLONE_NEWNET | CLONE_NEWUSER) if ret != 0: - logger.debug("System doesn't suport disabling network without admin privs") + logger.debug("System doesn't support disabling network without admin privs") return with open("/proc/self/uid_map", "w") as f: f.write("%s %s 1" % (uid, uid)) |