1 /* -*- Mode: C; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ 2 /* 3 * This file is part of the LibreOffice project. 4 * 5 * This Source Code Form is subject to the terms of the Mozilla Public 6 * License, v. 2.0. If a copy of the MPL was not distributed with this 7 * file, You can obtain one at http://mozilla.org/MPL/2.0/. 8 */ 9 10 #include <sal/config.h> 11 12 #include <atomic> 13 14 #include <comphelper/sequence.hxx> 15 #include <comphelper/profilezone.hxx> 16 #include <osl/time.h> 17 #include <osl/thread.h> 18 19 namespace comphelper 20 { 21 22 std::atomic<bool> ProfileZone::g_bRecording(false); 23 24 namespace ProfileRecording 25 { 26 27 static std::vector<OUString> g_aRecording; // recorded data 28 static long long g_aSumTime(0); // overall zone time in microsec 29 static int g_aNesting; // level of overlapped zones 30 static long long g_aStartTime; // start time of recording 31 static ::osl::Mutex g_aMutex; 32 startRecording(bool bStartRecording)33void startRecording(bool bStartRecording) 34 { 35 if (bStartRecording) 36 { 37 TimeValue systemTime; 38 osl_getSystemTime( &systemTime ); 39 ::osl::MutexGuard aGuard( g_aMutex ); 40 g_aStartTime = static_cast<long long>(systemTime.Seconds) * 1000000 + systemTime.Nanosec/1000; 41 g_aNesting = 0; 42 } 43 ProfileZone::g_bRecording = bStartRecording; 44 } 45 addRecording(const char * aProfileId,long long aCreateTime)46long long addRecording(const char * aProfileId, long long aCreateTime) 47 { 48 assert( ProfileZone::g_bRecording ); 49 50 TimeValue systemTime; 51 osl_getSystemTime( &systemTime ); 52 long long aTime = static_cast<long long>(systemTime.Seconds) * 1000000 + systemTime.Nanosec/1000; 53 54 if (!aProfileId) 55 aProfileId = "(null)"; 56 OUString aString(aProfileId, strlen(aProfileId), RTL_TEXTENCODING_UTF8); 57 58 OUString sRecordingData(OUString::number(osl_getThreadIdentifier(nullptr)) + " " + 59 OUString::number(aTime/1000000.0) + " " + aString + ": " + 60 (aCreateTime == 0 ? OUStringLiteral("start") : OUStringLiteral("stop")) + 61 (aCreateTime != 0 ? (" " + OUString::number((aTime - aCreateTime)/1000.0) + " ms") : OUString(""))); 62 63 ::osl::MutexGuard aGuard( g_aMutex ); 64 65 g_aRecording.emplace_back(sRecordingData); 66 if (aCreateTime == 0) 67 { 68 g_aNesting++; 69 return aTime; 70 } 71 // neglect ProfileZones created before startRecording 72 else if (aCreateTime >= g_aStartTime) 73 { 74 if (g_aNesting > 0) 75 g_aNesting--; 76 if (g_aNesting == 0) 77 g_aSumTime += aTime - aCreateTime; 78 } 79 return 0; 80 } 81 getRecordingAndClear()82css::uno::Sequence<OUString> getRecordingAndClear() 83 { 84 bool bRecording; 85 std::vector<OUString> aRecording; 86 { 87 ::osl::MutexGuard aGuard( g_aMutex ); 88 bRecording = ProfileZone::g_bRecording; 89 startRecording(false); 90 aRecording.swap(g_aRecording); 91 long long aSumTime = g_aSumTime; 92 aRecording.insert(aRecording.begin(), OUString::number(aSumTime/1000000.0)); 93 } 94 // reset start time and nesting level 95 startRecording(bRecording); 96 return ::comphelper::containerToSequence(aRecording); 97 } 98 99 } // namespace ProfileRecording 100 101 102 } // namespace comphelper 103 104 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ 105