|
libclues
Linux C++ Tracing Library
|
Callback interface for consumers of tracing events. More...
#include <EventConsumer.hxx>
Inheritance diagram for clues::EventConsumer:Public Types | |
| enum class | StatusFlag { INTERRUPTED = 1 << 0 , RESUMED = 1 << 1 , LOST_TO_MT_EXIT = 1 << 2 , ABI_CHANGED = 1 << 3 , CLONED_THREAD = 1 << 4 } |
| Different status flags that can appear in callbacks. More... | |
| using | StatusFlags = cosmos::BitMask<StatusFlag> |
Protected Member Functions | |
| virtual void | syscallEntry (Tracee &tracee, const SystemCall &sc, const StatusFlags flags) |
| A system call is about to be executed in the Tracee. | |
| virtual void | syscallExit (Tracee &tracee, const SystemCall &sc, const StatusFlags flags) |
| A system call has been finished. | |
| virtual void | attached (Tracee &tracee) |
| The tracee is now properly attached to. | |
| virtual void | signaled (Tracee &tracee, const cosmos::SigInfo &info) |
| The tracee has received a signal. | |
| virtual void | stopped (Tracee &tracee) |
| The tracee entered group-stop due to a stopping signal. | |
| virtual void | resumed (Tracee &tracee) |
| The tracee resumed due to SIGCONT. | |
| virtual void | exited (Tracee &tracee, const cosmos::WaitStatus status, const StatusFlags flags) |
| The tracee is about to end execution. | |
| virtual void | disappeared (Tracee &tracee, const cosmos::ChildState &data) |
| The tracee disappeared for unclear reasons. | |
| virtual void | newExecutionContext (Tracee &tracee, const std::string &old_executable, const cosmos::StringVector &old_cmdline, const std::optional< cosmos::ProcessID > old_pid) |
| A new program is executed in the tracee. | |
| virtual void | newChildProcess (Tracee &parent, Tracee &child, const cosmos::ptrace::Event event, const StatusFlags flags) |
| A new child process has been created. | |
| virtual void | vforkComplete (Tracee &parent, TraceePtr child) |
A vfork() in parent for child completed. | |
Friends | |
| class | Tracee |
| class | Engine |
Callback interface for consumers of tracing events.
This is the main point of interaction between the Engine class and its users. Tracing events for all active tracees will be delivered via this interface.
libclues currently operates in a single-threaded mode only. This means there will only one callback ever be active at any given time. Blocking should be avoided in the context of callbacks to prevent tracing to get stuck.
Clients only need to override those methods that they are interested in. If FollowChildren is active, then the attached() callback offers the possibility to detach from automatically attached child processes. Otherwise they will be fully traced as well.
Definition at line 32 of file EventConsumer.hxx.
| using clues::EventConsumer::StatusFlags = cosmos::BitMask<StatusFlag> |
Definition at line 51 of file EventConsumer.hxx.
|
strong |
Different status flags that can appear in callbacks.
| Enumerator | |
|---|---|
| INTERRUPTED | A system call was interrupted (only appears during syscallExit()). |
| RESUMED | A previously interrupted system call is resumed (only appears during syscallEntry()). |
| LOST_TO_MT_EXIT | An exit occurs because another thread called execve() or exit() (only appears in exited()). |
| ABI_CHANGED | The system call ABI changed since the last observed system call. |
| CLONED_THREAD | used in newChildProcess() to indicate that a new thread has been created. |
Definition at line 38 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
The tracee is now properly attached to.
This should be the first call that that is visible for a tracee. It occurs when the ptrace() relationship is established and a defined tracing state has been reached. The Tracee will be in PTRACE_EVENT_STOP.
The following situations can cause an attached() callback:
tracee was actively registered via Engine::addTracee().Engine::addTracee(const cosmos::ProcessID, ..., AttachThreads{true}). Any additional threads that exist in the process will then automatically be attached to. tracee.isInitiallyAttachedThread() will return true in this case. Reimplemented in clues::TermTracer.
Definition at line 135 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
The tracee disappeared for unclear reasons.
This callback can occur in a number of special situations like:
When this call occurs then the tracee can no longer be accessed via the tracing API. data still tells whether the tracee exited regularly or due to a signal.
Reimplemented in clues::TermTracer.
Definition at line 196 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
The tracee is about to end execution.
The tracee is about to either exit regularly, to be killed by a signal or to disappear due to an execve() in a multi-threaded process.
When this callback occurs the tracee can still be inspected using ptrace(). Once execution is continued the tracer <-> tracee relationship is lost.
If the exit happens due to an execve in a multi-threaded process then Status::LOST_TO_MT_EXIT is set in flags.
Reimplemented in clues::TermTracer.
Definition at line 172 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
A new child process has been created.
The existing tracee parent has created a new child process, which has automatically been attached to and is now represented in child.
Different ways to create a child process exist, these are differentiated via event. Note that some forms of clone() calls will appear as cosmos::ptrace::Event::FORK or cosmos::ptrace::Event::VFORK instead of cosmos::ptrace::Event::CLONE (when the clone() exit signal is set to SIGCHILD).
cosmos::ptrace::Event::VFORK_DONE occurs when the child process exited or exec()'d and can be ignored if there is no need for it.
StatusFlag::CLONED_THREAD will be set in flags in case the new child process is a thread of parent.
Reimplemented in clues::TermTracer.
Definition at line 260 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
A new program is executed in the tracee.
This call occurs after a successful execve() by the tracee.
The new executable path and command line can be retrieved via Tracee::executable() and Tracee::cmdLine(). The previous values are provided as input parameters.
The callee can decide to stop tracing (by detaching) at this point to prevent following the new tracing context.
If the tracee's process was multi-threaded then there is more complexity involved:
former_pid contains the former PID that the exec'ing thread had, which is now continuing as the main thread of the new execution context.Reimplemented in clues::TermTracer.
Definition at line 230 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
The tracee resumed due to SIGCONT.
Definition at line 155 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
The tracee has received a signal.
This callback notifies about signals being delivered to the tracee.
Reimplemented in clues::TermTracer.
Definition at line 144 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
The tracee entered group-stop due to a stopping signal.
Reimplemented in clues::TermTracer.
Definition at line 150 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
A system call is about to be executed in the Tracee.
At this stage only the type of system call as well system call parameters of ItemType::PARAM_IN or ItemType::PARAM_IN_OUT have useful values. Any out parameters and the return value should not be inspected.
Reimplemented in clues::TermTracer.
Definition at line 62 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
A system call has been finished.
If the system call failed then sc.hasErrorCode() returns true and the ErrnoResult can be inspected from sc.error().
If the system call succeeded sc.hasResultValue() returns true and any system call parameters of ItemType::PARAM_OUT or ItemType::PARAM_IN_OUT should have been updated by the kernel and can be updated and processed by the implementation.
If flags[StatusFlag::INTERRUPTED] is set, then the system call was interrupted by a signal and aborted by the kernel. Whether this happens depends on various factors, e.g. if the SA_RESTART flag is set in the Tracee for the signal which was received and also on the type of system call which is executed. If automatic system call restarting is not active then a regular EINTR error return will be observed and the Tracee has to actively deal with the situation.
libclues tries to keep track of when an automatically restarted system call will be resumed and will set flags[StatusFlag::RESUMED] during syscallEntry() accordingly. There are two different scenarios to take into account here:
restart_syscall() is injected by the kernel. This is the case when the signal was SIGSTOP and the system call was time-related, like clock_nanosleep(), to give userspace (libc) the chance to adjust times before resuming the system call.
libclues looks up the original system call and will not report SystemCallNr::RESTART_SYSCALL, but the resumed system call and will set StatusFlag::RESUMED accordingly.
rt_sigreturn() system call to appear to make out the end of the interruption and then looks for the next system call of the same type as the interrupted system call. When this situation is detected then StatusFlag::RESUMED is set as well. Reimplemented in clues::TermTracer.
Definition at line 110 of file EventConsumer.hxx.
|
inlineprotectedvirtual |
A vfork() in parent for child completed.
This is a special case of newChildProcess() event for vfork(). This is reported after the vfork() is complete i.e. the child either exited or performed an execve().
If child no longer exists then it is nullptr.
Definition at line 279 of file EventConsumer.hxx.
|
friend |
Definition at line 34 of file EventConsumer.hxx.
|
friend |
Definition at line 33 of file EventConsumer.hxx.