// Copyright (c) 1998 John Panzer. Permission is granted to // use, copy, modify, distribute, and sell this source code as // long as this copyright notice appears in all source files. #ifndef CALLMON_H_ #define CALLMON_H_ #include <string> #include <vector> class CallMonitor { public: typedef unsigned int ADDR; typedef __int64 TICKS; // Timing information CallMonitor(); // Thread-local singleton accessor static CallMonitor &threadObj(); static void threadAttach(CallMonitor *newObj); static void threadDetach(); // Called when a client function starts void enterProcedure(ADDR parentFramePtr,ADDR funcAddr, ADDR *retAddrPtr, const TICKS &entryTime); // Called when a client function exits void exitProcedure(ADDR parentFramePtr,ADDR *retAddrPtr, const TICKS &endTime); // Retrieves module and function name from address static void getFuncInfo(ADDR addr,std::string &moduleName, std::string &funcName); // Wrappers for system-dependent timing functions static inline void queryTicks(TICKS *t) { QueryPerformanceCounter((LARGE_INTEGER*)t); } static inline void queryTickFreq(TICKS *t) { QueryPerformanceFrequency((LARGE_INTEGER*)t); } protected: // Record for a single call struct CallInfo { ADDR funcAddr; // Function address ADDR parentFrame; // Parent stack frame address ADDR origRetAddr; // Function return address TICKS entryTime; // Time function was called TICKS startTime; // Time function started TICKS endTime; // Time function returned }; typedef std::vector<CallInfo> CallInfoStack; // Override to log entry events. virtual void logEntry(CallInfo &ci); // Override to log exit events. virtual void logExit(CallInfo &ci,bool normalRet); virtual ~CallMonitor(); // "Shadow" stack of active functions CallInfoStack callInfoStack; TICKS threadStartTime; // Time thread started private: static DWORD tlsSlot; }; #endif // CALLMON_H_ //End of File