1f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <unistd.h> 2f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <fcntl.h> 3f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <string.h> 4f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <stdlib.h> 5f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <errno.h> 6f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <ctype.h> 7f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <stdio.h> 8f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <dlfcn.h> 9cc3d76d1b717805740126aec7e0343f5a240cfbeStephen Smalley 10cc3d76d1b717805740126aec7e0343f5a240cfbeStephen Smalley#ifdef DARWIN 11cc3d76d1b717805740126aec7e0343f5a240cfbeStephen Smalley#include <sys/param.h> 12cc3d76d1b717805740126aec7e0343f5a240cfbeStephen Smalley#include <sys/mount.h> 13cc3d76d1b717805740126aec7e0343f5a240cfbeStephen Smalley#else 14f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <sys/vfs.h> 15cc3d76d1b717805740126aec7e0343f5a240cfbeStephen Smalley#endif 16cc3d76d1b717805740126aec7e0343f5a240cfbeStephen Smalley 17f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <stdint.h> 18f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include <limits.h> 19f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 20f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include "dso.h" 21f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include "policy.h" 22f074036424618c130dacb3464465a8b40bffef5Stephen Smalley#include "selinux_internal.h" 23f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 24f074036424618c130dacb3464465a8b40bffef5Stephen Smalleychar *selinux_mnt = NULL; 25f074036424618c130dacb3464465a8b40bffef5Stephen Smalleyint selinux_page_size = 0; 26f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 27f074036424618c130dacb3464465a8b40bffef5Stephen Smalleystatic void init_selinuxmnt(void) 28f074036424618c130dacb3464465a8b40bffef5Stephen Smalley{ 29f074036424618c130dacb3464465a8b40bffef5Stephen Smalley char buf[BUFSIZ], *p; 30f074036424618c130dacb3464465a8b40bffef5Stephen Smalley FILE *fp=NULL; 31f074036424618c130dacb3464465a8b40bffef5Stephen Smalley struct statfs sfbuf; 32f074036424618c130dacb3464465a8b40bffef5Stephen Smalley int rc; 33f074036424618c130dacb3464465a8b40bffef5Stephen Smalley char *bufp; 34f074036424618c130dacb3464465a8b40bffef5Stephen Smalley int exists = 0; 35f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 36f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (selinux_mnt) 37f074036424618c130dacb3464465a8b40bffef5Stephen Smalley return; 38f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 39f074036424618c130dacb3464465a8b40bffef5Stephen Smalley /* We check to see if the preferred mount point for selinux file 40f074036424618c130dacb3464465a8b40bffef5Stephen Smalley * system has a selinuxfs. */ 41f074036424618c130dacb3464465a8b40bffef5Stephen Smalley do { 42f074036424618c130dacb3464465a8b40bffef5Stephen Smalley rc = statfs(SELINUXMNT, &sfbuf); 43f074036424618c130dacb3464465a8b40bffef5Stephen Smalley } while (rc < 0 && errno == EINTR); 44f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (rc == 0) { 45f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if ((uint32_t)sfbuf.f_type == (uint32_t)SELINUX_MAGIC) { 46f074036424618c130dacb3464465a8b40bffef5Stephen Smalley selinux_mnt = strdup(SELINUXMNT); 47f074036424618c130dacb3464465a8b40bffef5Stephen Smalley return; 48f074036424618c130dacb3464465a8b40bffef5Stephen Smalley } 49f074036424618c130dacb3464465a8b40bffef5Stephen Smalley } 50f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 51f074036424618c130dacb3464465a8b40bffef5Stephen Smalley /* Drop back to detecting it the long way. */ 52f074036424618c130dacb3464465a8b40bffef5Stephen Smalley fp = fopen("/proc/filesystems", "r"); 53f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (!fp) 54f074036424618c130dacb3464465a8b40bffef5Stephen Smalley return; 55f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 56f074036424618c130dacb3464465a8b40bffef5Stephen Smalley while ((bufp = fgets(buf, sizeof buf - 1, fp)) != NULL) { 57f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (strstr(buf, "selinuxfs")) { 58f074036424618c130dacb3464465a8b40bffef5Stephen Smalley exists = 1; 59f074036424618c130dacb3464465a8b40bffef5Stephen Smalley break; 60f074036424618c130dacb3464465a8b40bffef5Stephen Smalley } 61f074036424618c130dacb3464465a8b40bffef5Stephen Smalley } 62f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 63f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (!exists) 64f074036424618c130dacb3464465a8b40bffef5Stephen Smalley goto out; 65f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 66f074036424618c130dacb3464465a8b40bffef5Stephen Smalley fclose(fp); 67f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 68f074036424618c130dacb3464465a8b40bffef5Stephen Smalley /* At this point, the usual spot doesn't have an selinuxfs so 69f074036424618c130dacb3464465a8b40bffef5Stephen Smalley * we look around for it */ 70f074036424618c130dacb3464465a8b40bffef5Stephen Smalley fp = fopen("/proc/mounts", "r"); 71f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (!fp) 72f074036424618c130dacb3464465a8b40bffef5Stephen Smalley goto out; 73f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 74f074036424618c130dacb3464465a8b40bffef5Stephen Smalley while ((bufp = fgets(buf, sizeof buf - 1, fp)) != NULL) { 75f074036424618c130dacb3464465a8b40bffef5Stephen Smalley char *tmp; 76f074036424618c130dacb3464465a8b40bffef5Stephen Smalley p = strchr(buf, ' '); 77f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (!p) 78f074036424618c130dacb3464465a8b40bffef5Stephen Smalley goto out; 79f074036424618c130dacb3464465a8b40bffef5Stephen Smalley p++; 80f074036424618c130dacb3464465a8b40bffef5Stephen Smalley tmp = strchr(p, ' '); 81f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (!tmp) 82f074036424618c130dacb3464465a8b40bffef5Stephen Smalley goto out; 83f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (!strncmp(tmp + 1, "selinuxfs ", 10)) { 84f074036424618c130dacb3464465a8b40bffef5Stephen Smalley *tmp = '\0'; 85f074036424618c130dacb3464465a8b40bffef5Stephen Smalley break; 86f074036424618c130dacb3464465a8b40bffef5Stephen Smalley } 87f074036424618c130dacb3464465a8b40bffef5Stephen Smalley } 88f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 89f074036424618c130dacb3464465a8b40bffef5Stephen Smalley /* If we found something, dup it */ 90f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (bufp) 91f074036424618c130dacb3464465a8b40bffef5Stephen Smalley selinux_mnt = strdup(p); 92f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 93f074036424618c130dacb3464465a8b40bffef5Stephen Smalley out: 94f074036424618c130dacb3464465a8b40bffef5Stephen Smalley if (fp) 95f074036424618c130dacb3464465a8b40bffef5Stephen Smalley fclose(fp); 96f074036424618c130dacb3464465a8b40bffef5Stephen Smalley return; 97f074036424618c130dacb3464465a8b40bffef5Stephen Smalley} 98f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 99f074036424618c130dacb3464465a8b40bffef5Stephen Smalleyvoid fini_selinuxmnt(void) 100f074036424618c130dacb3464465a8b40bffef5Stephen Smalley{ 101f074036424618c130dacb3464465a8b40bffef5Stephen Smalley free(selinux_mnt); 102f074036424618c130dacb3464465a8b40bffef5Stephen Smalley selinux_mnt = NULL; 103f074036424618c130dacb3464465a8b40bffef5Stephen Smalley} 104f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 105f074036424618c130dacb3464465a8b40bffef5Stephen Smalleyvoid set_selinuxmnt(char *mnt) 106f074036424618c130dacb3464465a8b40bffef5Stephen Smalley{ 107f074036424618c130dacb3464465a8b40bffef5Stephen Smalley selinux_mnt = strdup(mnt); 108f074036424618c130dacb3464465a8b40bffef5Stephen Smalley} 109f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 110f074036424618c130dacb3464465a8b40bffef5Stephen Smalleyhidden_def(set_selinuxmnt) 111f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 112f074036424618c130dacb3464465a8b40bffef5Stephen Smalleystatic void init_lib(void) __attribute__ ((constructor)); 113f074036424618c130dacb3464465a8b40bffef5Stephen Smalleystatic void init_lib(void) 114f074036424618c130dacb3464465a8b40bffef5Stephen Smalley{ 115f074036424618c130dacb3464465a8b40bffef5Stephen Smalley selinux_page_size = sysconf(_SC_PAGE_SIZE); 116f074036424618c130dacb3464465a8b40bffef5Stephen Smalley init_selinuxmnt(); 117f074036424618c130dacb3464465a8b40bffef5Stephen Smalley} 118f074036424618c130dacb3464465a8b40bffef5Stephen Smalley 119f074036424618c130dacb3464465a8b40bffef5Stephen Smalleystatic void fini_lib(void) __attribute__ ((destructor)); 120f074036424618c130dacb3464465a8b40bffef5Stephen Smalleystatic void fini_lib(void) 121f074036424618c130dacb3464465a8b40bffef5Stephen Smalley{ 122f074036424618c130dacb3464465a8b40bffef5Stephen Smalley fini_selinuxmnt(); 123f074036424618c130dacb3464465a8b40bffef5Stephen Smalley} 124