tomoyo.c 8.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310
  1. /*
  2. * security/tomoyo/tomoyo.c
  3. *
  4. * LSM hooks for TOMOYO Linux.
  5. *
  6. * Copyright (C) 2005-2009 NTT DATA CORPORATION
  7. *
  8. * Version: 2.2.0 2009/04/01
  9. *
  10. */
  11. #include <linux/security.h>
  12. #include "common.h"
  13. #include "tomoyo.h"
  14. #include "realpath.h"
  15. static int tomoyo_cred_alloc_blank(struct cred *new, gfp_t gfp)
  16. {
  17. new->security = NULL;
  18. return 0;
  19. }
  20. static int tomoyo_cred_prepare(struct cred *new, const struct cred *old,
  21. gfp_t gfp)
  22. {
  23. /*
  24. * Since "struct tomoyo_domain_info *" is a sharable pointer,
  25. * we don't need to duplicate.
  26. */
  27. new->security = old->security;
  28. return 0;
  29. }
  30. static void tomoyo_cred_transfer(struct cred *new, const struct cred *old)
  31. {
  32. /*
  33. * Since "struct tomoyo_domain_info *" is a sharable pointer,
  34. * we don't need to duplicate.
  35. */
  36. new->security = old->security;
  37. }
  38. static int tomoyo_bprm_set_creds(struct linux_binprm *bprm)
  39. {
  40. int rc;
  41. rc = cap_bprm_set_creds(bprm);
  42. if (rc)
  43. return rc;
  44. /*
  45. * Do only if this function is called for the first time of an execve
  46. * operation.
  47. */
  48. if (bprm->cred_prepared)
  49. return 0;
  50. /*
  51. * Load policy if /sbin/tomoyo-init exists and /sbin/init is requested
  52. * for the first time.
  53. */
  54. if (!tomoyo_policy_loaded)
  55. tomoyo_load_policy(bprm->filename);
  56. /*
  57. * Tell tomoyo_bprm_check_security() is called for the first time of an
  58. * execve operation.
  59. */
  60. bprm->cred->security = NULL;
  61. return 0;
  62. }
  63. static int tomoyo_bprm_check_security(struct linux_binprm *bprm)
  64. {
  65. struct tomoyo_domain_info *domain = bprm->cred->security;
  66. /*
  67. * Execute permission is checked against pathname passed to do_execve()
  68. * using current domain.
  69. */
  70. if (!domain) {
  71. /*
  72. * We will need to protect whole execve() operation when GC
  73. * starts kfree()ing "struct tomoyo_domain_info" because
  74. * bprm->cred->security points to "struct tomoyo_domain_info"
  75. * but "struct tomoyo_domain_info" does not have a refcounter.
  76. */
  77. const int idx = tomoyo_read_lock();
  78. const int err = tomoyo_find_next_domain(bprm);
  79. tomoyo_read_unlock(idx);
  80. return err;
  81. }
  82. /*
  83. * Read permission is checked against interpreters using next domain.
  84. * '1' is the result of open_to_namei_flags(O_RDONLY).
  85. */
  86. return tomoyo_check_open_permission(domain, &bprm->file->f_path, 1);
  87. }
  88. static int tomoyo_path_truncate(struct path *path, loff_t length,
  89. unsigned int time_attrs)
  90. {
  91. return tomoyo_check_1path_perm(tomoyo_domain(),
  92. TOMOYO_TYPE_TRUNCATE_ACL,
  93. path);
  94. }
  95. static int tomoyo_path_unlink(struct path *parent, struct dentry *dentry)
  96. {
  97. struct path path = { parent->mnt, dentry };
  98. return tomoyo_check_1path_perm(tomoyo_domain(),
  99. TOMOYO_TYPE_UNLINK_ACL,
  100. &path);
  101. }
  102. static int tomoyo_path_mkdir(struct path *parent, struct dentry *dentry,
  103. int mode)
  104. {
  105. struct path path = { parent->mnt, dentry };
  106. return tomoyo_check_1path_perm(tomoyo_domain(),
  107. TOMOYO_TYPE_MKDIR_ACL,
  108. &path);
  109. }
  110. static int tomoyo_path_rmdir(struct path *parent, struct dentry *dentry)
  111. {
  112. struct path path = { parent->mnt, dentry };
  113. return tomoyo_check_1path_perm(tomoyo_domain(),
  114. TOMOYO_TYPE_RMDIR_ACL,
  115. &path);
  116. }
  117. static int tomoyo_path_symlink(struct path *parent, struct dentry *dentry,
  118. const char *old_name)
  119. {
  120. struct path path = { parent->mnt, dentry };
  121. return tomoyo_check_1path_perm(tomoyo_domain(),
  122. TOMOYO_TYPE_SYMLINK_ACL,
  123. &path);
  124. }
  125. static int tomoyo_path_mknod(struct path *parent, struct dentry *dentry,
  126. int mode, unsigned int dev)
  127. {
  128. struct path path = { parent->mnt, dentry };
  129. int type = TOMOYO_TYPE_CREATE_ACL;
  130. switch (mode & S_IFMT) {
  131. case S_IFCHR:
  132. type = TOMOYO_TYPE_MKCHAR_ACL;
  133. break;
  134. case S_IFBLK:
  135. type = TOMOYO_TYPE_MKBLOCK_ACL;
  136. break;
  137. case S_IFIFO:
  138. type = TOMOYO_TYPE_MKFIFO_ACL;
  139. break;
  140. case S_IFSOCK:
  141. type = TOMOYO_TYPE_MKSOCK_ACL;
  142. break;
  143. }
  144. return tomoyo_check_1path_perm(tomoyo_domain(),
  145. type, &path);
  146. }
  147. static int tomoyo_path_link(struct dentry *old_dentry, struct path *new_dir,
  148. struct dentry *new_dentry)
  149. {
  150. struct path path1 = { new_dir->mnt, old_dentry };
  151. struct path path2 = { new_dir->mnt, new_dentry };
  152. return tomoyo_check_2path_perm(tomoyo_domain(),
  153. TOMOYO_TYPE_LINK_ACL,
  154. &path1, &path2);
  155. }
  156. static int tomoyo_path_rename(struct path *old_parent,
  157. struct dentry *old_dentry,
  158. struct path *new_parent,
  159. struct dentry *new_dentry)
  160. {
  161. struct path path1 = { old_parent->mnt, old_dentry };
  162. struct path path2 = { new_parent->mnt, new_dentry };
  163. return tomoyo_check_2path_perm(tomoyo_domain(),
  164. TOMOYO_TYPE_RENAME_ACL,
  165. &path1, &path2);
  166. }
  167. static int tomoyo_file_fcntl(struct file *file, unsigned int cmd,
  168. unsigned long arg)
  169. {
  170. if (cmd == F_SETFL && ((arg ^ file->f_flags) & O_APPEND))
  171. return tomoyo_check_rewrite_permission(tomoyo_domain(), file);
  172. return 0;
  173. }
  174. static int tomoyo_dentry_open(struct file *f, const struct cred *cred)
  175. {
  176. int flags = f->f_flags;
  177. if ((flags + 1) & O_ACCMODE)
  178. flags++;
  179. flags |= f->f_flags & (O_APPEND | O_TRUNC);
  180. /* Don't check read permission here if called from do_execve(). */
  181. if (current->in_execve)
  182. return 0;
  183. return tomoyo_check_open_permission(tomoyo_domain(), &f->f_path, flags);
  184. }
  185. static int tomoyo_file_ioctl(struct file *file, unsigned int cmd,
  186. unsigned long arg)
  187. {
  188. return tomoyo_check_1path_perm(tomoyo_domain(), TOMOYO_TYPE_IOCTL_ACL,
  189. &file->f_path);
  190. }
  191. static int tomoyo_path_chmod(struct dentry *dentry, struct vfsmount *mnt,
  192. mode_t mode)
  193. {
  194. struct path path = { mnt, dentry };
  195. return tomoyo_check_1path_perm(tomoyo_domain(), TOMOYO_TYPE_CHMOD_ACL,
  196. &path);
  197. }
  198. static int tomoyo_path_chown(struct path *path, uid_t uid, gid_t gid)
  199. {
  200. int error = 0;
  201. if (uid != (uid_t) -1)
  202. error = tomoyo_check_1path_perm(tomoyo_domain(),
  203. TOMOYO_TYPE_CHOWN_ACL, path);
  204. if (!error && gid != (gid_t) -1)
  205. error = tomoyo_check_1path_perm(tomoyo_domain(),
  206. TOMOYO_TYPE_CHGRP_ACL, path);
  207. return error;
  208. }
  209. static int tomoyo_path_chroot(struct path *path)
  210. {
  211. return tomoyo_check_1path_perm(tomoyo_domain(), TOMOYO_TYPE_CHROOT_ACL,
  212. path);
  213. }
  214. static int tomoyo_sb_mount(char *dev_name, struct path *path,
  215. char *type, unsigned long flags, void *data)
  216. {
  217. return tomoyo_check_1path_perm(tomoyo_domain(), TOMOYO_TYPE_MOUNT_ACL,
  218. path);
  219. }
  220. static int tomoyo_sb_umount(struct vfsmount *mnt, int flags)
  221. {
  222. struct path path = { mnt, mnt->mnt_root };
  223. return tomoyo_check_1path_perm(tomoyo_domain(), TOMOYO_TYPE_UMOUNT_ACL,
  224. &path);
  225. }
  226. static int tomoyo_sb_pivotroot(struct path *old_path, struct path *new_path)
  227. {
  228. return tomoyo_check_2path_perm(tomoyo_domain(),
  229. TOMOYO_TYPE_PIVOT_ROOT_ACL,
  230. new_path, old_path);
  231. }
  232. /*
  233. * tomoyo_security_ops is a "struct security_operations" which is used for
  234. * registering TOMOYO.
  235. */
  236. static struct security_operations tomoyo_security_ops = {
  237. .name = "tomoyo",
  238. .cred_alloc_blank = tomoyo_cred_alloc_blank,
  239. .cred_prepare = tomoyo_cred_prepare,
  240. .cred_transfer = tomoyo_cred_transfer,
  241. .bprm_set_creds = tomoyo_bprm_set_creds,
  242. .bprm_check_security = tomoyo_bprm_check_security,
  243. .file_fcntl = tomoyo_file_fcntl,
  244. .dentry_open = tomoyo_dentry_open,
  245. .path_truncate = tomoyo_path_truncate,
  246. .path_unlink = tomoyo_path_unlink,
  247. .path_mkdir = tomoyo_path_mkdir,
  248. .path_rmdir = tomoyo_path_rmdir,
  249. .path_symlink = tomoyo_path_symlink,
  250. .path_mknod = tomoyo_path_mknod,
  251. .path_link = tomoyo_path_link,
  252. .path_rename = tomoyo_path_rename,
  253. .file_ioctl = tomoyo_file_ioctl,
  254. .path_chmod = tomoyo_path_chmod,
  255. .path_chown = tomoyo_path_chown,
  256. .path_chroot = tomoyo_path_chroot,
  257. .sb_mount = tomoyo_sb_mount,
  258. .sb_umount = tomoyo_sb_umount,
  259. .sb_pivotroot = tomoyo_sb_pivotroot,
  260. };
  261. /* Lock for GC. */
  262. struct srcu_struct tomoyo_ss;
  263. static int __init tomoyo_init(void)
  264. {
  265. struct cred *cred = (struct cred *) current_cred();
  266. if (!security_module_enable(&tomoyo_security_ops))
  267. return 0;
  268. /* register ourselves with the security framework */
  269. if (register_security(&tomoyo_security_ops) ||
  270. init_srcu_struct(&tomoyo_ss))
  271. panic("Failure registering TOMOYO Linux");
  272. printk(KERN_INFO "TOMOYO Linux initialized\n");
  273. cred->security = &tomoyo_kernel_domain;
  274. tomoyo_realpath_init();
  275. return 0;
  276. }
  277. security_initcall(tomoyo_init);