summaryrefslogtreecommitdiff
path: root/Userland
diff options
context:
space:
mode:
authorBen Wiederhake <BenWiederhake.GitHub@gmx.de>2021-11-25 23:04:52 +0100
committerAndreas Kling <kling@serenityos.org>2021-12-05 22:59:09 +0100
commit70e96fb917a1beea4035dbcf4171cf1c1139df81 (patch)
tree1c9278e60e6f1a4fba3e2ab8ba1909d007ad4510 /Userland
parent0f8483f09ce079b5c8b1531867917f282996b2fd (diff)
downloadserenity-70e96fb917a1beea4035dbcf4171cf1c1139df81.zip
LibCore: Implement new ptrace_peekbuf wrapper for PT_PEEKBUF syscall
Diffstat (limited to 'Userland')
-rw-r--r--Userland/Libraries/LibC/sys/ptrace.cpp9
-rw-r--r--Userland/Libraries/LibCore/System.cpp16
-rw-r--r--Userland/Libraries/LibCore/System.h1
3 files changed, 26 insertions, 0 deletions
diff --git a/Userland/Libraries/LibC/sys/ptrace.cpp b/Userland/Libraries/LibC/sys/ptrace.cpp
index 61c3e41e12..5b498d6e17 100644
--- a/Userland/Libraries/LibC/sys/ptrace.cpp
+++ b/Userland/Libraries/LibC/sys/ptrace.cpp
@@ -12,6 +12,15 @@ extern "C" {
long ptrace(int request, pid_t tid, void* addr, void* data)
{
+ if (request == PT_PEEKBUF) {
+ // PT_PEEKBUF cannot easily be correctly used through this function signature:
+ // The amount of data to be copied is not available.
+ // We could VERIFY() here, but to safeguard against ports that attempt to use
+ // the same number, let's claim that the Kernel just doesn't know the command.
+ // Use Core::System::ptrace_peekbuf instead.
+ return EINVAL;
+ }
+
// PT_PEEK needs special handling since the syscall wrapper
// returns the peeked value as an int, which can be negative because of the cast.
// When using PT_PEEK, the user can check if an error occurred
diff --git a/Userland/Libraries/LibCore/System.cpp b/Userland/Libraries/LibCore/System.cpp
index 01cf0a24a7..15d8481886 100644
--- a/Userland/Libraries/LibCore/System.cpp
+++ b/Userland/Libraries/LibCore/System.cpp
@@ -12,6 +12,7 @@
#include <stdarg.h>
#include <sys/ioctl.h>
#include <sys/mman.h>
+#include <sys/ptrace.h>
#include <sys/socket.h>
#include <termios.h>
#include <unistd.h>
@@ -67,6 +68,21 @@ ErrorOr<int> recvfd(int sockfd, int options)
return Error::from_syscall("recvfd"sv, -errno);
return fd;
}
+
+ErrorOr<void> ptrace_peekbuf(pid_t tid, void const* tracee_addr, Bytes destination_buf)
+{
+ Syscall::SC_ptrace_buf_params buf_params {
+ { destination_buf.data(), destination_buf.size() }
+ };
+ Syscall::SC_ptrace_params params {
+ PT_PEEKBUF,
+ tid,
+ const_cast<void*>(tracee_addr),
+ (FlatPtr)&buf_params,
+ };
+ int rc = syscall(SC_ptrace, &params);
+ HANDLE_SYSCALL_RETURN_VALUE("ptrace_peekbuf", rc, {});
+}
#endif
ErrorOr<void> sigaction(int signal, struct sigaction const* action, struct sigaction* old_action)
diff --git a/Userland/Libraries/LibCore/System.h b/Userland/Libraries/LibCore/System.h
index 14b26db2e4..801c1e5f61 100644
--- a/Userland/Libraries/LibCore/System.h
+++ b/Userland/Libraries/LibCore/System.h
@@ -19,6 +19,7 @@ ErrorOr<void> unveil(StringView path, StringView permissions);
ErrorOr<Array<int, 2>> pipe2(int flags);
ErrorOr<void> sendfd(int sockfd, int fd);
ErrorOr<int> recvfd(int sockfd, int options);
+ErrorOr<void> ptrace_peekbuf(pid_t tid, void const* tracee_addr, Bytes destination_buf);
#endif
ErrorOr<void> sigaction(int signal, struct sigaction const* action, struct sigaction* old_action);