xref: /f-stack/tools/top/top.c (revision 73bdce41)
1 #include<unistd.h>
2 #include "ff_ipc.h"
3 
4 void
5 usage(void)
6 {
7     printf("Usage:\n");
8     printf("  top [-p <f-stack proc_id>] [-P <max proc_id>] "
9         "[-d <secs>] [-n <num>]\n");
10 }
11 
12 int cpu_status(struct ff_top_args *top)
13 {
14     int            ret;
15     struct ff_msg *msg, *retmsg = NULL;
16 
17     msg = ff_ipc_msg_alloc();
18     if (msg == NULL) {
19         errno = ENOMEM;
20         return -1;
21     }
22 
23     msg->msg_type = FF_TOP;
24     ret = ff_ipc_send(msg);
25     if (ret < 0) {
26         errno = EPIPE;
27         ff_ipc_msg_free(msg);
28         return -1;
29     }
30 
31     do {
32         if (retmsg != NULL) {
33             ff_ipc_msg_free(retmsg);
34         }
35 
36         ret = ff_ipc_recv(&retmsg, msg->msg_type);
37         if (ret < 0) {
38             errno = EPIPE;
39             return -1;
40         }
41     } while (msg != retmsg);
42 
43     *top = retmsg->top;
44 
45     ff_ipc_msg_free(msg);
46 
47     return 0;
48 }
49 
50 int main(int argc, char **argv)
51 {
52     int ch, delay = 1, n = 0;
53     unsigned int i, j;
54     struct ff_top_args top, otop;
55     struct ff_top_args ptop[RTE_MAX_LCORE], potop[RTE_MAX_LCORE];
56     int proc_id = 0, max_proc_id = -1;
57     float sys, usr, idle;
58     float psys, pusr, pidle;
59     unsigned long loops, ploops;
60 
61     ff_ipc_init();
62 
63 #define TOP_DIFF(member) (top.member - otop.member)
64 #define TOP_DIFF_P(member) (ptop[j].member - potop[j].member)
65 
66     while ((ch = getopt(argc, argv, "hp:P:d:n:")) != -1) {
67         switch(ch) {
68         case 'p':
69             proc_id = atoi(optarg);
70             ff_set_proc_id(proc_id);
71             break;
72         case 'P':
73             max_proc_id = atoi(optarg);
74             if (max_proc_id < 0 || max_proc_id >= RTE_MAX_LCORE) {
75                 usage();
76                 ff_ipc_exit();
77                 return -1;
78             }
79             break;
80         case 'd':
81             delay = atoi(optarg) ?: 1;
82             break;
83         case 'n':
84             n = atoi(optarg);
85             break;
86         case 'h':
87         default:
88             usage();
89             ff_ipc_exit();
90             return -1;
91         }
92     }
93 
94     for (i = 0; ; i++) {
95         if (max_proc_id == -1) {
96             if (cpu_status(&top)) {
97                 printf("fstack ipc message error !\n");
98                 ff_ipc_exit();
99                 return -1;
100             }
101 
102             if (i % 40 == 0) {
103                 printf("|---------|---------|---------|---------------|\n");
104                 printf("|%9s|%9s|%9s|%15s|\n", "idle", "sys", "usr", "loop");
105                 printf("|---------|---------|---------|---------------|\n");
106             }
107 
108             if (i) {
109                 sys = TOP_DIFF(sys_tsc) / (TOP_DIFF(work_tsc) / 100.0);
110                 usr = TOP_DIFF(usr_tsc) / (TOP_DIFF(work_tsc) / 100.0);
111                 idle = TOP_DIFF(idle_tsc) / (TOP_DIFF(work_tsc) / 100.0);
112 
113                 printf("|%8.2f%%|%8.2f%%|%8.2f%%|%15lu|\n",
114                     idle, sys, usr, TOP_DIFF(loops));
115             }
116         }else {
117             /*
118              * get and show cpu usage from proc_id to max_proc_id.
119              */
120             if (i % (40 / (max_proc_id - proc_id + 2)) == 0) {
121                 printf("|---------|---------|---------|"
122                     "---------|---------------|\n");
123                 printf("|%9s|%9s|%9s|%9s|%15s|\n",
124                     "proc_id", "idle", "sys", "usr", "loop");
125                 printf("|---------|---------|---------|"
126                     "---------|---------------|\n");
127             }
128 
129             sys = usr = idle = loops = 0;
130             for (j = proc_id; j <= max_proc_id; j++) {
131                 potop[j] = ptop[j];
132 
133                 ff_set_proc_id(j);
134                 if (cpu_status(&ptop[j])) {
135                     printf("fstack ipc message error, proc id:%d!\n", j);
136                     ff_ipc_exit();
137                     return -1;
138                 }
139 
140                 if (i) {
141                     psys = TOP_DIFF_P(sys_tsc) / \
142                         (TOP_DIFF_P(work_tsc) / 100.0);
143                     pusr = TOP_DIFF_P(usr_tsc) / \
144                         (TOP_DIFF_P(work_tsc) / 100.0);
145                     pidle = TOP_DIFF_P(idle_tsc) / \
146                         (TOP_DIFF_P(work_tsc) / 100.0);
147                     ploops = TOP_DIFF_P(loops);
148                     printf("|%9d|%8.2f%%|%8.2f%%|%8.2f%%|%15lu|\n",
149                         j, pidle, psys, pusr, ploops);
150 
151                     sys += psys;
152                     usr += pusr;
153                     idle += pidle;
154                     loops += ploops;
155 
156                     if (j == max_proc_id) {
157                         printf("|%9s|%8.2f%%|%8.2f%%|%8.2f%%|%15lu|\n",
158                             "total", idle, sys, usr, loops);
159                         printf("|         |         |         |"
160                             "         |               |\n");
161                     }
162                 }
163             }
164         }
165 
166         if (n && i >= n) {
167             break;
168         }
169 
170         otop = top;
171         sleep(delay);
172     }
173 
174     ff_ipc_exit();
175 
176     return 0;
177 }
178