ioprio.c 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252
  1. /*
  2. * fs/ioprio.c
  3. *
  4. * Copyright (C) 2004 Jens Axboe <axboe@kernel.dk>
  5. *
  6. * Helper functions for setting/querying io priorities of processes. The
  7. * system calls closely mimmick getpriority/setpriority, see the man page for
  8. * those. The prio argument is a composite of prio class and prio data, where
  9. * the data argument has meaning within that class. The standard scheduling
  10. * classes have 8 distinct prio levels, with 0 being the highest prio and 7
  11. * being the lowest.
  12. *
  13. * IOW, setting BE scheduling class with prio 2 is done ala:
  14. *
  15. * unsigned int prio = (IOPRIO_CLASS_BE << IOPRIO_CLASS_SHIFT) | 2;
  16. *
  17. * ioprio_set(PRIO_PROCESS, pid, prio);
  18. *
  19. * See also Documentation/block/ioprio.txt
  20. *
  21. */
  22. #include <linux/gfp.h>
  23. #include <linux/kernel.h>
  24. #include <linux/export.h>
  25. #include <linux/ioprio.h>
  26. #include <linux/cred.h>
  27. #include <linux/blkdev.h>
  28. #include <linux/capability.h>
  29. #include <linux/sched/user.h>
  30. #include <linux/sched/task.h>
  31. #include <linux/syscalls.h>
  32. #include <linux/security.h>
  33. #include <linux/pid_namespace.h>
  34. int set_task_ioprio(struct task_struct *task, int ioprio)
  35. {
  36. int err;
  37. struct io_context *ioc;
  38. const struct cred *cred = current_cred(), *tcred;
  39. rcu_read_lock();
  40. tcred = __task_cred(task);
  41. if (!uid_eq(tcred->uid, cred->euid) &&
  42. !uid_eq(tcred->uid, cred->uid) && !capable(CAP_SYS_NICE)) {
  43. rcu_read_unlock();
  44. return -EPERM;
  45. }
  46. rcu_read_unlock();
  47. err = security_task_setioprio(task, ioprio);
  48. if (err)
  49. return err;
  50. ioc = get_task_io_context(task, GFP_ATOMIC, NUMA_NO_NODE);
  51. if (ioc) {
  52. ioc->ioprio = ioprio;
  53. put_io_context(ioc);
  54. }
  55. return err;
  56. }
  57. EXPORT_SYMBOL_GPL(set_task_ioprio);
  58. int ioprio_check_cap(int ioprio)
  59. {
  60. int class = IOPRIO_PRIO_CLASS(ioprio);
  61. int data = IOPRIO_PRIO_DATA(ioprio);
  62. switch (class) {
  63. case IOPRIO_CLASS_RT:
  64. if (!capable(CAP_SYS_ADMIN))
  65. return -EPERM;
  66. /* fall through */
  67. /* rt has prio field too */
  68. case IOPRIO_CLASS_BE:
  69. if (data >= IOPRIO_BE_NR || data < 0)
  70. return -EINVAL;
  71. break;
  72. case IOPRIO_CLASS_IDLE:
  73. break;
  74. case IOPRIO_CLASS_NONE:
  75. if (data)
  76. return -EINVAL;
  77. break;
  78. default:
  79. return -EINVAL;
  80. }
  81. return 0;
  82. }
  83. SYSCALL_DEFINE3(ioprio_set, int, which, int, who, int, ioprio)
  84. {
  85. struct task_struct *p, *g;
  86. struct user_struct *user;
  87. struct pid *pgrp;
  88. kuid_t uid;
  89. int ret;
  90. ret = ioprio_check_cap(ioprio);
  91. if (ret)
  92. return ret;
  93. ret = -ESRCH;
  94. rcu_read_lock();
  95. switch (which) {
  96. case IOPRIO_WHO_PROCESS:
  97. if (!who)
  98. p = current;
  99. else
  100. p = find_task_by_vpid(who);
  101. if (p)
  102. ret = set_task_ioprio(p, ioprio);
  103. break;
  104. case IOPRIO_WHO_PGRP:
  105. if (!who)
  106. pgrp = task_pgrp(current);
  107. else
  108. pgrp = find_vpid(who);
  109. do_each_pid_thread(pgrp, PIDTYPE_PGID, p) {
  110. ret = set_task_ioprio(p, ioprio);
  111. if (ret)
  112. break;
  113. } while_each_pid_thread(pgrp, PIDTYPE_PGID, p);
  114. break;
  115. case IOPRIO_WHO_USER:
  116. uid = make_kuid(current_user_ns(), who);
  117. if (!uid_valid(uid))
  118. break;
  119. if (!who)
  120. user = current_user();
  121. else
  122. user = find_user(uid);
  123. if (!user)
  124. break;
  125. for_each_process_thread(g, p) {
  126. if (!uid_eq(task_uid(p), uid) ||
  127. !task_pid_vnr(p))
  128. continue;
  129. ret = set_task_ioprio(p, ioprio);
  130. if (ret)
  131. goto free_uid;
  132. }
  133. free_uid:
  134. if (who)
  135. free_uid(user);
  136. break;
  137. default:
  138. ret = -EINVAL;
  139. }
  140. rcu_read_unlock();
  141. return ret;
  142. }
  143. static int get_task_ioprio(struct task_struct *p)
  144. {
  145. int ret;
  146. ret = security_task_getioprio(p);
  147. if (ret)
  148. goto out;
  149. ret = IOPRIO_PRIO_VALUE(IOPRIO_CLASS_NONE, IOPRIO_NORM);
  150. task_lock(p);
  151. if (p->io_context)
  152. ret = p->io_context->ioprio;
  153. task_unlock(p);
  154. out:
  155. return ret;
  156. }
  157. int ioprio_best(unsigned short aprio, unsigned short bprio)
  158. {
  159. if (!ioprio_valid(aprio))
  160. aprio = IOPRIO_PRIO_VALUE(IOPRIO_CLASS_BE, IOPRIO_NORM);
  161. if (!ioprio_valid(bprio))
  162. bprio = IOPRIO_PRIO_VALUE(IOPRIO_CLASS_BE, IOPRIO_NORM);
  163. return min(aprio, bprio);
  164. }
  165. SYSCALL_DEFINE2(ioprio_get, int, which, int, who)
  166. {
  167. struct task_struct *g, *p;
  168. struct user_struct *user;
  169. struct pid *pgrp;
  170. kuid_t uid;
  171. int ret = -ESRCH;
  172. int tmpio;
  173. rcu_read_lock();
  174. switch (which) {
  175. case IOPRIO_WHO_PROCESS:
  176. if (!who)
  177. p = current;
  178. else
  179. p = find_task_by_vpid(who);
  180. if (p)
  181. ret = get_task_ioprio(p);
  182. break;
  183. case IOPRIO_WHO_PGRP:
  184. if (!who)
  185. pgrp = task_pgrp(current);
  186. else
  187. pgrp = find_vpid(who);
  188. do_each_pid_thread(pgrp, PIDTYPE_PGID, p) {
  189. tmpio = get_task_ioprio(p);
  190. if (tmpio < 0)
  191. continue;
  192. if (ret == -ESRCH)
  193. ret = tmpio;
  194. else
  195. ret = ioprio_best(ret, tmpio);
  196. } while_each_pid_thread(pgrp, PIDTYPE_PGID, p);
  197. break;
  198. case IOPRIO_WHO_USER:
  199. uid = make_kuid(current_user_ns(), who);
  200. if (!who)
  201. user = current_user();
  202. else
  203. user = find_user(uid);
  204. if (!user)
  205. break;
  206. for_each_process_thread(g, p) {
  207. if (!uid_eq(task_uid(p), user->uid) ||
  208. !task_pid_vnr(p))
  209. continue;
  210. tmpio = get_task_ioprio(p);
  211. if (tmpio < 0)
  212. continue;
  213. if (ret == -ESRCH)
  214. ret = tmpio;
  215. else
  216. ret = ioprio_best(ret, tmpio);
  217. }
  218. if (who)
  219. free_uid(user);
  220. break;
  221. default:
  222. ret = -EINVAL;
  223. }
  224. rcu_read_unlock();
  225. return ret;
  226. }