include/tools/link.hxx | 61 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 61 insertions(+)
New commits: commit aad7bd5ede2b3088098df69f143a92799931fd58 Author: Ashod Nakashian <ashod.nakash...@collabora.co.uk> AuthorDate: Sun May 12 17:16:27 2019 -0400 Commit: Jan Holesovsky <ke...@collabora.com> CommitDate: Mon Jul 15 11:56:39 2019 +0200 Link: support tracing link source and target By adding a couple of members to Link, we are now able to trace the target function name and the file:line where the Link instance in question was created (provided the LINK macro is used). This gives the invaluable ability to track down the source of a Link instance in the debugger, provided we have enabled this feature, which is enabled in DBG_UTIL automatically, unless explicitly enabled. Of course it is also possible to judiciously add LOG/fprintf statements to chase this info, if not outright track all links, if so we wish, by dumping from Link::Call, or at construction time of Link. Change-Id: Iab1dce31a179d28aaa1f20228e9e0405973b5e9b Reviewed-on: https://gerrit.libreoffice.org/72208 Tested-by: Jenkins CollaboraOffice <jenkinscollaboraoff...@gmail.com> Reviewed-by: Jan Holesovsky <ke...@collabora.com> diff --git a/include/tools/link.hxx b/include/tools/link.hxx index 8b65be4755dd..63c3a08d6776 100644 --- a/include/tools/link.hxx +++ b/include/tools/link.hxx @@ -24,6 +24,19 @@ #include <sal/types.h> +/// Support tracing link source and target. +/// When debugging async events, it's often critical +/// to find out not only where a link leads (i.e. the target +/// function), but also where it was created (file:line). +/// This adds support to track this information and allow +/// for logging/printing, and introspecting in the debugger. +#ifndef TRACE_LINKS +# ifdef DBG_UTIL +# define TRACE_LINKS 1 +# include <cstdio> +# endif +#endif + #define DECL_LINK(Member, ArgType, RetType) \ static RetType LinkStub##Member(void *, ArgType); \ RetType Member(ArgType) @@ -67,18 +80,47 @@ RetType Class::Member( \ SAL_UNUSED_PARAMETER Class *, SAL_UNUSED_PARAMETER ArgType) +#if TRACE_LINKS +#define XSTRINGIFY(X) #X +#define STRINGIFY(X) XSTRINGIFY(X) +#define LINK(Instance, Class, Member) ::tools::detail::makeLink( \ + ::tools::detail::castTo<Class *>(Instance), &Class::LinkStub##Member, __FILE__, __LINE__, STRINGIFY(Class::LinkStub##Member)) +#else #define LINK(Instance, Class, Member) ::tools::detail::makeLink( \ ::tools::detail::castTo<Class *>(Instance), &Class::LinkStub##Member) +#endif template<typename Arg, typename Ret> class SAL_WARN_UNUSED Link { public: typedef Ret Stub(void *, Arg); +#if TRACE_LINKS + Link() + : function_(nullptr) + , instance_(nullptr) + , file_("unknown") + , line_(0) + , target_("unknown") + { + } + + Link(void* instance, Stub* function, const char* const file = "unknown", const int line = 0, + const char* const target = "unknown") + : function_(function) + , instance_(instance) + , file_(file) + , line_(line) + , target_(target) + { + } + +#else Link(): function_(nullptr), instance_(nullptr) {} Link(void * instance, Stub * function): function_(function), instance_(instance) {} +#endif Ret Call(Arg data) const { return function_ == nullptr ? Ret() : (*function_)(instance_, data); } @@ -103,9 +145,21 @@ public: void *GetInstance() const { return instance_; } +#if TRACE_LINKS + const char* getSourceFilename() const { return file_; } + int getSourceLineNumber() const { return line_; } + const char* getTargetName() const { return target_; } +#endif + private: Stub * function_; void * instance_; + +#if TRACE_LINKS + const char* file_; + int line_; + const char* target_; +#endif }; // Class used to indicate that the Call() parameter is not in use: @@ -118,10 +172,17 @@ namespace tools { namespace detail { template<typename To, typename From> To castTo(From from) { return static_cast<To>(from); } +#if TRACE_LINKS +template<typename Arg, typename Ret> +Link<Arg, Ret> makeLink(void * instance, Ret (* function)(void *, Arg), const char* file, int line, const char* target) { + return Link<Arg, Ret>(instance, function, file, line, target); +} +#else template<typename Arg, typename Ret> Link<Arg, Ret> makeLink(void * instance, Ret (* function)(void *, Arg)) { return Link<Arg, Ret>(instance, function); } +#endif } } _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/libreoffice-commits