1
Fork 0
mirror of git://git.sv.gnu.org/emacs.git synced 2026-04-27 08:43:40 -07:00

Label the time series in the monitor.

In telemetry output, distinguish between labelling of (client) addresses and (MPS-internal) pointers, to avoid transgressing the distinction.
Add arena grain size, class, and serial number to ArenaCreate* events.
Add pool class and serial number to PoolInit event.

Copied from Perforce
 Change: 194086
This commit is contained in:
Gareth Rees 2018-06-22 11:05:46 +01:00
parent 6fd9abf9bd
commit c3a7104eff
11 changed files with 182 additions and 61 deletions

View file

@ -289,6 +289,7 @@ static Res ArenaAbsInit(Arena arena, Size grainSize, ArgList args)
if (res != ResOK)
goto failMFSInit;
EventLabelPointer(ArenaCBSBlockPool(arena), EventInternString("CBSBlock"));
return ResOK;
failMFSInit:
@ -497,6 +498,7 @@ Res ControlInit(Arena arena)
if (res != ResOK)
return res;
arena->poolReady = TRUE; /* <design/arena/#pool.ready> */
EventLabelPointer(&arena->controlPoolStruct, EventInternString("Control"));
return ResOK;
}

View file

@ -305,7 +305,8 @@ static Res ClientArenaCreate(Arena *arenaReturn, ArgList args)
arena->zoneShift = SizeFloorLog2(size >> MPS_WORD_SHIFT);
AVER(ArenaGrainSize(arena) == ChunkPageSize(arena->primary));
EVENT3(ArenaCreateCL, arena, size, base);
EVENT6(ArenaCreateCL, arena, size, base, grainSize,
ClassOfPoly(Arena, arena), arena->serial);
AVERT(ClientArena, clientArena);
*arenaReturn = arena;
return ResOK;

View file

@ -659,7 +659,8 @@ static Res VMArenaCreate(Arena *arenaReturn, ArgList args)
AVER(ChunkPageSize(chunk) == ArenaGrainSize(arena));
AVERT(VMArena, vmArena);
EVENT3(ArenaCreateVM, arena, size, chunkSize);
EVENT6(ArenaCreateVM, arena, size, chunkSize, grainSize,
ClassOfPoly(Arena, arena), arena->serial);
vmArena->extended(arena, chunk->base, chunkSize);

View file

