Revision 70bb89c174eea5b404bed840466a50ddefd0a02a authored by Keno Fischer on 15 April 2024, 08:14:05 UTC, committed by Keno Fischer on 15 April 2024, 08:14:05 UTC
This reverts commit 8d577ab3f24212a9762ad6673e8a8fb0ecd5a140.
1 parent 7ba1b33
gc-page-profiler.c
// This file is a part of Julia. License is MIT: https://julialang.org/license
#include "gc-page-profiler.h"
#ifdef __cplusplus
extern "C" {
#endif
// whether page profiling is enabled
int page_profile_enabled;
// number of pages written
size_t page_profile_pages_written;
// stream to write page profile to
ios_t *page_profile_stream;
// mutex for page profile
uv_mutex_t page_profile_lock;
gc_page_profiler_serializer_t gc_page_serializer_create(void) JL_NOTSAFEPOINT
{
gc_page_profiler_serializer_t serializer;
if (__unlikely(page_profile_enabled)) {
arraylist_new(&serializer.typestrs, GC_PAGE_SZ);
}
else {
serializer.typestrs.len = 0;
}
return serializer;
}
void gc_page_serializer_init(gc_page_profiler_serializer_t *serializer,
jl_gc_pagemeta_t *pg) JL_NOTSAFEPOINT
{
if (__unlikely(page_profile_enabled)) {
serializer->typestrs.len = 0;
serializer->data = (char *)pg->data;
serializer->osize = pg->osize;
}
}
void gc_page_serializer_destroy(gc_page_profiler_serializer_t *serializer) JL_NOTSAFEPOINT
{
if (__unlikely(page_profile_enabled)) {
arraylist_free(&serializer->typestrs);
}
}
void gc_page_serializer_write(gc_page_profiler_serializer_t *serializer,
const char *str) JL_NOTSAFEPOINT
{
if (__unlikely(page_profile_enabled)) {
arraylist_push(&serializer->typestrs, (void *)str);
}
}
void gc_enable_page_profile(void) JL_NOTSAFEPOINT
{
page_profile_enabled = 1;
}
void gc_disable_page_profile(void) JL_NOTSAFEPOINT
{
page_profile_enabled = 0;
}
int gc_page_profile_is_enabled(void) JL_NOTSAFEPOINT
{
return page_profile_enabled;
}
void gc_page_profile_write_preamble(gc_page_profiler_serializer_t *serializer)
JL_NOTSAFEPOINT
{
if (__unlikely(page_profile_enabled)) {
char str[GC_TYPE_STR_MAXLEN];
snprintf(str, GC_TYPE_STR_MAXLEN,
"{\"address\": \"%p\",\"object_size\": %d,\"objects\": [",
serializer->data, serializer->osize);
ios_write(page_profile_stream, str, strlen(str));
}
}
void gc_page_profile_write_epilogue(gc_page_profiler_serializer_t *serializer)
JL_NOTSAFEPOINT
{
if (__unlikely(page_profile_enabled)) {
const char *str = "]}";
ios_write(page_profile_stream, str, strlen(str));
}
}
void gc_page_profile_write_comma(gc_page_profiler_serializer_t *serializer) JL_NOTSAFEPOINT
{
if (__unlikely(page_profile_enabled)) {
// write comma if not first page
if (page_profile_pages_written > 0) {
const char *str = ",";
ios_write(page_profile_stream, str, strlen(str));
}
}
}
void gc_page_profile_write_to_file(gc_page_profiler_serializer_t *serializer)
JL_NOTSAFEPOINT
{
if (__unlikely(page_profile_enabled)) {
// write to file
uv_mutex_lock(&page_profile_lock);
gc_page_profile_write_comma(serializer);
gc_page_profile_write_preamble(serializer);
char str[GC_TYPE_STR_MAXLEN];
for (size_t i = 0; i < serializer->typestrs.len; i++) {
const char *name = (const char *)serializer->typestrs.items[i];
if (name == GC_SERIALIZER_EMPTY) {
snprintf(str, GC_TYPE_STR_MAXLEN, "\"empty\",");
}
else if (name == GC_SERIALIZER_GARBAGE) {
snprintf(str, GC_TYPE_STR_MAXLEN, "\"garbage\",");
}
else {
snprintf(str, GC_TYPE_STR_MAXLEN, "\"%s\",", name);
}
// remove trailing comma for last element
if (i == serializer->typestrs.len - 1) {
str[strlen(str) - 1] = '\0';
}
ios_write(page_profile_stream, str, strlen(str));
}
gc_page_profile_write_epilogue(serializer);
page_profile_pages_written++;
uv_mutex_unlock(&page_profile_lock);
}
}
void gc_page_profile_write_json_preamble(ios_t *stream) JL_NOTSAFEPOINT
{
if (__unlikely(page_profile_enabled)) {
uv_mutex_lock(&page_profile_lock);
const char *str = "{\"pages\": [";
ios_write(stream, str, strlen(str));
uv_mutex_unlock(&page_profile_lock);
}
}
void gc_page_profile_write_json_epilogue(ios_t *stream) JL_NOTSAFEPOINT
{
if (__unlikely(page_profile_enabled)) {
uv_mutex_lock(&page_profile_lock);
const char *str = "]}";
ios_write(stream, str, strlen(str));
uv_mutex_unlock(&page_profile_lock);
}
}
JL_DLLEXPORT void jl_gc_take_page_profile(ios_t *stream)
{
gc_enable_page_profile();
page_profile_pages_written = 0;
page_profile_stream = stream;
gc_page_profile_write_json_preamble(stream);
jl_gc_collect(JL_GC_FULL);
gc_page_profile_write_json_epilogue(stream);
gc_disable_page_profile();
}
#ifdef __cplusplus
}
#endif
![swh spinner](/static/img/swh-spinner.gif)
Computing file changes ...