1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-25 19:37:35 +00:00

SystemMonitor: Add Command column to ProcessModel

This column shows full command line of a process, or empty line if an
error occures when reading it. The command is not escaped for now.
This commit is contained in:
Maciej 2022-10-29 21:49:51 +02:00 committed by Sam Atkins
parent e4db71c88b
commit f4a5cd63bb
2 changed files with 30 additions and 0 deletions

View file

@ -12,6 +12,7 @@
#include <AK/NumberFormat.h> #include <AK/NumberFormat.h>
#include <LibCore/File.h> #include <LibCore/File.h>
#include <LibCore/ProcessStatisticsReader.h> #include <LibCore/ProcessStatisticsReader.h>
#include <LibCore/Stream.h>
#include <LibGUI/FileIconProvider.h> #include <LibGUI/FileIconProvider.h>
#include <LibGUI/Icon.h> #include <LibGUI/Icon.h>
#include <LibGUI/ModelIndex.h> #include <LibGUI/ModelIndex.h>
@ -133,6 +134,8 @@ String ProcessModel::column_name(int column) const
return "Pledge"; return "Pledge";
case Column::Veil: case Column::Veil:
return "Veil"; return "Veil";
case Column::Command:
return "Command";
default: default:
VERIFY_NOT_REACHED(); VERIFY_NOT_REACHED();
} }
@ -150,6 +153,7 @@ GUI::Variant ProcessModel::data(GUI::ModelIndex const& index, GUI::ModelRole rol
case Column::User: case Column::User:
case Column::Pledge: case Column::Pledge:
case Column::Veil: case Column::Veil:
case Column::Command:
return Gfx::TextAlignment::CenterLeft; return Gfx::TextAlignment::CenterLeft;
case Column::PID: case Column::PID:
case Column::TID: case Column::TID:
@ -221,6 +225,8 @@ GUI::Variant ProcessModel::data(GUI::ModelIndex const& index, GUI::ModelRole rol
return thread.current_state.cpu; return thread.current_state.cpu;
case Column::Name: case Column::Name:
return thread.current_state.name; return thread.current_state.name;
case Column::Command:
return thread.current_state.command;
case Column::Syscalls: case Column::Syscalls:
return thread.current_state.syscall_count; return thread.current_state.syscall_count;
case Column::InodeFaults: case Column::InodeFaults:
@ -289,6 +295,8 @@ GUI::Variant ProcessModel::data(GUI::ModelIndex const& index, GUI::ModelRole rol
if (thread.current_state.kernel) if (thread.current_state.kernel)
return String::formatted("{} (*)", thread.current_state.name); return String::formatted("{} (*)", thread.current_state.name);
return thread.current_state.name; return thread.current_state.name;
case Column::Command:
return thread.current_state.command;
case Column::Syscalls: case Column::Syscalls:
return thread.current_state.syscall_count; return thread.current_state.syscall_count;
case Column::InodeFaults: case Column::InodeFaults:
@ -400,6 +408,24 @@ Vector<GUI::ModelIndex> ProcessModel::matches(StringView searching, unsigned fla
return found_indices; return found_indices;
} }
static ErrorOr<String> try_read_command_line(pid_t pid)
{
auto file = TRY(Core::Stream::File::open(String::formatted("/proc/{}/cmdline", pid), Core::Stream::OpenMode::Read));
auto data = TRY(file->read_all());
auto json = TRY(JsonValue::from_string(StringView { data.bytes() }));
auto array = json.as_array().values();
return String::join(" "sv, array);
}
static String read_command_line(pid_t pid)
{
auto string_or_error = try_read_command_line(pid);
if (string_or_error.is_error()) {
return "";
}
return string_or_error.release_value();
}
void ProcessModel::update() void ProcessModel::update()
{ {
auto previous_tid_count = m_threads.size(); auto previous_tid_count = m_threads.size();
@ -442,6 +468,7 @@ void ProcessModel::update()
state.kernel = process.kernel; state.kernel = process.kernel;
state.executable = process.executable; state.executable = process.executable;
state.name = thread.name; state.name = thread.name;
state.command = read_command_line(process.pid);
state.uid = process.uid; state.uid = process.uid;
state.state = thread.state; state.state = thread.state;
state.user = process.username; state.user = process.username;

View file

@ -52,6 +52,7 @@ public:
UnixSocketWriteBytes, UnixSocketWriteBytes,
IPv4SocketReadBytes, IPv4SocketReadBytes,
IPv4SocketWriteBytes, IPv4SocketWriteBytes,
Command,
__Count __Count
}; };
@ -105,6 +106,7 @@ private:
bool kernel { false }; bool kernel { false };
String executable { "" }; String executable { "" };
String name { "" }; String name { "" };
String command { "" };
uid_t uid { 0 }; uid_t uid { 0 };
String state { "" }; String state { "" };
String user { "" }; String user { "" };
@ -149,6 +151,7 @@ private:
this->kernel = other.kernel; this->kernel = other.kernel;
this->executable = other.executable; this->executable = other.executable;
this->name = other.name; this->name = other.name;
this->command = other.command;
this->uid = other.uid; this->uid = other.uid;
this->state = other.state; this->state = other.state;
this->user = other.user; this->user = other.user;