report-json-serializer: app and top serializers
[apps/native/ttsd-worker-task.git] / src / stats.c
1 /*
2  * Copyright (c) 2018 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Flora License, Version 1.1 (the License);
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://floralicense.org/license/
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an AS IS BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 #include "stats.h"
18 #include "procfs.h"
19 #include "err-check.h"
20
21 static int ncpus;
22
23 int stats_get_system_cpu_usage_average(struct stats_system *previous, struct stats_system *current, float *usage)
24 {
25         struct stats_system diff;
26
27         diff.busy_ticks = current->busy_ticks > previous->busy_ticks ? current->busy_ticks - previous->busy_ticks : 0;
28
29         diff.total_ticks = current->total_ticks > previous->total_ticks ? current->total_ticks - previous->total_ticks : 0;
30
31         if (diff.total_ticks == 0) {
32                 *usage = 0;
33         } else {
34                 *usage = (float)diff.busy_ticks / diff.total_ticks;
35         }
36
37         return 0;
38 }
39
40 int stats_update_system_stats(struct stats_system *sys)
41 {
42         ON_NULL_RETURN_VAL(sys, -1);
43
44         struct procfs_system_cpu_usage_info info;
45
46         if (procfs_read_system_cpu_usage(&info) != 0) {
47                 return -1;
48         }
49
50         sys->busy_ticks = info.user + info.system + info.nice + info.irq + info.softirq;
51         sys->total_ticks = info.user + info.system + info.nice + info.irq + info.softirq + info.idle + info.iowait;
52
53         return 0;
54 }
55
56 int stats_get_system_memory_usage(float *usage)
57 {
58         ON_NULL_RETURN_VAL(usage, -1);
59
60         struct procfs_system_memory_usage_info info;
61
62         if (procfs_read_system_memory_usage(&info) != 0) {
63                 ERR("procfs_read_system_memory_usage failed.");
64                 return -1;
65         }
66
67         *usage = (float)info.used / info.total;
68
69         return 0;
70 }
71
72 int stats_update_process_stats(int pid, struct stats_process *stats)
73 {
74         ON_TRUE_RETURN_VAL(pid < 0, -1);
75         ON_NULL_RETURN_VAL(stats, -1);
76
77         struct procfs_process_cpu_usage_info proc_info;
78         struct procfs_system_cpu_usage_info sys_info;
79
80         if (procfs_read_process_cpu_usage(pid, &proc_info) != 0) {
81                 ERR("procfs_read_process_cpu_usage failed.");
82                 return -1;
83         }
84
85         if (procfs_read_system_cpu_usage(&sys_info) != 0) {
86                 ERR("procfs_read_system_cpu_usage failed.");
87                 return -1;
88         }
89
90         stats->process_ticks = proc_info.stime + proc_info.utime;
91         stats->system_ticks = sys_info.user + sys_info.system + sys_info.nice + sys_info.idle;
92
93
94         return 0;
95 }
96
97 int stats_get_process_cpu_usage_average(struct stats_process *previous, struct stats_process *current, float *usage)
98 {
99         struct stats_process diff;
100
101         diff.process_ticks = current->process_ticks > previous->process_ticks ? current->process_ticks - previous->process_ticks: 0;
102         diff.system_ticks = current->system_ticks > previous->system_ticks ? current->system_ticks - previous->system_ticks : 0;
103
104         if (diff.system_ticks == 0)
105                 *usage = 0;
106         else
107                 *usage = (float)diff.process_ticks / diff.system_ticks * ncpus;
108
109         return 0;
110 }
111
112 int stats_get_process_memory_usage(int pid, float *usage)
113 {
114         ON_TRUE_RETURN_VAL(pid < 0, -1);
115         ON_NULL_RETURN_VAL(usage, -1);
116
117         struct procfs_process_memory_usage_info mem_info;
118         struct procfs_system_memory_usage_info sys_info;
119
120         if (procfs_read_process_memory_usage(pid, &mem_info) != 0) {
121                 ERR("procfs_read_process_memory_usage failed.");
122                 return -1;
123         }
124
125         if (procfs_read_system_memory_usage(&sys_info) != 0) {
126                 ERR("procfs_read_system_memory_usage failed.");
127                 return -1;
128         }
129
130         *usage = sys_info.total > 0 ? (float)mem_info.rss / sys_info.total : 0;
131
132         return 0;
133 }
134
135 int stats_get_load_averages(float *a1, float *a5, float *a15)
136 {
137         struct procfs_load_average_info info;
138
139         if (procfs_read_system_load_average(&info) != 0) {
140                 ERR("procfs_read_system_load_average failed.");
141                 return -1;
142         }
143
144         if (a1) *a1 = info.one_min_avg;
145         if (a5) *a5 = info.five_min_avg;
146         if (a15) *a15 = info.fifteen_min_avg;
147
148         return 0;
149 }
150
151 int stats_init()
152 {
153         if (procfs_read_cpu_count(&ncpus) != 0) {
154                 ERR("procfs_read_cpu_count failed.");
155                 return -1;
156         }
157         return 0;
158 }