diff --git a/openmp/libomptarget/src/CMakeLists.txt b/openmp/libomptarget/src/CMakeLists.txt --- a/openmp/libomptarget/src/CMakeLists.txt +++ b/openmp/libomptarget/src/CMakeLists.txt @@ -21,6 +21,7 @@ ) if(LIBOMP_OMPT_SUPPORT_IN_LIBOMPTARGET) + list(APPEND LIBOMPTARGET_SRC_FILES ${CMAKE_CURRENT_SOURCE_DIR}/ompt-target.cpp) list(APPEND LIBOMPTARGET_LLVM_INCLUDE_DIRS ${LIBOMP_INCLUDE_DIR} ${LIBOMP_SRC_DIR}) endif() diff --git a/openmp/libomptarget/src/ompt-target.h b/openmp/libomptarget/src/ompt-target.h --- a/openmp/libomptarget/src/ompt-target.h +++ b/openmp/libomptarget/src/ompt-target.h @@ -1,29 +1,97 @@ #ifndef LIBOMPTARGET_OMPT_TARGET_H #define LIBOMPTARGET_OMPT_TARGET_H +#include "kmp_config.h" +#if OMPT_SUPPORT #include "omp-tools.h" +#define FROM_LIBOMPTARGET 1 +#include "ompt-target-api.h" +#undef FROM_LIBOMPTARGET -#define _OMP_EXTERN extern "C" +#define OMPT_GET_RETURN_ADDRESS(level) __builtin_return_address(level) -#define OMPT_WEAK_ATTRIBUTE __attribute__((weak)) +#define OMPT_ARG(...) , __VA_ARGS__ -// The following structs are used to pass target-related OMPT callbacks to -// libomptarget. The structs' definitions should be in sync with the definitions -// in libomptarget/src/ompt_internal.h +#define OMPT_FIRST_ARG(...) __VA_ARGS__ -/* Bitmap to mark OpenMP 5.1 target events as registered*/ -typedef struct ompt_target_callbacks_active_s { - unsigned int enabled : 1; -#define ompt_event_macro(event, callback, eventid) unsigned int event : 1; +extern ompt_target_callbacks_active_t OmptTargetEnabled; - FOREACH_OMPT_51_TARGET_EVENT(ompt_event_macro) +extern int HostDeviceNum; -#undef ompt_event_macro -} ompt_target_callbacks_active_t; +// TODO (lechenyu): Will move following classes into openmp runtime +// TODO (lechenyu): Need to add additional parameters to initialize and clean +// target_data for omp_target_* routines +class OmptTargetDataOp { +private: + ompt_target_data_op_t OpType; + void *SrcAddr; + int SrcDeviceNum; + void *DestAddr; + int DestDeviceNum; + size_t Bytes; + bool OmpRoutine; + void *CodePtr; + bool Active; -extern ompt_target_callbacks_active_t ompt_target_enabled; +public: + OmptTargetDataOp(ompt_target_data_op_t OpType, void *SrcAddr, + int SrcDeviceNum, void *DestAddr, int DestDeviceNum, + size_t Bytes, bool OmpRoutine, void *CodePtr); + ~OmptTargetDataOp(); + void setDestAddr(void *DestAddr); +}; -_OMP_EXTERN OMPT_WEAK_ATTRIBUTE bool -libomp_start_tool(ompt_target_callbacks_active_t *libomptarget_ompt_enabled); +class OmptTargetMapping { +private: + int32_t Capacity; + int32_t Size; + void **HostAddr; + void **DeviceAddr; + size_t *Bytes; + unsigned int *MappingFlags; + void *CodePtr; + bool Active; + +public: + typedef enum ConstructorType { + TARGET = 1, + TARGET_DATA_BEGIN = 2, + TARGET_DATA_END = 3 + } ConstructorType; + + OmptTargetMapping(int Capacity, void *CodePtr); + ~OmptTargetMapping(); + void addMapping(void *HstAddr, void *TgtAddr, size_t Byte, int64_t ArgType, + ConstructorType ConType); + void invokeCallback(); +}; + +class OmptTarget { +private: + ompt_target_t Kind; + int DeviceNum; + void *CodePtr; + bool Active; + +public: + OmptTarget(ompt_target_t Kind, int DeviceNum, void *CodePtr); + ~OmptTarget(); +}; + +class OmptTargetSubmit { +private: + unsigned int RequestedNumTeams; + bool Active; + +public: + OmptTargetSubmit(unsigned int RequestedNumTeams); + ~OmptTargetSubmit(); +}; +#else + +#define OMPT_ARG(...) +#define OMPT_FIRST_ARG(...) + +#endif // OMPT_SUPPORT #endif // LIBOMPTARGET_OMPT_TARGET_H diff --git a/openmp/libomptarget/src/ompt-target.cpp b/openmp/libomptarget/src/ompt-target.cpp --- a/openmp/libomptarget/src/ompt-target.cpp +++ b/openmp/libomptarget/src/ompt-target.cpp @@ -1,3 +1,149 @@ #include "ompt-target.h" +#include "omptarget.h" -ompt_target_callbacks_active_t ompt_target_enabled; +ompt_target_callbacks_active_t OmptTargetEnabled; + +int HostDeviceNum; + +OmptTargetDataOp::OmptTargetDataOp(ompt_target_data_op_t OpType, void *SrcAddr, + int SrcDeviceNum, void *DestAddr, + int DestDeviceNum, size_t Bytes, + bool OmpRoutine, void *CodePtr) + : OpType(OpType), SrcAddr(SrcAddr), SrcDeviceNum(SrcDeviceNum), + DestAddr(DestAddr), DestDeviceNum(DestDeviceNum), Bytes(Bytes), + OmpRoutine(OmpRoutine), CodePtr(CodePtr) { + this->Active = OmptTargetEnabled.enabled && + OmptTargetEnabled.ompt_callback_target_data_op_emi; + if (Active) { + libomp_ompt_callback_target_data_op_emi( + ompt_scope_begin, OpType, SrcAddr, SrcDeviceNum, DestAddr, + DestDeviceNum, Bytes, OmpRoutine, CodePtr); + } +} + +OmptTargetDataOp::~OmptTargetDataOp() { + if (Active) { + libomp_ompt_callback_target_data_op_emi( + ompt_scope_end, OpType, SrcAddr, SrcDeviceNum, DestAddr, DestDeviceNum, + Bytes, OmpRoutine, CodePtr); + } +} + +void OmptTargetDataOp::setDestAddr(void *DestAddr) { + this->DestAddr = DestAddr; +} + +OmptTargetMapping::OmptTargetMapping(int Capacity, void *CodePtr) + : Capacity(Capacity), Size(0), CodePtr(CodePtr) { + this->Active = OmptTargetEnabled.enabled && + OmptTargetEnabled.ompt_callback_target_map_emi; + if (Active && Capacity) { + HostAddr = new void *[Capacity]; + DeviceAddr = new void *[Capacity]; + Bytes = new size_t[Capacity]; + MappingFlags = new unsigned int[Capacity]; + } else { + HostAddr = nullptr; + DeviceAddr = nullptr; + Bytes = nullptr; + MappingFlags = nullptr; + } +} + +OmptTargetMapping::~OmptTargetMapping() { + if (Active && Capacity) { + delete[] HostAddr; + delete[] DeviceAddr; + delete[] Bytes; + delete[] MappingFlags; + } +} + +// This function should only be invoked when capacity is non-zero +void OmptTargetMapping::addMapping(void *HstAddr, void *TgtAddr, size_t Byte, + int64_t ArgType, ConstructorType ConType) { + if (Active) { + // Calculate mapping_flag using arg_type + unsigned int Flag = 0; + if (ConType == TARGET) { + if (ArgType & OMP_TGT_MAPTYPE_TO) { + Flag |= ompt_target_map_flag_to; + } + if (ArgType & OMP_TGT_MAPTYPE_FROM) { + Flag |= ompt_target_map_flag_from; + } + if (!Flag) { + Flag |= ompt_target_map_flag_alloc; + } + } else if (ConType == TARGET_DATA_BEGIN) { + if (ArgType & OMP_TGT_MAPTYPE_TO) { + Flag |= ompt_target_map_flag_to; + } else { + Flag |= ompt_target_map_flag_alloc; + } + } else if (ConType == TARGET_DATA_END) { + if (ArgType & OMP_TGT_MAPTYPE_FROM) { + Flag |= ompt_target_map_flag_from; + } else if (ArgType & OMP_TGT_MAPTYPE_DELETE) { + Flag |= ompt_target_map_flag_delete; + } else { + Flag |= ompt_target_map_flag_release; + } + } + if (ArgType & OMP_TGT_MAPTYPE_IMPLICIT) { + Flag |= ompt_target_map_flag_implicit; + } + if (ArgType & OMP_TGT_MAPTYPE_ALWAYS) { + Flag |= ompt_target_map_flag_always; + } + if (ArgType & OMP_TGT_MAPTYPE_PRESENT) { + Flag |= ompt_target_map_flag_present; + } + if (ArgType & OMP_TGT_MAPTYPE_CLOSE) { + Flag |= ompt_target_map_flag_close; + } + + HostAddr[Size] = HstAddr; + DeviceAddr[Size] = TgtAddr; + Bytes[Size] = Byte; + MappingFlags[Size] = Flag; + Size += 1; + } +} + +void OmptTargetMapping::invokeCallback() { + if (Active) { + libomp_ompt_callback_target_map_emi(Size, HostAddr, DeviceAddr, Bytes, + MappingFlags, CodePtr); + } +} + +OmptTarget::OmptTarget(ompt_target_t Kind, int DeviceNum, void *CodePtr) + : Kind(Kind), DeviceNum(DeviceNum), CodePtr(CodePtr) { + this->Active = + OmptTargetEnabled.enabled && OmptTargetEnabled.ompt_callback_target_emi; + if (Active) { + libomp_ompt_callback_target_emi(Kind, ompt_scope_begin, DeviceNum, CodePtr); + } +} + +OmptTarget::~OmptTarget() { + if (Active) { + libomp_ompt_callback_target_emi(Kind, ompt_scope_end, DeviceNum, CodePtr); + } +} + +OmptTargetSubmit::OmptTargetSubmit(unsigned int RequestedNumTeams) + : RequestedNumTeams(RequestedNumTeams) { + this->Active = OmptTargetEnabled.enabled && + OmptTargetEnabled.ompt_callback_target_submit_emi; + if (Active) { + libomp_ompt_callback_target_submit_emi(ompt_scope_begin, RequestedNumTeams); + } +} + +OmptTargetSubmit::~OmptTargetSubmit() { + if (Active) { + libomp_ompt_callback_target_submit_emi(ompt_scope_end, RequestedNumTeams); + } +} diff --git a/openmp/libomptarget/src/rtl.cpp b/openmp/libomptarget/src/rtl.cpp --- a/openmp/libomptarget/src/rtl.cpp +++ b/openmp/libomptarget/src/rtl.cpp @@ -12,6 +12,7 @@ #include "rtl.h" #include "device.h" +#include "ompt-target.h" #include "private.h" #if OMPT_SUPPORT @@ -190,10 +191,10 @@ DP("Init OMPT for libomptarget\n"); if (libomp_start_tool) { DP("Retrieve libomp_start_tool successfully\n"); - if (!libomp_start_tool(&ompt_target_enabled)) { + if (!libomp_start_tool(&OmptTargetEnabled)) { DP("Turn off OMPT in libomptarget because libomp_start_tool returns " "false\n"); - memset(&ompt_target_enabled, 0, sizeof(ompt_target_enabled)); + memset(&OmptTargetEnabled, 0, sizeof(OmptTargetEnabled)); } } #endif @@ -396,6 +397,11 @@ PM->RTLsMtx.unlock(); DP("Done registering entries!\n"); +#if OMPT_SUPPORT + if (OmptTargetEnabled.enabled) { + HostDeviceNum = omp_get_initial_device(); + } +#endif } void RTLsTy::UnregisterLib(__tgt_bin_desc *desc) {