示例#1
0
 def test_by_task_struct(self):
     pid = fork_and_pause()
     wait_until(proc_blocked, pid)
     self.assertIn("pause",
                   str(self.prog.stack_trace(find_task(self.prog, pid))))
     os.kill(pid, signal.SIGKILL)
     os.waitpid(pid, 0)
示例#2
0
    def setUpClass(cls):
        # It'd be nice to just use addClassCleanup(), but that was added in
        # Python 3.8.
        cls.__cleanups = []
        try:
            super().setUpClass()

            # Don't enable cgroup2 on systems that aren't already using it (or
            # don't support it).
            cgroup2_enabled = False
            try:
                with open("/proc/self/cgroup", "rb") as f:
                    for line in f:
                        if line.startswith(b"0::"):
                            cgroup2_enabled = True
                            break
            except FileNotFoundError:
                pass
            if not cgroup2_enabled:
                raise unittest.SkipTest("cgroup2 not enabled")

            # It's easier to mount the cgroup2 filesystem than to find it.
            cgroup2_mount = Path(tempfile.mkdtemp(prefix="drgn-tests-"))
            cls.__cleanups.append((cgroup2_mount.rmdir, ))
            mount("cgroup2", cgroup2_mount, "cgroup2",
                  MS_NOSUID | MS_NODEV | MS_NOEXEC)
            cls.__cleanups.append((umount, cgroup2_mount))

            cls.root_cgroup = cls.prog["cgrp_dfl_root"].cgrp.address_of_()

            pid = fork_and_pause()
            try:
                task = find_task(cls.prog, pid)

                parent_cgroup_dir = Path(
                    tempfile.mkdtemp(prefix="drgn-tests-", dir=cgroup2_mount))
                cls.__cleanups.append((parent_cgroup_dir.rmdir, ))
                cls.parent_cgroup_name = os.fsencode(parent_cgroup_dir.name)
                cls.parent_cgroup_path = b"/" + cls.parent_cgroup_name

                (parent_cgroup_dir / "cgroup.procs").write_text(str(pid))
                cls.parent_cgroup = task.cgroups.dfl_cgrp.read_()

                child_cgroup_dir = parent_cgroup_dir / "child"
                child_cgroup_dir.mkdir()
                cls.__cleanups.append((child_cgroup_dir.rmdir, ))
                cls.child_cgroup_name = os.fsencode(child_cgroup_dir.name)
                cls.child_cgroup_path = (cls.parent_cgroup_path + b"/" +
                                         cls.child_cgroup_name)

                (child_cgroup_dir / "cgroup.procs").write_text(str(pid))
                cls.child_cgroup = task.cgroups.dfl_cgrp.read_()
            finally:
                os.kill(pid, signal.SIGKILL)
                os.waitpid(pid, 0)
        except BaseException:
            for cleanup in reversed(cls.__cleanups):
                cleanup[0](*cleanup[1:])
            raise
示例#3
0
文件: test_user.py 项目: osandov/drgn
 def test_find_user(self):
     for uid in self.UIDS:
         pid = fork_and_pause(functools.partial(os.setuid, uid))
         try:
             wait_until(lambda: proc_state(pid) == "S")
             found_uid = find_user(self.prog, uid).uid.val.value_()
         finally:
             os.kill(pid, signal.SIGKILL)
         self.assertEqual(found_uid, uid)
示例#4
0
文件: test_user.py 项目: osandov/drgn
 def test_for_each_user(self):
     pids = []
     try:
         for uid in self.UIDS:
             pid = fork_and_pause(functools.partial(os.setuid, uid))
             wait_until(lambda: proc_state(pid) == "S")
             pids.append(pid)
         found_uids = {user.uid.val.value_() for user in for_each_user(self.prog)}
     finally:
         for pid in pids:
             os.kill(pid, signal.SIGKILL)
     self.assertTrue(self.UIDS.issubset(found_uids))
示例#5
0
 def test_registers(self):
     # Smoke test that we get at least one register and that
     # StackFrame.registers() agrees with StackFrame.register().
     pid = fork_and_pause()
     wait_until(proc_blocked, pid)
     trace = self.prog.stack_trace(pid)
     have_registers = False
     for frame in trace:
         for name, value in frame.registers().items():
             self.assertEqual(frame.register(name), value)
             have_registers = True
     self.assertTrue(have_registers)
     os.kill(pid, signal.SIGKILL)
     os.waitpid(pid, 0)
示例#6
0
 def _test_by_pid(self, orc):
     old_orc = int(os.environ.get("DRGN_PREFER_ORC_UNWINDER", "0")) != 0
     with setenv("DRGN_PREFER_ORC_UNWINDER", "1" if orc else "0"):
         if orc == old_orc:
             prog = self.prog
         else:
             prog = Program()
             prog.set_kernel()
             self._load_debug_info(prog)
         pid = fork_and_pause()
         wait_until(proc_blocked, pid)
         self.assertIn("pause", str(prog.stack_trace(pid)))
         os.kill(pid, signal.SIGKILL)
         os.waitpid(pid, 0)
示例#7
0
 def test_local_variable(self):
     pid = fork_and_pause()
     wait_until(proc_blocked, pid)
     for frame in self.prog.stack_trace(pid):
         if frame.name in ("context_switch", "__schedule"):
             try:
                 prev = frame["prev"]
             except KeyError:
                 continue
             if not prev.absent_:
                 self.assertEqual(prev.pid, pid)
                 break
     else:
         self.skipTest("prev not found in context_switch or __schedule")
     os.kill(pid, signal.SIGKILL)
     os.waitpid(pid, 0)
示例#8
0
    def test_task_state_to_char(self):
        task = find_task(self.prog, os.getpid())
        self.assertEqual(task_state_to_char(task), "R")

        pid = fork_and_pause()
        task = find_task(self.prog, pid)

        wait_until(lambda: proc_state(pid) == "S")
        self.assertEqual(task_state_to_char(task), "S")

        os.kill(pid, signal.SIGSTOP)
        wait_until(lambda: proc_state(pid) == "T")
        self.assertEqual(task_state_to_char(task), "T")

        os.kill(pid, signal.SIGKILL)
        wait_until(lambda: proc_state(pid) == "Z")
        self.assertEqual(task_state_to_char(task), "Z")

        os.waitpid(pid, 0)