18c2ecf20Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0-or-later 28c2ecf20Sopenharmony_ci/* 38c2ecf20Sopenharmony_ci * 48c2ecf20Sopenharmony_ci * mdp - make dummy policy 58c2ecf20Sopenharmony_ci * 68c2ecf20Sopenharmony_ci * When pointed at a kernel tree, builds a dummy policy for that kernel 78c2ecf20Sopenharmony_ci * with exactly one type with full rights to itself. 88c2ecf20Sopenharmony_ci * 98c2ecf20Sopenharmony_ci * Copyright (C) IBM Corporation, 2006 108c2ecf20Sopenharmony_ci * 118c2ecf20Sopenharmony_ci * Authors: Serge E. Hallyn <serue@us.ibm.com> 128c2ecf20Sopenharmony_ci */ 138c2ecf20Sopenharmony_ci 148c2ecf20Sopenharmony_ci 158c2ecf20Sopenharmony_ci/* NOTE: we really do want to use the kernel headers here */ 168c2ecf20Sopenharmony_ci#define __EXPORTED_HEADERS__ 178c2ecf20Sopenharmony_ci 188c2ecf20Sopenharmony_ci#include <stdio.h> 198c2ecf20Sopenharmony_ci#include <stdlib.h> 208c2ecf20Sopenharmony_ci#include <unistd.h> 218c2ecf20Sopenharmony_ci#include <string.h> 228c2ecf20Sopenharmony_ci#include <linux/kconfig.h> 238c2ecf20Sopenharmony_ci 248c2ecf20Sopenharmony_cistatic void usage(char *name) 258c2ecf20Sopenharmony_ci{ 268c2ecf20Sopenharmony_ci printf("usage: %s [-m] policy_file context_file\n", name); 278c2ecf20Sopenharmony_ci exit(1); 288c2ecf20Sopenharmony_ci} 298c2ecf20Sopenharmony_ci 308c2ecf20Sopenharmony_ci/* Class/perm mapping support */ 318c2ecf20Sopenharmony_cistruct security_class_mapping { 328c2ecf20Sopenharmony_ci const char *name; 338c2ecf20Sopenharmony_ci const char *perms[sizeof(unsigned) * 8 + 1]; 348c2ecf20Sopenharmony_ci}; 358c2ecf20Sopenharmony_ci 368c2ecf20Sopenharmony_ci#include "classmap.h" 378c2ecf20Sopenharmony_ci#include "initial_sid_to_string.h" 388c2ecf20Sopenharmony_ci#include "policycap_names.h" 398c2ecf20Sopenharmony_ci 408c2ecf20Sopenharmony_ci#define ARRAY_SIZE(arr) (sizeof(arr) / sizeof((arr)[0])) 418c2ecf20Sopenharmony_ci 428c2ecf20Sopenharmony_ciint main(int argc, char *argv[]) 438c2ecf20Sopenharmony_ci{ 448c2ecf20Sopenharmony_ci int i, j, mls = 0; 458c2ecf20Sopenharmony_ci int initial_sid_to_string_len; 468c2ecf20Sopenharmony_ci char **arg, *polout, *ctxout; 478c2ecf20Sopenharmony_ci 488c2ecf20Sopenharmony_ci FILE *fout; 498c2ecf20Sopenharmony_ci 508c2ecf20Sopenharmony_ci if (argc < 3) 518c2ecf20Sopenharmony_ci usage(argv[0]); 528c2ecf20Sopenharmony_ci arg = argv+1; 538c2ecf20Sopenharmony_ci if (argc==4 && strcmp(argv[1], "-m") == 0) { 548c2ecf20Sopenharmony_ci mls = 1; 558c2ecf20Sopenharmony_ci arg++; 568c2ecf20Sopenharmony_ci } 578c2ecf20Sopenharmony_ci polout = *arg++; 588c2ecf20Sopenharmony_ci ctxout = *arg; 598c2ecf20Sopenharmony_ci 608c2ecf20Sopenharmony_ci fout = fopen(polout, "w"); 618c2ecf20Sopenharmony_ci if (!fout) { 628c2ecf20Sopenharmony_ci printf("Could not open %s for writing\n", polout); 638c2ecf20Sopenharmony_ci usage(argv[0]); 648c2ecf20Sopenharmony_ci } 658c2ecf20Sopenharmony_ci 668c2ecf20Sopenharmony_ci /* print out the classes */ 678c2ecf20Sopenharmony_ci for (i = 0; secclass_map[i].name; i++) 688c2ecf20Sopenharmony_ci fprintf(fout, "class %s\n", secclass_map[i].name); 698c2ecf20Sopenharmony_ci fprintf(fout, "\n"); 708c2ecf20Sopenharmony_ci 718c2ecf20Sopenharmony_ci initial_sid_to_string_len = sizeof(initial_sid_to_string) / sizeof (char *); 728c2ecf20Sopenharmony_ci /* print out the sids */ 738c2ecf20Sopenharmony_ci for (i = 1; i < initial_sid_to_string_len; i++) { 748c2ecf20Sopenharmony_ci const char *name = initial_sid_to_string[i]; 758c2ecf20Sopenharmony_ci 768c2ecf20Sopenharmony_ci if (name) 778c2ecf20Sopenharmony_ci fprintf(fout, "sid %s\n", name); 788c2ecf20Sopenharmony_ci else 798c2ecf20Sopenharmony_ci fprintf(fout, "sid unused%d\n", i); 808c2ecf20Sopenharmony_ci } 818c2ecf20Sopenharmony_ci fprintf(fout, "\n"); 828c2ecf20Sopenharmony_ci 838c2ecf20Sopenharmony_ci /* print out the class permissions */ 848c2ecf20Sopenharmony_ci for (i = 0; secclass_map[i].name; i++) { 858c2ecf20Sopenharmony_ci struct security_class_mapping *map = &secclass_map[i]; 868c2ecf20Sopenharmony_ci fprintf(fout, "class %s\n", map->name); 878c2ecf20Sopenharmony_ci fprintf(fout, "{\n"); 888c2ecf20Sopenharmony_ci for (j = 0; map->perms[j]; j++) 898c2ecf20Sopenharmony_ci fprintf(fout, "\t%s\n", map->perms[j]); 908c2ecf20Sopenharmony_ci fprintf(fout, "}\n\n"); 918c2ecf20Sopenharmony_ci } 928c2ecf20Sopenharmony_ci fprintf(fout, "\n"); 938c2ecf20Sopenharmony_ci 948c2ecf20Sopenharmony_ci /* print out mls declarations and constraints */ 958c2ecf20Sopenharmony_ci if (mls) { 968c2ecf20Sopenharmony_ci fprintf(fout, "sensitivity s0;\n"); 978c2ecf20Sopenharmony_ci fprintf(fout, "sensitivity s1;\n"); 988c2ecf20Sopenharmony_ci fprintf(fout, "dominance { s0 s1 }\n"); 998c2ecf20Sopenharmony_ci fprintf(fout, "category c0;\n"); 1008c2ecf20Sopenharmony_ci fprintf(fout, "category c1;\n"); 1018c2ecf20Sopenharmony_ci fprintf(fout, "level s0:c0.c1;\n"); 1028c2ecf20Sopenharmony_ci fprintf(fout, "level s1:c0.c1;\n"); 1038c2ecf20Sopenharmony_ci#define SYSTEMLOW "s0" 1048c2ecf20Sopenharmony_ci#define SYSTEMHIGH "s1:c0.c1" 1058c2ecf20Sopenharmony_ci for (i = 0; secclass_map[i].name; i++) { 1068c2ecf20Sopenharmony_ci struct security_class_mapping *map = &secclass_map[i]; 1078c2ecf20Sopenharmony_ci 1088c2ecf20Sopenharmony_ci fprintf(fout, "mlsconstrain %s {\n", map->name); 1098c2ecf20Sopenharmony_ci for (j = 0; map->perms[j]; j++) 1108c2ecf20Sopenharmony_ci fprintf(fout, "\t%s\n", map->perms[j]); 1118c2ecf20Sopenharmony_ci /* 1128c2ecf20Sopenharmony_ci * This requires all subjects and objects to be 1138c2ecf20Sopenharmony_ci * single-level (l2 eq h2), and that the subject 1148c2ecf20Sopenharmony_ci * level dominate the object level (h1 dom h2) 1158c2ecf20Sopenharmony_ci * in order to have any permissions to it. 1168c2ecf20Sopenharmony_ci */ 1178c2ecf20Sopenharmony_ci fprintf(fout, "} (l2 eq h2 and h1 dom h2);\n\n"); 1188c2ecf20Sopenharmony_ci } 1198c2ecf20Sopenharmony_ci } 1208c2ecf20Sopenharmony_ci 1218c2ecf20Sopenharmony_ci /* enable all policy capabilities */ 1228c2ecf20Sopenharmony_ci for (i = 0; i < ARRAY_SIZE(selinux_policycap_names); i++) 1238c2ecf20Sopenharmony_ci fprintf(fout, "policycap %s;\n", selinux_policycap_names[i]); 1248c2ecf20Sopenharmony_ci 1258c2ecf20Sopenharmony_ci /* types, roles, and allows */ 1268c2ecf20Sopenharmony_ci fprintf(fout, "type base_t;\n"); 1278c2ecf20Sopenharmony_ci fprintf(fout, "role base_r;\n"); 1288c2ecf20Sopenharmony_ci fprintf(fout, "role base_r types { base_t };\n"); 1298c2ecf20Sopenharmony_ci for (i = 0; secclass_map[i].name; i++) 1308c2ecf20Sopenharmony_ci fprintf(fout, "allow base_t base_t:%s *;\n", 1318c2ecf20Sopenharmony_ci secclass_map[i].name); 1328c2ecf20Sopenharmony_ci fprintf(fout, "user user_u roles { base_r }"); 1338c2ecf20Sopenharmony_ci if (mls) 1348c2ecf20Sopenharmony_ci fprintf(fout, " level %s range %s - %s", SYSTEMLOW, 1358c2ecf20Sopenharmony_ci SYSTEMLOW, SYSTEMHIGH); 1368c2ecf20Sopenharmony_ci fprintf(fout, ";\n"); 1378c2ecf20Sopenharmony_ci 1388c2ecf20Sopenharmony_ci#define SUBJUSERROLETYPE "user_u:base_r:base_t" 1398c2ecf20Sopenharmony_ci#define OBJUSERROLETYPE "user_u:object_r:base_t" 1408c2ecf20Sopenharmony_ci 1418c2ecf20Sopenharmony_ci /* default sids */ 1428c2ecf20Sopenharmony_ci for (i = 1; i < initial_sid_to_string_len; i++) { 1438c2ecf20Sopenharmony_ci const char *name = initial_sid_to_string[i]; 1448c2ecf20Sopenharmony_ci 1458c2ecf20Sopenharmony_ci if (name) 1468c2ecf20Sopenharmony_ci fprintf(fout, "sid %s ", name); 1478c2ecf20Sopenharmony_ci else 1488c2ecf20Sopenharmony_ci fprintf(fout, "sid unused%d\n", i); 1498c2ecf20Sopenharmony_ci fprintf(fout, SUBJUSERROLETYPE "%s\n", 1508c2ecf20Sopenharmony_ci mls ? ":" SYSTEMLOW : ""); 1518c2ecf20Sopenharmony_ci } 1528c2ecf20Sopenharmony_ci fprintf(fout, "\n"); 1538c2ecf20Sopenharmony_ci 1548c2ecf20Sopenharmony_ci#define FS_USE(behavior, fstype) \ 1558c2ecf20Sopenharmony_ci fprintf(fout, "fs_use_%s %s " OBJUSERROLETYPE "%s;\n", \ 1568c2ecf20Sopenharmony_ci behavior, fstype, mls ? ":" SYSTEMLOW : "") 1578c2ecf20Sopenharmony_ci 1588c2ecf20Sopenharmony_ci /* 1598c2ecf20Sopenharmony_ci * Filesystems whose inode labels can be fetched via getxattr. 1608c2ecf20Sopenharmony_ci */ 1618c2ecf20Sopenharmony_ci#ifdef CONFIG_EXT2_FS_SECURITY 1628c2ecf20Sopenharmony_ci FS_USE("xattr", "ext2"); 1638c2ecf20Sopenharmony_ci#endif 1648c2ecf20Sopenharmony_ci#ifdef CONFIG_EXT4_FS_SECURITY 1658c2ecf20Sopenharmony_ci#ifdef CONFIG_EXT4_USE_FOR_EXT2 1668c2ecf20Sopenharmony_ci FS_USE("xattr", "ext2"); 1678c2ecf20Sopenharmony_ci#endif 1688c2ecf20Sopenharmony_ci FS_USE("xattr", "ext3"); 1698c2ecf20Sopenharmony_ci FS_USE("xattr", "ext4"); 1708c2ecf20Sopenharmony_ci#endif 1718c2ecf20Sopenharmony_ci#ifdef CONFIG_JFS_SECURITY 1728c2ecf20Sopenharmony_ci FS_USE("xattr", "jfs"); 1738c2ecf20Sopenharmony_ci#endif 1748c2ecf20Sopenharmony_ci#ifdef CONFIG_REISERFS_FS_SECURITY 1758c2ecf20Sopenharmony_ci FS_USE("xattr", "reiserfs"); 1768c2ecf20Sopenharmony_ci#endif 1778c2ecf20Sopenharmony_ci#ifdef CONFIG_JFFS2_FS_SECURITY 1788c2ecf20Sopenharmony_ci FS_USE("xattr", "jffs2"); 1798c2ecf20Sopenharmony_ci#endif 1808c2ecf20Sopenharmony_ci#ifdef CONFIG_XFS_FS 1818c2ecf20Sopenharmony_ci FS_USE("xattr", "xfs"); 1828c2ecf20Sopenharmony_ci#endif 1838c2ecf20Sopenharmony_ci#ifdef CONFIG_GFS2_FS 1848c2ecf20Sopenharmony_ci FS_USE("xattr", "gfs2"); 1858c2ecf20Sopenharmony_ci#endif 1868c2ecf20Sopenharmony_ci#ifdef CONFIG_BTRFS_FS 1878c2ecf20Sopenharmony_ci FS_USE("xattr", "btrfs"); 1888c2ecf20Sopenharmony_ci#endif 1898c2ecf20Sopenharmony_ci#ifdef CONFIG_F2FS_FS_SECURITY 1908c2ecf20Sopenharmony_ci FS_USE("xattr", "f2fs"); 1918c2ecf20Sopenharmony_ci#endif 1928c2ecf20Sopenharmony_ci#ifdef CONFIG_OCFS2_FS 1938c2ecf20Sopenharmony_ci FS_USE("xattr", "ocsfs2"); 1948c2ecf20Sopenharmony_ci#endif 1958c2ecf20Sopenharmony_ci#ifdef CONFIG_OVERLAY_FS 1968c2ecf20Sopenharmony_ci FS_USE("xattr", "overlay"); 1978c2ecf20Sopenharmony_ci#endif 1988c2ecf20Sopenharmony_ci#ifdef CONFIG_SQUASHFS_XATTR 1998c2ecf20Sopenharmony_ci FS_USE("xattr", "squashfs"); 2008c2ecf20Sopenharmony_ci#endif 2018c2ecf20Sopenharmony_ci 2028c2ecf20Sopenharmony_ci /* 2038c2ecf20Sopenharmony_ci * Filesystems whose inodes are labeled from allocating task. 2048c2ecf20Sopenharmony_ci */ 2058c2ecf20Sopenharmony_ci FS_USE("task", "pipefs"); 2068c2ecf20Sopenharmony_ci FS_USE("task", "sockfs"); 2078c2ecf20Sopenharmony_ci 2088c2ecf20Sopenharmony_ci /* 2098c2ecf20Sopenharmony_ci * Filesystems whose inode labels are computed from both 2108c2ecf20Sopenharmony_ci * the allocating task and the superblock label. 2118c2ecf20Sopenharmony_ci */ 2128c2ecf20Sopenharmony_ci#ifdef CONFIG_UNIX98_PTYS 2138c2ecf20Sopenharmony_ci FS_USE("trans", "devpts"); 2148c2ecf20Sopenharmony_ci#endif 2158c2ecf20Sopenharmony_ci#ifdef CONFIG_HUGETLBFS 2168c2ecf20Sopenharmony_ci FS_USE("trans", "hugetlbfs"); 2178c2ecf20Sopenharmony_ci#endif 2188c2ecf20Sopenharmony_ci#ifdef CONFIG_TMPFS 2198c2ecf20Sopenharmony_ci FS_USE("trans", "tmpfs"); 2208c2ecf20Sopenharmony_ci#endif 2218c2ecf20Sopenharmony_ci#ifdef CONFIG_DEVTMPFS 2228c2ecf20Sopenharmony_ci FS_USE("trans", "devtmpfs"); 2238c2ecf20Sopenharmony_ci#endif 2248c2ecf20Sopenharmony_ci#ifdef CONFIG_POSIX_MQUEUE 2258c2ecf20Sopenharmony_ci FS_USE("trans", "mqueue"); 2268c2ecf20Sopenharmony_ci#endif 2278c2ecf20Sopenharmony_ci 2288c2ecf20Sopenharmony_ci#define GENFSCON(fstype, prefix) \ 2298c2ecf20Sopenharmony_ci fprintf(fout, "genfscon %s %s " OBJUSERROLETYPE "%s\n", \ 2308c2ecf20Sopenharmony_ci fstype, prefix, mls ? ":" SYSTEMLOW : "") 2318c2ecf20Sopenharmony_ci 2328c2ecf20Sopenharmony_ci /* 2338c2ecf20Sopenharmony_ci * Filesystems whose inodes are labeled from path prefix match 2348c2ecf20Sopenharmony_ci * relative to the filesystem root. Depending on the filesystem, 2358c2ecf20Sopenharmony_ci * only a single label for all inodes may be supported. Here 2368c2ecf20Sopenharmony_ci * we list the filesystem types for which per-file labeling is 2378c2ecf20Sopenharmony_ci * supported using genfscon; any other filesystem type can also 2388c2ecf20Sopenharmony_ci * be added by only with a single entry for all of its inodes. 2398c2ecf20Sopenharmony_ci */ 2408c2ecf20Sopenharmony_ci#ifdef CONFIG_PROC_FS 2418c2ecf20Sopenharmony_ci GENFSCON("proc", "/"); 2428c2ecf20Sopenharmony_ci#endif 2438c2ecf20Sopenharmony_ci#ifdef CONFIG_SECURITY_SELINUX 2448c2ecf20Sopenharmony_ci GENFSCON("selinuxfs", "/"); 2458c2ecf20Sopenharmony_ci#endif 2468c2ecf20Sopenharmony_ci#ifdef CONFIG_SYSFS 2478c2ecf20Sopenharmony_ci GENFSCON("sysfs", "/"); 2488c2ecf20Sopenharmony_ci#endif 2498c2ecf20Sopenharmony_ci#ifdef CONFIG_DEBUG_FS 2508c2ecf20Sopenharmony_ci GENFSCON("debugfs", "/"); 2518c2ecf20Sopenharmony_ci#endif 2528c2ecf20Sopenharmony_ci#ifdef CONFIG_TRACING 2538c2ecf20Sopenharmony_ci GENFSCON("tracefs", "/"); 2548c2ecf20Sopenharmony_ci#endif 2558c2ecf20Sopenharmony_ci#ifdef CONFIG_PSTORE 2568c2ecf20Sopenharmony_ci GENFSCON("pstore", "/"); 2578c2ecf20Sopenharmony_ci#endif 2588c2ecf20Sopenharmony_ci GENFSCON("cgroup", "/"); 2598c2ecf20Sopenharmony_ci GENFSCON("cgroup2", "/"); 2608c2ecf20Sopenharmony_ci 2618c2ecf20Sopenharmony_ci fclose(fout); 2628c2ecf20Sopenharmony_ci 2638c2ecf20Sopenharmony_ci fout = fopen(ctxout, "w"); 2648c2ecf20Sopenharmony_ci if (!fout) { 2658c2ecf20Sopenharmony_ci printf("Wrote policy, but cannot open %s for writing\n", ctxout); 2668c2ecf20Sopenharmony_ci usage(argv[0]); 2678c2ecf20Sopenharmony_ci } 2688c2ecf20Sopenharmony_ci fprintf(fout, "/ " OBJUSERROLETYPE "%s\n", mls ? ":" SYSTEMLOW : ""); 2698c2ecf20Sopenharmony_ci fprintf(fout, "/.* " OBJUSERROLETYPE "%s\n", mls ? ":" SYSTEMLOW : ""); 2708c2ecf20Sopenharmony_ci fclose(fout); 2718c2ecf20Sopenharmony_ci 2728c2ecf20Sopenharmony_ci return 0; 2738c2ecf20Sopenharmony_ci} 274