diff options
| author | ruki <[email protected]> | 2024-12-20 12:16:29 +0800 |
|---|---|---|
| committer | GitHub <[email protected]> | 2024-12-20 12:16:29 +0800 |
| commit | c8222c8a893e2e82c1f6fbb8f894fba24398f33a (patch) | |
| tree | b3e2c004c7c5deef2fea2fce366cd105dbcffd49 | |
| parent | ca53159567407c93e948c265fa9c36fbcb1752bc (diff) | |
| parent | 0b000b3edb52bc2b9b981f7208a4634df7d85d12 (diff) | |
Merge pull request #5993 from xmake-io/profile
Profile process perf
| -rw-r--r-- | xmake/core/base/os.lua | 71 | ||||
| -rw-r--r-- | xmake/core/base/profiler.lua | 2 |
2 files changed, 72 insertions, 1 deletions
diff --git a/xmake/core/base/os.lua b/xmake/core/base/os.lua index 6a1151e23..c1675196b 100644 --- a/xmake/core/base/os.lua +++ b/xmake/core/base/os.lua @@ -279,8 +279,48 @@ function os._is_tracing_process() return is_tracing end +-- profile process performance? +function os._is_profiling_process_perf() + local is_profiling = os._IS_PROFILING_PROCESS_PERF + if is_profiling == nil then + local profile = os.getenv("XMAKE_PROFILE") + if profile then + profile = profile:trim() + if profile == "perf:process" then + is_profiling = true + end + end + is_profiling = is_profiling or false + os._IS_PROFILING_PROCESS_PERF = is_profiling + end + return is_profiling +end + -- run all exit callback function os._run_exit_cbs(ok, errors) + + -- show process performance reports + local profileperf = os._is_profiling_process_perf() + if profileperf then + if os._PROCESS_PROFILEINFO then + local perfinfo = {} + local totaltime = 0 + for runcmd, profileinfo in pairs(os._PROCESS_PROFILEINFO) do + profileinfo.runcmd = runcmd + totaltime = totaltime + profileinfo.totaltime + table.insert(perfinfo, profileinfo) + end + table.sort(perfinfo, function (a, b) return a.totaltime > b.totaltime end) + for _, profileinfo in ipairs(perfinfo) do + local percent = (profileinfo.totaltime / totaltime) * 100 + if percent < 1 then + break + end + utils.print("%6.3f, %6.2f%%, %7d, %s", profileinfo.totaltime, percent, profileinfo.runcount, profileinfo.runcmd) + end + end + end + local exit_callbacks = os._EXIT_CALLBACKS if exit_callbacks then for _, cb in ipairs(exit_callbacks) do @@ -905,6 +945,13 @@ function os.execv(program, argv, opt) detach = opt.detach, exclusive = opt.exclusive} + -- profile process performance + local runtime + local profileperf = os._is_profiling_process_perf() + if profileperf then + runtime = os.mclock() + end + -- open command local ok = -1 local errors @@ -936,6 +983,30 @@ function os.execv(program, argv, opt) -- close process proc:close() + + -- save profile info + if profileperf then + runtime = os.mclock() - runtime + + local profileinfo = os._PROCESS_PROFILEINFO + if profileinfo == nil then + profileinfo = {} + os._PROCESS_PROFILEINFO = profileinfo + end + + local runcmd + runcmd = filename + if argv and #argv > 0 then + runcmd = runcmd .. " " .. os.args(argv) + end + local perfinfo = profileinfo[runcmd] + if perfinfo == nil then + perfinfo = {} + profileinfo[runcmd] = perfinfo + end + perfinfo.totaltime = (perfinfo.totaltime or 0) + runtime + perfinfo.runcount = (perfinfo.runcount or 0) + 1 + end else -- cannot execute process return nil, os.strerror() diff --git a/xmake/core/base/profiler.lua b/xmake/core/base/profiler.lua index 331f02c5e..ae0ced4fc 100644 --- a/xmake/core/base/profiler.lua +++ b/xmake/core/base/profiler.lua @@ -247,7 +247,7 @@ function profiler:leave(name, ...) end end --- get profiler mode, e.g. perf:call, perf:tag, trace +-- get profiler mode, e.g. perf:call, perf:tag, perf:process, trace function profiler:mode() local mode = self._MODE if mode == nil then |
