diff --git a/clients/drcachesim/common/options.cpp b/clients/drcachesim/common/options.cpp index e98349d0a05..64c5c2d02ad 100644 --- a/clients/drcachesim/common/options.cpp +++ b/clients/drcachesim/common/options.cpp @@ -98,7 +98,7 @@ droption_t op_alt_module_dir( DROPTION_SCOPE_FRONTEND, "alt_module_dir", "", "Alternate module search directory", "Specifies a directory containing libraries referenced in -module_file for " "analysis tools, or in the raw modules file for post-prcoessing of offline " - "raw trace files."); + "raw trace files. This directory takes precedence over the recorded path."); droption_t op_funclist_file( DROPTION_SCOPE_ALL, "funclist_file", "", diff --git a/clients/drcachesim/tools/opcode_mix_launcher.cpp b/clients/drcachesim/tools/opcode_mix_launcher.cpp index 40d5a36d876..79e3c123273 100644 --- a/clients/drcachesim/tools/opcode_mix_launcher.cpp +++ b/clients/drcachesim/tools/opcode_mix_launcher.cpp @@ -64,7 +64,8 @@ static droption_t op_module_file( static droption_t op_alt_module_dir( DROPTION_SCOPE_FRONTEND, "alt_module_dir", "", "Alternate module search directory", - "Specifies a directory containing libraries referenced in -module_file."); + "Specifies a directory containing libraries referenced in -module_file. " + "This directory takes precedence over the recorded path."); droption_t op_verbose(DROPTION_SCOPE_ALL, "verbose", 0, 0, 64, "Verbosity level", diff --git a/clients/drcachesim/tracer/raw2trace.cpp b/clients/drcachesim/tracer/raw2trace.cpp index ddc99c6095a..0c04df0f9f1 100644 --- a/clients/drcachesim/tracer/raw2trace.cpp +++ b/clients/drcachesim/tracer/raw2trace.cpp @@ -311,6 +311,14 @@ raw2trace_t::read_and_map_modules() return module_mapper_->get_last_error(); } +// Maps each module into the address space. +// There are several types of mapping entries in the module list: +// 1) Raw bits directly stored. It is simply pointed at. +// 2) Extra segments for a module. A single mapping is used for all +// segments, so extras are ignored. +// 3) A main segment. The module's file is located by first looking in +// the alt_module_dir_; if not found, the path present during tracing +// is searched. void module_mapper_t::read_and_map_modules() { @@ -345,19 +353,29 @@ module_mapper_t::read_and_map_modules() // 0 size indicates this is a secondary segment. modvec_[info.containing_index].map_base, 0)); } else { - size_t map_size; - byte *base_pc = - dr_map_executable_file(info.path, DR_MAPEXE_SKIP_WRITABLE, &map_size); - if (base_pc == NULL && !alt_module_dir_.empty()) { + size_t map_size = 0; + byte *base_pc = NULL; + if (!alt_module_dir_.empty()) { + // First try the specified module dir. It takes precedence to allow + // overriding the recorded path even when an identical-seeming path + // exists on the processing machine (e.g., system libraries). + // XXX: We should add a checksum on UNIX to match Windows and have + // a sanity check on the library version. std::string basename(info.path); size_t sep_index = basename.find_last_of(DIRSEP ALT_DIRSEP); if (sep_index != std::string::npos) basename = std::string(basename, sep_index + 1, std::string::npos); std::string new_path = alt_module_dir_ + DIRSEP + basename; - VPRINT(1, "Failed to find %s; trying %s\n", info.path, new_path.c_str()); + VPRINT(2, "Trying to map %s\n", new_path.c_str()); base_pc = dr_map_executable_file(new_path.c_str(), DR_MAPEXE_SKIP_WRITABLE, &map_size); } + if (base_pc == NULL) { + // Try the recorded path. + VPRINT(2, "Trying to map %s\n", info.path); + base_pc = + dr_map_executable_file(info.path, DR_MAPEXE_SKIP_WRITABLE, &map_size); + } if (base_pc == NULL) { // We expect to fail to map dynamorio.dll for x64 Windows as it // is built /fixed. (We could try to have the map succeed w/o relocs, diff --git a/clients/drcachesim/tracer/raw2trace_launcher.cpp b/clients/drcachesim/tracer/raw2trace_launcher.cpp index cd25c19b2c9..50f5ff3f487 100644 --- a/clients/drcachesim/tracer/raw2trace_launcher.cpp +++ b/clients/drcachesim/tracer/raw2trace_launcher.cpp @@ -57,7 +57,7 @@ static droption_t static droption_t op_alt_module_dir( DROPTION_SCOPE_FRONTEND, "alt_module_dir", "", "Alternate module search directory", "Specifies a directory to look for binaries needed to post-process " - "the trace that are not found in the path recorded during tracing."); + "the trace. This directory takes precedence over the recorded path."); static droption_t op_verbose(DROPTION_SCOPE_FRONTEND, "verbose", 0, "Verbosity level for diagnostic output",