1/* See LICENSE file for copyright and license details. */
2
3
4#include <stdio.h>
5#include <stdlib.h>
6#include <string.h>
7#include <time.h>
8#include <utmpx.h>
9
10#include "config.h"
11#include "util.h"
12
13int get_uptime(long *);
14int get_loads(double *);
15
16static void
17usage(void)
18{
19 eprintf("usage: %s\n", argv0);
20}
21
22// ?man uptime: show system uptime
23// ?man display how long the system has been running and load averages
24int
25main(int argc, char *argv[])
26{
27 struct utmpx utx;
28 FILE *ufp;
29 long uptime;
30 double loads[3];
31 time_t tmptime;
32 struct tm *now;
33 unsigned int days, hours, minutes;
34 int nusers = 0;
35 size_t n;
36
37 ARGBEGIN {
38 default:
39 usage();
40 } ARGEND;
41
42 if (argc)
43 usage();
44
45 if (get_uptime(&uptime) < 0)
46 eprintf("get_uptime:");
47 if (get_loads(loads) < 0)
48 eprintf("get_loads:");
49
50 time(&tmptime);
51 now = localtime(&tmptime);
52 printf(" %02d:%02d:%02d up ", now->tm_hour, now->tm_min, now->tm_sec);
53
54 uptime /= 60;
55 minutes = uptime % 60;
56 uptime /= 60;
57 hours = uptime % 24;
58 days = uptime / 24;
59 if (days)
60 printf("%d day%s, ", days, days != 1 ? "s" : "");
61 if (hours)
62 printf("%2d:%02d, ", hours, minutes);
63 else
64 printf("%d min, ", minutes);
65
66 if ((ufp = fopen(UTMP_PATH, "r"))) {
67 while ((n = fread(&utx, sizeof(utx), 1, ufp)) > 0) {
68 if (!utx.ut_user[0])
69 continue;
70 if (utx.ut_type != USER_PROCESS)
71 continue;
72 nusers++;
73 }
74 if (ferror(ufp))
75 eprintf("%s: read error:", UTMP_PATH);
76 fclose(ufp);
77 printf(" %d user%s, ", nusers, nusers != 1 ? "s" : "");
78 }
79
80 printf(" load average: %.02f, %.02f, %.02f\n",
81 loads[0], loads[1], loads[2]);
82
83 if (fshut(stdin, "<stdin>") | fshut(stdout, "<stdout>"))
84 return 1;
85
86 return 0;
87}