blob: c8fb1a7778ed9cf57f7a0913c368d2578c0a71a4 [file] [log] [blame]
Denis Vlasenko4acdb462009-01-31 21:45:57 +00001/* vi: set sw=4 ts=4: */
2/*
3 * ionice implementation for busybox based on linux-utils-ng 2.14
4 *
5 * Copyright (C) 2008 by <u173034@informatik.uni-oldenburg.de>
6 *
Denys Vlasenko0ef64bd2010-08-16 20:14:46 +02007 * Licensed under GPLv2 or later, see file LICENSE in this source tree.
Denis Vlasenko4acdb462009-01-31 21:45:57 +00008 */
Denys Vlasenkofb4da162016-11-22 23:14:24 +01009//config:config IONICE
Denys Vlasenkob097a842018-12-28 03:20:17 +010010//config: bool "ionice (3.8 kb)"
Denys Vlasenkofb4da162016-11-22 23:14:24 +010011//config: default y
Denys Vlasenkofb4da162016-11-22 23:14:24 +010012//config: help
Denys Vlasenko72089cf2017-07-21 09:50:55 +020013//config: Set/set program io scheduling class and priority
14//config: Requires kernel >= 2.6.13
Denis Vlasenko4acdb462009-01-31 21:45:57 +000015
Denys Vlasenko5c527dc2017-08-04 19:55:01 +020016//applet:IF_IONICE(APPLET_NOEXEC(ionice, ionice, BB_DIR_BIN, BB_SUID_DROP, ionice))
Denys Vlasenkof88e3bf2016-11-22 23:54:17 +010017
18//kbuild:lib-$(CONFIG_IONICE) += ionice.o
19
Pere Orga5bc8c002011-04-11 03:29:49 +020020//usage:#define ionice_trivial_usage
Denys Vlasenkoa2f18d92020-12-18 04:12:51 +010021//usage: "[-c 1-3] [-n 0-7] [-p PID] [PROG ARGS]"
Pere Orga5bc8c002011-04-11 03:29:49 +020022//usage:#define ionice_full_usage "\n\n"
23//usage: "Change I/O priority and class\n"
Denys Vlasenkoa2f18d92020-12-18 04:12:51 +010024//usage: "\n -c N Class. 1:realtime 2:best-effort 3:idle"
25//usage: "\n -n N Priority"
Pere Orga5bc8c002011-04-11 03:29:49 +020026
Denis Vlasenko4acdb462009-01-31 21:45:57 +000027#include <sys/syscall.h>
28#include <asm/unistd.h>
29#include "libbb.h"
30
31static int ioprio_set(int which, int who, int ioprio)
32{
33 return syscall(SYS_ioprio_set, which, who, ioprio);
34}
35
36static int ioprio_get(int which, int who)
37{
38 return syscall(SYS_ioprio_get, which, who);
39}
40
41enum {
42 IOPRIO_WHO_PROCESS = 1,
43 IOPRIO_WHO_PGRP,
44 IOPRIO_WHO_USER
45};
46
47enum {
48 IOPRIO_CLASS_NONE,
49 IOPRIO_CLASS_RT,
50 IOPRIO_CLASS_BE,
51 IOPRIO_CLASS_IDLE
52};
53
Denys Vlasenko3e134eb2016-04-22 18:09:21 +020054static const char to_prio[] ALIGN1 = "none\0realtime\0best-effort\0idle";
Denis Vlasenko4acdb462009-01-31 21:45:57 +000055
56#define IOPRIO_CLASS_SHIFT 13
57
58int ionice_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
59int ionice_main(int argc UNUSED_PARAM, char **argv)
60{
61 /* Defaults */
62 int ioclass = 0;
63 int pri = 0;
Denys Vlasenkoa2f18d92020-12-18 04:12:51 +010064 int pid = 0; /* affect own process */
Denis Vlasenko4acdb462009-01-31 21:45:57 +000065 int opt;
66 enum {
67 OPT_n = 1,
68 OPT_c = 2,
69 OPT_p = 4,
70 };
71
72 /* Numeric params */
Denis Vlasenko4acdb462009-01-31 21:45:57 +000073 /* '+': stop at first non-option */
Denys Vlasenko237bedd2016-07-06 21:58:02 +020074 opt = getopt32(argv, "+n:+c:+p:+", &pri, &ioclass, &pid);
Denis Vlasenko4acdb462009-01-31 21:45:57 +000075 argv += optind;
Denis Vlasenko3266aa92009-04-01 11:24:04 +000076
Denis Vlasenko4acdb462009-01-31 21:45:57 +000077 if (opt & OPT_c) {
78 if (ioclass > 3)
79 bb_error_msg_and_die("bad class %d", ioclass);
80// Do we need this (compat?)?
81// if (ioclass == IOPRIO_CLASS_NONE)
82// ioclass = IOPRIO_CLASS_BE;
83// if (ioclass == IOPRIO_CLASS_IDLE) {
84// //if (opt & OPT_n)
85// // bb_error_msg("ignoring priority for idle class");
86// pri = 7;
87// }
88 }
Denis Vlasenko3266aa92009-04-01 11:24:04 +000089
Denis Vlasenko4acdb462009-01-31 21:45:57 +000090 if (!(opt & (OPT_n|OPT_c))) {
91 if (!(opt & OPT_p) && *argv)
Denys Vlasenko77832482010-08-12 14:14:45 +020092 pid = xatoi_positive(*argv);
Denis Vlasenko4acdb462009-01-31 21:45:57 +000093
94 pri = ioprio_get(IOPRIO_WHO_PROCESS, pid);
95 if (pri == -1)
96 bb_perror_msg_and_die("ioprio_%cet", 'g');
97
98 ioclass = (pri >> IOPRIO_CLASS_SHIFT) & 0x3;
99 pri &= 0xff;
100 printf((ioclass == IOPRIO_CLASS_IDLE) ? "%s\n" : "%s: prio %d\n",
101 nth_string(to_prio, ioclass), pri);
102 } else {
103//printf("pri=%d class=%d val=%x\n",
104//pri, ioclass, pri | (ioclass << IOPRIO_CLASS_SHIFT));
105 pri |= (ioclass << IOPRIO_CLASS_SHIFT);
106 if (ioprio_set(IOPRIO_WHO_PROCESS, pid, pri) == -1)
107 bb_perror_msg_and_die("ioprio_%cet", 's');
Denys Vlasenko41ddd9f2010-06-25 01:46:53 +0200108 if (argv[0]) {
Pascal Bellard21e8e8d2010-07-04 00:57:03 +0200109 BB_EXECVP_or_die(argv);
Denis Vlasenko4acdb462009-01-31 21:45:57 +0000110 }
111 }
112
113 return EXIT_SUCCESS;
114}