4 from ctypes import CDLL
5 from ctypes import get_errno
6 from ctypes.util import find_library
7 from typing import Dict
8 from typing import List
9 from typing import Optional
14 def nodeid_to_method_name(nodeid: str) -> str:
15 """file_name.py::ClassName::method_name[parametrize] -> method_name"""
16 return nodeid.split("::")[-1].split("[")[0]
19 class LibCWrapper(object):
21 path: Optional[str] = find_library("c")
23 raise RuntimeError("libc not found")
24 self._libc = CDLL(path, use_errno=True)
26 def modfind(self, mod_name: str) -> int:
27 if self._libc.modfind(bytes(mod_name, encoding="ascii")) == -1:
31 def kldload(self, kld_name: str) -> int:
32 if self._libc.kldload(bytes(kld_name, encoding="ascii")) == -1:
36 def jail_attach(self, jid: int) -> int:
37 if self._libc.jail_attach(jid) != 0:
45 class BaseTest(object):
46 NEED_ROOT: bool = False # True if the class needs root privileges for the setup
47 TARGET_USER = None # Set to the target user by the framework
48 REQUIRED_MODULES: List[str] = []
50 def require_module(self, mod_name: str, skip=True):
51 error_code = libc.modfind(mod_name)
54 err_str = os.strerror(error_code)
55 txt = "kernel module '{}' not available: {}".format(mod_name, err_str)
61 def _check_modules(self):
62 for mod_name in self.REQUIRED_MODULES:
63 self.require_module(mod_name)
66 def atf_vars(self) -> Dict[str, str]:
68 return {k[len(px):]: v for k, v in os.environ.items() if k.startswith(px)}
70 def drop_privileges_user(self, user: str):
71 uid = pwd.getpwnam(user)[2]
72 print("Dropping privs to {}/{}".format(user, uid))
75 def drop_privileges(self):
77 if self.TARGET_USER == "unprivileged":
78 user = self.atf_vars["unprivileged-user"]
80 user = self.TARGET_USER
81 self.drop_privileges_user(user)
84 def test_id(self) -> str:
85 # 'test_ip6_output.py::TestIP6Output::test_output6_pktinfo[ipandif] (setup)'
86 return os.environ.get("PYTEST_CURRENT_TEST").split(" ")[0]
88 def setup_method(self, method):
89 """Run all pre-requisits for the test execution"""