xref: /openbmc/linux/fs/proc/loadavg.c (revision 5b3acc8d)
15b3acc8dSAlexey Dobriyan #include <linux/fs.h>
25b3acc8dSAlexey Dobriyan #include <linux/init.h>
35b3acc8dSAlexey Dobriyan #include <linux/pid_namespace.h>
45b3acc8dSAlexey Dobriyan #include <linux/proc_fs.h>
55b3acc8dSAlexey Dobriyan #include <linux/sched.h>
65b3acc8dSAlexey Dobriyan #include <linux/seq_file.h>
75b3acc8dSAlexey Dobriyan #include <linux/seqlock.h>
85b3acc8dSAlexey Dobriyan #include <linux/time.h>
95b3acc8dSAlexey Dobriyan 
105b3acc8dSAlexey Dobriyan #define LOAD_INT(x) ((x) >> FSHIFT)
115b3acc8dSAlexey Dobriyan #define LOAD_FRAC(x) LOAD_INT(((x) & (FIXED_1-1)) * 100)
125b3acc8dSAlexey Dobriyan 
135b3acc8dSAlexey Dobriyan static int loadavg_proc_show(struct seq_file *m, void *v)
145b3acc8dSAlexey Dobriyan {
155b3acc8dSAlexey Dobriyan 	int a, b, c;
165b3acc8dSAlexey Dobriyan 	unsigned long seq;
175b3acc8dSAlexey Dobriyan 
185b3acc8dSAlexey Dobriyan 	do {
195b3acc8dSAlexey Dobriyan 		seq = read_seqbegin(&xtime_lock);
205b3acc8dSAlexey Dobriyan 		a = avenrun[0] + (FIXED_1/200);
215b3acc8dSAlexey Dobriyan 		b = avenrun[1] + (FIXED_1/200);
225b3acc8dSAlexey Dobriyan 		c = avenrun[2] + (FIXED_1/200);
235b3acc8dSAlexey Dobriyan 	} while (read_seqretry(&xtime_lock, seq));
245b3acc8dSAlexey Dobriyan 
255b3acc8dSAlexey Dobriyan 	seq_printf(m, "%d.%02d %d.%02d %d.%02d %ld/%d %d\n",
265b3acc8dSAlexey Dobriyan 		LOAD_INT(a), LOAD_FRAC(a),
275b3acc8dSAlexey Dobriyan 		LOAD_INT(b), LOAD_FRAC(b),
285b3acc8dSAlexey Dobriyan 		LOAD_INT(c), LOAD_FRAC(c),
295b3acc8dSAlexey Dobriyan 		nr_running(), nr_threads,
305b3acc8dSAlexey Dobriyan 		task_active_pid_ns(current)->last_pid);
315b3acc8dSAlexey Dobriyan 	return 0;
325b3acc8dSAlexey Dobriyan }
335b3acc8dSAlexey Dobriyan 
345b3acc8dSAlexey Dobriyan static int loadavg_proc_open(struct inode *inode, struct file *file)
355b3acc8dSAlexey Dobriyan {
365b3acc8dSAlexey Dobriyan 	return single_open(file, loadavg_proc_show, NULL);
375b3acc8dSAlexey Dobriyan }
385b3acc8dSAlexey Dobriyan 
395b3acc8dSAlexey Dobriyan static const struct file_operations loadavg_proc_fops = {
405b3acc8dSAlexey Dobriyan 	.open		= loadavg_proc_open,
415b3acc8dSAlexey Dobriyan 	.read		= seq_read,
425b3acc8dSAlexey Dobriyan 	.llseek		= seq_lseek,
435b3acc8dSAlexey Dobriyan 	.release	= single_release,
445b3acc8dSAlexey Dobriyan };
455b3acc8dSAlexey Dobriyan 
465b3acc8dSAlexey Dobriyan static int __init proc_loadavg_init(void)
475b3acc8dSAlexey Dobriyan {
485b3acc8dSAlexey Dobriyan 	proc_create("loadavg", 0, NULL, &loadavg_proc_fops);
495b3acc8dSAlexey Dobriyan 	return 0;
505b3acc8dSAlexey Dobriyan }
515b3acc8dSAlexey Dobriyan module_init(proc_loadavg_init);
52