@ -297,6 +297,16 @@ void EventLabelAddr(Addr addr, EventStringId id)
}
/* EventLabelPointer -- emit event to label pointer with the given id */
void EventLabelPointer(Pointer pointer, EventStringId id)
{
AVER((Serial)id < EventInternSerial);
EVENT2(LabelPointer, pointer, id);
}
/* Convert event parameter sort to WriteF arguments */
#define EVENT_WRITE_PARAM_MOST(name, index, sort, ident) \
@ -492,6 +502,15 @@ void EventLabelAddr(Addr addr, Word id)
}
void EventLabelPointer(Pointer pointer, Word id)
{
UNUSED(pointer);
UNUSED(id);
/* EventLabelPointer is reached in varieties without events, but
doesn't have to do anything. */
}
Res EventDescribe(Event event, mps_lib_FILE *stream, Count depth)
{
UNUSED(event);

View file

@ -32,6 +32,7 @@ extern EventControlSet EventControl(EventControlSet resetMask,
extern EventStringId EventInternString(const char *label);
extern EventStringId EventInternGenString(size_t, const char *label);
extern void EventLabelAddr(Addr addr, Word id);
extern void EventLabelPointer(Pointer pointer, Word id);
extern void EventFlush(EventKind kind);
extern Res EventDescribe(Event event, mps_lib_FILE *stream, Count depth);
extern Res EventWrite(Event event, mps_lib_FILE *stream);

View file

@ -67,7 +67,7 @@
*/
#define EventNameMAX ((size_t)19)
#define EventCodeMAX ((EventCode)0x0088)
#define EventCodeMAX ((EventCode)0x0089)
#define EVENT_LIST(EVENT, X) \
/* 0123456789012345678 <- don't exceed without changing EventNameMAX */ \
@ -194,7 +194,8 @@
EVENT(X, ArenaUseFreeZone , 0x0085, TRUE, Arena) \
/* EVENT(X, ArenaBlacklistZone , 0x0086, TRUE, Arena) */ \
EVENT(X, PauseTimeSet , 0x0087, TRUE, Arena) \
EVENT(X, TraceEndGen , 0x0088, TRUE, Trace)
EVENT(X, TraceEndGen , 0x0088, TRUE, Trace) \
EVENT(X, LabelPointer , 0x0089, TRUE, User)
/* Remember to update EventNameMAX and EventCodeMAX above!
@ -233,7 +234,10 @@
#define EVENT_ArenaCreateVM_PARAMS(PARAM, X) \
PARAM(X, 0, P, arena) \
PARAM(X, 1, W, userSize) \
PARAM(X, 2, W, chunkSize)
PARAM(X, 2, W, chunkSize) \
PARAM(X, 3, W, grainSize) \
PARAM(X, 4, P, arenaClass) \
PARAM(X, 5, U, serial)
#define EVENT_ArenaCreateVMNZ_PARAMS(PARAM, X) \
PARAM(X, 0, P, arena) \
@ -279,7 +283,10 @@
#define EVENT_ArenaCreateCL_PARAMS(PARAM, X) \
PARAM(X, 0, P, arena) \
PARAM(X, 1, W, size) \
PARAM(X, 2, A, base)
PARAM(X, 2, A, base) \
PARAM(X, 3, W, grainSize) \
PARAM(X, 4, P, arenaClass) \
PARAM(X, 5, U, serial)
#define EVENT_ArenaDestroy_PARAMS(PARAM, X) \
PARAM(X, 0, P, arena)
@ -298,7 +305,8 @@
#define EVENT_PoolInit_PARAMS(PARAM, X) \
PARAM(X, 0, P, pool) \
PARAM(X, 1, P, arena) \
PARAM(X, 2, P, poolClass)
PARAM(X, 2, P, poolClass) \
PARAM(X, 3, U, serial)
#define EVENT_PoolFinish_PARAMS(PARAM, X) \
PARAM(X, 0, P, pool)
@ -712,6 +720,10 @@
PARAM(X, 4, W, preservedInPlace) /* bytes preserved in generation */ \
PARAM(X, 5, D, mortality) /* updated mortality */
#define EVENT_LabelPointer_PARAMS(PARAM, X) \
PARAM(X, 0, P, pointer) \
PARAM(X, 1, W, stringId)
#endif /* eventdef_h */

View file

@ -233,14 +233,16 @@ static char *parseString(char **pInOut)
}
/* Event logs have interned strings (i.e. they construct a partial
* function from non-negatie integer IDs to strings), and can label
* addresses with intern string IDs (i.e. they construct a partial
* function from address to string ID). We need two tables to keep
* track of these. */
* function from non-negative integer IDs to strings), and can label
* addresses and pointers with intern string IDs (i.e. they construct
* a partial function from address or pointer to string ID). We need
* three tables to keep track of these. */
static Table internTable; /* dictionary of intern ids to strings */
static Table labelTable; /* dictionary of addrs to intern ids */
static Table labelAddrTable; /* dictionary of addrs to intern ids */
static Table labelPointerTable; /* dictionary of pointers to intern ids */
static void createTables(mps_pool_t pool)
{
@ -255,11 +257,18 @@ static void createTables(mps_pool_t pool)
everror("Couldn't make intern table.");
/* We assume that 0 and 1 are invalid as Addrs. */
res = TableCreate(&labelTable, (size_t)1<<7,
res = TableCreate(&labelAddrTable, (size_t)1<<7,
tableAlloc, tableFree, pool,
0, 1);
if (res != ResOK)
everror("Couldn't make label table.");
everror("Couldn't make address label table.");
/* We assume that 0 and 1 are invalid as Pointers. */
res = TableCreate(&labelPointerTable, (size_t)1<<7,
tableAlloc, tableFree, pool,
0, 1);
if (res != ResOK)
everror("Couldn't make pointer label table.");
}
/* recordIntern -- record an interned string in the table. a copy of
@ -326,8 +335,9 @@ static size_t labelFind(LabelList list, EventClock clock)
}
/* recordLabel records a label: an association (made at the time given
* by 'clock') between an address and a string ID. These are encoded
* as two hexadecimal numbers in the string pointed to by 'p'.
* by 'clock') between a client address or an internal pointer and a
* string ID. These are encoded as two hexadecimal numbers in the
* string pointed to by 'p'.
*
* Note that the event log may have been generated on a platform with
* addresses larger than Word on the current platform. If that happens
@ -344,7 +354,7 @@ static size_t labelFind(LabelList list, EventClock clock)
* probably a bad idea and maybe doomed to failure.
*/
static void recordLabel(mps_pool_t pool, EventClock clock, char *p)
static void recordLabel(mps_pool_t pool, Table table, EventClock clock, char *p)
{
ulongest_t address;
LabelList list;
@ -359,7 +369,7 @@ static void recordLabel(mps_pool_t pool, EventClock clock, char *p)
return;
}
if (TableLookup(&tmp, labelTable, (TableKey)address)) {
if (TableLookup(&tmp, table, (TableKey)address)) {
list = tmp;
} else {
/* First label for this address */
@ -368,7 +378,7 @@ static void recordLabel(mps_pool_t pool, EventClock clock, char *p)
everror("Can't allocate space for a label list");
list = tmp;
list->n = 0;
res = TableDefine(labelTable, (TableKey)address, list);
res = TableDefine(table, (TableKey)address, list);
if (res != ResOK)
everror("Couldn't create a label mapping.");
}
@ -400,15 +410,16 @@ static void recordLabel(mps_pool_t pool, EventClock clock, char *p)
static int hexWordWidth = (MPS_WORD_WIDTH+3)/4;
/* printAddr -- output a ulongest_t in hex, with the interned string
* if the value is in the label table */
/* printLabelled -- output a ulongest_t in hex, with the interned
* string if the value is in the table */
static void printAddr(EventClock clock, ulongest_t addr, const char *ident)
static void printLabelled(EventClock clock, ulongest_t value,
const char *ident, Table table)
{
void *tmp;
printf("%s:%0*" PRIXLONGEST, ident, hexWordWidth, addr);
if (TableLookup(&tmp, labelTable, (TableKey)addr)) {
printf("%s:%0*" PRIXLONGEST, ident, hexWordWidth, value);
if (table != NULL && TableLookup(&tmp, table, (TableKey)value)) {
LabelList list = tmp;
size_t pos = labelFind(list, clock);
if (pos > 0) {
@ -430,10 +441,15 @@ static void printAddr(EventClock clock, ulongest_t addr, const char *ident)
#define processParamA(ident) \
val_hex = parseHex(&p); \
printAddr(clock, val_hex, #ident);
printLabelled(clock, val_hex, #ident, labelAddrTable);
#define processParamP processParamA
#define processParamW processParamA
#define processParamP(ident) \
val_hex = parseHex(&p); \
printLabelled(clock, val_hex, #ident, labelPointerTable);
#define processParamW(ident) \
val_hex = parseHex(&p); \
printLabelled(clock, val_hex, #ident, NULL);
#define processParamU(ident) \
val_hex = parseHex(&p); \
@ -515,7 +531,9 @@ static void readLog(mps_pool_t pool, FILE *input)
if (code == EventInternCode) {
recordIntern(pool, q);
} else if (code == EventLabelCode) {
recordLabel(pool, clock, q);
recordLabel(pool, labelAddrTable, clock, q);
} else if (code == EventLabelPointerCode) {
recordLabel(pool, labelPointerTable, clock, q);
} else if (code == EventEventInitCode) {
ulongest_t major, median, minor, maxCode, maxNameLen, wordWidth, clocksPerSec;
major = parseHex(&q); /* EVENT_VERSION_MAJOR */

View file

@ -2,12 +2,6 @@
*
* $Id$
* Copyright (c) 2001-2014 Ravenbrook Limited. See end of file for license.
*
* TRANSGRESSIONS
*
* .trans.label: We label meters with EventLabelAddr, but of course that's
* meant for labelling Addr's. We get away with it as long as the type
* Meter is compatible with Addr.
*/
#include "meter.h"
@ -30,7 +24,7 @@ void MeterInit(Meter meter, const char *name, void *owner)
meter->min = (Size)-1;
sym = EventInternString(name);
EventLabelAddr((Addr)meter, sym); /* see .trans.label */
EventLabelPointer(meter, sym);
EVENT2(MeterInit, meter, owner);
}

View file

@ -147,7 +147,8 @@ Res PoolInit(Pool pool, Arena arena, PoolClass klass, ArgList args)
if (res != ResOK)
return res;
EVENT3(PoolInit, pool, PoolArena(pool), ClassOfPoly(Pool, pool));
EVENT4(PoolInit, pool, PoolArena(pool), ClassOfPoly(Pool, pool),
pool->serial);
return ResOK;
}

View file

@ -138,8 +138,7 @@ void ClassRegister(InstClass klass)
/* label the pool class with its name */
EventInit();
classId = EventInternString(ClassName(klass));
/* NOTE: this breaks <design/type/#addr.use> */
EventLabelAddr((Addr)klass, classId);
EventLabelPointer(klass, classId);
}