这个博客主要留给自己参考用的,不指望帮助到其他人。
内核版本 5.4.83
1、首先注册了sel_fs_type文件系统,提供了一系列接口,这里只分析了sel_load_ops,这个用来解析规则数据库,解析到的数据会放到avtab_node结构体的变量中,然后将变量插入到一个表中。
init_sel_fs
sel_fill_super
selinux_fs_info_create
fsi->state = &selinux_state;
fsi->sb = sb;
sb->s_fs_info = fsi;
sel_write_load
security_load_policy(fsi->state, data, count);
policydb = &state->ss->policydb;
policydb_read(policydb, fp);
avtab_read(&p->te_avtab, fp, p);
avtab_read_item(a, fp, pol, avtab_insertf, NULL); //avtab_insertf
avtab_insert(a, k, d);
avtab_insert_node(h, hvalue, prev, cur, key, datum);
struct avtab_node *newnode;
newnode->key = *key;
newnode->datum.u.data = datum->u.data;
struct avtab_node **n = &h->htable[hvalue];
*n = newnode;
2、selinux作为一个安全模块,需要相关配置才能生效。初始化流程主要注册了一系列回调函数。
selinux_init
selinux_ss_init(&selinux_state.ss);
selinux_avc_init(&selinux_state.avc);
security_add_hooks(selinux_hooks, ARRAY_SIZE(selinux_hooks), "selinux");
3、这里只分析了一个回调函数。主要是根据ssid, tsid, tclass在表中找到相应的规则数据,然后判断操作是否允许。state->avc是一个缓存器。
selinux_inode_create
may_create(dir, dentry, SECCLASS_FILE);
avc_has_perm(&selinux_state, sid, dsec->sid, SECCLASS_DIR, DIR__ADD_NAME | DIR__SEARCH, &ad);
avc_has_perm_noaudit(state, ssid, tsid, tclass, requested, 0, &avd);
//node = avc_lookup(state->avc, ssid, tsid, tclass);
//memcpy(avd, &node->ae.avd, sizeof(*avd));
avc_compute_av(state, ssid, tsid, tclass, avd, &xp_node);
security_compute_av(state, ssid, tsid, tclass, avd, &xp_node->xp);
context_struct_compute_av(policydb, scontext, tcontext, tclass, avd, xperms);
node = avtab_search_node(&policydb->te_avtab, &avkey);
avd->allowed |= node->datum.u.data;
avc_insert(state->avc, ssid, tsid, tclass, avd, xp_node);
//denied = requested & ~(avd->allowed);
//rc = avc_denied(state, ssid, tsid, tclass, requested, 0, 0, flags, avd);
return rc;