/**
* Copyright (C) Mellanox Technologies Ltd. 2001-2018. ALL RIGHTS RESERVED.
*
* See file LICENSE for terms.
*/
#ifndef UCS_PROFILE_ON_H_
#define UCS_PROFILE_ON_H_
#include "profile_defs.h"
#include <ucs/sys/compiler_def.h>
#include <ucs/sys/preprocessor.h>
#include <ucs/config/global_opts.h>
BEGIN_C_DECLS
/** @file profile_on.h */
/* Helper macro */
#define _UCS_PROFILE_RECORD(_type, _name, _param64, _param32, _loc_id_p) \
{ \
if (*(_loc_id_p) != 0) { \
ucs_profile_record((_type), (_name), (_param64), (_param32), \
__FILE__, __LINE__, __FUNCTION__, (_loc_id_p)); \
} \
}
/* Helper macro */
#define __UCS_PROFILE_CODE(_name, _loop_var) \
int _loop_var ; \
for (({ UCS_PROFILE_SCOPE_BEGIN(); _loop_var = 1;}); \
_loop_var; \
({ UCS_PROFILE_SCOPE_END(_name); _loop_var = 0;}))
/* Helper macro */
#define _UCS_PROFILE_CODE(_name, _var_suffix) \
__UCS_PROFILE_CODE(_name, UCS_PP_TOKENPASTE(loop, _var_suffix))
/**
* Record a profiling event.
*
* @param _type Event type.
* @param _name Event name.
* @param _param32 Custom 32-bit parameter.
* @param _param64 Custom 64-bit parameter.
*/
#define UCS_PROFILE(_type, _name, _param32, _param64) \
{ \
static int loc_id = -1; \
_UCS_PROFILE_RECORD((_type), (_name), (_param32), (_param64), &loc_id); \
}
/**
* Record a profiling sample event.
*
* @param _name Event name.
*/
#define UCS_PROFILE_SAMPLE(_name) \
UCS_PROFILE(UCS_PROFILE_TYPE_SAMPLE, (_name), 0, 0)
/**
* Record a scope-begin profiling event.
*/
#define UCS_PROFILE_SCOPE_BEGIN() \
{ \
UCS_PROFILE(UCS_PROFILE_TYPE_SCOPE_BEGIN, "", 0, 0); \
ucs_compiler_fence(); \
}
/**
* Record a scope-end profiling event.
*
* @param _name Scope name.
*/
#define UCS_PROFILE_SCOPE_END(_name) \
{ \
ucs_compiler_fence(); \
UCS_PROFILE(UCS_PROFILE_TYPE_SCOPE_END, _name, 0, 0); \
}
/**
* Declare a profiled scope of code.
*
* Usage:
* UCS_PROFILE_CODE(<name>) {
* <code>
* }
*
* @param _name Scope name.
*/
#define UCS_PROFILE_CODE(_name) \
_UCS_PROFILE_CODE(_name, UCS_PP_UNIQUE_ID)
/**
* Create a profiled function.
*
* Usage:
* UCS_PROFILE_FUNC(<retval>, <name>, (a, b), int a, char b)
*
* @param _ret_type Function return type.
* @param _name Function name.
* @param _arglist List of argument *names* only.
* @param ... Argument declarations (with types).
*/
#define UCS_PROFILE_FUNC(_ret_type, _name, _arglist, ...) \
static UCS_F_ALWAYS_INLINE _ret_type _name##_inner(__VA_ARGS__); \
\
_ret_type _name(__VA_ARGS__) { \
UCS_PROFILE_SCOPE_BEGIN(); \
_ret_type _ret = _name##_inner _arglist; \
UCS_PROFILE_SCOPE_END(#_name); \
return _ret; \
} \
static UCS_F_ALWAYS_INLINE _ret_type _name##_inner(__VA_ARGS__)
/**
* Create a profiled function whose return type is void.
*
* Usage:
* UCS_PROFILE_FUNC_VOID(<name>, (a, b), int a, char b)
*
* @param _name Function name.
* @param _arglist List of argument *names* only.
* @param ... Argument declarations (with types).
*/
#define UCS_PROFILE_FUNC_VOID(_name, _arglist, ...) \
static UCS_F_ALWAYS_INLINE void _name##_inner(__VA_ARGS__); \
\
void _name(__VA_ARGS__) { \
UCS_PROFILE_SCOPE_BEGIN(); \
_name##_inner _arglist; \
UCS_PROFILE_SCOPE_END(#_name); \
} \
static UCS_F_ALWAYS_INLINE void _name##_inner(__VA_ARGS__)
/*
* Profile a function call, and specify explicit name string for the profile.
* Useful when calling a function by a pointer.
*
* Usage:
* UCS_PROFILE_NAMED_CALL("name", function, arg1, arg2)
*
* @param _name Name string for the profile.
* @param _func Function name.
* @param ... Function call arguments.
*/
#define UCS_PROFILE_NAMED_CALL(_name, _func, ...) \
({ \
typeof(_func(__VA_ARGS__)) retval; \
UCS_PROFILE_SCOPE_BEGIN(); \
retval = _func(__VA_ARGS__); \
UCS_PROFILE_SCOPE_END(_name); \
retval; \
})
/*
* Profile a function call.
*
* Usage:
* UCS_PROFILE_CALL(function, arg1, arg2)
*
* @param _func Function name.
* @param ... Function call arguments.
*/
#define UCS_PROFILE_CALL(_func, ...) \
UCS_PROFILE_NAMED_CALL(#_func, _func, ## __VA_ARGS__)
/*
* Profile a function call which does not return a value, and specify explicit
* name string for the profile. Useful when calling a function by a pointer.
*
* Usage:
* UCS_PROFILE_NAMED_CALL_VOID("name", function, arg1, arg2)
*
* @param _name Name string for the profile.
* @param _func Function name.
* @param ... Function call arguments.
*/
#define UCS_PROFILE_NAMED_CALL_VOID(_name, _func, ...) \
{ \
UCS_PROFILE_SCOPE_BEGIN(); \
_func(__VA_ARGS__); \
UCS_PROFILE_SCOPE_END(_name); \
}
/*
* Profile a function call which does not return a value.
*
* Usage:
* UCS_PROFILE_CALL_VOID(function, arg1, arg2)
*
* @param _func Function name.
* @param ... Function call arguments.
*/
#define UCS_PROFILE_CALL_VOID(_func, ...) \
UCS_PROFILE_NAMED_CALL_VOID(#_func, _func, ## __VA_ARGS__)
/*
* Profile a new request allocation.
*
* @param _req Request pointer.
* @param _name Allocation site name.
* @param _param32 Custom 32-bit parameter.
*/
#define UCS_PROFILE_REQUEST_NEW(_req, _name, _param32) \
UCS_PROFILE(UCS_PROFILE_TYPE_REQUEST_NEW, (_name), (_param32), (uintptr_t)(_req));
/*
* Profile a request progress event.
*
* @param _req Request pointer.
* @param _name Event name.
* @param _param32 Custom 32-bit parameter.
*/
#define UCS_PROFILE_REQUEST_EVENT(_req, _name, _param32) \
UCS_PROFILE(UCS_PROFILE_TYPE_REQUEST_EVENT, (_name), (_param32), (uintptr_t)(_req));
/*
* Profile a request progress event with status check.
*
* @param _req Request pointer.
* @param _name Event name.
* @param _param32 Custom 32-bit parameter.
* @param _status Status of the last progress event.
*/
#define UCS_PROFILE_REQUEST_EVENT_CHECK_STATUS(_req, _name, _param32, _status) \
if (!UCS_STATUS_IS_ERR(_status)) { \
UCS_PROFILE_REQUEST_EVENT((_req), (_name), (_param32)); \
}
/*
* Profile a request release.
*
* @param _req Request pointer.
*/
#define UCS_PROFILE_REQUEST_FREE(_req) \
UCS_PROFILE(UCS_PROFILE_TYPE_REQUEST_FREE, "", 0, (uintptr_t)(_req));
/*
* Store a new record with the given data.
* SHOULD NOT be used directly - use UCS_PROFILE macros instead.
*
* @param [in] type Location type.
* @param [in] name Location name.
* @param [in] param32 custom 32-bit parameter.
* @param [in] param64 custom 64-bit parameter.
* @param [in] file Source file name.
* @param [in] line Source line number.
* @param [in] function Calling function name.
* @param [in,out] loc_id_p Variable used to maintain the location ID.
*/
void ucs_profile_record(ucs_profile_type_t type, const char *name,
uint32_t param32, uint64_t param64, const char *file,
int line, const char *function, volatile int *loc_id_p);
/**
* Reset the internal array of profiling locations.
* Used for testing purposes only.
*/
void ucs_profile_reset_locations();
END_C_DECLS
#endif