libsysprof-analyze: add API to get symbol to represent process

And include a fallback in case we never got an actual Process frame which
will contain the cmdline for the process. We need to hold onto the fallback
too so that we can keep symbols lightweight by not having to reference them
so long as the document is alive.
This commit is contained in:
Christian Hergert
2023-05-24 15:19:44 -07:00
parent 5b00127d7d
commit f12f2b760c
4 changed files with 64 additions and 0 deletions

View File

@ -24,6 +24,7 @@
#include "sysprof-document.h"
#include "sysprof-symbolizer.h"
#include "sysprof-symbol.h"
G_BEGIN_DECLS
@ -55,5 +56,7 @@ gboolean _sysprof_document_is_native (SysprofDocument *self)
GRefString *_sysprof_document_ref_string (SysprofDocument *self,
const char *name);
GtkBitset *_sysprof_document_traceables (SysprofDocument *self);
SysprofSymbol *_sysprof_document_process_symbol (SysprofDocument *self,
int pid);
G_END_DECLS

View File

@ -44,6 +44,7 @@
#include "sysprof-mount-namespace-private.h"
#include "sysprof-process-info-private.h"
#include "sysprof-strings-private.h"
#include "sysprof-symbol-private.h"
#include "sysprof-symbolizer-private.h"
#include "line-reader-private.h"
@ -456,6 +457,40 @@ sysprof_document_load_overlays (SysprofDocument *self)
}
}
static void
sysprof_document_load_processes (SysprofDocument *self)
{
GtkBitsetIter iter;
guint i;
g_assert (SYSPROF_IS_DOCUMENT (self));
if (gtk_bitset_iter_init_first (&iter, self->processes, &i))
{
do
{
g_autoptr(SysprofDocumentProcess) process = g_list_model_get_item (G_LIST_MODEL (self), i);
int pid = sysprof_document_frame_get_pid (SYSPROF_DOCUMENT_FRAME (process));
SysprofProcessInfo *process_info = _sysprof_document_process_info (self, pid, TRUE);
const char *cmdline = sysprof_document_process_get_command_line (process);
if (cmdline != NULL)
{
g_auto(GStrv) parts = NULL;
if ((parts = g_strsplit (cmdline , " ", 2)))
{
g_clear_object (&process_info->symbol);
process_info->symbol =
_sysprof_symbol_new (sysprof_strings_get (self->strings, parts[0]),
NULL, NULL, 0, 0);
}
}
}
while (gtk_bitset_iter_next (&iter, &i));
}
}
static void
sysprof_document_load_counters (SysprofDocument *self)
{
@ -690,6 +725,7 @@ sysprof_document_load_worker (GTask *task,
sysprof_document_load_mounts (self);
sysprof_document_load_mountinfos (self);
sysprof_document_load_memory_maps (self);
sysprof_document_load_processes (self);
sysprof_document_load_overlays (self);
sysprof_document_load_counters (self);
@ -1155,3 +1191,19 @@ sysprof_document_callgraph_finish (SysprofDocument *self,
return g_task_propagate_pointer (G_TASK (result), error);
}
SysprofSymbol *
_sysprof_document_process_symbol (SysprofDocument *self,
int pid)
{
SysprofProcessInfo *info;
g_return_val_if_fail (SYSPROF_IS_DOCUMENT (self), NULL);
info = _sysprof_document_process_info (self, pid, TRUE);
if (info->symbol)
return info->symbol;
return info->fallback_symbol;
}

View File

@ -31,6 +31,8 @@ typedef struct _SysprofProcessInfo
SysprofAddressLayout *address_layout;
SysprofMountNamespace *mount_namespace;
SysprofSymbolCache *symbol_cache;
SysprofSymbol *fallback_symbol;
SysprofSymbol *symbol;
int pid;
} SysprofProcessInfo;

View File

@ -21,6 +21,7 @@
#include "config.h"
#include "sysprof-process-info-private.h"
#include "sysprof-symbol-private.h"
G_DEFINE_BOXED_TYPE (SysprofProcessInfo,
sysprof_process_info,
@ -32,12 +33,16 @@ sysprof_process_info_new (SysprofMountNamespace *mount_namespace,
int pid)
{
SysprofProcessInfo *self;
char symname[32];
g_snprintf (symname, sizeof symname, "[Process %d]", pid);
self = g_atomic_rc_box_new0 (SysprofProcessInfo);
self->pid = pid;
self->address_layout = sysprof_address_layout_new ();
self->symbol_cache = sysprof_symbol_cache_new ();
self->mount_namespace = mount_namespace;
self->fallback_symbol = _sysprof_symbol_new (g_ref_string_new (symname), NULL, NULL, 0, 0);
return self;
}
@ -56,6 +61,8 @@ sysprof_process_info_finalize (gpointer data)
g_clear_object (&self->address_layout);
g_clear_object (&self->symbol_cache);
g_clear_object (&self->mount_namespace);
g_clear_object (&self->fallback_symbol);
g_clear_object (&self->symbol);
self->pid = 0;
}