1.Selinux简介
SELinux(Security-Enhanced Linux) 是美国国家安全局(NSA)对于强制访问控制的实现,是 Linux历史上最杰出的新安全子系统。
SELinux的软件设计架构是参照Flask,Flask是一种灵活的操作系统安全架构,并且在Fluke research operating system中得到了实现。Flask的主要特点是把安全策略执行代码和安全策略决策代码,划分成了两个组件。安全策略决策代码在Flask架构中称作Security Server。除了这两个组件以外,另外一个组件Vector Cache(AVC), 主要提供策略决策结果的缓存,以此提高Security Server的性能。
SELinux 运行有三个运行状态,分别是disabled, permissive 和 enforcing
Disable: 禁用SELinux,不会给任何新资源打Label,如果重新启用的话,将会给资源重新打上Lable,过程会比较缓慢。
Permissive:如果违反安全策略,并不会真正的执行拒绝操作,替代的方式是记录一条log信息。\
Enforcing: 默认模式,SELinux的正常状态,会实际禁用违反策略的操作
2.设置和获取selinux的标志
static char *g_pszSelinuxFileSystemString=NULL;
static char **g_pSelinuxFileSystemStringPointer = &g_pszSelinuxFileSystemString;
//用户设置selinux的标志
int setSelinuxFlag(int value) {
int fd=0, length=0;
char fileContentBuffer[20]={0};
char filePath[1024]={0};
if (*g_pSelinuxFileSystemStringPointer == NULL) {
errno = 2;
return -1;
}
snprintf(filePath, 1024, "%s/enforce", *g_pSelinuxFileSystemStringPointer);
fd = open(filePath, 2);
if (fd < 0)
return -1;
snprintf(fileContentBuffer, 20, "%d", value);
length = strlen(fileContentBuffer);
length = write(fd, fileContentBuffer, len);
close(fd);
return length >> 31;
}
//用于获取selinux的标志
int getSelinuxFlag() {
int fd=0, readLength=0, value=0;
char fileContentBuffer[20]={0};
char filePath[1024]={0};
if (*g_pSelinuxFileSystemStringPointer == NULL) {
errno = 2;
return -1;
}
snprintf(filePath, 1024, "%s/enforce", *g_pSelinuxFileSystemStringPointer);
fd = open(filePath, 0);
if (fd < 0)
return -1;
memset(fileContentBuffer, 0, 20);
readLength = read(fd, fileContentBuffer, 19);
close(fd);
if (readLength < 0)
return -1;
readLength = sscanf(fileContentBuffer, "%d", &value);
if (readLength != 1)
return -1;
return value;
}
3.检测selinux实现
//检测selinux
void checkSelinux() {
if (*g_pSelinuxFileSystemStringPointer == NULL) {
int ret=0;
FILE *pFilesystems=NULL;
char fileLineBuffer[1024]={0};
struct statfs statfsBuffer={0};
while ((ret = statfs("/sys/fs/selinux", &statfsBuffer)) < 0) {
if (errno == EINTR)
continue;
LOGE("statfs error:%s\n", strerror(errno));
return ;
}
if (ret == 0 && statfsBuffer.f_type == 0xF97CFF8C ) {
*g_pSelinuxFileSystemStringPointer = strdup("/sys/fs/selinux");
return;
}
pFilesystems = fopen("/proc/filesystems", "r");
if (pFilesystems == NULL)
return ;
do {
if (fgets(fileLineBuffer, 1024, pFilesystems) == NULL) {
fclose(pFilesystems);
return ;
}
if (strstr(fileLineBuffer, "selinuxfs")) {
break;
}
} while (1);
fclose(pFilesystems);
pFilesystems = fopen("/proc/mounts", "r");
if (pFilesystems == NULL)
return ;
do {
char *spacePosition;
char *fileSystemName;
if (fgets(fileLineBuffer, 1024, pFilesystems) == NULL) {
fclose(pFilesystems);
return ;
}
spacePosition = strchr(fileLineBuffer, ' ');
if (spacePosition == NULL) {
fclose(pFilesystems);
return ;
}
spacePosition++;
fileSystemName = spacePosition;
spacePosition = strchr(fileSystemName, ' ');
if (spacePosition == NULL) {
fclose(pFilesystems);
return ;
}
spacePosition++;
if (strncmp(spacePosition, "selinuxfs ", 10) != 0)
continue;
*(spacePosition -1) = 0;
*g_pSelinuxFileSystemStringPointer = strdup(fileSystemName);
break;
} while (1);
fclose(pFilesystems);
}
}