19590837bSKentaro Takeda /* 29590837bSKentaro Takeda * security/tomoyo/common.h 39590837bSKentaro Takeda * 476bb0895STetsuo Handa * Header file for TOMOYO. 59590837bSKentaro Takeda * 676bb0895STetsuo Handa * Copyright (C) 2005-2010 NTT DATA CORPORATION 79590837bSKentaro Takeda */ 89590837bSKentaro Takeda 99590837bSKentaro Takeda #ifndef _SECURITY_TOMOYO_COMMON_H 109590837bSKentaro Takeda #define _SECURITY_TOMOYO_COMMON_H 119590837bSKentaro Takeda 129590837bSKentaro Takeda #include <linux/ctype.h> 139590837bSKentaro Takeda #include <linux/string.h> 149590837bSKentaro Takeda #include <linux/mm.h> 159590837bSKentaro Takeda #include <linux/file.h> 169590837bSKentaro Takeda #include <linux/kmod.h> 179590837bSKentaro Takeda #include <linux/fs.h> 189590837bSKentaro Takeda #include <linux/sched.h> 199590837bSKentaro Takeda #include <linux/namei.h> 209590837bSKentaro Takeda #include <linux/mount.h> 219590837bSKentaro Takeda #include <linux/list.h> 2276bb0895STetsuo Handa #include <linux/cred.h> 2376bb0895STetsuo Handa struct linux_binprm; 249590837bSKentaro Takeda 2576bb0895STetsuo Handa /********** Constants definitions. **********/ 2676bb0895STetsuo Handa 2776bb0895STetsuo Handa /* 2876bb0895STetsuo Handa * TOMOYO uses this hash only when appending a string into the string 2976bb0895STetsuo Handa * table. Frequency of appending strings is very low. So we don't need 3076bb0895STetsuo Handa * large (e.g. 64k) hash size. 256 will be sufficient. 3176bb0895STetsuo Handa */ 3276bb0895STetsuo Handa #define TOMOYO_HASH_BITS 8 3376bb0895STetsuo Handa #define TOMOYO_MAX_HASH (1u<<TOMOYO_HASH_BITS) 3476bb0895STetsuo Handa 3576bb0895STetsuo Handa /* 3676bb0895STetsuo Handa * This is the max length of a token. 3776bb0895STetsuo Handa * 3876bb0895STetsuo Handa * A token consists of only ASCII printable characters. 3976bb0895STetsuo Handa * Non printable characters in a token is represented in \ooo style 4076bb0895STetsuo Handa * octal string. Thus, \ itself is represented as \\. 4176bb0895STetsuo Handa */ 4276bb0895STetsuo Handa #define TOMOYO_MAX_PATHNAME_LEN 4000 4376bb0895STetsuo Handa 4476bb0895STetsuo Handa /* Profile number is an integer between 0 and 255. */ 4576bb0895STetsuo Handa #define TOMOYO_MAX_PROFILES 256 4676bb0895STetsuo Handa 4776bb0895STetsuo Handa /* Keywords for ACLs. */ 4876bb0895STetsuo Handa #define TOMOYO_KEYWORD_ALIAS "alias " 4976bb0895STetsuo Handa #define TOMOYO_KEYWORD_ALLOW_READ "allow_read " 5076bb0895STetsuo Handa #define TOMOYO_KEYWORD_DELETE "delete " 5176bb0895STetsuo Handa #define TOMOYO_KEYWORD_DENY_REWRITE "deny_rewrite " 5276bb0895STetsuo Handa #define TOMOYO_KEYWORD_FILE_PATTERN "file_pattern " 5376bb0895STetsuo Handa #define TOMOYO_KEYWORD_INITIALIZE_DOMAIN "initialize_domain " 5476bb0895STetsuo Handa #define TOMOYO_KEYWORD_KEEP_DOMAIN "keep_domain " 5576bb0895STetsuo Handa #define TOMOYO_KEYWORD_NO_INITIALIZE_DOMAIN "no_initialize_domain " 5676bb0895STetsuo Handa #define TOMOYO_KEYWORD_NO_KEEP_DOMAIN "no_keep_domain " 577762fbffSTetsuo Handa #define TOMOYO_KEYWORD_PATH_GROUP "path_group " 584c3e9e2dSTetsuo Handa #define TOMOYO_KEYWORD_NUMBER_GROUP "number_group " 5976bb0895STetsuo Handa #define TOMOYO_KEYWORD_SELECT "select " 6076bb0895STetsuo Handa #define TOMOYO_KEYWORD_USE_PROFILE "use_profile " 6176bb0895STetsuo Handa #define TOMOYO_KEYWORD_IGNORE_GLOBAL_ALLOW_READ "ignore_global_allow_read" 6276bb0895STetsuo Handa /* A domain definition starts with <kernel>. */ 6376bb0895STetsuo Handa #define TOMOYO_ROOT_NAME "<kernel>" 6476bb0895STetsuo Handa #define TOMOYO_ROOT_NAME_LEN (sizeof(TOMOYO_ROOT_NAME) - 1) 6576bb0895STetsuo Handa 664c3e9e2dSTetsuo Handa /* Value type definition. */ 674c3e9e2dSTetsuo Handa #define TOMOYO_VALUE_TYPE_INVALID 0 684c3e9e2dSTetsuo Handa #define TOMOYO_VALUE_TYPE_DECIMAL 1 694c3e9e2dSTetsuo Handa #define TOMOYO_VALUE_TYPE_OCTAL 2 704c3e9e2dSTetsuo Handa #define TOMOYO_VALUE_TYPE_HEXADECIMAL 3 714c3e9e2dSTetsuo Handa 7276bb0895STetsuo Handa /* Index numbers for Access Controls. */ 73084da356STetsuo Handa enum tomoyo_mac_index { 74084da356STetsuo Handa TOMOYO_MAC_FOR_FILE, /* domain_policy.conf */ 75084da356STetsuo Handa TOMOYO_MAX_ACCEPT_ENTRY, 76084da356STetsuo Handa TOMOYO_VERBOSE, 77084da356STetsuo Handa TOMOYO_MAX_CONTROL_INDEX 78084da356STetsuo Handa }; 7976bb0895STetsuo Handa 8076bb0895STetsuo Handa /* Index numbers for Access Controls. */ 81084da356STetsuo Handa enum tomoyo_acl_entry_type_index { 827ef61233STetsuo Handa TOMOYO_TYPE_PATH_ACL, 837ef61233STetsuo Handa TOMOYO_TYPE_PATH2_ACL, 84084da356STetsuo Handa }; 8576bb0895STetsuo Handa 8676bb0895STetsuo Handa /* Index numbers for File Controls. */ 8776bb0895STetsuo Handa 8876bb0895STetsuo Handa /* 8976bb0895STetsuo Handa * TYPE_READ_WRITE_ACL is special. TYPE_READ_WRITE_ACL is automatically set 9076bb0895STetsuo Handa * if both TYPE_READ_ACL and TYPE_WRITE_ACL are set. Both TYPE_READ_ACL and 9176bb0895STetsuo Handa * TYPE_WRITE_ACL are automatically set if TYPE_READ_WRITE_ACL is set. 9276bb0895STetsuo Handa * TYPE_READ_WRITE_ACL is automatically cleared if either TYPE_READ_ACL or 9376bb0895STetsuo Handa * TYPE_WRITE_ACL is cleared. Both TYPE_READ_ACL and TYPE_WRITE_ACL are 9476bb0895STetsuo Handa * automatically cleared if TYPE_READ_WRITE_ACL is cleared. 9576bb0895STetsuo Handa */ 9676bb0895STetsuo Handa 97084da356STetsuo Handa enum tomoyo_path_acl_index { 987ef61233STetsuo Handa TOMOYO_TYPE_READ_WRITE, 997ef61233STetsuo Handa TOMOYO_TYPE_EXECUTE, 1007ef61233STetsuo Handa TOMOYO_TYPE_READ, 1017ef61233STetsuo Handa TOMOYO_TYPE_WRITE, 1027ef61233STetsuo Handa TOMOYO_TYPE_CREATE, 1037ef61233STetsuo Handa TOMOYO_TYPE_UNLINK, 1047ef61233STetsuo Handa TOMOYO_TYPE_MKDIR, 1057ef61233STetsuo Handa TOMOYO_TYPE_RMDIR, 1067ef61233STetsuo Handa TOMOYO_TYPE_MKFIFO, 1077ef61233STetsuo Handa TOMOYO_TYPE_MKSOCK, 1087ef61233STetsuo Handa TOMOYO_TYPE_MKBLOCK, 1097ef61233STetsuo Handa TOMOYO_TYPE_MKCHAR, 1107ef61233STetsuo Handa TOMOYO_TYPE_TRUNCATE, 1117ef61233STetsuo Handa TOMOYO_TYPE_SYMLINK, 1127ef61233STetsuo Handa TOMOYO_TYPE_REWRITE, 1137ef61233STetsuo Handa TOMOYO_TYPE_IOCTL, 1147ef61233STetsuo Handa TOMOYO_TYPE_CHMOD, 1157ef61233STetsuo Handa TOMOYO_TYPE_CHOWN, 1167ef61233STetsuo Handa TOMOYO_TYPE_CHGRP, 1177ef61233STetsuo Handa TOMOYO_TYPE_CHROOT, 1187ef61233STetsuo Handa TOMOYO_TYPE_MOUNT, 1197ef61233STetsuo Handa TOMOYO_TYPE_UMOUNT, 1207ef61233STetsuo Handa TOMOYO_MAX_PATH_OPERATION 121084da356STetsuo Handa }; 12276bb0895STetsuo Handa 123084da356STetsuo Handa enum tomoyo_path2_acl_index { 1247ef61233STetsuo Handa TOMOYO_TYPE_LINK, 1257ef61233STetsuo Handa TOMOYO_TYPE_RENAME, 1267ef61233STetsuo Handa TOMOYO_TYPE_PIVOT_ROOT, 1277ef61233STetsuo Handa TOMOYO_MAX_PATH2_OPERATION 128084da356STetsuo Handa }; 12976bb0895STetsuo Handa 130084da356STetsuo Handa enum tomoyo_securityfs_interface_index { 131084da356STetsuo Handa TOMOYO_DOMAINPOLICY, 132084da356STetsuo Handa TOMOYO_EXCEPTIONPOLICY, 133084da356STetsuo Handa TOMOYO_DOMAIN_STATUS, 134084da356STetsuo Handa TOMOYO_PROCESS_STATUS, 135084da356STetsuo Handa TOMOYO_MEMINFO, 136084da356STetsuo Handa TOMOYO_SELFDOMAIN, 137084da356STetsuo Handa TOMOYO_VERSION, 138084da356STetsuo Handa TOMOYO_PROFILE, 139084da356STetsuo Handa TOMOYO_MANAGER 140084da356STetsuo Handa }; 14176bb0895STetsuo Handa 14276bb0895STetsuo Handa /********** Structure definitions. **********/ 1439590837bSKentaro Takeda 144c3fa109aSTetsuo Handa /* 145c3fa109aSTetsuo Handa * tomoyo_page_buffer is a structure which is used for holding a pathname 146c3fa109aSTetsuo Handa * obtained from "struct dentry" and "struct vfsmount" pair. 147c3fa109aSTetsuo Handa * As of now, it is 4096 bytes. If users complain that 4096 bytes is too small 148c3fa109aSTetsuo Handa * (because TOMOYO escapes non ASCII printable characters using \ooo format), 149c3fa109aSTetsuo Handa * we will make the buffer larger. 150c3fa109aSTetsuo Handa */ 1519590837bSKentaro Takeda struct tomoyo_page_buffer { 1529590837bSKentaro Takeda char buffer[4096]; 1539590837bSKentaro Takeda }; 1549590837bSKentaro Takeda 155c3fa109aSTetsuo Handa /* 156c3fa109aSTetsuo Handa * tomoyo_path_info is a structure which is used for holding a string data 157c3fa109aSTetsuo Handa * used by TOMOYO. 158c3fa109aSTetsuo Handa * This structure has several fields for supporting pattern matching. 159c3fa109aSTetsuo Handa * 160c3fa109aSTetsuo Handa * (1) "name" is the '\0' terminated string data. 161c3fa109aSTetsuo Handa * (2) "hash" is full_name_hash(name, strlen(name)). 162c3fa109aSTetsuo Handa * This allows tomoyo_pathcmp() to compare by hash before actually compare 163c3fa109aSTetsuo Handa * using strcmp(). 164c3fa109aSTetsuo Handa * (3) "const_len" is the length of the initial segment of "name" which 165c3fa109aSTetsuo Handa * consists entirely of non wildcard characters. In other words, the length 166c3fa109aSTetsuo Handa * which we can compare two strings using strncmp(). 167c3fa109aSTetsuo Handa * (4) "is_dir" is a bool which is true if "name" ends with "/", 168c3fa109aSTetsuo Handa * false otherwise. 169c3fa109aSTetsuo Handa * TOMOYO distinguishes directory and non-directory. A directory ends with 170c3fa109aSTetsuo Handa * "/" and non-directory does not end with "/". 171c3fa109aSTetsuo Handa * (5) "is_patterned" is a bool which is true if "name" contains wildcard 172c3fa109aSTetsuo Handa * characters, false otherwise. This allows TOMOYO to use "hash" and 173c3fa109aSTetsuo Handa * strcmp() for string comparison if "is_patterned" is false. 174c3fa109aSTetsuo Handa */ 1759590837bSKentaro Takeda struct tomoyo_path_info { 1769590837bSKentaro Takeda const char *name; 1779590837bSKentaro Takeda u32 hash; /* = full_name_hash(name, strlen(name)) */ 1789590837bSKentaro Takeda u16 const_len; /* = tomoyo_const_part_length(name) */ 1799590837bSKentaro Takeda bool is_dir; /* = tomoyo_strendswith(name, "/") */ 1809590837bSKentaro Takeda bool is_patterned; /* = tomoyo_path_contains_pattern(name) */ 1819590837bSKentaro Takeda }; 1829590837bSKentaro Takeda 1839590837bSKentaro Takeda /* 18476bb0895STetsuo Handa * tomoyo_name_entry is a structure which is used for linking 18576bb0895STetsuo Handa * "struct tomoyo_path_info" into tomoyo_name_list . 1869590837bSKentaro Takeda */ 18776bb0895STetsuo Handa struct tomoyo_name_entry { 18876bb0895STetsuo Handa struct list_head list; 18976bb0895STetsuo Handa atomic_t users; 19076bb0895STetsuo Handa struct tomoyo_path_info entry; 19176bb0895STetsuo Handa }; 1929590837bSKentaro Takeda 193c3fa109aSTetsuo Handa /* 194c3fa109aSTetsuo Handa * tomoyo_path_info_with_data is a structure which is used for holding a 195c3fa109aSTetsuo Handa * pathname obtained from "struct dentry" and "struct vfsmount" pair. 196c3fa109aSTetsuo Handa * 197c3fa109aSTetsuo Handa * "struct tomoyo_path_info_with_data" consists of "struct tomoyo_path_info" 198c3fa109aSTetsuo Handa * and buffer for the pathname, while "struct tomoyo_page_buffer" consists of 199c3fa109aSTetsuo Handa * buffer for the pathname only. 200c3fa109aSTetsuo Handa * 201c3fa109aSTetsuo Handa * "struct tomoyo_path_info_with_data" is intended to allow TOMOYO to release 202c3fa109aSTetsuo Handa * both "struct tomoyo_path_info" and buffer for the pathname by single kfree() 203c3fa109aSTetsuo Handa * so that we don't need to return two pointers to the caller. If the caller 204c3fa109aSTetsuo Handa * puts "struct tomoyo_path_info" on stack memory, we will be able to remove 205c3fa109aSTetsuo Handa * "struct tomoyo_path_info_with_data". 206c3fa109aSTetsuo Handa */ 2079590837bSKentaro Takeda struct tomoyo_path_info_with_data { 2088e2d39a1STetsuo Handa /* Keep "head" first, for this pointer is passed to kfree(). */ 2099590837bSKentaro Takeda struct tomoyo_path_info head; 210a106cbfdSTetsuo Handa char barrier1[16]; /* Safeguard for overrun. */ 2119590837bSKentaro Takeda char body[TOMOYO_MAX_PATHNAME_LEN]; 2129590837bSKentaro Takeda char barrier2[16]; /* Safeguard for overrun. */ 2139590837bSKentaro Takeda }; 2149590837bSKentaro Takeda 2157762fbffSTetsuo Handa struct tomoyo_name_union { 2167762fbffSTetsuo Handa const struct tomoyo_path_info *filename; 2177762fbffSTetsuo Handa struct tomoyo_path_group *group; 2187762fbffSTetsuo Handa u8 is_group; 2197762fbffSTetsuo Handa }; 2207762fbffSTetsuo Handa 2214c3e9e2dSTetsuo Handa struct tomoyo_number_union { 2224c3e9e2dSTetsuo Handa unsigned long values[2]; 2234c3e9e2dSTetsuo Handa struct tomoyo_number_group *group; 2244c3e9e2dSTetsuo Handa u8 min_type; 2254c3e9e2dSTetsuo Handa u8 max_type; 2264c3e9e2dSTetsuo Handa u8 is_group; 2274c3e9e2dSTetsuo Handa }; 2284c3e9e2dSTetsuo Handa 2297762fbffSTetsuo Handa /* Structure for "path_group" directive. */ 2307762fbffSTetsuo Handa struct tomoyo_path_group { 2317762fbffSTetsuo Handa struct list_head list; 2327762fbffSTetsuo Handa const struct tomoyo_path_info *group_name; 2337762fbffSTetsuo Handa struct list_head member_list; 2347762fbffSTetsuo Handa atomic_t users; 2357762fbffSTetsuo Handa }; 2367762fbffSTetsuo Handa 2374c3e9e2dSTetsuo Handa /* Structure for "number_group" directive. */ 2384c3e9e2dSTetsuo Handa struct tomoyo_number_group { 2394c3e9e2dSTetsuo Handa struct list_head list; 2404c3e9e2dSTetsuo Handa const struct tomoyo_path_info *group_name; 2414c3e9e2dSTetsuo Handa struct list_head member_list; 2424c3e9e2dSTetsuo Handa atomic_t users; 2434c3e9e2dSTetsuo Handa }; 2444c3e9e2dSTetsuo Handa 2457762fbffSTetsuo Handa /* Structure for "path_group" directive. */ 2467762fbffSTetsuo Handa struct tomoyo_path_group_member { 2477762fbffSTetsuo Handa struct list_head list; 2487762fbffSTetsuo Handa bool is_deleted; 2497762fbffSTetsuo Handa const struct tomoyo_path_info *member_name; 2507762fbffSTetsuo Handa }; 2517762fbffSTetsuo Handa 2524c3e9e2dSTetsuo Handa /* Structure for "number_group" directive. */ 2534c3e9e2dSTetsuo Handa struct tomoyo_number_group_member { 2544c3e9e2dSTetsuo Handa struct list_head list; 2554c3e9e2dSTetsuo Handa bool is_deleted; 2564c3e9e2dSTetsuo Handa struct tomoyo_number_union number; 2574c3e9e2dSTetsuo Handa }; 2584c3e9e2dSTetsuo Handa 2599590837bSKentaro Takeda /* 260c3fa109aSTetsuo Handa * tomoyo_acl_info is a structure which is used for holding 261c3fa109aSTetsuo Handa * 262c3fa109aSTetsuo Handa * (1) "list" which is linked to the ->acl_info_list of 263c3fa109aSTetsuo Handa * "struct tomoyo_domain_info" 264ea13ddbaSTetsuo Handa * (2) "type" which tells type of the entry (either 2657ef61233STetsuo Handa * "struct tomoyo_path_acl" or "struct tomoyo_path2_acl"). 2669590837bSKentaro Takeda * 2679590837bSKentaro Takeda * Packing "struct tomoyo_acl_info" allows 2687ef61233STetsuo Handa * "struct tomoyo_path_acl" to embed "u8" + "u16" and 2697ef61233STetsuo Handa * "struct tomoyo_path2_acl" to embed "u8" 2709590837bSKentaro Takeda * without enlarging their structure size. 2719590837bSKentaro Takeda */ 2729590837bSKentaro Takeda struct tomoyo_acl_info { 2739590837bSKentaro Takeda struct list_head list; 2749590837bSKentaro Takeda u8 type; 2759590837bSKentaro Takeda } __packed; 2769590837bSKentaro Takeda 277c3fa109aSTetsuo Handa /* 278c3fa109aSTetsuo Handa * tomoyo_domain_info is a structure which is used for holding permissions 279c3fa109aSTetsuo Handa * (e.g. "allow_read /lib/libc-2.5.so") given to each domain. 280c3fa109aSTetsuo Handa * It has following fields. 281c3fa109aSTetsuo Handa * 282c3fa109aSTetsuo Handa * (1) "list" which is linked to tomoyo_domain_list . 283c3fa109aSTetsuo Handa * (2) "acl_info_list" which is linked to "struct tomoyo_acl_info". 284c3fa109aSTetsuo Handa * (3) "domainname" which holds the name of the domain. 285c3fa109aSTetsuo Handa * (4) "profile" which remembers profile number assigned to this domain. 286c3fa109aSTetsuo Handa * (5) "is_deleted" is a bool which is true if this domain is marked as 287c3fa109aSTetsuo Handa * "deleted", false otherwise. 288c3fa109aSTetsuo Handa * (6) "quota_warned" is a bool which is used for suppressing warning message 289c3fa109aSTetsuo Handa * when learning mode learned too much entries. 290ea13ddbaSTetsuo Handa * (7) "ignore_global_allow_read" is a bool which is true if this domain 291ea13ddbaSTetsuo Handa * should ignore "allow_read" directive in exception policy. 292ea13ddbaSTetsuo Handa * (8) "transition_failed" is a bool which is set to true when this domain was 293ea13ddbaSTetsuo Handa * unable to create a new domain at tomoyo_find_next_domain() because the 294ea13ddbaSTetsuo Handa * name of the domain to be created was too long or it could not allocate 295ea13ddbaSTetsuo Handa * memory. If set to true, more than one process continued execve() 296ea13ddbaSTetsuo Handa * without domain transition. 297ec8e6a4eSTetsuo Handa * (9) "users" is an atomic_t that holds how many "struct cred"->security 298ec8e6a4eSTetsuo Handa * are referring this "struct tomoyo_domain_info". If is_deleted == true 299ec8e6a4eSTetsuo Handa * and users == 0, this struct will be kfree()d upon next garbage 300ec8e6a4eSTetsuo Handa * collection. 301c3fa109aSTetsuo Handa * 302c3fa109aSTetsuo Handa * A domain's lifecycle is an analogy of files on / directory. 303c3fa109aSTetsuo Handa * Multiple domains with the same domainname cannot be created (as with 304c3fa109aSTetsuo Handa * creating files with the same filename fails with -EEXIST). 305c3fa109aSTetsuo Handa * If a process reached a domain, that process can reside in that domain after 306c3fa109aSTetsuo Handa * that domain is marked as "deleted" (as with a process can access an already 307c3fa109aSTetsuo Handa * open()ed file after that file was unlink()ed). 308c3fa109aSTetsuo Handa */ 3099590837bSKentaro Takeda struct tomoyo_domain_info { 3109590837bSKentaro Takeda struct list_head list; 3119590837bSKentaro Takeda struct list_head acl_info_list; 3129590837bSKentaro Takeda /* Name of this domain. Never NULL. */ 3139590837bSKentaro Takeda const struct tomoyo_path_info *domainname; 3149590837bSKentaro Takeda u8 profile; /* Profile number to use. */ 315a0558fc3STetsuo Handa bool is_deleted; /* Delete flag. */ 3169590837bSKentaro Takeda bool quota_warned; /* Quota warnning flag. */ 317ea13ddbaSTetsuo Handa bool ignore_global_allow_read; /* Ignore "allow_read" flag. */ 318ea13ddbaSTetsuo Handa bool transition_failed; /* Domain transition failed flag. */ 319ec8e6a4eSTetsuo Handa atomic_t users; /* Number of referring credentials. */ 3209590837bSKentaro Takeda }; 3219590837bSKentaro Takeda 3229590837bSKentaro Takeda /* 3237ef61233STetsuo Handa * tomoyo_path_acl is a structure which is used for holding an 324c3fa109aSTetsuo Handa * entry with one pathname operation (e.g. open(), mkdir()). 325c3fa109aSTetsuo Handa * It has following fields. 326c3fa109aSTetsuo Handa * 327c3fa109aSTetsuo Handa * (1) "head" which is a "struct tomoyo_acl_info". 328c3fa109aSTetsuo Handa * (2) "perm" which is a bitmask of permitted operations. 3297762fbffSTetsuo Handa * (3) "name" is the pathname. 330c3fa109aSTetsuo Handa * 331c3fa109aSTetsuo Handa * Directives held by this structure are "allow_read/write", "allow_execute", 332c3fa109aSTetsuo Handa * "allow_read", "allow_write", "allow_create", "allow_unlink", "allow_mkdir", 333c3fa109aSTetsuo Handa * "allow_rmdir", "allow_mkfifo", "allow_mksock", "allow_mkblock", 334937bf613STetsuo Handa * "allow_mkchar", "allow_truncate", "allow_symlink", "allow_rewrite", 335937bf613STetsuo Handa * "allow_chmod", "allow_chown", "allow_chgrp", "allow_chroot", "allow_mount" 336937bf613STetsuo Handa * and "allow_unmount". 3379590837bSKentaro Takeda */ 3387ef61233STetsuo Handa struct tomoyo_path_acl { 3397ef61233STetsuo Handa struct tomoyo_acl_info head; /* type = TOMOYO_TYPE_PATH_ACL */ 340937bf613STetsuo Handa u8 perm_high; 3419590837bSKentaro Takeda u16 perm; 3427762fbffSTetsuo Handa struct tomoyo_name_union name; 3439590837bSKentaro Takeda }; 3449590837bSKentaro Takeda 345c3fa109aSTetsuo Handa /* 3467ef61233STetsuo Handa * tomoyo_path2_acl is a structure which is used for holding an 347937bf613STetsuo Handa * entry with two pathnames operation (i.e. link(), rename() and pivot_root()). 348c3fa109aSTetsuo Handa * It has following fields. 349c3fa109aSTetsuo Handa * 350c3fa109aSTetsuo Handa * (1) "head" which is a "struct tomoyo_acl_info". 351c3fa109aSTetsuo Handa * (2) "perm" which is a bitmask of permitted operations. 3527762fbffSTetsuo Handa * (3) "name1" is the source/old pathname. 3537762fbffSTetsuo Handa * (4) "name2" is the destination/new pathname. 354c3fa109aSTetsuo Handa * 355937bf613STetsuo Handa * Directives held by this structure are "allow_rename", "allow_link" and 356937bf613STetsuo Handa * "allow_pivot_root". 357c3fa109aSTetsuo Handa */ 3587ef61233STetsuo Handa struct tomoyo_path2_acl { 3597ef61233STetsuo Handa struct tomoyo_acl_info head; /* type = TOMOYO_TYPE_PATH2_ACL */ 3609590837bSKentaro Takeda u8 perm; 3617762fbffSTetsuo Handa struct tomoyo_name_union name1; 3627762fbffSTetsuo Handa struct tomoyo_name_union name2; 3639590837bSKentaro Takeda }; 3649590837bSKentaro Takeda 365c3fa109aSTetsuo Handa /* 366c3fa109aSTetsuo Handa * tomoyo_io_buffer is a structure which is used for reading and modifying 367c3fa109aSTetsuo Handa * configuration via /sys/kernel/security/tomoyo/ interface. 368c3fa109aSTetsuo Handa * It has many fields. ->read_var1 , ->read_var2 , ->write_var1 are used as 369c3fa109aSTetsuo Handa * cursors. 370c3fa109aSTetsuo Handa * 371c3fa109aSTetsuo Handa * Since the content of /sys/kernel/security/tomoyo/domain_policy is a list of 372c3fa109aSTetsuo Handa * "struct tomoyo_domain_info" entries and each "struct tomoyo_domain_info" 373c3fa109aSTetsuo Handa * entry has a list of "struct tomoyo_acl_info", we need two cursors when 374c3fa109aSTetsuo Handa * reading (one is for traversing tomoyo_domain_list and the other is for 375c3fa109aSTetsuo Handa * traversing "struct tomoyo_acl_info"->acl_info_list ). 376c3fa109aSTetsuo Handa * 377c3fa109aSTetsuo Handa * If a line written to /sys/kernel/security/tomoyo/domain_policy starts with 378c3fa109aSTetsuo Handa * "select ", TOMOYO seeks the cursor ->read_var1 and ->write_var1 to the 379c3fa109aSTetsuo Handa * domain with the domainname specified by the rest of that line (NULL is set 380c3fa109aSTetsuo Handa * if seek failed). 381c3fa109aSTetsuo Handa * If a line written to /sys/kernel/security/tomoyo/domain_policy starts with 382c3fa109aSTetsuo Handa * "delete ", TOMOYO deletes an entry or a domain specified by the rest of that 383c3fa109aSTetsuo Handa * line (->write_var1 is set to NULL if a domain was deleted). 384c3fa109aSTetsuo Handa * If a line written to /sys/kernel/security/tomoyo/domain_policy starts with 385c3fa109aSTetsuo Handa * neither "select " nor "delete ", an entry or a domain specified by that line 386c3fa109aSTetsuo Handa * is appended. 387c3fa109aSTetsuo Handa */ 3889590837bSKentaro Takeda struct tomoyo_io_buffer { 3899590837bSKentaro Takeda int (*read) (struct tomoyo_io_buffer *); 3909590837bSKentaro Takeda int (*write) (struct tomoyo_io_buffer *); 3919590837bSKentaro Takeda /* Exclusive lock for this structure. */ 3929590837bSKentaro Takeda struct mutex io_sem; 393fdb8ebb7STetsuo Handa /* Index returned by tomoyo_read_lock(). */ 394fdb8ebb7STetsuo Handa int reader_idx; 3959590837bSKentaro Takeda /* The position currently reading from. */ 3969590837bSKentaro Takeda struct list_head *read_var1; 3979590837bSKentaro Takeda /* Extra variables for reading. */ 3989590837bSKentaro Takeda struct list_head *read_var2; 3999590837bSKentaro Takeda /* The position currently writing to. */ 4009590837bSKentaro Takeda struct tomoyo_domain_info *write_var1; 4019590837bSKentaro Takeda /* The step for reading. */ 4029590837bSKentaro Takeda int read_step; 4039590837bSKentaro Takeda /* Buffer for reading. */ 4049590837bSKentaro Takeda char *read_buf; 4059590837bSKentaro Takeda /* EOF flag for reading. */ 4069590837bSKentaro Takeda bool read_eof; 4079590837bSKentaro Takeda /* Read domain ACL of specified PID? */ 4089590837bSKentaro Takeda bool read_single_domain; 4099590837bSKentaro Takeda /* Extra variable for reading. */ 4109590837bSKentaro Takeda u8 read_bit; 4119590837bSKentaro Takeda /* Bytes available for reading. */ 4129590837bSKentaro Takeda int read_avail; 4139590837bSKentaro Takeda /* Size of read buffer. */ 4149590837bSKentaro Takeda int readbuf_size; 4159590837bSKentaro Takeda /* Buffer for writing. */ 4169590837bSKentaro Takeda char *write_buf; 4179590837bSKentaro Takeda /* Bytes available for writing. */ 4189590837bSKentaro Takeda int write_avail; 4199590837bSKentaro Takeda /* Size of write buffer. */ 4209590837bSKentaro Takeda int writebuf_size; 4219590837bSKentaro Takeda }; 4229590837bSKentaro Takeda 42376bb0895STetsuo Handa /* 42476bb0895STetsuo Handa * tomoyo_globally_readable_file_entry is a structure which is used for holding 42576bb0895STetsuo Handa * "allow_read" entries. 42676bb0895STetsuo Handa * It has following fields. 42776bb0895STetsuo Handa * 42876bb0895STetsuo Handa * (1) "list" which is linked to tomoyo_globally_readable_list . 42976bb0895STetsuo Handa * (2) "filename" is a pathname which is allowed to open(O_RDONLY). 43076bb0895STetsuo Handa * (3) "is_deleted" is a bool which is true if marked as deleted, false 43176bb0895STetsuo Handa * otherwise. 43276bb0895STetsuo Handa */ 43376bb0895STetsuo Handa struct tomoyo_globally_readable_file_entry { 43476bb0895STetsuo Handa struct list_head list; 43576bb0895STetsuo Handa const struct tomoyo_path_info *filename; 43676bb0895STetsuo Handa bool is_deleted; 43776bb0895STetsuo Handa }; 43876bb0895STetsuo Handa 43976bb0895STetsuo Handa /* 44076bb0895STetsuo Handa * tomoyo_pattern_entry is a structure which is used for holding 44176bb0895STetsuo Handa * "tomoyo_pattern_list" entries. 44276bb0895STetsuo Handa * It has following fields. 44376bb0895STetsuo Handa * 44476bb0895STetsuo Handa * (1) "list" which is linked to tomoyo_pattern_list . 44576bb0895STetsuo Handa * (2) "pattern" is a pathname pattern which is used for converting pathnames 44676bb0895STetsuo Handa * to pathname patterns during learning mode. 44776bb0895STetsuo Handa * (3) "is_deleted" is a bool which is true if marked as deleted, false 44876bb0895STetsuo Handa * otherwise. 44976bb0895STetsuo Handa */ 45076bb0895STetsuo Handa struct tomoyo_pattern_entry { 45176bb0895STetsuo Handa struct list_head list; 45276bb0895STetsuo Handa const struct tomoyo_path_info *pattern; 45376bb0895STetsuo Handa bool is_deleted; 45476bb0895STetsuo Handa }; 45576bb0895STetsuo Handa 45676bb0895STetsuo Handa /* 45776bb0895STetsuo Handa * tomoyo_no_rewrite_entry is a structure which is used for holding 45876bb0895STetsuo Handa * "deny_rewrite" entries. 45976bb0895STetsuo Handa * It has following fields. 46076bb0895STetsuo Handa * 46176bb0895STetsuo Handa * (1) "list" which is linked to tomoyo_no_rewrite_list . 46276bb0895STetsuo Handa * (2) "pattern" is a pathname which is by default not permitted to modify 46376bb0895STetsuo Handa * already existing content. 46476bb0895STetsuo Handa * (3) "is_deleted" is a bool which is true if marked as deleted, false 46576bb0895STetsuo Handa * otherwise. 46676bb0895STetsuo Handa */ 46776bb0895STetsuo Handa struct tomoyo_no_rewrite_entry { 46876bb0895STetsuo Handa struct list_head list; 46976bb0895STetsuo Handa const struct tomoyo_path_info *pattern; 47076bb0895STetsuo Handa bool is_deleted; 47176bb0895STetsuo Handa }; 47276bb0895STetsuo Handa 47376bb0895STetsuo Handa /* 47476bb0895STetsuo Handa * tomoyo_domain_initializer_entry is a structure which is used for holding 47576bb0895STetsuo Handa * "initialize_domain" and "no_initialize_domain" entries. 47676bb0895STetsuo Handa * It has following fields. 47776bb0895STetsuo Handa * 47876bb0895STetsuo Handa * (1) "list" which is linked to tomoyo_domain_initializer_list . 47976bb0895STetsuo Handa * (2) "domainname" which is "a domainname" or "the last component of a 48076bb0895STetsuo Handa * domainname". This field is NULL if "from" clause is not specified. 48176bb0895STetsuo Handa * (3) "program" which is a program's pathname. 48276bb0895STetsuo Handa * (4) "is_deleted" is a bool which is true if marked as deleted, false 48376bb0895STetsuo Handa * otherwise. 48476bb0895STetsuo Handa * (5) "is_not" is a bool which is true if "no_initialize_domain", false 48576bb0895STetsuo Handa * otherwise. 48676bb0895STetsuo Handa * (6) "is_last_name" is a bool which is true if "domainname" is "the last 48776bb0895STetsuo Handa * component of a domainname", false otherwise. 48876bb0895STetsuo Handa */ 48976bb0895STetsuo Handa struct tomoyo_domain_initializer_entry { 49076bb0895STetsuo Handa struct list_head list; 49176bb0895STetsuo Handa const struct tomoyo_path_info *domainname; /* This may be NULL */ 49276bb0895STetsuo Handa const struct tomoyo_path_info *program; 49376bb0895STetsuo Handa bool is_deleted; 49476bb0895STetsuo Handa bool is_not; /* True if this entry is "no_initialize_domain". */ 49576bb0895STetsuo Handa /* True if the domainname is tomoyo_get_last_name(). */ 49676bb0895STetsuo Handa bool is_last_name; 49776bb0895STetsuo Handa }; 49876bb0895STetsuo Handa 49976bb0895STetsuo Handa /* 50076bb0895STetsuo Handa * tomoyo_domain_keeper_entry is a structure which is used for holding 50176bb0895STetsuo Handa * "keep_domain" and "no_keep_domain" entries. 50276bb0895STetsuo Handa * It has following fields. 50376bb0895STetsuo Handa * 50476bb0895STetsuo Handa * (1) "list" which is linked to tomoyo_domain_keeper_list . 50576bb0895STetsuo Handa * (2) "domainname" which is "a domainname" or "the last component of a 50676bb0895STetsuo Handa * domainname". 50776bb0895STetsuo Handa * (3) "program" which is a program's pathname. 50876bb0895STetsuo Handa * This field is NULL if "from" clause is not specified. 50976bb0895STetsuo Handa * (4) "is_deleted" is a bool which is true if marked as deleted, false 51076bb0895STetsuo Handa * otherwise. 51176bb0895STetsuo Handa * (5) "is_not" is a bool which is true if "no_initialize_domain", false 51276bb0895STetsuo Handa * otherwise. 51376bb0895STetsuo Handa * (6) "is_last_name" is a bool which is true if "domainname" is "the last 51476bb0895STetsuo Handa * component of a domainname", false otherwise. 51576bb0895STetsuo Handa */ 51676bb0895STetsuo Handa struct tomoyo_domain_keeper_entry { 51776bb0895STetsuo Handa struct list_head list; 51876bb0895STetsuo Handa const struct tomoyo_path_info *domainname; 51976bb0895STetsuo Handa const struct tomoyo_path_info *program; /* This may be NULL */ 52076bb0895STetsuo Handa bool is_deleted; 52176bb0895STetsuo Handa bool is_not; /* True if this entry is "no_keep_domain". */ 52276bb0895STetsuo Handa /* True if the domainname is tomoyo_get_last_name(). */ 52376bb0895STetsuo Handa bool is_last_name; 52476bb0895STetsuo Handa }; 52576bb0895STetsuo Handa 52676bb0895STetsuo Handa /* 52776bb0895STetsuo Handa * tomoyo_alias_entry is a structure which is used for holding "alias" entries. 52876bb0895STetsuo Handa * It has following fields. 52976bb0895STetsuo Handa * 53076bb0895STetsuo Handa * (1) "list" which is linked to tomoyo_alias_list . 53176bb0895STetsuo Handa * (2) "original_name" which is a dereferenced pathname. 53276bb0895STetsuo Handa * (3) "aliased_name" which is a symlink's pathname. 53376bb0895STetsuo Handa * (4) "is_deleted" is a bool which is true if marked as deleted, false 53476bb0895STetsuo Handa * otherwise. 53576bb0895STetsuo Handa */ 53676bb0895STetsuo Handa struct tomoyo_alias_entry { 53776bb0895STetsuo Handa struct list_head list; 53876bb0895STetsuo Handa const struct tomoyo_path_info *original_name; 53976bb0895STetsuo Handa const struct tomoyo_path_info *aliased_name; 54076bb0895STetsuo Handa bool is_deleted; 54176bb0895STetsuo Handa }; 54276bb0895STetsuo Handa 54376bb0895STetsuo Handa /* 54476bb0895STetsuo Handa * tomoyo_policy_manager_entry is a structure which is used for holding list of 54576bb0895STetsuo Handa * domainnames or programs which are permitted to modify configuration via 54676bb0895STetsuo Handa * /sys/kernel/security/tomoyo/ interface. 54776bb0895STetsuo Handa * It has following fields. 54876bb0895STetsuo Handa * 54976bb0895STetsuo Handa * (1) "list" which is linked to tomoyo_policy_manager_list . 55076bb0895STetsuo Handa * (2) "manager" is a domainname or a program's pathname. 55176bb0895STetsuo Handa * (3) "is_domain" is a bool which is true if "manager" is a domainname, false 55276bb0895STetsuo Handa * otherwise. 55376bb0895STetsuo Handa * (4) "is_deleted" is a bool which is true if marked as deleted, false 55476bb0895STetsuo Handa * otherwise. 55576bb0895STetsuo Handa */ 55676bb0895STetsuo Handa struct tomoyo_policy_manager_entry { 55776bb0895STetsuo Handa struct list_head list; 55876bb0895STetsuo Handa /* A path to program or a domainname. */ 55976bb0895STetsuo Handa const struct tomoyo_path_info *manager; 56076bb0895STetsuo Handa bool is_domain; /* True if manager is a domainname. */ 56176bb0895STetsuo Handa bool is_deleted; /* True if this entry is deleted. */ 56276bb0895STetsuo Handa }; 56376bb0895STetsuo Handa 56476bb0895STetsuo Handa /********** Function prototypes. **********/ 56576bb0895STetsuo Handa 5667762fbffSTetsuo Handa /* Check whether the given name matches the given name_union. */ 5677762fbffSTetsuo Handa bool tomoyo_compare_name_union(const struct tomoyo_path_info *name, 5687762fbffSTetsuo Handa const struct tomoyo_name_union *ptr); 5699590837bSKentaro Takeda /* Check whether the domain has too many ACL entries to hold. */ 5709590837bSKentaro Takeda bool tomoyo_domain_quota_is_ok(struct tomoyo_domain_info * const domain); 5719590837bSKentaro Takeda /* Transactional sprintf() for policy dump. */ 5729590837bSKentaro Takeda bool tomoyo_io_printf(struct tomoyo_io_buffer *head, const char *fmt, ...) 5739590837bSKentaro Takeda __attribute__ ((format(printf, 2, 3))); 5749590837bSKentaro Takeda /* Check whether the domainname is correct. */ 57517080008STetsuo Handa bool tomoyo_is_correct_domain(const unsigned char *domainname); 5769590837bSKentaro Takeda /* Check whether the token is correct. */ 5779590837bSKentaro Takeda bool tomoyo_is_correct_path(const char *filename, const s8 start_type, 57817080008STetsuo Handa const s8 pattern_type, const s8 end_type); 5799590837bSKentaro Takeda /* Check whether the token can be a domainname. */ 5809590837bSKentaro Takeda bool tomoyo_is_domain_def(const unsigned char *buffer); 5817762fbffSTetsuo Handa bool tomoyo_parse_name_union(const char *filename, 5827762fbffSTetsuo Handa struct tomoyo_name_union *ptr); 5837762fbffSTetsuo Handa /* Check whether the given filename matches the given path_group. */ 5847762fbffSTetsuo Handa bool tomoyo_path_matches_group(const struct tomoyo_path_info *pathname, 5857762fbffSTetsuo Handa const struct tomoyo_path_group *group, 5867762fbffSTetsuo Handa const bool may_use_pattern); 5874c3e9e2dSTetsuo Handa /* Check whether the given value matches the given number_group. */ 5884c3e9e2dSTetsuo Handa bool tomoyo_number_matches_group(const unsigned long min, 5894c3e9e2dSTetsuo Handa const unsigned long max, 5904c3e9e2dSTetsuo Handa const struct tomoyo_number_group *group); 5919590837bSKentaro Takeda /* Check whether the given filename matches the given pattern. */ 5929590837bSKentaro Takeda bool tomoyo_path_matches_pattern(const struct tomoyo_path_info *filename, 5939590837bSKentaro Takeda const struct tomoyo_path_info *pattern); 5944c3e9e2dSTetsuo Handa 5954c3e9e2dSTetsuo Handa bool tomoyo_print_number_union(struct tomoyo_io_buffer *head, 5964c3e9e2dSTetsuo Handa const struct tomoyo_number_union *ptr); 5974c3e9e2dSTetsuo Handa bool tomoyo_parse_number_union(char *data, struct tomoyo_number_union *num); 5984c3e9e2dSTetsuo Handa 5999590837bSKentaro Takeda /* Read "alias" entry in exception policy. */ 6009590837bSKentaro Takeda bool tomoyo_read_alias_policy(struct tomoyo_io_buffer *head); 6019590837bSKentaro Takeda /* 6029590837bSKentaro Takeda * Read "initialize_domain" and "no_initialize_domain" entry 6039590837bSKentaro Takeda * in exception policy. 6049590837bSKentaro Takeda */ 6059590837bSKentaro Takeda bool tomoyo_read_domain_initializer_policy(struct tomoyo_io_buffer *head); 6069590837bSKentaro Takeda /* Read "keep_domain" and "no_keep_domain" entry in exception policy. */ 6079590837bSKentaro Takeda bool tomoyo_read_domain_keeper_policy(struct tomoyo_io_buffer *head); 6089590837bSKentaro Takeda /* Read "file_pattern" entry in exception policy. */ 6099590837bSKentaro Takeda bool tomoyo_read_file_pattern(struct tomoyo_io_buffer *head); 6107762fbffSTetsuo Handa /* Read "path_group" entry in exception policy. */ 6117762fbffSTetsuo Handa bool tomoyo_read_path_group_policy(struct tomoyo_io_buffer *head); 6124c3e9e2dSTetsuo Handa /* Read "number_group" entry in exception policy. */ 6134c3e9e2dSTetsuo Handa bool tomoyo_read_number_group_policy(struct tomoyo_io_buffer *head); 6149590837bSKentaro Takeda /* Read "allow_read" entry in exception policy. */ 6159590837bSKentaro Takeda bool tomoyo_read_globally_readable_policy(struct tomoyo_io_buffer *head); 6169590837bSKentaro Takeda /* Read "deny_rewrite" entry in exception policy. */ 6179590837bSKentaro Takeda bool tomoyo_read_no_rewrite_policy(struct tomoyo_io_buffer *head); 6187762fbffSTetsuo Handa /* Tokenize a line. */ 6197762fbffSTetsuo Handa bool tomoyo_tokenize(char *buffer, char *w[], size_t size); 6209590837bSKentaro Takeda /* Write domain policy violation warning message to console? */ 6219590837bSKentaro Takeda bool tomoyo_verbose_mode(const struct tomoyo_domain_info *domain); 6229590837bSKentaro Takeda /* Convert double path operation to operation name. */ 6237ef61233STetsuo Handa const char *tomoyo_path22keyword(const u8 operation); 6249590837bSKentaro Takeda /* Get the last component of the given domainname. */ 6259590837bSKentaro Takeda const char *tomoyo_get_last_name(const struct tomoyo_domain_info *domain); 6269590837bSKentaro Takeda /* Get warning message. */ 6279590837bSKentaro Takeda const char *tomoyo_get_msg(const bool is_enforce); 6289590837bSKentaro Takeda /* Convert single path operation to operation name. */ 6297ef61233STetsuo Handa const char *tomoyo_path2keyword(const u8 operation); 6309590837bSKentaro Takeda /* Create "alias" entry in exception policy. */ 6319590837bSKentaro Takeda int tomoyo_write_alias_policy(char *data, const bool is_delete); 6329590837bSKentaro Takeda /* 6339590837bSKentaro Takeda * Create "initialize_domain" and "no_initialize_domain" entry 6349590837bSKentaro Takeda * in exception policy. 6359590837bSKentaro Takeda */ 6369590837bSKentaro Takeda int tomoyo_write_domain_initializer_policy(char *data, const bool is_not, 6379590837bSKentaro Takeda const bool is_delete); 6389590837bSKentaro Takeda /* Create "keep_domain" and "no_keep_domain" entry in exception policy. */ 6399590837bSKentaro Takeda int tomoyo_write_domain_keeper_policy(char *data, const bool is_not, 6409590837bSKentaro Takeda const bool is_delete); 6419590837bSKentaro Takeda /* 6429590837bSKentaro Takeda * Create "allow_read/write", "allow_execute", "allow_read", "allow_write", 6439590837bSKentaro Takeda * "allow_create", "allow_unlink", "allow_mkdir", "allow_rmdir", 6449590837bSKentaro Takeda * "allow_mkfifo", "allow_mksock", "allow_mkblock", "allow_mkchar", 6459590837bSKentaro Takeda * "allow_truncate", "allow_symlink", "allow_rewrite", "allow_rename" and 6469590837bSKentaro Takeda * "allow_link" entry in domain policy. 6479590837bSKentaro Takeda */ 6489590837bSKentaro Takeda int tomoyo_write_file_policy(char *data, struct tomoyo_domain_info *domain, 6499590837bSKentaro Takeda const bool is_delete); 6509590837bSKentaro Takeda /* Create "allow_read" entry in exception policy. */ 6519590837bSKentaro Takeda int tomoyo_write_globally_readable_policy(char *data, const bool is_delete); 6529590837bSKentaro Takeda /* Create "deny_rewrite" entry in exception policy. */ 6539590837bSKentaro Takeda int tomoyo_write_no_rewrite_policy(char *data, const bool is_delete); 6549590837bSKentaro Takeda /* Create "file_pattern" entry in exception policy. */ 6559590837bSKentaro Takeda int tomoyo_write_pattern_policy(char *data, const bool is_delete); 6567762fbffSTetsuo Handa /* Create "path_group" entry in exception policy. */ 6577762fbffSTetsuo Handa int tomoyo_write_path_group_policy(char *data, const bool is_delete); 6584c3e9e2dSTetsuo Handa /* Create "number_group" entry in exception policy. */ 6594c3e9e2dSTetsuo Handa int tomoyo_write_number_group_policy(char *data, const bool is_delete); 6609590837bSKentaro Takeda /* Find a domain by the given name. */ 6619590837bSKentaro Takeda struct tomoyo_domain_info *tomoyo_find_domain(const char *domainname); 6629590837bSKentaro Takeda /* Find or create a domain by the given name. */ 6639590837bSKentaro Takeda struct tomoyo_domain_info *tomoyo_find_or_assign_new_domain(const char * 6649590837bSKentaro Takeda domainname, 6659590837bSKentaro Takeda const u8 profile); 6667762fbffSTetsuo Handa 6677762fbffSTetsuo Handa /* Allocate memory for "struct tomoyo_path_group". */ 6687762fbffSTetsuo Handa struct tomoyo_path_group *tomoyo_get_path_group(const char *group_name); 6694c3e9e2dSTetsuo Handa struct tomoyo_number_group *tomoyo_get_number_group(const char *group_name); 6707762fbffSTetsuo Handa 6719590837bSKentaro Takeda /* Check mode for specified functionality. */ 6729590837bSKentaro Takeda unsigned int tomoyo_check_flags(const struct tomoyo_domain_info *domain, 6739590837bSKentaro Takeda const u8 index); 6749590837bSKentaro Takeda /* Fill in "struct tomoyo_path_info" members. */ 6759590837bSKentaro Takeda void tomoyo_fill_path_info(struct tomoyo_path_info *ptr); 6769590837bSKentaro Takeda /* Run policy loader when /sbin/init starts. */ 6779590837bSKentaro Takeda void tomoyo_load_policy(const char *filename); 6789590837bSKentaro Takeda 6794c3e9e2dSTetsuo Handa void tomoyo_put_number_union(struct tomoyo_number_union *ptr); 6804c3e9e2dSTetsuo Handa 68176bb0895STetsuo Handa /* Convert binary string to ascii string. */ 68276bb0895STetsuo Handa int tomoyo_encode(char *buffer, int buflen, const char *str); 68376bb0895STetsuo Handa 68476bb0895STetsuo Handa /* Returns realpath(3) of the given pathname but ignores chroot'ed root. */ 68576bb0895STetsuo Handa int tomoyo_realpath_from_path2(struct path *path, char *newname, 68676bb0895STetsuo Handa int newname_len); 68776bb0895STetsuo Handa 68876bb0895STetsuo Handa /* 68976bb0895STetsuo Handa * Returns realpath(3) of the given pathname but ignores chroot'ed root. 69076bb0895STetsuo Handa * These functions use kzalloc(), so the caller must call kfree() 69176bb0895STetsuo Handa * if these functions didn't return NULL. 69276bb0895STetsuo Handa */ 69376bb0895STetsuo Handa char *tomoyo_realpath(const char *pathname); 69476bb0895STetsuo Handa /* 69576bb0895STetsuo Handa * Same with tomoyo_realpath() except that it doesn't follow the final symlink. 69676bb0895STetsuo Handa */ 69776bb0895STetsuo Handa char *tomoyo_realpath_nofollow(const char *pathname); 69876bb0895STetsuo Handa /* Same with tomoyo_realpath() except that the pathname is already solved. */ 69976bb0895STetsuo Handa char *tomoyo_realpath_from_path(struct path *path); 70076bb0895STetsuo Handa 70176bb0895STetsuo Handa /* Check memory quota. */ 70276bb0895STetsuo Handa bool tomoyo_memory_ok(void *ptr); 7039e4b50e9STetsuo Handa void *tomoyo_commit_ok(void *data, const unsigned int size); 70476bb0895STetsuo Handa 70576bb0895STetsuo Handa /* 70676bb0895STetsuo Handa * Keep the given name on the RAM. 70776bb0895STetsuo Handa * The RAM is shared, so NEVER try to modify or kfree() the returned name. 70876bb0895STetsuo Handa */ 70976bb0895STetsuo Handa const struct tomoyo_path_info *tomoyo_get_name(const char *name); 71076bb0895STetsuo Handa 71176bb0895STetsuo Handa /* Check for memory usage. */ 71276bb0895STetsuo Handa int tomoyo_read_memory_counter(struct tomoyo_io_buffer *head); 71376bb0895STetsuo Handa 71476bb0895STetsuo Handa /* Set memory quota. */ 71576bb0895STetsuo Handa int tomoyo_write_memory_quota(struct tomoyo_io_buffer *head); 71676bb0895STetsuo Handa 71776bb0895STetsuo Handa /* Initialize realpath related code. */ 71876bb0895STetsuo Handa void __init tomoyo_realpath_init(void); 71976bb0895STetsuo Handa int tomoyo_check_exec_perm(struct tomoyo_domain_info *domain, 72076bb0895STetsuo Handa const struct tomoyo_path_info *filename); 72176bb0895STetsuo Handa int tomoyo_check_open_permission(struct tomoyo_domain_info *domain, 72276bb0895STetsuo Handa struct path *path, const int flag); 72397d6931eSTetsuo Handa int tomoyo_path_perm(const u8 operation, struct path *path); 72497d6931eSTetsuo Handa int tomoyo_path2_perm(const u8 operation, struct path *path1, 72597d6931eSTetsuo Handa struct path *path2); 72697d6931eSTetsuo Handa int tomoyo_check_rewrite_permission(struct file *filp); 72776bb0895STetsuo Handa int tomoyo_find_next_domain(struct linux_binprm *bprm); 72876bb0895STetsuo Handa 7297762fbffSTetsuo Handa /* Drop refcount on tomoyo_name_union. */ 7307762fbffSTetsuo Handa void tomoyo_put_name_union(struct tomoyo_name_union *ptr); 7317762fbffSTetsuo Handa 732847b173eSTetsuo Handa /* Run garbage collector. */ 733847b173eSTetsuo Handa void tomoyo_run_gc(void); 734847b173eSTetsuo Handa 735847b173eSTetsuo Handa void tomoyo_memory_free(void *ptr); 736847b173eSTetsuo Handa 73776bb0895STetsuo Handa /********** External variable definitions. **********/ 73876bb0895STetsuo Handa 73976bb0895STetsuo Handa /* Lock for GC. */ 74076bb0895STetsuo Handa extern struct srcu_struct tomoyo_ss; 74176bb0895STetsuo Handa 74276bb0895STetsuo Handa /* The list for "struct tomoyo_domain_info". */ 74376bb0895STetsuo Handa extern struct list_head tomoyo_domain_list; 74476bb0895STetsuo Handa 7457762fbffSTetsuo Handa extern struct list_head tomoyo_path_group_list; 7464c3e9e2dSTetsuo Handa extern struct list_head tomoyo_number_group_list; 747847b173eSTetsuo Handa extern struct list_head tomoyo_domain_initializer_list; 748847b173eSTetsuo Handa extern struct list_head tomoyo_domain_keeper_list; 749847b173eSTetsuo Handa extern struct list_head tomoyo_alias_list; 750847b173eSTetsuo Handa extern struct list_head tomoyo_globally_readable_list; 751847b173eSTetsuo Handa extern struct list_head tomoyo_pattern_list; 752847b173eSTetsuo Handa extern struct list_head tomoyo_no_rewrite_list; 753847b173eSTetsuo Handa extern struct list_head tomoyo_policy_manager_list; 754847b173eSTetsuo Handa extern struct list_head tomoyo_name_list[TOMOYO_MAX_HASH]; 755847b173eSTetsuo Handa 75676bb0895STetsuo Handa /* Lock for protecting policy. */ 75776bb0895STetsuo Handa extern struct mutex tomoyo_policy_lock; 75876bb0895STetsuo Handa 75976bb0895STetsuo Handa /* Has /sbin/init started? */ 76076bb0895STetsuo Handa extern bool tomoyo_policy_loaded; 76176bb0895STetsuo Handa 76276bb0895STetsuo Handa /* The kernel's domain. */ 76376bb0895STetsuo Handa extern struct tomoyo_domain_info tomoyo_kernel_domain; 76476bb0895STetsuo Handa 76576bb0895STetsuo Handa /********** Inlined functions. **********/ 76676bb0895STetsuo Handa 76776bb0895STetsuo Handa static inline int tomoyo_read_lock(void) 76876bb0895STetsuo Handa { 76976bb0895STetsuo Handa return srcu_read_lock(&tomoyo_ss); 77076bb0895STetsuo Handa } 77176bb0895STetsuo Handa 77276bb0895STetsuo Handa static inline void tomoyo_read_unlock(int idx) 77376bb0895STetsuo Handa { 77476bb0895STetsuo Handa srcu_read_unlock(&tomoyo_ss, idx); 77576bb0895STetsuo Handa } 77676bb0895STetsuo Handa 7779590837bSKentaro Takeda /* strcmp() for "struct tomoyo_path_info" structure. */ 7789590837bSKentaro Takeda static inline bool tomoyo_pathcmp(const struct tomoyo_path_info *a, 7799590837bSKentaro Takeda const struct tomoyo_path_info *b) 7809590837bSKentaro Takeda { 7819590837bSKentaro Takeda return a->hash != b->hash || strcmp(a->name, b->name); 7829590837bSKentaro Takeda } 7839590837bSKentaro Takeda 7849590837bSKentaro Takeda /** 7859590837bSKentaro Takeda * tomoyo_is_valid - Check whether the character is a valid char. 7869590837bSKentaro Takeda * 7879590837bSKentaro Takeda * @c: The character to check. 7889590837bSKentaro Takeda * 7899590837bSKentaro Takeda * Returns true if @c is a valid character, false otherwise. 7909590837bSKentaro Takeda */ 7919590837bSKentaro Takeda static inline bool tomoyo_is_valid(const unsigned char c) 7929590837bSKentaro Takeda { 7939590837bSKentaro Takeda return c > ' ' && c < 127; 7949590837bSKentaro Takeda } 7959590837bSKentaro Takeda 7969590837bSKentaro Takeda /** 7979590837bSKentaro Takeda * tomoyo_is_invalid - Check whether the character is an invalid char. 7989590837bSKentaro Takeda * 7999590837bSKentaro Takeda * @c: The character to check. 8009590837bSKentaro Takeda * 8019590837bSKentaro Takeda * Returns true if @c is an invalid character, false otherwise. 8029590837bSKentaro Takeda */ 8039590837bSKentaro Takeda static inline bool tomoyo_is_invalid(const unsigned char c) 8049590837bSKentaro Takeda { 8059590837bSKentaro Takeda return c && (c <= ' ' || c >= 127); 8069590837bSKentaro Takeda } 8079590837bSKentaro Takeda 80876bb0895STetsuo Handa static inline void tomoyo_put_name(const struct tomoyo_path_info *name) 80976bb0895STetsuo Handa { 81076bb0895STetsuo Handa if (name) { 81176bb0895STetsuo Handa struct tomoyo_name_entry *ptr = 81276bb0895STetsuo Handa container_of(name, struct tomoyo_name_entry, entry); 81376bb0895STetsuo Handa atomic_dec(&ptr->users); 81476bb0895STetsuo Handa } 81576bb0895STetsuo Handa } 8169590837bSKentaro Takeda 8177762fbffSTetsuo Handa static inline void tomoyo_put_path_group(struct tomoyo_path_group *group) 8187762fbffSTetsuo Handa { 8197762fbffSTetsuo Handa if (group) 8207762fbffSTetsuo Handa atomic_dec(&group->users); 8217762fbffSTetsuo Handa } 8227762fbffSTetsuo Handa 8234c3e9e2dSTetsuo Handa static inline void tomoyo_put_number_group(struct tomoyo_number_group *group) 8244c3e9e2dSTetsuo Handa { 8254c3e9e2dSTetsuo Handa if (group) 8264c3e9e2dSTetsuo Handa atomic_dec(&group->users); 8274c3e9e2dSTetsuo Handa } 8284c3e9e2dSTetsuo Handa 82976bb0895STetsuo Handa static inline struct tomoyo_domain_info *tomoyo_domain(void) 83076bb0895STetsuo Handa { 83176bb0895STetsuo Handa return current_cred()->security; 83276bb0895STetsuo Handa } 8339590837bSKentaro Takeda 83476bb0895STetsuo Handa static inline struct tomoyo_domain_info *tomoyo_real_domain(struct task_struct 83576bb0895STetsuo Handa *task) 83676bb0895STetsuo Handa { 83776bb0895STetsuo Handa return task_cred_xxx(task, security); 83876bb0895STetsuo Handa } 8399590837bSKentaro Takeda 8407762fbffSTetsuo Handa static inline bool tomoyo_is_same_acl_head(const struct tomoyo_acl_info *p1, 8417762fbffSTetsuo Handa const struct tomoyo_acl_info *p2) 8427762fbffSTetsuo Handa { 8437762fbffSTetsuo Handa return p1->type == p2->type; 8447762fbffSTetsuo Handa } 8457762fbffSTetsuo Handa 8467762fbffSTetsuo Handa static inline bool tomoyo_is_same_name_union 8477762fbffSTetsuo Handa (const struct tomoyo_name_union *p1, const struct tomoyo_name_union *p2) 8487762fbffSTetsuo Handa { 8497762fbffSTetsuo Handa return p1->filename == p2->filename && p1->group == p2->group && 8507762fbffSTetsuo Handa p1->is_group == p2->is_group; 8517762fbffSTetsuo Handa } 8527762fbffSTetsuo Handa 8534c3e9e2dSTetsuo Handa static inline bool tomoyo_is_same_number_union 8544c3e9e2dSTetsuo Handa (const struct tomoyo_number_union *p1, const struct tomoyo_number_union *p2) 8554c3e9e2dSTetsuo Handa { 8564c3e9e2dSTetsuo Handa return p1->values[0] == p2->values[0] && p1->values[1] == p2->values[1] 8574c3e9e2dSTetsuo Handa && p1->group == p2->group && p1->min_type == p2->min_type && 8584c3e9e2dSTetsuo Handa p1->max_type == p2->max_type && p1->is_group == p2->is_group; 8594c3e9e2dSTetsuo Handa } 8604c3e9e2dSTetsuo Handa 8617762fbffSTetsuo Handa static inline bool tomoyo_is_same_path_acl(const struct tomoyo_path_acl *p1, 8627762fbffSTetsuo Handa const struct tomoyo_path_acl *p2) 8637762fbffSTetsuo Handa { 8647762fbffSTetsuo Handa return tomoyo_is_same_acl_head(&p1->head, &p2->head) && 8657762fbffSTetsuo Handa tomoyo_is_same_name_union(&p1->name, &p2->name); 8667762fbffSTetsuo Handa } 8677762fbffSTetsuo Handa 8687762fbffSTetsuo Handa static inline bool tomoyo_is_same_path2_acl(const struct tomoyo_path2_acl *p1, 8697762fbffSTetsuo Handa const struct tomoyo_path2_acl *p2) 8707762fbffSTetsuo Handa { 8717762fbffSTetsuo Handa return tomoyo_is_same_acl_head(&p1->head, &p2->head) && 8727762fbffSTetsuo Handa tomoyo_is_same_name_union(&p1->name1, &p2->name1) && 8737762fbffSTetsuo Handa tomoyo_is_same_name_union(&p1->name2, &p2->name2); 8747762fbffSTetsuo Handa } 8757762fbffSTetsuo Handa 8769e4b50e9STetsuo Handa static inline bool tomoyo_is_same_domain_initializer_entry 8779e4b50e9STetsuo Handa (const struct tomoyo_domain_initializer_entry *p1, 8789e4b50e9STetsuo Handa const struct tomoyo_domain_initializer_entry *p2) 8799e4b50e9STetsuo Handa { 8809e4b50e9STetsuo Handa return p1->is_not == p2->is_not && p1->is_last_name == p2->is_last_name 8819e4b50e9STetsuo Handa && p1->domainname == p2->domainname 8829e4b50e9STetsuo Handa && p1->program == p2->program; 8839e4b50e9STetsuo Handa } 8849e4b50e9STetsuo Handa 8859e4b50e9STetsuo Handa static inline bool tomoyo_is_same_domain_keeper_entry 8869e4b50e9STetsuo Handa (const struct tomoyo_domain_keeper_entry *p1, 8879e4b50e9STetsuo Handa const struct tomoyo_domain_keeper_entry *p2) 8889e4b50e9STetsuo Handa { 8899e4b50e9STetsuo Handa return p1->is_not == p2->is_not && p1->is_last_name == p2->is_last_name 8909e4b50e9STetsuo Handa && p1->domainname == p2->domainname 8919e4b50e9STetsuo Handa && p1->program == p2->program; 8929e4b50e9STetsuo Handa } 8939e4b50e9STetsuo Handa 8949e4b50e9STetsuo Handa static inline bool tomoyo_is_same_alias_entry 8959e4b50e9STetsuo Handa (const struct tomoyo_alias_entry *p1, const struct tomoyo_alias_entry *p2) 8969e4b50e9STetsuo Handa { 8979e4b50e9STetsuo Handa return p1->original_name == p2->original_name && 8989e4b50e9STetsuo Handa p1->aliased_name == p2->aliased_name; 8999e4b50e9STetsuo Handa } 9009e4b50e9STetsuo Handa 9019590837bSKentaro Takeda /** 9029590837bSKentaro Takeda * list_for_each_cookie - iterate over a list with cookie. 9039590837bSKentaro Takeda * @pos: the &struct list_head to use as a loop cursor. 9049590837bSKentaro Takeda * @cookie: the &struct list_head to use as a cookie. 9059590837bSKentaro Takeda * @head: the head for your list. 9069590837bSKentaro Takeda * 907fdb8ebb7STetsuo Handa * Same with list_for_each_rcu() except that this primitive uses @cookie 9089590837bSKentaro Takeda * so that we can continue iteration. 9099590837bSKentaro Takeda * @cookie must be NULL when iteration starts, and @cookie will become 9109590837bSKentaro Takeda * NULL when iteration finishes. 9119590837bSKentaro Takeda */ 9129590837bSKentaro Takeda #define list_for_each_cookie(pos, cookie, head) \ 9139590837bSKentaro Takeda for (({ if (!cookie) \ 9149590837bSKentaro Takeda cookie = head; }), \ 915fdb8ebb7STetsuo Handa pos = rcu_dereference((cookie)->next); \ 9169590837bSKentaro Takeda prefetch(pos->next), pos != (head) || ((cookie) = NULL); \ 917fdb8ebb7STetsuo Handa (cookie) = pos, pos = rcu_dereference(pos->next)) 918fdb8ebb7STetsuo Handa 9199590837bSKentaro Takeda #endif /* !defined(_SECURITY_TOMOYO_COMMON_H) */ 920