This revision was automatically updated to reflect the committed changes. Closed by commit rG6db44e52ce47: [Linux] Add kernel.yama.ptrace_scope note when ptrace fails to attach. (authored by rupprecht).
Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D144904/new/ https://reviews.llvm.org/D144904 Files: lldb/source/Plugins/Process/Linux/NativeProcessLinux.cpp lldb/source/Plugins/Process/Linux/Procfs.cpp lldb/source/Plugins/Process/Linux/Procfs.h lldb/unittests/Process/Linux/ProcfsTests.cpp
Index: lldb/unittests/Process/Linux/ProcfsTests.cpp =================================================================== --- lldb/unittests/Process/Linux/ProcfsTests.cpp +++ lldb/unittests/Process/Linux/ProcfsTests.cpp @@ -102,3 +102,19 @@ ASSERT_TRUE((bool)cpu_ids); ASSERT_GT((int)cpu_ids->size(), 0) << "We must see at least one core"; } + +TEST(Perf, RealPtraceScope) { + // We first check we can read /proc/sys/kernel/yama/ptrace_scope + auto buffer_or_error = + errorOrToExpected(getProcFile("sys/kernel/yama/ptrace_scope")); + if (!buffer_or_error) + GTEST_SKIP() << toString(buffer_or_error.takeError()); + + // At this point we shouldn't fail parsing the ptrace_scope value. + Expected<int> ptrace_scope = GetPtraceScope(); + ASSERT_TRUE((bool)ptrace_scope) << ptrace_scope.takeError(); + ASSERT_GE(*ptrace_scope, 0) + << "Sensible values of ptrace_scope are between 0 and 3"; + ASSERT_LE(*ptrace_scope, 3) + << "Sensible values of ptrace_scope are between 0 and 3"; +} Index: lldb/source/Plugins/Process/Linux/Procfs.h =================================================================== --- lldb/source/Plugins/Process/Linux/Procfs.h +++ lldb/source/Plugins/Process/Linux/Procfs.h @@ -28,5 +28,11 @@ /// if errors didn't happen. llvm::Expected<llvm::ArrayRef<lldb::cpu_id_t>> GetAvailableLogicalCoreIDs(); +/// \return +/// The current value of /proc/sys/kernel/yama/ptrace_scope, parsed as an +/// integer, or an error if the proc file cannot be read or has non-integer +/// contents. +llvm::Expected<int> GetPtraceScope(); + } // namespace process_linux } // namespace lldb_private Index: lldb/source/Plugins/Process/Linux/Procfs.cpp =================================================================== --- lldb/source/Plugins/Process/Linux/Procfs.cpp +++ lldb/source/Plugins/Process/Linux/Procfs.cpp @@ -8,6 +8,7 @@ #include "Procfs.h" #include "lldb/Host/linux/Support.h" +#include "llvm/Support/Error.h" #include "llvm/Support/MemoryBuffer.h" #include "llvm/Support/Threading.h" #include <optional> @@ -68,3 +69,18 @@ } return *logical_cores_ids; } + +llvm::Expected<int> lldb_private::process_linux::GetPtraceScope() { + ErrorOr<std::unique_ptr<MemoryBuffer>> ptrace_scope_file = + getProcFile("sys/kernel/yama/ptrace_scope"); + if (!*ptrace_scope_file) + return errorCodeToError(ptrace_scope_file.getError()); + // The contents should be something like "1\n". Trim it so we get "1". + StringRef buffer = (*ptrace_scope_file)->getBuffer().trim(); + int ptrace_scope_value; + if (buffer.getAsInteger(10, ptrace_scope_value)) { + return createStringError(inconvertibleErrorCode(), + "Invalid ptrace_scope value: '%s'", buffer.data()); + } + return ptrace_scope_value; +} Index: lldb/source/Plugins/Process/Linux/NativeProcessLinux.cpp =================================================================== --- lldb/source/Plugins/Process/Linux/NativeProcessLinux.cpp +++ lldb/source/Plugins/Process/Linux/NativeProcessLinux.cpp @@ -45,6 +45,7 @@ #include "lldb/Utility/StringExtractor.h" #include "llvm/ADT/ScopeExit.h" #include "llvm/Support/Errno.h" +#include "llvm/Support/Error.h" #include "llvm/Support/FileSystem.h" #include "llvm/Support/Threading.h" @@ -214,6 +215,43 @@ return error; } +static llvm::Error AddPtraceScopeNote(llvm::Error original_error) { + Expected<int> ptrace_scope = GetPtraceScope(); + if (auto E = ptrace_scope.takeError()) { + Log *log = GetLog(POSIXLog::Process); + LLDB_LOG(log, "error reading value of ptrace_scope: {0}", E); + + // The original error is probably more interesting than not being able to + // read or interpret ptrace_scope. + return original_error; + } + + // We only have suggestions to provide for 1-3. + switch (*ptrace_scope) { + case 1: + case 2: + return llvm::createStringError( + std::error_code(errno, std::generic_category()), + "The current value of ptrace_scope is %d, which can cause ptrace to " + "fail to attach to a running process. To fix this, run:\n" + "\tsudo sysctl -w kernel.yama.ptrace_scope=0\n" + "For more information, see: " + "https://www.kernel.org/doc/Documentation/security/Yama.txt.", + *ptrace_scope); + case 3: + return llvm::createStringError( + std::error_code(errno, std::generic_category()), + "The current value of ptrace_scope is 3, which will cause ptrace to " + "fail to attach to a running process. This value cannot be changed " + "without rebooting.\n" + "For more information, see: " + "https://www.kernel.org/doc/Documentation/security/Yama.txt."); + case 0: + default: + return original_error; + } +} + // Public Static Methods llvm::Expected<std::unique_ptr<NativeProcessProtocol>> @@ -352,6 +390,11 @@ it = tids_to_attach.erase(it); continue; } + if (status.GetError() == EPERM) { + // Depending on the value of ptrace_scope, we can return a different + // error that suggests how to fix it. + return AddPtraceScopeNote(status.ToError()); + } return status.ToError(); }
_______________________________________________ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits