Integrated perfetto + roctracer (#5)
- hosttrace library automatically collects and merges timestamps for HIP API calls and kernels with the host-side instrumentation - mostly eliminates the need for using external rocprof - added thread_instruction_count in perfetto output - increased hosttrace min_loop_address_range to 512 - disabled instrumenting functions with dynamic callsites by default - miscellaneous cmake updates * roctracer support - fully integrated perfetto + roctracer outputs - thread_instruction_count in perfetto - increased min_loop_address_range to 512 - disabled instrumenting functions with dynamic callsites by default - updated timemory submodule * hosttrace_launch_compiler - support for using an alternative compiler as needed via launch compiler - elfio added as submodule (not currently used) - miscellaneous cmake updates * README update + host/device categories + misc - timemory fix for TIMEMORY_ROCTRACER_ENABLED - transpose fix * papi_tuple_t -> papi_tot_ins - minor fix to Findroctracer.cmake
This commit is contained in:
zatwierdzone przez
GitHub
rodzic
b6e65d69f6
commit
a061b7947f
Executable
+138
@@ -0,0 +1,138 @@
|
||||
#!/bin/bash
|
||||
|
||||
EXE=$(basename ${1})
|
||||
DIR=cpu.prof.${EXE}
|
||||
mkdir -p ${DIR}
|
||||
|
||||
# gperf settings
|
||||
: ${N:=0}
|
||||
: ${GPERF_PROFILE:=""}
|
||||
: ${GPERF_PROFILE_BASE:=${DIR}/gperf}
|
||||
: ${MALLOCSTATS:=1}
|
||||
: ${CPUPROFILE_FREQUENCY:=250}
|
||||
: ${CPUPROFILE_REALTIME:=1}
|
||||
|
||||
# rendering settings
|
||||
: ${INTERACTIVE:=0}
|
||||
: ${IMG_FORMAT:="png"}
|
||||
#: ${DOT_ARGS:='-Gsize=24,24\! -Gdpi=200'}
|
||||
: ${DOT_ARGS:=""}
|
||||
: ${PPROF_ARGS:="--no_strip_temp --functions"}
|
||||
|
||||
if [ "$(uname)" = "Darwin" ]; then
|
||||
if [ "${IMG_FORMAT}" = "jpeg" ]; then
|
||||
IMG_FORMAT="jpg"
|
||||
fi
|
||||
fi
|
||||
run-verbose()
|
||||
{
|
||||
echo "${@}" 1>&2
|
||||
eval ${@}
|
||||
}
|
||||
|
||||
while [ -z "${GPERF_PROFILE}" ]
|
||||
do
|
||||
TEST_FILE=${GPERF_PROFILE_BASE}.${N}
|
||||
if [ ! -f "${TEST_FILE}" ]; then
|
||||
GPERF_PROFILE=${TEST_FILE}
|
||||
fi
|
||||
N=$((${N}+1))
|
||||
done
|
||||
|
||||
export MALLOCSTATS
|
||||
export CPUPROFILE_FREQUENCY
|
||||
export CPUPROFILE_REALTIME
|
||||
|
||||
echo -e "\n\t--> Outputting profile to '${GPERF_PROFILE}'...\n"
|
||||
|
||||
# remove profile file if unsucessful execution
|
||||
cleanup-failure() { set +v ; echo "failure"; rm -f ${GPERF_PROFILE}; exit 1; }
|
||||
trap cleanup-failure SIGHUP SIGINT SIGQUIT SIGILL SIGABRT SIGKILL
|
||||
|
||||
ADD_LIBS()
|
||||
{
|
||||
for i in $@
|
||||
do
|
||||
if [ -z "${ADD_LIB_LIST}" ]; then
|
||||
ADD_LIB_LIST="--add_lib=${i}"
|
||||
else
|
||||
ADD_LIB_LIST="${ADD_LIB_LIST} --add_lib=${i}"
|
||||
fi
|
||||
done
|
||||
}
|
||||
|
||||
ADD_PRELOAD()
|
||||
{
|
||||
for i in $@
|
||||
do
|
||||
if [ -z "${LIBS}" ]; then
|
||||
LIBS=${i}
|
||||
else
|
||||
LIBS="${LIBS}:${i}"
|
||||
fi
|
||||
done
|
||||
}
|
||||
|
||||
# configure pre-loading of profiler library
|
||||
PROJECT_LIBRARIES="$(find ${PWD} -type f | egrep 'libtimemory|libctimemory' | egrep -v '\.a$|\.dSYM' | egrep '\.so$|\.dylib$')"
|
||||
run-verbose ADD_LIBS ${PROJECT_LIBRARIES}
|
||||
if [ "$(uname)" = "Darwin" ]; then
|
||||
run-verbose ADD_PRELOAD $(otool -L ${1} | egrep 'profiler' | awk '{print $1}')
|
||||
LIBS=$(echo ${LIBS} | sed 's/^://g')
|
||||
if [ -n "${LIBS}" ]; then
|
||||
export DYLD_FORCE_FLAT_NAMESPACE=1
|
||||
echo "DYLD_INSERT_LIBRARIES=${LIBS}"
|
||||
fi
|
||||
else
|
||||
run-verbose ADD_PRELOAD $(ldd ${1} | egrep 'profiler' | awk '{print $(NF-1)}') /usr/lib/x86_64-linux-gnu/libprofiler.so
|
||||
LIBS=$(echo ${LIBS} | sed 's/^://g')
|
||||
if [ -n "${LIB}" ]; then
|
||||
echo "LD_PRELOAD=${LIBS}"
|
||||
fi
|
||||
fi
|
||||
|
||||
set -e
|
||||
# run the application
|
||||
if [ "$(uname)" = "Darwin" ]; then
|
||||
eval DYLD_INSERT_LIBRARIES=${LIBS} CPUPROFILE_FREQUENCY=${CPUPROFILE_FREQUENCY} CPUPROFILE=${GPERF_PROFILE} $@ | tee ${GPERF_PROFILE}.log
|
||||
else
|
||||
eval LD_PRELOAD=${LIBS} CPUPROFILE_FREQUENCY=${CPUPROFILE_FREQUENCY} CPUPROFILE=${GPERF_PROFILE} $@ | tee ${GPERF_PROFILE}.log
|
||||
fi
|
||||
set +e
|
||||
|
||||
echo-dart-measurement()
|
||||
{
|
||||
local _NAME=${1}
|
||||
local _TYPE=${2}
|
||||
local _PATH=${3}
|
||||
echo "<DartMeasurementFile name=\"${_NAME}\" type=\"image/${_TYPE}\">${_PATH}</DartMeasurementFile>"
|
||||
}
|
||||
|
||||
# generate the results
|
||||
EXT=so
|
||||
if [ "$(uname)" = "Darwin" ]; then EXT=dylib; fi
|
||||
if [ -f "${GPERF_PROFILE}" ]; then
|
||||
: ${PPROF:=$(which google-pprof)}
|
||||
: ${PPROF:=$(which pprof)}
|
||||
if [ -n "${PPROF}" ]; then
|
||||
run-verbose ${PPROF} --text ${ADD_LIB_LIST} ${PPROF_ARGS} ${1} ${GPERF_PROFILE} 1> ${GPERF_PROFILE}.txt.tmp
|
||||
run-verbose cat ${GPERF_PROFILE}.txt.tmp | c++filt -n -t &> ${GPERF_PROFILE}.txt
|
||||
run-verbose ${PPROF} --text --cum ${ADD_LIB_LIST} ${PPROF_ARGS} ${1} ${GPERF_PROFILE} 1> ${GPERF_PROFILE}.cum.txt.tmp
|
||||
run-verbose cat ${GPERF_PROFILE}.cum.txt.tmp | c++filt -n -t &> ${GPERF_PROFILE}.cum.txt
|
||||
rm -f *.txt.tmp
|
||||
# if dot is available
|
||||
if [ -n "$(which dot)" ]; then
|
||||
run-verbose ${PPROF} --dot ${ADD_LIB_LIST} ${PPROF_ARGS} ${1} ${GPERF_PROFILE} 1> ${GPERF_PROFILE}.dot
|
||||
run-verbose dot ${DOT_ARGS} -T${IMG_FORMAT} ${GPERF_PROFILE}.dot -o ${GPERF_PROFILE}.${IMG_FORMAT}
|
||||
echo-dart-measurement ${GPERF_PROFILE}.${IMG_FORMAT} ${IMG_FORMAT} ${PWD}/${GPERF_PROFILE}.${IMG_FORMAT}
|
||||
fi
|
||||
if [ "${INTERACTIVE}" -gt 0 ]; then
|
||||
run-verbose ${PPROF} ${ADD_LIB_LIST} ${PPROF_ARGS} ${1} ${GPERF_PROFILE}
|
||||
fi
|
||||
else
|
||||
echo -e "google-pprof/pprof not found!"
|
||||
fi
|
||||
else
|
||||
echo -e "profile file \"${GPERF_PROFILE}\" not found!"
|
||||
ls -la
|
||||
fi
|
||||
Executable
+75
@@ -0,0 +1,75 @@
|
||||
#!/bin/bash -e
|
||||
#
|
||||
# This script allows CMAKE_CXX_COMPILER to be a standard
|
||||
# C++ compiler and hosttrace sets RULE_LAUNCH_COMPILE and
|
||||
# RULE_LAUNCH_LINK in CMake so that all compiler and link
|
||||
# commands are prefixed with this script followed by the
|
||||
# C++ compiler. Thus if $1 == $2 then we know the command
|
||||
# was intended for the C++ compiler and we discard both
|
||||
# $1 and $2 and redirect the command to linker.
|
||||
# If $1 != $2 then we know that the command was not intended
|
||||
# for the C++ compiler and we just discard $1 and launch
|
||||
# the original command. Examples of when $2 will not equal
|
||||
# $1 are 'ar', 'cmake', etc. during the linking phase
|
||||
#
|
||||
|
||||
# emit a message about the underlying command executed
|
||||
: ${DEBUG:=0}
|
||||
: ${HOSTTRACE_DEBUG_LAUNCH_COMPILER:=${DEBUG}}
|
||||
|
||||
debug-message()
|
||||
{
|
||||
if [ "${HOSTTRACE_DEBUG_LAUNCH_COMPILER}" -ne 0 ]; then
|
||||
echo -e "##### $(basename ${BASH_SOURCE[0]}) executing: \"$@\"... #####"
|
||||
fi
|
||||
}
|
||||
|
||||
# if hosttrace compiler is not passed, someone is probably trying to invoke it directly
|
||||
if [ -z "${1}" ]; then
|
||||
echo -e "\n${BASH_SOURCE[0]} was invoked without the hosttrace compiler as the first argument."
|
||||
echo "This script is not indended to be directly invoked by any mechanism other"
|
||||
echo -e "than through a RULE_LAUNCH_COMPILE or RULE_LAUNCH_LINK property set in CMake.\n"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# if hosttrace compiler is not passed, someone is probably trying to invoke it directly
|
||||
if [ -z "${2}" ]; then
|
||||
echo -e "\n${BASH_SOURCE[0]} was invoked without the C++ compiler as the second argument."
|
||||
echo "This script is not indended to be directly invoked by any mechanism other"
|
||||
echo -e "than through a RULE_LAUNCH_COMPILE or RULE_LAUNCH_LINK property set in CMake.\n"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# if there aren't two args, this isn't necessarily invalid, just a bit strange
|
||||
if [ -z "${3}" ]; then exit 0; fi
|
||||
|
||||
# store the hosttrace compiler
|
||||
HOSTTRACE_COMPILER=${1}
|
||||
|
||||
# remove the hosttrace compiler from the arguments
|
||||
shift
|
||||
|
||||
# store the expected C++ compiler
|
||||
CXX_COMPILER=${1}
|
||||
|
||||
# remove the expected C++ compiler from the arguments
|
||||
shift
|
||||
|
||||
if [[ "${CXX_COMPILER}" != "${1}" ]]; then
|
||||
debug-message $@
|
||||
# the command does not depend on hosttrace so just execute the command w/o re-directing to ${HOSTTRACE_COMPILER}
|
||||
eval $@
|
||||
else
|
||||
# the executable is the C++ compiler, so we need to re-direct to ${HOSTTRACE_COMPILER}
|
||||
if [ ! -f "${HOSTTRACE_COMPILER}" ]; then
|
||||
echo -e "\nError: the compiler redirect for hosttrace was not found at ${HOSTTRACE_COMPILER}\n"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# discard the compiler from the command
|
||||
shift
|
||||
|
||||
debug-message ${HOSTTRACE_COMPILER} $@
|
||||
# execute ${HOSTTRACE_COMPILER} (again, usually nvcc_wrapper)
|
||||
${HOSTTRACE_COMPILER} $@
|
||||
fi
|
||||
Reference in New Issue
Block a user