]> mj.ucw.cz Git - libucw.git/blob - lib/profile.c
Added a Poor Man's Profiler :-)
[libucw.git] / lib / profile.c
1 /*
2  *      Sherlock Library -- Poor Man's Profiler
3  *
4  *      (c) 2001 Martin Mares <mj@ucw.cz>
5  */
6
7 #include "lib/lib.h"
8 #include "lib/profile.h"
9
10 #include <stdio.h>
11
12 #ifdef CONFIG_PROFILE_TOD
13 #include <sys/time.h>
14
15 void
16 prof_init(prof_t *c)
17 {
18   c->sec = c->usec = 0;
19 }
20
21 void
22 prof_switch(prof_t *o, prof_t *n)
23 {
24   struct timeval tv;
25   gettimeofday(&tv, NULL);
26   if (n)
27     {
28       n->start_sec = tv.tv_sec;
29       n->start_usec = tv.tv_usec;
30     }
31   if (o)
32     {
33       o->sec += tv.tv_sec - o->start_sec;
34       o->usec += tv.tv_usec - o->start_usec;
35       if (o->usec < 0)
36         {
37           o->usec += 1000000;
38           o->sec++;
39         }
40       else while (o->usec >= 1000000)
41         {
42           o->usec -= 1000000;
43           o->sec--;
44         }
45     }
46 }
47
48 int
49 prof_format(char *buf, prof_t *c)
50 {
51   return sprintf(buf, "%d.%06d", c->sec, c->usec);
52 }
53 #endif
54
55 #ifdef CONFIG_PROFILE_TSC
56 void
57 prof_init(prof_t *c)
58 {
59   c->ticks = 0;
60 }
61
62 int
63 prof_format(char *buf, prof_t *c)
64 {
65   return sprintf(buf, "%Ld", c->ticks);
66 }
67 #endif
68
69 #ifdef CONFIG_PROFILE_KTSC
70 #include <fcntl.h>
71 #include <unistd.h>
72 static int self_prof_fd = -1;
73
74 void
75 prof_init(prof_t *c)
76 {
77   if (self_prof_fd < 0)
78     {
79       self_prof_fd = open("/proc/self/profile", O_RDONLY, 0);
80       if (self_prof_fd < 0)
81         die("Unable to open /proc/self/profile: %m");
82     }
83   c->ticks_user = 0;
84   c->ticks_sys = 0;
85 }
86
87 void
88 prof_switch(prof_t *o, prof_t *n)
89 {
90   u64 u, s;
91   byte buf[256];
92
93   int l = pread(self_prof_fd, buf, sizeof(buf)-1, 0);
94   ASSERT(l > 0 && l < (int)sizeof(buf)-1);
95   buf[l] = 0;
96   l = sscanf(buf, "%Ld%Ld", &u, &s);
97   ASSERT(l == 2);
98
99   if (n)
100     {
101       n->start_user = u;
102       n->start_sys = s;
103     }
104   if (o)
105     {
106       u -= o->start_user;
107       o->ticks_user += u;
108       s -= o->start_sys;
109       o->ticks_sys += s;
110     }
111 }
112
113 int
114 prof_format(char *buf, prof_t *c)
115 {
116   return sprintf(buf, "%Ld+%Ld", c->ticks_user, c->ticks_sys);
117 }
118 #endif