mirror of
https://github.com/varun-r-mallya/sysprof.git
synced 2025-12-31 20:36:25 +00:00
libsysprof-analyze: add SysprofProcessInfo
This internal type is used to collect things about a process like the memory maps, address layout, and symbol cache. This can persist once parsed at startup, then applied to objects created on demand such as the SysprofDocumentProcess or used by symbolizers internally rather than complicated function arguments.
This commit is contained in:
@ -29,6 +29,7 @@ libsysprof_analyze_private_sources = [
|
||||
'sysprof-mount.c',
|
||||
'sysprof-mount-device.c',
|
||||
'sysprof-mount-namespace.c',
|
||||
'sysprof-process-info.c',
|
||||
'sysprof-strings.c',
|
||||
'sysprof-symbol-cache.c',
|
||||
]
|
||||
|
||||
@ -169,11 +169,9 @@ search_for_symbol_cb (gconstpointer a,
|
||||
}
|
||||
|
||||
static SysprofSymbol *
|
||||
sysprof_bundled_symbolizer_symbolize (SysprofSymbolizer *symbolizer,
|
||||
SysprofMountNamespace *mount_namespace,
|
||||
SysprofAddressLayout *address_layout,
|
||||
int pid,
|
||||
SysprofAddress address)
|
||||
sysprof_bundled_symbolizer_symbolize (SysprofSymbolizer *symbolizer,
|
||||
const SysprofProcessInfo *process_info,
|
||||
SysprofAddress address)
|
||||
{
|
||||
SysprofBundledSymbolizer *self = SYSPROF_BUNDLED_SYMBOLIZER (symbolizer);
|
||||
g_autoptr(GRefString) tag = NULL;
|
||||
@ -181,7 +179,7 @@ sysprof_bundled_symbolizer_symbolize (SysprofSymbolizer *symbolizer,
|
||||
const Decoded key = {
|
||||
.addr_begin = address,
|
||||
.addr_end = address,
|
||||
.pid = pid,
|
||||
.pid = process_info->pid,
|
||||
.offset = 0,
|
||||
.tag_offset = 0,
|
||||
};
|
||||
|
||||
31
src/libsysprof-analyze/sysprof-document-process-private.h
Normal file
31
src/libsysprof-analyze/sysprof-document-process-private.h
Normal file
@ -0,0 +1,31 @@
|
||||
/* sysprof-document-process-private.h
|
||||
*
|
||||
* Copyright 2023 Christian Hergert <chergert@redhat.com>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "sysprof-document-process.h"
|
||||
#include "sysprof-process-info-private.h"
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
void _sysprof_document_process_set_info (SysprofDocumentProcess *self,
|
||||
SysprofProcessInfo *process_info);
|
||||
|
||||
G_END_DECLS
|
||||
@ -21,11 +21,12 @@
|
||||
#include "config.h"
|
||||
|
||||
#include "sysprof-document-frame-private.h"
|
||||
#include "sysprof-document-process.h"
|
||||
#include "sysprof-document-process-private.h"
|
||||
|
||||
struct _SysprofDocumentProcess
|
||||
{
|
||||
SysprofDocumentFrame parent_instance;
|
||||
SysprofDocumentFrame parent_instance;
|
||||
SysprofProcessInfo *process_info;
|
||||
};
|
||||
|
||||
struct _SysprofDocumentProcessClass
|
||||
@ -43,6 +44,16 @@ G_DEFINE_FINAL_TYPE (SysprofDocumentProcess, sysprof_document_process, SYSPROF_T
|
||||
|
||||
static GParamSpec *properties [N_PROPS];
|
||||
|
||||
static void
|
||||
sysprof_document_process_finalize (GObject *object)
|
||||
{
|
||||
SysprofDocumentProcess *self = (SysprofDocumentProcess *)object;
|
||||
|
||||
g_clear_pointer (&self->process_info, sysprof_process_info_unref);
|
||||
|
||||
G_OBJECT_CLASS (sysprof_document_process_parent_class)->finalize (object);
|
||||
}
|
||||
|
||||
static void
|
||||
sysprof_document_process_get_property (GObject *object,
|
||||
guint prop_id,
|
||||
@ -67,6 +78,7 @@ sysprof_document_process_class_init (SysprofDocumentProcessClass *klass)
|
||||
{
|
||||
GObjectClass *object_class = G_OBJECT_CLASS (klass);
|
||||
|
||||
object_class->finalize = sysprof_document_process_finalize;
|
||||
object_class->get_property = sysprof_document_process_get_property;
|
||||
|
||||
properties [PROP_COMMAND_LINE] =
|
||||
@ -93,3 +105,14 @@ sysprof_document_process_get_command_line (SysprofDocumentProcess *self)
|
||||
|
||||
return SYSPROF_DOCUMENT_FRAME_CSTRING (self, proc->cmdline);
|
||||
}
|
||||
|
||||
void
|
||||
_sysprof_document_process_set_info (SysprofDocumentProcess *self,
|
||||
SysprofProcessInfo *process_info)
|
||||
{
|
||||
g_return_if_fail (SYSPROF_IS_DOCUMENT_PROCESS (self));
|
||||
g_return_if_fail (process_info != NULL);
|
||||
g_return_if_fail (self->process_info == NULL);
|
||||
|
||||
self->process_info = sysprof_process_info_ref (process_info);
|
||||
}
|
||||
|
||||
@ -22,13 +22,13 @@
|
||||
|
||||
#include "sysprof-document.h"
|
||||
#include "sysprof-document-symbols.h"
|
||||
#include "sysprof-process-info-private.h"
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
void _sysprof_document_symbols_new (SysprofDocument *document,
|
||||
SysprofSymbolizer *symbolizer,
|
||||
GHashTable *pid_to_mount_namespaces,
|
||||
GHashTable *pid_to_address_layouts,
|
||||
GHashTable *pid_to_process_info,
|
||||
GCancellable *cancellable,
|
||||
GAsyncReadyCallback callback,
|
||||
gpointer user_data);
|
||||
|
||||
@ -31,9 +31,8 @@
|
||||
|
||||
struct _SysprofDocumentSymbols
|
||||
{
|
||||
GObject parent_instance;
|
||||
GObject parent_instance;
|
||||
SysprofSymbol *context_switches[SYSPROF_ADDRESS_CONTEXT_GUEST_USER+1];
|
||||
GHashTable *pid_to_symbol_cache;
|
||||
};
|
||||
|
||||
G_DEFINE_FINAL_TYPE (SysprofDocumentSymbols, sysprof_document_symbols, G_TYPE_OBJECT)
|
||||
@ -46,8 +45,6 @@ sysprof_document_symbols_finalize (GObject *object)
|
||||
for (guint i = 0; i < G_N_ELEMENTS (self->context_switches); i++)
|
||||
g_clear_object (&self->context_switches[i]);
|
||||
|
||||
g_clear_pointer (&self->pid_to_symbol_cache, g_hash_table_unref);
|
||||
|
||||
G_OBJECT_CLASS (sysprof_document_symbols_parent_class)->finalize (object);
|
||||
}
|
||||
|
||||
@ -62,7 +59,6 @@ sysprof_document_symbols_class_init (SysprofDocumentSymbolsClass *klass)
|
||||
static void
|
||||
sysprof_document_symbols_init (SysprofDocumentSymbols *self)
|
||||
{
|
||||
self->pid_to_symbol_cache = g_hash_table_new_full (NULL, NULL, NULL, g_object_unref);
|
||||
}
|
||||
|
||||
typedef struct _Symbolize
|
||||
@ -70,8 +66,7 @@ typedef struct _Symbolize
|
||||
SysprofDocument *document;
|
||||
SysprofSymbolizer *symbolizer;
|
||||
SysprofDocumentSymbols *symbols;
|
||||
GHashTable *pid_to_address_layouts;
|
||||
GHashTable *pid_to_mount_namespaces;
|
||||
GHashTable *pid_to_process_info;
|
||||
} Symbolize;
|
||||
|
||||
static void
|
||||
@ -80,18 +75,15 @@ symbolize_free (Symbolize *state)
|
||||
g_clear_object (&state->document);
|
||||
g_clear_object (&state->symbolizer);
|
||||
g_clear_object (&state->symbols);
|
||||
g_clear_pointer (&state->pid_to_address_layouts, g_hash_table_unref);
|
||||
g_clear_pointer (&state->pid_to_mount_namespaces, g_hash_table_unref);
|
||||
g_clear_pointer (&state->pid_to_process_info, g_hash_table_unref);
|
||||
g_free (state);
|
||||
}
|
||||
|
||||
static void
|
||||
sysprof_document_symbols_add_traceable (SysprofDocumentSymbols *self,
|
||||
SysprofProcessInfo *process_info,
|
||||
SysprofDocumentTraceable *traceable,
|
||||
SysprofSymbolizer *symbolizer,
|
||||
SysprofMountNamespace *mount_namespace,
|
||||
SysprofAddressLayout *address_layout,
|
||||
SysprofSymbolCache *symbol_cache)
|
||||
SysprofSymbolizer *symbolizer)
|
||||
{
|
||||
SysprofAddressContext last_context;
|
||||
guint64 *addresses;
|
||||
@ -99,6 +91,7 @@ sysprof_document_symbols_add_traceable (SysprofDocumentSymbols *self,
|
||||
int pid;
|
||||
|
||||
g_assert (SYSPROF_IS_DOCUMENT_SYMBOLS (self));
|
||||
g_assert (process_info != NULL);
|
||||
g_assert (SYSPROF_IS_DOCUMENT_TRACEABLE (traceable));
|
||||
g_assert (SYSPROF_IS_SYMBOLIZER (symbolizer));
|
||||
|
||||
@ -118,16 +111,16 @@ sysprof_document_symbols_add_traceable (SysprofDocumentSymbols *self,
|
||||
{
|
||||
last_context = context;
|
||||
}
|
||||
else if (sysprof_symbol_cache_lookup (symbol_cache, address) != NULL)
|
||||
else if (sysprof_symbol_cache_lookup (process_info->symbol_cache, address) != NULL)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
g_autoptr(SysprofSymbol) symbol = _sysprof_symbolizer_symbolize (symbolizer, mount_namespace, address_layout, pid, address);
|
||||
g_autoptr(SysprofSymbol) symbol = _sysprof_symbolizer_symbolize (symbolizer, process_info, address);
|
||||
|
||||
if (symbol != NULL)
|
||||
sysprof_symbol_cache_take (symbol_cache, g_steal_pointer (&symbol));
|
||||
sysprof_symbol_cache_take (process_info->symbol_cache, g_steal_pointer (&symbol));
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -187,19 +180,17 @@ sysprof_document_symbols_worker (GTask *task,
|
||||
{
|
||||
g_autoptr(SysprofDocumentTraceable) traceable = g_list_model_get_item (model, i);
|
||||
int pid = sysprof_document_frame_get_pid (SYSPROF_DOCUMENT_FRAME (traceable));
|
||||
SysprofMountNamespace *mount_namespace = g_hash_table_lookup (state->pid_to_mount_namespaces, GINT_TO_POINTER (pid));
|
||||
SysprofAddressLayout *address_layout = g_hash_table_lookup (state->pid_to_address_layouts, GINT_TO_POINTER (pid));
|
||||
SysprofSymbolCache *symbol_cache = g_hash_table_lookup (state->symbols->pid_to_symbol_cache, GINT_TO_POINTER (pid));
|
||||
SysprofProcessInfo *process_info = g_hash_table_lookup (state->pid_to_process_info, GINT_TO_POINTER (pid));
|
||||
|
||||
if (symbol_cache == NULL)
|
||||
{
|
||||
symbol_cache = sysprof_symbol_cache_new ();
|
||||
g_hash_table_insert (state->symbols->pid_to_symbol_cache,
|
||||
GINT_TO_POINTER (pid),
|
||||
symbol_cache);
|
||||
}
|
||||
/* We might hit this if we have "Process 0" which may be useful to
|
||||
* let users know can take processing time. For now, that will just
|
||||
* get skipped unless we deem it really valuable (you'll just jump
|
||||
* to "- - Kernel - -" anyway.
|
||||
*/
|
||||
if (process_info == NULL)
|
||||
continue;
|
||||
|
||||
sysprof_document_symbols_add_traceable (state->symbols, traceable, state->symbolizer, mount_namespace, address_layout, symbol_cache);
|
||||
sysprof_document_symbols_add_traceable (state->symbols, process_info, traceable, state->symbolizer);
|
||||
}
|
||||
while (gtk_bitset_iter_next (&iter, &i));
|
||||
}
|
||||
@ -212,8 +203,7 @@ sysprof_document_symbols_worker (GTask *task,
|
||||
void
|
||||
_sysprof_document_symbols_new (SysprofDocument *document,
|
||||
SysprofSymbolizer *symbolizer,
|
||||
GHashTable *pid_to_mount_namespaces,
|
||||
GHashTable *pid_to_address_layouts,
|
||||
GHashTable *pid_to_process_info,
|
||||
GCancellable *cancellable,
|
||||
GAsyncReadyCallback callback,
|
||||
gpointer user_data)
|
||||
@ -228,8 +218,7 @@ _sysprof_document_symbols_new (SysprofDocument *document,
|
||||
state->document = g_object_ref (document);
|
||||
state->symbolizer = g_object_ref (symbolizer);
|
||||
state->symbols = g_object_new (SYSPROF_TYPE_DOCUMENT_SYMBOLS, NULL);
|
||||
state->pid_to_address_layouts = g_hash_table_ref (pid_to_address_layouts);
|
||||
state->pid_to_mount_namespaces = g_hash_table_ref (pid_to_mount_namespaces);
|
||||
state->pid_to_process_info = g_hash_table_ref (pid_to_process_info);
|
||||
|
||||
task = g_task_new (NULL, cancellable, callback, user_data);
|
||||
g_task_set_source_tag (task, _sysprof_document_symbols_new);
|
||||
|
||||
@ -31,10 +31,12 @@
|
||||
#include "sysprof-document-file-private.h"
|
||||
#include "sysprof-document-frame-private.h"
|
||||
#include "sysprof-document-mmap.h"
|
||||
#include "sysprof-document-process-private.h"
|
||||
#include "sysprof-document-symbols-private.h"
|
||||
#include "sysprof-mount-private.h"
|
||||
#include "sysprof-mount-device-private.h"
|
||||
#include "sysprof-mount-namespace-private.h"
|
||||
#include "sysprof-process-info-private.h"
|
||||
#include "sysprof-strings-private.h"
|
||||
#include "sysprof-symbolizer-private.h"
|
||||
|
||||
@ -56,8 +58,7 @@ struct _SysprofDocument
|
||||
GtkBitset *mmaps;
|
||||
|
||||
GHashTable *files_first_position;
|
||||
GHashTable *pid_to_address_layouts;
|
||||
GHashTable *pid_to_mount_namespaces;
|
||||
GHashTable *pid_to_process_info;
|
||||
|
||||
SysprofMountNamespace *mount_namespace;
|
||||
|
||||
@ -89,16 +90,28 @@ sysprof_document_get_item (GListModel *model,
|
||||
{
|
||||
SysprofDocument *self = SYSPROF_DOCUMENT (model);
|
||||
SysprofDocumentFramePointer *ptr;
|
||||
SysprofDocumentFrame *ret;
|
||||
|
||||
if (position >= self->frames->len)
|
||||
return NULL;
|
||||
|
||||
ptr = &g_array_index (self->frames, SysprofDocumentFramePointer, position);
|
||||
ret = _sysprof_document_frame_new (self->mapped_file,
|
||||
(gconstpointer)&self->base[ptr->offset],
|
||||
ptr->length,
|
||||
self->needs_swap);
|
||||
|
||||
return _sysprof_document_frame_new (self->mapped_file,
|
||||
(gconstpointer)&self->base[ptr->offset],
|
||||
ptr->length,
|
||||
self->needs_swap);
|
||||
/* Annotate processes with pre-calculated info */
|
||||
if (SYSPROF_IS_DOCUMENT_PROCESS (ret))
|
||||
{
|
||||
int pid = sysprof_document_frame_get_pid (ret);
|
||||
SysprofProcessInfo *process_info = g_hash_table_lookup (self->pid_to_process_info, GINT_TO_POINTER (pid));
|
||||
|
||||
if (process_info != NULL)
|
||||
_sysprof_document_process_set_info (SYSPROF_DOCUMENT_PROCESS (ret), process_info);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void
|
||||
@ -120,6 +133,26 @@ _sysprof_document_traceables (SysprofDocument *self)
|
||||
return self->traceables;
|
||||
}
|
||||
|
||||
SysprofProcessInfo *
|
||||
_sysprof_document_process_info (SysprofDocument *self,
|
||||
int pid,
|
||||
gboolean may_create)
|
||||
{
|
||||
SysprofProcessInfo *process_info;
|
||||
|
||||
g_return_val_if_fail (SYSPROF_IS_DOCUMENT (self), NULL);
|
||||
|
||||
process_info = g_hash_table_lookup (self->pid_to_process_info, GINT_TO_POINTER (pid));
|
||||
|
||||
if (process_info == NULL && may_create)
|
||||
{
|
||||
process_info = sysprof_process_info_new (sysprof_mount_namespace_copy (self->mount_namespace), pid);
|
||||
g_hash_table_insert (self->pid_to_process_info, GINT_TO_POINTER (pid), process_info);
|
||||
}
|
||||
|
||||
return process_info;
|
||||
}
|
||||
|
||||
static void
|
||||
decode_space (gchar **str)
|
||||
{
|
||||
@ -152,8 +185,7 @@ sysprof_document_finalize (GObject *object)
|
||||
|
||||
g_clear_pointer (&self->strings, sysprof_strings_unref);
|
||||
|
||||
g_clear_pointer (&self->pid_to_address_layouts, g_hash_table_unref);
|
||||
g_clear_pointer (&self->pid_to_mount_namespaces, g_hash_table_unref);
|
||||
g_clear_pointer (&self->pid_to_process_info, g_hash_table_unref);
|
||||
g_clear_pointer (&self->mapped_file, g_mapped_file_unref);
|
||||
g_clear_pointer (&self->frames, g_array_unref);
|
||||
|
||||
@ -189,8 +221,7 @@ sysprof_document_init (SysprofDocument *self)
|
||||
self->mmaps = gtk_bitset_new_empty ();
|
||||
|
||||
self->files_first_position = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL);
|
||||
self->pid_to_address_layouts = g_hash_table_new_full (NULL, NULL, NULL, g_object_unref);
|
||||
self->pid_to_mount_namespaces = g_hash_table_new_full (NULL, NULL, NULL, g_object_unref);
|
||||
self->pid_to_process_info = g_hash_table_new_full (NULL, NULL, NULL, (GDestroyNotify)sysprof_process_info_unref);
|
||||
|
||||
self->mount_namespace = sysprof_mount_namespace_new ();
|
||||
}
|
||||
@ -209,15 +240,9 @@ sysprof_document_load_memory_maps (SysprofDocument *self)
|
||||
{
|
||||
g_autoptr(SysprofDocumentMmap) map = sysprof_document_get_item ((GListModel *)self, i);
|
||||
int pid = sysprof_document_frame_get_pid (SYSPROF_DOCUMENT_FRAME (map));
|
||||
SysprofAddressLayout *address_layout = g_hash_table_lookup (self->pid_to_address_layouts, GINT_TO_POINTER (pid));
|
||||
SysprofProcessInfo *process_info = _sysprof_document_process_info (self, pid, TRUE);
|
||||
|
||||
if G_UNLIKELY (address_layout == NULL)
|
||||
{
|
||||
address_layout = sysprof_address_layout_new ();
|
||||
g_hash_table_insert (self->pid_to_address_layouts, GINT_TO_POINTER (pid), address_layout);
|
||||
}
|
||||
|
||||
sysprof_address_layout_take (address_layout, g_steal_pointer (&map));
|
||||
sysprof_address_layout_take (process_info->address_layout, g_steal_pointer (&map));
|
||||
}
|
||||
while (gtk_bitset_iter_next (&iter, &i));
|
||||
}
|
||||
@ -304,7 +329,7 @@ sysprof_document_load_mountinfo (SysprofDocument *self,
|
||||
int pid,
|
||||
GBytes *bytes)
|
||||
{
|
||||
g_autoptr(SysprofMountNamespace) mount_namespace = NULL;
|
||||
SysprofProcessInfo *process_info;
|
||||
const char *contents;
|
||||
LineReader reader;
|
||||
gsize contents_len;
|
||||
@ -319,7 +344,10 @@ sysprof_document_load_mountinfo (SysprofDocument *self,
|
||||
g_assert (contents != NULL);
|
||||
g_assert (contents[contents_len] == 0);
|
||||
|
||||
mount_namespace = sysprof_mount_namespace_copy (self->mount_namespace);
|
||||
process_info = _sysprof_document_process_info (self, pid, FALSE);
|
||||
|
||||
g_assert (process_info != NULL);
|
||||
g_assert (process_info->mount_namespace != NULL);
|
||||
|
||||
line_reader_init (&reader, (char *)contents, contents_len);
|
||||
while ((line = line_reader_next (&reader, &line_len)))
|
||||
@ -329,12 +357,8 @@ sysprof_document_load_mountinfo (SysprofDocument *self,
|
||||
line[line_len] = 0;
|
||||
|
||||
if ((mount = sysprof_mount_new_for_mountinfo (self->strings, line)))
|
||||
sysprof_mount_namespace_add_mount (mount_namespace, g_steal_pointer (&mount));
|
||||
sysprof_mount_namespace_add_mount (process_info->mount_namespace, g_steal_pointer (&mount));
|
||||
}
|
||||
|
||||
g_hash_table_insert (self->pid_to_mount_namespaces,
|
||||
GINT_TO_POINTER (pid),
|
||||
g_steal_pointer (&mount_namespace));
|
||||
}
|
||||
|
||||
static void
|
||||
@ -345,10 +369,9 @@ sysprof_document_load_mountinfos (SysprofDocument *self)
|
||||
|
||||
g_assert (SYSPROF_IS_DOCUMENT (self));
|
||||
|
||||
g_hash_table_iter_init (&hiter, self->pid_to_address_layouts);
|
||||
g_hash_table_iter_init (&hiter, self->pid_to_process_info);
|
||||
while (g_hash_table_iter_next (&hiter, &key, &value))
|
||||
{
|
||||
g_autoptr(SysprofMountNamespace) mount_namespace = sysprof_mount_namespace_new ();
|
||||
int pid = GPOINTER_TO_INT (key);
|
||||
g_autofree char *path = g_strdup_printf ("/proc/%d/mountinfo", pid);
|
||||
g_autoptr(SysprofDocumentFile) file = sysprof_document_lookup_file (self, path);
|
||||
@ -565,15 +588,14 @@ sysprof_document_symbolize_prepare_cb (GObject *object,
|
||||
|
||||
g_assert (self != NULL);
|
||||
g_assert (SYSPROF_IS_DOCUMENT (self));
|
||||
g_assert (self->pid_to_mount_namespaces != NULL);
|
||||
g_assert (self->pid_to_process_info != NULL);
|
||||
|
||||
if (!_sysprof_symbolizer_prepare_finish (symbolizer, result, &error))
|
||||
g_task_return_error (task, g_steal_pointer (&error));
|
||||
else
|
||||
_sysprof_document_symbols_new (g_task_get_source_object (task),
|
||||
symbolizer,
|
||||
self->pid_to_mount_namespaces,
|
||||
self->pid_to_address_layouts,
|
||||
self->pid_to_process_info,
|
||||
g_task_get_cancellable (task),
|
||||
sysprof_document_symbolize_symbols_cb,
|
||||
g_object_ref (task));
|
||||
|
||||
@ -118,18 +118,16 @@ sysprof_multi_symbolizer_prepare_finish (SysprofSymbolizer *symbolizer,
|
||||
}
|
||||
|
||||
static SysprofSymbol *
|
||||
sysprof_multi_symbolizer_symbolize (SysprofSymbolizer *symbolizer,
|
||||
SysprofMountNamespace *mount_namespace,
|
||||
SysprofAddressLayout *address_layout,
|
||||
int pid,
|
||||
SysprofAddress address)
|
||||
sysprof_multi_symbolizer_symbolize (SysprofSymbolizer *symbolizer,
|
||||
const SysprofProcessInfo *process_info,
|
||||
SysprofAddress address)
|
||||
{
|
||||
SysprofMultiSymbolizer *self = SYSPROF_MULTI_SYMBOLIZER (symbolizer);
|
||||
|
||||
for (guint i = 0; i < self->symbolizers->len; i++)
|
||||
{
|
||||
SysprofSymbolizer *child = g_ptr_array_index (self->symbolizers, i);
|
||||
SysprofSymbol *symbol = _sysprof_symbolizer_symbolize (child, mount_namespace, address_layout, pid, address);
|
||||
SysprofSymbol *symbol = _sysprof_symbolizer_symbolize (child, process_info, address);
|
||||
|
||||
if (symbol != NULL)
|
||||
return symbol;
|
||||
|
||||
42
src/libsysprof-analyze/sysprof-process-info-private.h
Normal file
42
src/libsysprof-analyze/sysprof-process-info-private.h
Normal file
@ -0,0 +1,42 @@
|
||||
/* sysprof-process-info-private.h
|
||||
*
|
||||
* Copyright 2023 Christian Hergert <chergert@redhat.com>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "sysprof-address-layout-private.h"
|
||||
#include "sysprof-mount-namespace-private.h"
|
||||
#include "sysprof-symbol-cache-private.h"
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
typedef struct _SysprofProcessInfo
|
||||
{
|
||||
SysprofAddressLayout *address_layout;
|
||||
SysprofMountNamespace *mount_namespace;
|
||||
SysprofSymbolCache *symbol_cache;
|
||||
int pid;
|
||||
} SysprofProcessInfo;
|
||||
|
||||
SysprofProcessInfo *sysprof_process_info_new (SysprofMountNamespace *mount_namespace,
|
||||
int pid);
|
||||
SysprofProcessInfo *sysprof_process_info_ref (SysprofProcessInfo *self);
|
||||
void sysprof_process_info_unref (SysprofProcessInfo *self);
|
||||
|
||||
G_END_DECLS
|
||||
67
src/libsysprof-analyze/sysprof-process-info.c
Normal file
67
src/libsysprof-analyze/sysprof-process-info.c
Normal file
@ -0,0 +1,67 @@
|
||||
/* sysprof-process-info.c
|
||||
*
|
||||
* Copyright 2023 Christian Hergert <chergert@redhat.com>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
|
||||
#include "sysprof-process-info-private.h"
|
||||
|
||||
G_DEFINE_BOXED_TYPE (SysprofProcessInfo,
|
||||
sysprof_process_info,
|
||||
sysprof_process_info_ref,
|
||||
sysprof_process_info_unref)
|
||||
|
||||
SysprofProcessInfo *
|
||||
sysprof_process_info_new (SysprofMountNamespace *mount_namespace,
|
||||
int pid)
|
||||
{
|
||||
SysprofProcessInfo *self;
|
||||
|
||||
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;
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
SysprofProcessInfo *
|
||||
sysprof_process_info_ref (SysprofProcessInfo *self)
|
||||
{
|
||||
return g_atomic_rc_box_acquire (self);
|
||||
}
|
||||
|
||||
static void
|
||||
sysprof_process_info_finalize (gpointer data)
|
||||
{
|
||||
SysprofProcessInfo *self = data;
|
||||
|
||||
g_clear_object (&self->address_layout);
|
||||
g_clear_object (&self->symbol_cache);
|
||||
g_clear_object (&self->mount_namespace);
|
||||
|
||||
self->pid = 0;
|
||||
}
|
||||
|
||||
void
|
||||
sysprof_process_info_unref (SysprofProcessInfo *self)
|
||||
{
|
||||
g_atomic_rc_box_release_full (self, sysprof_process_info_finalize);
|
||||
}
|
||||
@ -25,6 +25,7 @@
|
||||
#include "sysprof-symbol.h"
|
||||
#include "sysprof-symbolizer.h"
|
||||
#include "sysprof-mount-namespace-private.h"
|
||||
#include "sysprof-process-info-private.h"
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
@ -39,34 +40,30 @@ struct _SysprofSymbolizerClass
|
||||
{
|
||||
GObjectClass parent_class;
|
||||
|
||||
void (*prepare_async) (SysprofSymbolizer *self,
|
||||
SysprofDocument *document,
|
||||
GCancellable *cancellable,
|
||||
GAsyncReadyCallback callback,
|
||||
gpointer user_data);
|
||||
gboolean (*prepare_finish) (SysprofSymbolizer *self,
|
||||
GAsyncResult *result,
|
||||
GError **error);
|
||||
SysprofSymbol *(*symbolize) (SysprofSymbolizer *self,
|
||||
SysprofMountNamespace *mount_namespace,
|
||||
SysprofAddressLayout *address_layout,
|
||||
int pid,
|
||||
SysprofAddress address);
|
||||
void (*prepare_async) (SysprofSymbolizer *self,
|
||||
SysprofDocument *document,
|
||||
GCancellable *cancellable,
|
||||
GAsyncReadyCallback callback,
|
||||
gpointer user_data);
|
||||
gboolean (*prepare_finish) (SysprofSymbolizer *self,
|
||||
GAsyncResult *result,
|
||||
GError **error);
|
||||
SysprofSymbol *(*symbolize) (SysprofSymbolizer *self,
|
||||
const SysprofProcessInfo *process_info,
|
||||
SysprofAddress address);
|
||||
};
|
||||
|
||||
|
||||
void _sysprof_symbolizer_prepare_async (SysprofSymbolizer *self,
|
||||
SysprofDocument *document,
|
||||
GCancellable *cancellable,
|
||||
GAsyncReadyCallback callback,
|
||||
gpointer user_data);
|
||||
gboolean _sysprof_symbolizer_prepare_finish (SysprofSymbolizer *self,
|
||||
GAsyncResult *result,
|
||||
GError **error);
|
||||
SysprofSymbol *_sysprof_symbolizer_symbolize (SysprofSymbolizer *self,
|
||||
SysprofMountNamespace *mount_namespace,
|
||||
SysprofAddressLayout *address_layout,
|
||||
int pid,
|
||||
SysprofAddress address);
|
||||
void _sysprof_symbolizer_prepare_async (SysprofSymbolizer *self,
|
||||
SysprofDocument *document,
|
||||
GCancellable *cancellable,
|
||||
GAsyncReadyCallback callback,
|
||||
gpointer user_data);
|
||||
gboolean _sysprof_symbolizer_prepare_finish (SysprofSymbolizer *self,
|
||||
GAsyncResult *result,
|
||||
GError **error);
|
||||
SysprofSymbol *_sysprof_symbolizer_symbolize (SysprofSymbolizer *self,
|
||||
const SysprofProcessInfo *process_info,
|
||||
SysprofAddress address);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
@ -91,11 +91,9 @@ _sysprof_symbolizer_prepare_finish (SysprofSymbolizer *self,
|
||||
}
|
||||
|
||||
SysprofSymbol *
|
||||
_sysprof_symbolizer_symbolize (SysprofSymbolizer *self,
|
||||
SysprofMountNamespace *mount_namespace,
|
||||
SysprofAddressLayout *address_layout,
|
||||
int pid,
|
||||
SysprofAddress address)
|
||||
_sysprof_symbolizer_symbolize (SysprofSymbolizer *self,
|
||||
const SysprofProcessInfo *process_info,
|
||||
SysprofAddress address)
|
||||
{
|
||||
return SYSPROF_SYMBOLIZER_GET_CLASS (self)->symbolize (self, mount_namespace, address_layout, pid, address);
|
||||
return SYSPROF_SYMBOLIZER_GET_CLASS (self)->symbolize (self, process_info, address);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user