apps.plugin optimization for per process open files accounting
Costa Tsaousis (ktsaou) committed
Jan 22, 2017 at 04:06 UTC
fe990a9b86896f47f197d8791f3a649f4148589b
1 file changed
+91
-90
src/apps_plugin.c
+91
-90
@@ -13,6 +13,8 @@
13
// etc.
14
#define RATES_DETAIL 10000ULL
15
16
+#define MAX_SPARE_FDS 10
17
+
18
int debug = 0;
19
20
int update_every = 1;
@@ -86,7 +88,9 @@ struct target {
88
unsigned long long io_storage_bytes_written;
89
// unsigned long long io_cancelled_write_bytes;
90
89
- int *fds;
91
+ int *target_fds;
92
+ int target_fds_size;
93
+
94
unsigned long long openfiles;
95
unsigned long long openpipes;
96
unsigned long long opensockets;
@@ -490,8 +494,8 @@ static inline struct pid_stat *get_pid_entry(pid_t pid) {
494
}
495
496
all_pids[pid] = callocz(sizeof(struct pid_stat), 1);
493
- all_pids[pid]->fds = callocz(sizeof(int), 100);
494
- all_pids[pid]->fds_size = 100;
497
+ all_pids[pid]->fds = callocz(sizeof(int), MAX_SPARE_FDS);
498
+ all_pids[pid]->fds_size = MAX_SPARE_FDS;
499
500
if(root_of_pids) root_of_pids->prev = all_pids[pid];
501
all_pids[pid]->next = root_of_pids;
@@ -1182,17 +1186,17 @@ static inline int read_pid_file_descriptors(struct pid_stat *p) {
1186
if(fdid >= p->fds_size) {
1187
// it is small, extend it
1188
if(unlikely(debug))
1185
- fprintf(stderr, "apps.plugin: extending fd memory slots for %s from %d to %d\n", p->comm, p->fds_size, fdid + 100);
1189
+ fprintf(stderr, "apps.plugin: extending fd memory slots for %s from %d to %d\n", p->comm, p->fds_size, fdid + MAX_SPARE_FDS);
1190
1187
- p->fds = reallocz(p->fds, (fdid + 100) * sizeof(int));
1191
+ p->fds = reallocz(p->fds, (fdid + MAX_SPARE_FDS) * sizeof(int));
1192
if(!p->fds) {
1193
fatal("Cannot re-allocate fds for %s", p->comm);
1194
break;
1195
}
1196
1197
// and initialize it
1194
- for(c = p->fds_size ; c < (fdid + 100) ; c++) p->fds[c] = 0;
1195
- p->fds_size = fdid + 100;
1198
+ for(c = p->fds_size ; c < (fdid + MAX_SPARE_FDS) ; c++) p->fds[c] = 0;
1199
+ p->fds_size = fdid + MAX_SPARE_FDS;
1200
}
1201
1202
if(p->fds[fdid] == 0) {
@@ -1914,9 +1918,6 @@ static long zero_all_targets(struct target *root) {
1918
for (w = root; w ; w = w->next) {
1919
count++;
1920
1917
- if(w->fds) freez(w->fds);
1918
- w->fds = NULL;
1919
-
1921
w->minflt = 0;
1922
w->majflt = 0;
1923
w->utime = 0;
@@ -1946,89 +1947,44 @@ static long zero_all_targets(struct target *root) {
1947
w->io_storage_bytes_read = 0;
1948
w->io_storage_bytes_written = 0;
1949
// w->io_cancelled_write_bytes = 0;
1950
+
1951
+ // zero file counters
1952
+ if(w->target_fds) {
1953
+ memset(w->target_fds, 0, sizeof(int) * w->target_fds_size);
1954
+ w->openfiles = 0;
1955
+ w->openpipes = 0;
1956
+ w->opensockets = 0;
1957
+ w->openinotifies = 0;
1958
+ w->openeventfds = 0;
1959
+ w->opentimerfds = 0;
1960
+ w->opensignalfds = 0;
1961
+ w->openeventpolls = 0;
1962
+ w->openother = 0;
1963
+ }
1964
}
1965
1966
return count;
1967
}
1968
1954
-static inline void aggregate_pid_on_target(struct target *w, struct pid_stat *p, struct target *o) {
1955
- (void)o;
1956
-
1957
- if(unlikely(!w->fds))
1958
- w->fds = callocz(sizeof(int), (size_t) all_files_size);
1959
-
1960
- if(likely(p->updated)) {
1961
- w->cutime += p->cutime;
1962
- w->cstime += p->cstime;
1963
- w->cgtime += p->cgtime;
1964
- w->cminflt += p->cminflt;
1965
- w->cmajflt += p->cmajflt;
1966
-
1967
- w->utime += p->utime;
1968
- w->stime += p->stime;
1969
- w->gtime += p->gtime;
1970
- w->minflt += p->minflt;
1971
- w->majflt += p->majflt;
1972
-
1973
- // w->rss += p->rss;
1974
-
1975
- w->statm_size += p->statm_size;
1976
- w->statm_resident += p->statm_resident;
1977
- w->statm_share += p->statm_share;
1978
- // w->statm_text += p->statm_text;
1979
- // w->statm_lib += p->statm_lib;
1980
- // w->statm_data += p->statm_data;
1981
- // w->statm_dirty += p->statm_dirty;
1982
-
1983
- w->io_logical_bytes_read += p->io_logical_bytes_read;
1984
- w->io_logical_bytes_written += p->io_logical_bytes_written;
1985
- // w->io_read_calls += p->io_read_calls;
1986
- // w->io_write_calls += p->io_write_calls;
1987
- w->io_storage_bytes_read += p->io_storage_bytes_read;
1988
- w->io_storage_bytes_written += p->io_storage_bytes_written;
1989
- // w->io_cancelled_write_bytes += p->io_cancelled_write_bytes;
1990
-
1991
- w->processes++;
1992
- w->num_threads += p->num_threads;
1993
-
1994
- if(likely(w->fds)) {
1995
- int c;
1996
- for(c = 0; c < p->fds_size ;c++) {
1997
- if(p->fds[c] == 0) continue;
1969
+static inline void reallocate_target_fds(struct target *w) {
1970
+ w->target_fds = reallocz(w->target_fds, sizeof(int) * all_files_size);
1971
+ memset(&w->target_fds[w->target_fds_size], 0, sizeof(int) * (all_files_size - w->target_fds_size));
1972
+ w->target_fds_size = all_files_size;
1973
+}
1974
1999
- if(likely(p->fds[c] < all_files_size)) {
2000
- if(w->fds) w->fds[p->fds[c]]++;
2001
- }
2002
- else
2003
- error("Invalid fd number %d", p->fds[c]);
2004
- }
2005
- }
1975
+static inline void aggregate_pid_fds_on_target(struct target *w, struct pid_stat *p) {
1976
+ if(unlikely(!w->target_fds || w->target_fds_size < all_files_size))
1977
+ reallocate_target_fds(w);
1978
2007
- if(unlikely(debug || w->debug))
2008
- fprintf(stderr, "apps.plugin: \taggregating '%s' pid %d on target '%s' utime=%llu, stime=%llu, gtime=%llu, cutime=%llu, cstime=%llu, cgtime=%llu, minflt=%llu, majflt=%llu, cminflt=%llu, cmajflt=%llu\n", p->comm, p->pid, w->name, p->utime, p->stime, p->gtime, p->cutime, p->cstime, p->cgtime, p->minflt, p->majflt, p->cminflt, p->cmajflt);
2009
- }
2010
-}
1979
+ int c, size = p->fds_size, *fds = p->fds;
1980
+ for(c = 0; c < size ;c++) {
1981
+ int fd = fds[c];
1982
2012
-static inline void count_targets_fds(struct target *root) {
2013
- int c;
2014
- struct target *w;
1983
+ if(likely(fd <= 0 || fd >= all_files_size))
1984
+ continue;
1985
2016
- for (w = root; w ; w = w->next) {
2017
- if(!w->fds) continue;
2018
-
2019
- w->openfiles = 0;
2020
- w->openpipes = 0;
2021
- w->opensockets = 0;
2022
- w->openinotifies = 0;
2023
- w->openeventfds = 0;
2024
- w->opentimerfds = 0;
2025
- w->opensignalfds = 0;
2026
- w->openeventpolls = 0;
2027
- w->openother = 0;
2028
-
2029
- for(c = 1; c < all_files_size ;c++) {
2030
- if(w->fds[c] > 0)
2031
- switch(all_files[c].type) {
1986
+ if(unlikely(!w->target_fds[fd])) {
1987
+ switch(all_files[fd].type) {
1988
case FILETYPE_FILE:
1989
w->openfiles++;
1990
break;
@@ -2065,9 +2021,51 @@ static inline void count_targets_fds(struct target *root) {
2021
w->openother++;
2022
}
2023
}
2024
+ w->target_fds[fd]++;
2025
+ }
2026
+}
2027
+
2028
+static inline void aggregate_pid_on_target(struct target *w, struct pid_stat *p, struct target *o) {
2029
+ (void)o;
2030
2069
- freez(w->fds);
2070
- w->fds = NULL;
2031
+ if(likely(p->updated)) {
2032
+ w->cutime += p->cutime;
2033
+ w->cstime += p->cstime;
2034
+ w->cgtime += p->cgtime;
2035
+ w->cminflt += p->cminflt;
2036
+ w->cmajflt += p->cmajflt;
2037
+
2038
+ w->utime += p->utime;
2039
+ w->stime += p->stime;
2040
+ w->gtime += p->gtime;
2041
+ w->minflt += p->minflt;
2042
+ w->majflt += p->majflt;
2043
+
2044
+ // w->rss += p->rss;
2045
+
2046
+ w->statm_size += p->statm_size;
2047
+ w->statm_resident += p->statm_resident;
2048
+ w->statm_share += p->statm_share;
2049
+ // w->statm_text += p->statm_text;
2050
+ // w->statm_lib += p->statm_lib;
2051
+ // w->statm_data += p->statm_data;
2052
+ // w->statm_dirty += p->statm_dirty;
2053
+
2054
+ w->io_logical_bytes_read += p->io_logical_bytes_read;
2055
+ w->io_logical_bytes_written += p->io_logical_bytes_written;
2056
+ // w->io_read_calls += p->io_read_calls;
2057
+ // w->io_write_calls += p->io_write_calls;
2058
+ w->io_storage_bytes_read += p->io_storage_bytes_read;
2059
+ w->io_storage_bytes_written += p->io_storage_bytes_written;
2060
+ // w->io_cancelled_write_bytes += p->io_cancelled_write_bytes;
2061
+
2062
+ w->processes++;
2063
+ w->num_threads += p->num_threads;
2064
+
2065
+ aggregate_pid_fds_on_target(w, p);
2066
+
2067
+ if(unlikely(debug || w->debug))
2068
+ fprintf(stderr, "apps.plugin: \taggregating '%s' pid %d on target '%s' utime=%llu, stime=%llu, gtime=%llu, cutime=%llu, cstime=%llu, cgtime=%llu, minflt=%llu, majflt=%llu, cminflt=%llu, cmajflt=%llu\n", p->comm, p->pid, w->name, p->utime, p->stime, p->gtime, p->cutime, p->cstime, p->cgtime, p->minflt, p->majflt, p->cminflt, p->cmajflt);
2069
}
2070
}
2071
@@ -2130,10 +2128,6 @@ static void calculate_netdata_statistics(void) {
2128
2129
}
2130
2133
- count_targets_fds(apps_groups_root_target);
2134
- count_targets_fds(users_root_target);
2135
- count_targets_fds(groups_root_target);
2136
-
2131
cleanup_exited_pids();
2132
}
2133
@@ -2882,10 +2876,17 @@ int main(int argc, char **argv)
2876
usec_t now = now_realtime_usec();
2877
usec_t next = now - (now % step) + step;
2878
2879
+#ifdef NETDATA_PROFILING
2880
+#warning "compiling for profiling"
2881
+ static int profiling_count=0;
2882
+ profiling_count++;
2883
+ if(unlikely(profiling_count > 1000)) exit(0);
2884
+#else
2885
while(now < next) {
2886
sleep_usec(next - now);
2887
now = now_realtime_usec();
2888
}
2889
+#endif
2890
2891
if(!collect_data_for_all_processes_from_proc()) {
2892
error("Cannot collect /proc data for running processes. Disabling apps.plugin...");