Skip to content

Commit

Permalink
i#1729 offline traces: generate unoptimized traces
Browse files Browse the repository at this point in the history
Adds two new options for offline trace generation in drcachesim: -offline
and -outdir.

Updates the launcher to skip the simulator launch when -offline is
requested.

Updates the tracer to write to a file instead of a pipe when -offline is
set.  The trace entry format is still the same: it will be modified in the
future to include timestamps and to shrink its size, with a postprocessor
component filling in statically-identifiable information.

Adds packing to trace_entry_t to ensure it can be used as a cross-platform
persistent representation.

A test will be added once file reading is in place.

Review-URL: https://codereview.appspot.com/310890043
  • Loading branch information
derekbruening committed Sep 18, 2016
1 parent 9ae3828 commit d4b3e61
Show file tree
Hide file tree
Showing 6 changed files with 172 additions and 64 deletions.
16 changes: 14 additions & 2 deletions clients/drcachesim/common/options.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/* **********************************************************
* Copyright (c) 2015 Google, Inc. All rights reserved.
* Copyright (c) 2015-2016 Google, Inc. All rights reserved.
* **********************************************************/

/*
Expand Down Expand Up @@ -36,12 +36,24 @@
#include "droption.h"
#include "options.h"

droption_t<bool> op_offline
(DROPTION_SCOPE_ALL, "offline", false, "Store trace files for offline analysis",
"By default, traces are processed online, sent over a pipe to a simulator. "
"If this option is enabled, trace data is instead written to files in -outdir "
"for later offline analysis. No simulator is executed.");

droption_t<std::string> op_ipc_name
(DROPTION_SCOPE_ALL, "ipc_name", "drcachesimpipe", "Base name of named pipe",
"Specifies the base name of the named pipe used to communicate between the target "
"For online tracing and simulation (the default, unless -offline is requested), "
"specifies the base name of the named pipe used to communicate between the target "
"application processes and the caching device simulator. A unique name must be chosen "
"for each instance of the simulator being run at any one time.");

droption_t<std::string> op_outdir
(DROPTION_SCOPE_ALL, "outdir", ".", "Target directory for offline trace files",
"For the offline analysis mode (when -offline is requested), specifies the path "
"to a directory where per-thread trace files will be written.");

droption_t<unsigned int> op_num_cores
(DROPTION_SCOPE_FRONTEND, "cores", 4, "Number of cores",
"Specifies the number of cores to simulate.");
Expand Down
4 changes: 3 additions & 1 deletion clients/drcachesim/common/options.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/* **********************************************************
* Copyright (c) 2015 Google, Inc. All rights reserved.
* Copyright (c) 2015-2016 Google, Inc. All rights reserved.
* **********************************************************/

/*
Expand Down Expand Up @@ -45,7 +45,9 @@
#include <string>
#include "droption.h"

extern droption_t<bool> op_offline;
extern droption_t<std::string> op_ipc_name;
extern droption_t<std::string> op_outdir;
extern droption_t<unsigned int> op_num_cores;
extern droption_t<unsigned int> op_line_size;
extern droption_t<bytesize_t> op_L1I_size;
Expand Down
9 changes: 6 additions & 3 deletions clients/drcachesim/common/trace_entry.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/* **********************************************************
* Copyright (c) 2015 Google, Inc. All rights reserved.
* Copyright (c) 2015-2016 Google, Inc. All rights reserved.
* **********************************************************/

/*
Expand Down Expand Up @@ -44,6 +44,7 @@
#define _TRACE_ENTRY_H_ 1

#include <stdint.h>
#include "utils.h"

typedef uintptr_t addr_t;

Expand Down Expand Up @@ -116,7 +117,8 @@ extern const char * const trace_type_names[];
// - a flush request
// - a prefetch request
// - a thread/process
typedef struct _trace_entry_t {
START_PACKED_STRUCTURE
struct _trace_entry_t {
unsigned short type; // 2 bytes: trace_type_t
// 2 bytes: mem ref size, instr length, or num of instrs for instr bundle
unsigned short size;
Expand All @@ -125,7 +127,8 @@ typedef struct _trace_entry_t {
// The length of each instr in the instr bundle
unsigned char length[sizeof(addr_t)];
};
} trace_entry_t;
} END_PACKED_STRUCTURE;
typedef struct _trace_entry_t trace_entry_t;

static inline bool
type_is_prefetch(unsigned short type)
Expand Down
21 changes: 20 additions & 1 deletion clients/drcachesim/common/utils.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/* **********************************************************
* Copyright (c) 2015 Google, Inc. All rights reserved.
* Copyright (c) 2015-2016 Google, Inc. All rights reserved.
* **********************************************************/

