mirror of
https://github.com/jemalloc/jemalloc.git
synced 2026-07-24 13:53:11 +00:00
[pa-bench] Add clock to pa benchmark
This commit is contained in:
committed by
Guangli Dai
parent
a199278f37
commit
707aab0c95
@@ -16,13 +16,14 @@
|
|||||||
* HPA: shard_ind_int,addr_int,nsecs_int,probe,size_int
|
* HPA: shard_ind_int,addr_int,nsecs_int,probe,size_int
|
||||||
* SEC: process_id,thread_id,thread_name,nsecs_int,_c4,sec_ptr_int,sec_shard_ptr_int,edata_ptr_int,size_int,is_frequent_reuse_int
|
* SEC: process_id,thread_id,thread_name,nsecs_int,_c4,sec_ptr_int,sec_shard_ptr_int,edata_ptr_int,size_int,is_frequent_reuse_int
|
||||||
*
|
*
|
||||||
* Output format (4 columns):
|
* Output format (5 columns):
|
||||||
* shard_ind_int,operation_index,size_or_alloc_index,is_frequent
|
* shard_ind_int,operation_index,size_or_alloc_index,nsecs,is_frequent
|
||||||
* where:
|
* where:
|
||||||
* - shard_ind_int: shard index as integer
|
* - shard_ind_int: shard index as integer
|
||||||
* - operation_index: 0=alloc, 1=dalloc
|
* - operation_index: 0=alloc, 1=dalloc
|
||||||
* - size_or_alloc_index: for alloc operations show bytes,
|
* - size_or_alloc_index: for alloc operations show bytes,
|
||||||
* for dalloc operations show index of corresponding alloc
|
* for dalloc operations show index of corresponding alloc
|
||||||
|
* - nsecs: nanonosec of some monotonic clock
|
||||||
* - is_frequent: 1 if frequent reuse allocation, 0 otherwise
|
* - is_frequent: 1 if frequent reuse allocation, 0 otherwise
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@@ -250,14 +251,14 @@ parse_sec_line(
|
|||||||
|
|
||||||
void
|
void
|
||||||
write_output_header(std::ofstream &output) {
|
write_output_header(std::ofstream &output) {
|
||||||
output << "shard_ind,operation,size_or_alloc_index,is_frequent\n";
|
output << "shard_ind,operation,size_or_alloc_index,nsecs,is_frequent\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
write_output_event(std::ofstream &output, int shard_ind, int operation,
|
write_output_event(std::ofstream &output, int shard_ind, int operation,
|
||||||
size_t value, bool is_frequent) {
|
size_t value, uint64_t nsecs, bool is_frequent) {
|
||||||
output << shard_ind << "," << operation << "," << value << ","
|
output << shard_ind << "," << operation << "," << value << "," << nsecs
|
||||||
<< (is_frequent ? 1 : 0) << "\n";
|
<< "," << (is_frequent ? 1 : 0) << "\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t
|
size_t
|
||||||
@@ -319,7 +320,7 @@ process_trace_file(const std::string &input_filename,
|
|||||||
if (is_alloc_operation(event.probe)) {
|
if (is_alloc_operation(event.probe)) {
|
||||||
/* This is an allocation */
|
/* This is an allocation */
|
||||||
write_output_event(output, event.shard_ind, 0,
|
write_output_event(output, event.shard_ind, 0,
|
||||||
event.size, event.is_frequent);
|
event.size, event.nsecs, event.is_frequent);
|
||||||
|
|
||||||
/* Track this allocation with the current sequence number */
|
/* Track this allocation with the current sequence number */
|
||||||
tracker.add_allocation(event.addr, event.size,
|
tracker.add_allocation(event.addr, event.size,
|
||||||
@@ -335,7 +336,8 @@ process_trace_file(const std::string &input_filename,
|
|||||||
assert(event.nsecs >= record->nsecs);
|
assert(event.nsecs >= record->nsecs);
|
||||||
/* Found matching allocation with valid timing */
|
/* Found matching allocation with valid timing */
|
||||||
write_output_event(output, event.shard_ind, 1,
|
write_output_event(output, event.shard_ind, 1,
|
||||||
record->alloc_index, event.is_frequent);
|
record->alloc_index, event.nsecs,
|
||||||
|
event.is_frequent);
|
||||||
tracker.remove_allocation(event.addr);
|
tracker.remove_allocation(event.addr);
|
||||||
output_count++; /* Count this deallocation */
|
output_count++; /* Count this deallocation */
|
||||||
} else {
|
} else {
|
||||||
@@ -390,7 +392,7 @@ main(int argc, char *argv[]) {
|
|||||||
<< " output_file - Output file for simulator with format:"
|
<< " output_file - Output file for simulator with format:"
|
||||||
<< std::endl;
|
<< std::endl;
|
||||||
std::cerr
|
std::cerr
|
||||||
<< " shard_ind,operation,size_or_alloc_index,is_frequent"
|
<< " shard_ind,operation,size_or_alloc_index,nsecs,is_frequent"
|
||||||
<< std::endl;
|
<< std::endl;
|
||||||
std::cerr << std::endl;
|
std::cerr << std::endl;
|
||||||
std::cerr << "Output format:" << std::endl;
|
std::cerr << "Output format:" << std::endl;
|
||||||
|
|||||||
@@ -35,6 +35,7 @@ typedef struct {
|
|||||||
int shard_ind;
|
int shard_ind;
|
||||||
pa_op_t operation;
|
pa_op_t operation;
|
||||||
size_t size_or_alloc_index;
|
size_t size_or_alloc_index;
|
||||||
|
uint64_t nsecs;
|
||||||
int is_frequent;
|
int is_frequent;
|
||||||
} pa_event_t;
|
} pa_event_t;
|
||||||
|
|
||||||
@@ -73,6 +74,29 @@ static shard_infrastructure_t *g_shard_infra =
|
|||||||
NULL; /* Per-shard PA infrastructure */
|
NULL; /* Per-shard PA infrastructure */
|
||||||
static pa_central_t g_pa_central; /* Global PA central */
|
static pa_central_t g_pa_central; /* Global PA central */
|
||||||
|
|
||||||
|
/* Override for curtime */
|
||||||
|
static hpa_hooks_t hpa_hooks_override;
|
||||||
|
static nstime_t cur_time_clock;
|
||||||
|
|
||||||
|
void
|
||||||
|
curtime(nstime_t *r_time, bool first_reading) {
|
||||||
|
if (first_reading) {
|
||||||
|
nstime_init_zero(r_time);
|
||||||
|
}
|
||||||
|
*r_time = cur_time_clock;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
set_clock(uint64_t nsecs) {
|
||||||
|
nstime_init(&cur_time_clock, nsecs);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
init_hpa_hooks() {
|
||||||
|
hpa_hooks_override = hpa_hooks_default;
|
||||||
|
hpa_hooks_override.curtime = curtime;
|
||||||
|
}
|
||||||
|
|
||||||
static void cleanup_pa_infrastructure(int num_shards);
|
static void cleanup_pa_infrastructure(int num_shards);
|
||||||
|
|
||||||
static bool
|
static bool
|
||||||
@@ -125,8 +149,9 @@ initialize_pa_infrastructure(int num_shards) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Initialize PA central with HPA enabled */
|
/* Initialize PA central with HPA enabled */
|
||||||
|
init_hpa_hooks();
|
||||||
if (pa_central_init(&g_pa_central, central_base, true /* hpa */,
|
if (pa_central_init(&g_pa_central, central_base, true /* hpa */,
|
||||||
&hpa_hooks_default)) {
|
&hpa_hooks_override)) {
|
||||||
printf("DEBUG: Failed to initialize PA central\n");
|
printf("DEBUG: Failed to initialize PA central\n");
|
||||||
base_delete(tsd_tsdn(tsd_fetch()), central_base);
|
base_delete(tsd_tsdn(tsd_fetch()), central_base);
|
||||||
free(g_shard_stats);
|
free(g_shard_stats);
|
||||||
@@ -237,14 +262,15 @@ static bool
|
|||||||
parse_csv_line(const char *line, pa_event_t *event) {
|
parse_csv_line(const char *line, pa_event_t *event) {
|
||||||
/* Expected format: shard_ind,operation,size_or_alloc_index,is_frequent */
|
/* Expected format: shard_ind,operation,size_or_alloc_index,is_frequent */
|
||||||
int operation;
|
int operation;
|
||||||
int fields = sscanf(line, "%d,%d,%zu,%d", &event->shard_ind, &operation,
|
int fields = sscanf(line, "%d,%d,%zu,%lu,%d", &event->shard_ind,
|
||||||
&event->size_or_alloc_index, &event->is_frequent);
|
&operation, &event->size_or_alloc_index, &event->nsecs,
|
||||||
|
&event->is_frequent);
|
||||||
|
|
||||||
if (fields < 3) { /* is_frequent is optional */
|
if (fields < 4) { /* is_frequent is optional */
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (fields == 3) {
|
if (fields == 4) {
|
||||||
event->is_frequent = 0; /* Default value */
|
event->is_frequent = 0; /* Default value */
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -393,6 +419,7 @@ simulate_trace(
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
set_clock(event->nsecs);
|
||||||
switch (event->operation) {
|
switch (event->operation) {
|
||||||
case PA_ALLOC: {
|
case PA_ALLOC: {
|
||||||
size_t size = event->size_or_alloc_index;
|
size_t size = event->size_or_alloc_index;
|
||||||
|
|||||||
Reference in New Issue
Block a user