重要函数的分析正如上文所介绍的安全服务器的作用,这些功能最终都会交由具体的应用来实现,下面主要针对SELinux来对这些功能的核心实现函数进行分析。
1.security_context_to_sid_core()
security_context_to_sid_core()函数是获取安全上下文对应的SID的核心,其他的函数,如security_context_to_sid()函数(该函数用于获取给定的安全上下文对应的SID)、security_contet_to_sid_default()函数(该函数用于获取给定的安全上下文对应的SID,如果需要的话,返回指定的默认的SID)等均是简单的封装了该函数,下面主要对其进行分析。
security_context_to_sid_core()函数用于获取字符串形式的安全上下文对应的SID,成功时返回0,函数头如下所示:
static int security_context_to_sid_core(constchar *scontext,u32scontext_len,
u32*sid, u32def_sid, gfp_tgfp_flags,int force)
该函数包含6个参数:scontext表示字符串形式的安全上下文;scontext_len表示scontext的长度;sid用来存放scontext对应的SID;def_sid指定了默认的SID;gfp_flags表示内存分配的标志;force只是一个标志。对于该函数,其函数调用流程如图所示,下面结合源码对该函数主要执行步骤进行说明:
①判断ss_initialized变量是否设置。如果没有设置,表示安全服务器还没有初始化,此时通过循环来依次比较初始SID对应的安全上下文字符串是否与待转换的字符串形式的安全上下文相等,若相等,则将相应的初始SID赋给sid,反之将SECINITSID_KERNEL赋给sid,最后返回0。
②调用kmalloc()函数来申请长度为scontext_len的空间来存放scontext。
③调用string_to_context_struct()函数将字符串形式的安全上下文转换为相应的安全上下文结构体。
④调用sidtab_context_to_sid()函数获取指定的安全上下文对应的SID。
⑤调用context_destroy()函数来销毁相应的临时安全上下文结构。
⑥调用kfree()函数释放中间申请的临时的存储空间。
⑦结束并返回。
![]()
相对于该函数,还有一个函数security_sid_to_context_core(),该函数是获取给定的SID对应的上下文的核心函数,其用于将SID关联的安全上下文的字符串写入动态分配的内存中,函数头如下所示:
static int security_sid_to_context_core(u32sid, char **scontext,u32*scontext_len,int force)
该函数包含4个参数:sid表示待转换的目标SID;scontext用来存储sid对应的字符串形式的安全上下文;scontext_len用来存储字符串形式的安全上下文的长度;force只是一个标志。
![]()
如图所示,下面结合源码对该函数的主要执行步骤进行说明:
①判断ss_initialized变量是否设置。如果没有设置,表示安全服务器还没有初始化。此时判断sid是否小于等于SECINITSID_NUM:
a.如果sid小于等于SECINITSID_NUM,说明待转换的sid为一个初始SID,此时通过initial_sid_to_string()函数获取sid对应的字符串,然后根据字符串的长度申请相应的存储空间,并将该字符串存放到该存储空间中,最后让scontext指向该段空间,并返回。
b.如果sid大于SECINITSID_NUM,说明sid是一个无效的SID,则设置错误码并返回。
②根据参数force是否设置来调用相应的函数来从sid表中获取待转换的sid对应的安全上下文。如果参数force为真,则调用sidtab_search_force()函数,反之调用sidtab_search()函数。
③判断sid对应的安全上下文是否有效,如果无效,则设置相应的错误码,然后返回。
④调用context_struct_to_string()函数来将待转换sid对应的安全上下文字符串写入到一个动态分配的字符串中。
⑤结束并返回。