/*
Expand Down Expand Up @@ -48,6 +48,25 @@
#define BUFFER_LAST_ELEMENT(buf) buf[BUFFER_SIZE_ELEMENTS(buf) - 1]
#define NULL_TERMINATE_BUFFER(buf) BUFFER_LAST_ELEMENT(buf) = 0

#define BOOLS_MATCH(b1, b2) (!!(b1) == !!(b2))

#ifdef WINDOWS
/* Use special C99 operator _Pragma to generate a pragma from a macro */
# if _MSC_VER <= 1200
# define ACTUAL_PRAGMA(p) _Pragma ( #p )
# else
# define ACTUAL_PRAGMA(p) __pragma ( p )
# endif
/* Usage: if planning to typedef, that must be done separately, as MSVC will
* not take _pragma after typedef.
*/
# define START_PACKED_STRUCTURE ACTUAL_PRAGMA( pack(push,1) )
# define END_PACKED_STRUCTURE ACTUAL_PRAGMA( pack(pop) )
#else
# define START_PACKED_STRUCTURE /* nothing */
# define END_PACKED_STRUCTURE __attribute__ ((__packed__))
#endif

static inline int
compute_log2(int value)
{
Expand Down
62 changes: 43 additions & 19 deletions clients/drcachesim/launcher.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/* **********************************************************
* Copyright (c) 2015 Google, Inc. All rights reserved.
* Copyright (c) 2015-2016 Google, Inc. All rights reserved.
* **********************************************************/

/*
Expand Down Expand Up @@ -81,6 +81,13 @@ file_is_readable(const char *path)
return (drfront_access(path, DRFRONT_READ, &ret) == DRFRONT_SUCCESS && ret);
}

static bool
file_is_writable(const char *path)
{
bool ret = false;
return (drfront_access(path, DRFRONT_WRITE, &ret) == DRFRONT_SUCCESS && ret);
}

static void
get_full_path(const char *app, char *buf, size_t buflen/*# elements*/)
{
Expand Down Expand Up @@ -157,6 +164,9 @@ _tmain(int argc, const TCHAR *targv[])
bool is64, is32;
analyzer_t *analyzer = NULL;
std::string tracer_ops;
#ifdef UNIX
pid_t child;
#endif

#if defined(WINDOWS) && !defined(_UNICODE)
# error _UNICODE must be defined
Expand Down Expand Up @@ -222,20 +232,29 @@ _tmain(int argc, const TCHAR *targv[])
assert(false); // won't get here
}

// declare the analyzer based on its type
if (op_simulator_type.get_value() == CPU_CACHE)
analyzer = new cache_simulator_t;
else if (op_simulator_type.get_value() == TLB)
analyzer = new tlb_simulator_t;
else {
ERROR("Usage error: unsupported analyzer type. "
"Please choose " CPU_CACHE" or " TLB".\n");
return false;
}
if (op_offline.get_value()) {
// Initial sanity check: may still be unwritable by this user, but this
// serves as at least an existence check.
if (!file_is_writable(op_outdir.get_value().c_str())) {
FATAL_ERROR("invalid -outdir %s", op_outdir.get_value().c_str());
assert(false); // won't get here
}
} else {
// declare the analyzer based on its type
if (op_simulator_type.get_value() == CPU_CACHE)
analyzer = new cache_simulator_t;
else if (op_simulator_type.get_value() == TLB)
analyzer = new tlb_simulator_t;
else {
ERROR("Usage error: unsupported analyzer type. "
"Please choose " CPU_CACHE" or " TLB".\n");
return false;
}

if (!analyzer->init()) {
FATAL_ERROR("failed to initialize analyzer");
assert(false); // won't get here
if (!analyzer->init()) {
FATAL_ERROR("failed to initialize analyzer");
assert(false); // won't get here
}
}

tracer_ops = op_tracer_ops.get_value();
Expand All @@ -245,12 +264,15 @@ _tmain(int argc, const TCHAR *targv[])
NOTIFY(1, "INFO", "DynamoRIO configuration directory is %s", buf);

#ifdef UNIX
pid_t child = fork();
if (op_offline.get_value())
child = 0;
else
child = fork();
if (child < 0) {
FATAL_ERROR("failed to fork");
assert(false); // won't get here
} else if (child == 0) {
/* child */
/* child, or offline where we exec this process */
if (!configure_application(app_name, app_argv, tracer_ops, &inject_data) ||
!dr_inject_process_inject(inject_data, false/*!force*/, NULL)) {
FATAL_ERROR("unable to inject");
Expand All @@ -268,9 +290,11 @@ _tmain(int argc, const TCHAR *targv[])
dr_inject_process_run(inject_data);
#endif

if (!analyzer->run()) {
FATAL_ERROR("failed to run analyzer");
assert(false); // won't get here
if (!op_offline.get_value()) {
if (!analyzer->run()) {
FATAL_ERROR("failed to run analyzer");
assert(false); // won't get here
}
}

#ifdef WINDOWS
Expand Down
Loading

0 comments on commit d4b3e61

Please sign in to comment.