1 (* Copyright (C) Doom 2D: Forever Developers
2 *
3 * This program is free software: you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation, either version 3 of the License, or
6 * (at your option) any later version.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 *)
16 // stopwatch timer to measure short periods (like frame rendering phases)
17 {$INCLUDE a_modes.inc}
18 {.$DEFINE XPROFILER_SLOW_AVERAGE}
21 interface
23 uses
24 SysUtils,
25 {$IF DEFINED(LINUX) OR DEFINED(ANDROID)}
26 {$DEFINE STOPWATCH_IS_HERE}
27 unixtype, linux
28 {$ELSEIF DEFINED(WINDOWS)}
29 {$DEFINE STOPWATCH_IS_HERE}
30 Windows
31 {$ELSEIF DEFINED(HAIKU)}
32 {$DEFINE STOPWATCH_IS_HERE}
33 unixtype
34 {$ELSE}
35 {$IFDEF STOPWATCH_IS_HERE}
36 {$UNDEF STOPWATCH_IS_HERE}
37 {$ENDIF}
38 {$WARNING You suck!}
39 {$ENDIF}
40 ;
42 {$IF DEFINED(STOPWATCH_IS_HERE)}
43 type
45 strict private
50 strict private
56 public
60 public
64 // the following is like start/stop, but doesn't reset elapsed time
72 {$ENDIF}
75 const
78 type
80 private
81 //const FilterFadeoff = 0.05; // 5%
83 private
86 //curval: Single;
92 private
98 public
109 private
110 {$IF DEFINED(STOPWATCH_IS_HERE)}
111 type
120 var
125 {$ENDIF}
127 public
132 public
136 // call this on frame start
138 // call this on frame end
144 // this will reuse the section with the given name (if there is any); use `sectionEnd()` to end it as usual
153 implementation
155 {$IF DEFINED(LINUX)}
157 {$ELSE}
159 {$ENDIF}
161 var
166 // ////////////////////////////////////////////////////////////////////////// //
168 var
170 begin
172 begin
173 {$IF DEFINED(LINUX)}
174 if (clock_getres(CLOCK_MONOTONIC, @r) <> 0) then raise Exception.Create('profiler error: cannot get timer resolution');
179 {$ELSEIF DEFINED(WINDOWS)}
183 {$ENDIF}
189 var
191 begin
192 //if (mFrequency = 0) then initTimerIntr();
193 {$IF DEFINED(LINUX)}
196 {$ELSEIF DEFINED(WINDOWS)}
199 {$ENDIF}
204 begin
209 // ////////////////////////////////////////////////////////////////////////// //
211 begin
217 begin
224 var
226 begin
235 begin
242 begin
249 begin
257 begin
266 begin
274 begin
280 begin
286 // ////////////////////////////////////////////////////////////////////////// //
287 procedure TProfilerBar.initialize (aHistSize: Integer); begin SetLength(history, aHistSize); hisLast := -1; curAccum := 0; curAccumCount := 0; end;
290 var
292 begin
294 if (hisLast = -1) then begin hisLast := High(history); curAccum := 0; curAccumCount := 0; for idx := 0 to High(history) do history[idx] := val; end;
295 if (curAccumCount = Length(history)) then Dec(curAccum, UInt64(history[(hisLast+1) mod Length(history)])) else Inc(curAccumCount);
300 //curval := FilterFadeoff*val+(1.0-FilterFadeoff)*curval;
304 {$IFDEF XPROFILER_SLOW_AVERAGE}
306 {$ENDIF}
307 begin
308 {$IFDEF XPROFILER_SLOW_AVERAGE}
312 {$ELSE}
313 //result := round(curval);
315 {$ENDIF}
321 begin
322 if (idx < 0) or (idx >= Length(history)) then result := 0 else result := history[(hisLast-idx+Length(history)*2) mod Length(history)];
326 // ////////////////////////////////////////////////////////////////////////// //
328 begin
334 {$IF DEFINED(STOPWATCH_IS_HERE)}
339 {$ENDIF}
344 var
346 begin
349 {$IF DEFINED(STOPWATCH_IS_HERE)}
351 {$ENDIF}
357 begin
358 {$IF DEFINED(STOPWATCH_IS_HERE)}
363 {$ENDIF}
367 {$IF DEFINED(STOPWATCH_IS_HERE)}
368 var
373 var
375 begin
377 begin
379 begin
387 {$ENDIF}
388 begin
389 {$IF DEFINED(STOPWATCH_IS_HERE)}
393 begin
394 // first time?
396 begin
397 //if (length(bars) <> 0) then raise Exception.Create('FUUUUUUUUUUUUUUU');
400 begin
409 // update bars
412 begin
416 //bars[0].update(xptimer.elapsedMicro);
418 end
419 else
420 begin
422 begin
430 {$ENDIF}
434 {$IF DEFINED(STOPWATCH_IS_HERE)}
435 var
438 {$ENDIF}
439 begin
440 {$IF DEFINED(STOPWATCH_IS_HERE)}
450 // calculate level
454 {$ENDIF}
458 {$IF DEFINED(STOPWATCH_IS_HERE)}
459 var
461 {$ENDIF}
462 begin
463 {$IF DEFINED(STOPWATCH_IS_HERE)}
466 begin
468 begin
470 begin
472 if (xpsecs[idx].prevAct <> -1) then raise Exception.Create('profiler error(1): double resume: "'+aName+'"');
476 exit;
481 {$ENDIF}
485 {$IF DEFINED(STOPWATCH_IS_HERE)}
486 var
488 {$ENDIF}
489 begin
490 {$IF DEFINED(STOPWATCH_IS_HERE)}
495 // go back to parent
498 {$ENDIF}
502 begin