]> git.ipfire.org Git - thirdparty/util-linux.git/blob - schedutils/ionice.c
ionice: cleanup error messages, add NLS support
[thirdparty/util-linux.git] / schedutils / ionice.c
1 /*
2 * ionice: set or get process io scheduling class and priority
3 *
4 * Copyright (C) 2005 Jens Axboe <axboe@suse.de> SUSE Labs
5 *
6 * Released under the terms of the GNU General Public License version 2
7 *
8 */
9 #include <stdio.h>
10 #include <stdlib.h>
11 #include <errno.h>
12 #include <getopt.h>
13 #include <unistd.h>
14 #include <sys/ptrace.h>
15 #include <sys/syscall.h>
16 #include <asm/unistd.h>
17 #include <err.h>
18
19 #include "nls.h"
20
21 static inline int ioprio_set(int which, int who, int ioprio)
22 {
23 return syscall(SYS_ioprio_set, which, who, ioprio);
24 }
25
26 static inline int ioprio_get(int which, int who)
27 {
28 return syscall(SYS_ioprio_get, which, who);
29 }
30
31 enum {
32 IOPRIO_CLASS_NONE,
33 IOPRIO_CLASS_RT,
34 IOPRIO_CLASS_BE,
35 IOPRIO_CLASS_IDLE,
36 };
37
38 enum {
39 IOPRIO_WHO_PROCESS = 1,
40 IOPRIO_WHO_PGRP,
41 IOPRIO_WHO_USER,
42 };
43
44 #define IOPRIO_CLASS_SHIFT 13
45
46 const char *to_prio[] = { "none", "realtime", "best-effort", "idle", };
47
48 static void usage(int rc)
49 {
50 fprintf(stdout, _(
51 "\nionice - sets or gets process io scheduling class and priority.\n\n"
52 "Usage: ionice [OPTIONS] [COMMAND [ARG]...]\n\n"
53 " -n <classdata> class data (0-7, lower being higher prio)\n"
54 " -c <class> scheduling class\n"
55 " 1: realtime, 2: best-effort, 3: idle\n"
56 " -p <pid> process pid\n"
57 " -t ignore failures, run command unconditionally\n"
58 " -h this help\n\n"));
59
60 exit(rc);
61 }
62
63 int main(int argc, char *argv[])
64 {
65 int ioprio = 4, set = 0, tolerant = 0, ioprio_class = IOPRIO_CLASS_BE;
66 int c, pid = 0;
67
68 setlocale(LC_ALL, "");
69 bindtextdomain(PACKAGE, LOCALEDIR);
70 textdomain(PACKAGE);
71
72 while ((c = getopt(argc, argv, "+n:c:p:th")) != EOF) {
73 switch (c) {
74 case 'n':
75 ioprio = strtol(optarg, NULL, 10);
76 set |= 1;
77 break;
78 case 'c':
79 ioprio_class = strtol(optarg, NULL, 10);
80 set |= 2;
81 break;
82 case 'p':
83 pid = strtol(optarg, NULL, 10);
84 break;
85 case 't':
86 tolerant = 1;
87 break;
88 case 'h':
89 usage(EXIT_SUCCESS);
90 default:
91 usage(EXIT_FAILURE);
92 }
93 }
94
95 switch (ioprio_class) {
96 case IOPRIO_CLASS_NONE:
97 ioprio_class = IOPRIO_CLASS_BE;
98 break;
99 case IOPRIO_CLASS_RT:
100 case IOPRIO_CLASS_BE:
101 break;
102 case IOPRIO_CLASS_IDLE:
103 if (set & 1)
104 warnx(_("ignoring given class data for idle class"));
105 ioprio = 7;
106 break;
107 default:
108 errx(EXIT_FAILURE, _("bad prio class %d"), ioprio_class);
109 }
110
111 if (!set) {
112 if (!pid && argv[optind])
113 pid = strtol(argv[optind], NULL, 10);
114
115 ioprio = ioprio_get(IOPRIO_WHO_PROCESS, pid);
116
117 if (ioprio == -1)
118 err(EXIT_FAILURE, _("ioprio_get failed"));
119 else {
120 ioprio_class = ioprio >> IOPRIO_CLASS_SHIFT;
121 if (ioprio_class != IOPRIO_CLASS_IDLE) {
122 ioprio = ioprio & 0xff;
123 printf("%s: prio %d\n", to_prio[ioprio_class], ioprio);
124 } else
125 printf("%s\n", to_prio[ioprio_class]);
126 }
127 } else {
128 if (ioprio_set(IOPRIO_WHO_PROCESS, pid, ioprio | ioprio_class << IOPRIO_CLASS_SHIFT) == -1) {
129 if (!tolerant)
130 err(EXIT_FAILURE, _("ioprio_set failed"));
131 }
132
133 if (argv[optind]) {
134 execvp(argv[optind], &argv[optind]);
135 /* execvp should never return */
136 err(EXIT_FAILURE, _("execvp failed"));
137 }
138 }
139
140 exit(EXIT_SUCCESS);
141 }