发明内容
鉴于上述问题,提出了本发明以便提供一种克服上述问题或者至少部分地解决上述问题的一种可加载内核模块的编译方法和相应的一种可加载内核模块的编译装置。
依据本发明的一个方面,提供了一种可加载内核模块的编译方法,包括:
当应用程序的组件被触发时,读取所述组件对应的一个或多个可加载内核模块LKM模板;
检测所述一个或多个可加载内核模块LKM模板是否支持当前设备的处理器和/或当前操作系统的系统内核;
若是,则对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配;
采用适配的可加载内核模块LKM模板编译目标可加载内核模块LKM。
可选地,所述可加载内核模块LKM模板通过以下方式生成:
基于模板操作系统的内核环境编译可加载内核模块LKM模板。
可选地,所述可加载内核模块LKM模板还通过以下方式生成:
将所述可加载内核模块LKM模板编译为二进制数组;
将所述二进制数组与模板标识固化在源文件中;
其中,所述模板标识包括可支持的处理器版本信息、组件标识、可支持的内核版本范围中的至少一个;所述模板操作系统的系统内核的内核版本归属于内核版本范围。
可选地,所述读取所述组件对应的一个或多个可加载内核模块LKM模板的步骤包括:
获取与所述组件匹配的组件标识;
读取所述组件标识对应的一个或多个可加载内核模块LKM模板。
可选地,所述获取与所述组件匹配的组件标识的步骤包括:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中、与所述组件匹配的组件标识。
可选地,所述检测所述一个或多个可加载内核模块LKM模板是否支持当前设备的处理器和/或当前操作系统的系统内核的步骤包括:
获取所述可加载内核模块LKM模板支持的处理器版本信息;
读取当前设备的处理器的版本信息;
检测当前设备的处理器的版本信息是否与所述源文件中处理器版本信息匹配;
若是,则判断所述可加载内核模块LKM模板支持当前设备的处理器。
可选地,所述获取所述可加载内核模块LKM模板支持的处理器版本信息的步骤包括:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的处理器版本信息。
可选地,所述检测所述一个或多个可加载内核模块LKM模板是否支持当前设备的处理器和/或当前操作系统的系统内核的步骤包括:
获取所述可加载内核模块LKM模板支持的内核版本范围;
读取当前操作系统的系统内核的版本信息;
检测当前操作系统的系统内核的版本信息是否归属于所述源文件中的内核版本范围;
若是,则判断所述可加载内核模块LKM模板支持当前操作系统的系统内核。
可选地,所述获取所述可加载内核模块LKM模板支持的内核版本范围的步骤包括:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的内核版本范围。
可选地,所述对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配的步骤包括:
分别读取所述可加载内核模块LKM模板中的配置信息Vermagic和操作系统中的配置信息Vermagic;
判断所述可加载内核模块LKM模板中的配置信息Vermagic与所述操作系统中的配置信息Vermagic是否匹配;
当匹配时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
可选地,所述对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配的步骤包括:
当未匹配时,将操作系统中的配置信息Vermagic的值替换对应的可加载内核模块LKM模板中读取配置信息Vermagic的值。
可选地,所述对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配的步骤包括:
从所述可加载内核模块LKM模板中读取编译所需的第一符号;
读取与操作系统适配的、编译所需的第二符号;
将所述第二符号的值替换所述第一符号的值;
当全部符号的值替换成功时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
可选地,所述读取与操作系统适配的、编译所需的符号的步骤包括:
从操作系统的指定文件中读取编译所需的第二符号;
和/或,
从操作系统的其他可加载内核模块LKM中读取编译所需的第二符号。
可选地,所述采用适配的可加载内核模块LKM模板编译目标可加载内核模块LKM的步骤包括:
当适配的可加载内核模块LKM模板固化在源文件时,从源文件中读取二进制数组形式的可加载内核模块LKM模板;
采用二进制数组形式的可加载内核模块LKM模板编译目标可加载内核模块LKM。
可选地,所述方法还包括:
将所述目标可加载内核模块LKM加载进当前操作系统的系统内核中。
根据本发明的另一方面,提供了一种可加载内核模块的编译装置,包括:
读取模块,适于在应用程序的组件被触发时,读取所述组件对应的一个或多个可加载内核模块LKM模板;
检测模块,适于检测所述一个或多个可加载内核模块LKM模板是否支持当前设备的处理器和/或当前操作系统的系统内核;若是,则调用适配模块;
适配模块,适于对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配;
编译模块,适于采用适配的可加载内核模块LKM模板编译目标可加载内核模块LKM。
可选地,所述可加载内核模块LKM模板通过以下方式生成:
基于模板操作系统的内核环境编译可加载内核模块LKM模板。
可选地,所述可加载内核模块LKM模板还通过以下方式生成:
将所述可加载内核模块LKM模板编译为二进制数组;
将所述二进制数组与模板标识固化在源文件中;
其中,所述模板标识包括可支持的处理器版本信息、组件标识、可支持的内核版本范围中的至少一个;所述模板操作系统的系统内核的内核版本归属于内核版本范围。
可选地,所述读取模块还适于:
获取与所述组件匹配的组件标识;
读取所述组件标识对应的一个或多个可加载内核模块LKM模板。
可选地,所述读取模块还适于:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中、与所述组件匹配的组件标识。
可选地,所述检测模块还适于:
获取所述可加载内核模块LKM模板支持的处理器版本信息;
读取当前设备的处理器的版本信息;
检测当前设备的处理器的版本信息是否与所述源文件中处理器版本信息匹配;
若是,则判断所述可加载内核模块LKM模板支持当前设备的处理器。
可选地,所述检测模块还适于:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的处理器版本信息。
可选地,所述检测模块还适于:
获取所述可加载内核模块LKM模板支持的内核版本范围;
读取当前操作系统的系统内核的版本信息;
检测当前操作系统的系统内核的版本信息是否归属于所述源文件中的内核版本范围;
若是,则判断所述可加载内核模块LKM模板支持当前操作系统的系统内核。
可选地,所述检测模块还适于:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的内核版本范围。
可选地,所述适配模块还适于:
分别读取所述可加载内核模块LKM模板中的配置信息Vermagic和操作系统中的配置信息Vermagic;
判断所述可加载内核模块LKM模板中的配置信息Vermagic与所述操作系统中的配置信息Vermagic是否匹配;
当匹配时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
可选地,所述适配模块还适于:
当未匹配时,将操作系统中的配置信息Vermagic的值替换对应的可加载内核模块LKM模板中读取配置信息Vermagic的值。
可选地,所述适配模块还适于:
从所述可加载内核模块LKM模板中读取编译所需的第一符号;
读取与操作系统适配的、编译所需的第二符号;
将所述第二符号的值替换所述第一符号的值;
当全部符号的值替换成功时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
可选地,所述适配模块还适于:
从操作系统的指定文件中读取编译所需的第二符号;
和/或,
从操作系统的其他可加载内核模块LKM中读取编译所需的第二符号。
可选地,所述编译模块还适于:
当适配的可加载内核模块LKM模板固化在源文件时,从源文件中读取二进制数组形式的可加载内核模块LKM模板;
采用二进制数组形式的可加载内核模块LKM模板编译目标可加载内核模块LKM。
可选地,所述装置还包括:
加载模块,适于将所述目标可加载内核模块LKM加载进当前操作系统的系统内核中。
本发明实施例读取被触发组件对应的一个或多个可加载内核模块LKM模板,在支持当前设备的处理器和/或当前操作系统的系统内核的情况下,采用与当前操作系统的系统内核适配的可加载内核模块LKM模板编译目标可加载内核模块LKM,通过可控数量的模板,在操作系统对模板进行必要的编辑最终生成可以转载入操作系统的LKM,大大减少了工作量、降低了成本,便于逐步地让应用程序支持不同的体系架构和内核范围,最终推出可以支持多种处理器体系架构和非常大范围的系统内核的应用程序。
上述说明仅是本发明技术方案的概述,为了能够更清楚了解本发明的技术手段,而可依照说明书的内容予以实施,并且为了让本发明的上述和其它目的、特征和优点能够更明显易懂,以下特举本发明的具体实施方式。
具体实施方式
下面将参照附图更详细地描述本公开的示例性实施例。虽然附图中显示了本公开的示例性实施例,然而应当理解,可以以各种形式实现本公开而不应被这里阐述的实施例所限制。相反,提供这些实施例是为了能够更透彻地理解本公开,并且能够将本公开的范围完整的传达给本领域的技术人员。
参照图1,示出了根据本发明一个实施例的一种可加载内核模块的编译方法实施例的步骤流程图,具体可以包括如下步骤:
步骤101,当应用程序的组件被触发时,读取所述组件对应的一个或多个可加载内核模块LKM模板;
Linux内核以源代码形式发布,发行商/用户可以根据自己的需要进行配置并编译。
LKM是Linux内核的可加载扩展模块,它需要使用相应版本的Linux内核代码进行编译。这样编译出来的文件扩展名是.ko,通常情况下与内核版本匹配的LKM才可以被内核加载。
在实际应用中,由于Linux内核比较自由,每次启动都可能使用不同版本的内核,为了每次应用程序的正常运行,在每次Linux系统的应用层启动应用程序时,可以触发组件,执行一次适配,以生成目标可加载内核模块LKM,并加载到Linux内核中。
在本发明的一种可选实施例中,所述可加载内核模块LKM模板可以通过以下方式生成:
子步骤S11,基于模板操作系统的内核环境编译可加载内核模块LKM模板。
子步骤S12,将所述可加载内核模块LKM模板编译为二进制数组;
子步骤S13,将所述二进制数组与模板标识固化在源文件中;
其中,所述模板标识可以包括可支持的处理器版本信息、组件标识、可支持的内核版本范围中的至少一个;所述模板操作系统的系统内核的内核版本可以归属于内核版本范围。
如图2所示,本发明实施例中,可以以将三个维度的信息(处理器版本信息、组件标识、内核版本范围)定义一个可加载内核模块LKM模板编译。
例如,fileprotect_3_10_x86_64.ko可以表示支持3.10开头的Linux内核、支持x86_64的处理器的“fileprotect”(即文件保护组件)的可加载内核模块LKM模板编译。
具体而言,本发明实施例中可以在应用程序中划分出一个或多个组件,例如,实现保护文件功能的“文件保护”组件、实现保护目录功能的“目录保护”组件,实现进程免遭其他程序关闭的“进程免杀”组件等等。
针对每个组件,可以编译不同的编译可加载内核模块LKM模板。
划分组件,一方面,可以分散驱动安装失败的风险,例如,“进程免杀”组件能适配成功安装进入操作系统,但“文件保护”组件用到的某个符号无法适配成功,这样如果“进程免杀”组件和“文件保护”组件两个功能放在一个可加载内核模块LKM模板里,则“进程免杀”组件也无法使用了,反之,则“文件保护”组件失效时,“进程免杀”组件还是可以正常工作。另一方面,可以方便逐步开发和发布应用程序,避免一次编译过多的可加载内核模块LKM模板,降低开发的工作量。
应用程序的组件至少可以支持当前设备的处理器CPU、当前操作系统的系统内核。进一步地,为了减少适配的工作量,应用程序的组件可以支持各类设备的处理器CPU,同时兼容各种Linux系统的系统内核。
在编译可加载内核模块LKM模板时,可以选取一个或多个系统内核组成内核版本范围,在该内核版本范围内的系统内核,其关键的数据结构不会发生显著变化,在代码二进制布局上大致一样,使得可加载内核模块LKM模板对于该内核版本范围内的系统内核具有通用性,可以实现可加载内核模块LKM模板的兼容。
在一个示例中,可以选取Linux内核版本号的前两位中作为一个要支持的内核版本范围(或称大版本)。
Linux内核版本号一边由3组数字组成:第一个组数字、第二组数字、第三组数字。
其中,第一个组数字,可以是目前发布的内核主版本。
第二个组数字,偶数可以表示稳定版本、奇数可以表示开发中版本。
第三个组数字,可以表示错误修补的次数。
例如,可以针对3.10.20-11和3.1020-12rc5的Linux内核版本号组成一个内核版本范围3.10,可以针对3.11.35-3089rc1的Linux内核版本号组成一个内核版本范围3.11。
一般而言,Linux内核并没有windows内核那样严格地前后兼容,不同版本内核函数和结构可能变化非常大。但是,主版本号一致的内核,基础API(应用程序编程接口,Application Program Interface)和数据结构变化相对少,可以认为比较稳定。
用版本号的第一组数字和第二组数字进行内核版本范围的划分,可以明显降低驱动编写难度和提高稳定性,其投入产出比比在一个驱动里适配所有内核版本要高很多。
当然,在实际中可以结合驱动使用到的API和数据结构及kernel代码的具体情况,组成内核版本范围,本发明实施例对此不加以限制。
在发布应用程序的时候可以将可加载内核模块LKM模板在内核版本范围中选取(如随机选取、指定选取等)一个内核版本的内核上编译。
将生成的可加载内核模块LKM模板(扩展名可以为ko)保存为二进制数组,将三个维度的信息(处理器版本信息、组件标识、内核版本范围)以文件名或变量名的形式,固化在源文件(C Plus Plus,cpp,C++语言编写的源代码文件)中。
将可加载内核模块LKM模板使用工具保存为二进制数组,实际上相当于将这个可加载内核模块LKM模板携带在另一个可执行文件中。
将这个二进制数组再写回操作系统中,可以会得到一样的可加载内核模块LKM模板。固化在应用程序里的是内核版本范围的可加载内核模块LKM模板,归属于该内核版本范围的内核版本对应的可加载内核模块LKM模板数量巨大,可以将通过使用内核版本范围的可加载内核模块LKM模板适配之后生成。
固化在源文件cpp中,可以在运行的时候方便的修改二进制数组内容然后回写到硬盘上。
其中,组件标识可以记录在文件名里,内核版本范围和处理器版本信息可以记录在变量名里。
针对“文件保护”组件编译的可加载内核模块LKM模板的示例可以如下:
rootkit-fileprot.cpp
针对“进程免杀”组件编译的可加载内核模块LKM模板的示例可以如下:
rootkit-unkill.cpp
其中,上述cpp文件里的某个二进制数据,即对应一个可加载内核模块LKM模板。
例如,unkill_3_8_mips64对应kernel=3.8.x,处理器架构为mips 64位,“进程免杀”组件的可加载内核模块LKM模板。该可加载内核模块LKM模板可以安装在mips64体系架构的处理器,kernel版本为3.8开头的系统内核上。
由于每份加载内核模块LKM模板的代码量非常小(几K),可以将所有支持的处理器和内核版本的加载内核模块LKM模板静态编译到应用程序的可执行程序中。
在本发明的一种可选实施例中,步骤101可以包括如下子步骤:
子步骤S21,获取与所述组件匹配的组件标识;
本发明实施例中,可以查找被触发的组件匹配的组件标识,以查询到该组件对应的加载内核模块LKM模板。
在本发明实施例的一种可选示例中,子步骤S21可以包括如下子步骤:
子步骤S211,当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中、与所述组件匹配的组件标识。
在本示例中,若组件标识记录在文件名里,则可以从文件名中读取与组件匹配的组件标识。
若组件标识记录在变量名里,则可以从变量名中读取与组件匹配的组件标识。
子步骤S22,读取所述组件标识对应的一个或多个可加载内核模块LKM模板。
在本发明实施例中,可以从应用程序的可执行程序中,读取被触发组件对应的一个或多个可加载内核模块LKM模板。
步骤102,检测所述一个或多个可加载内核模块LKM模板是否支持当前设备的处理器和/或当前操作系统的系统内核;若是,则执行步骤103;
在本发明实施例中,从一个或多个可加载内核模块LKM模板中,查找支持当前设备的处理器和/或当前操作系统的系统内核的可加载内核模块LKM模板。
在本发明的一种可选实施例中,步骤102可以包括如下子步骤:
子步骤S31,获取所述可加载内核模块LKM模板支持的处理器版本信息;
本发明实施例中,可以查找可加载内核模块LKM模板支持的处理器版本信息,以查询到支持当前设备的处理器CPU的可加载内核模块LKM模板。
在本发明实施例的一种可选示例中,子步骤S31可以包括如下子步骤:
子步骤S311,当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的处理器版本信息。
在本示例中,若处理器版本信息记录在文件名里,则可以从文件名中读取处理器版本信息。
若处理器版本信息记录在变量名里,则可以从变量名中读取处理器版本信息。
子步骤S32,读取当前设备的处理器的版本信息;
在具体实现中,可以通过cpuid指令、getconf指令等方式读取当前设备的处理器CPU的版本信息。
子步骤S33,检测当前设备的处理器的版本信息是否与所述源文件中处理器版本信息匹配;若是,则执行子步骤S34;
子步骤S34,判断所述可加载内核模块LKM模板支持当前设备的处理器。
若当前设备的处理器的版本信息与源文件中处理器版本信息匹配,则可以认为可加载内核模块LKM模板支持当前设备的处理器,可以继续适配流程。
若当前设备的处理器的版本信息与源文件中处理器版本信息不匹配,则可以认为可加载内核模块LKM模板不支持当前设备的处理器,可以停止适配流程。
在本发明的一种可选实施例中,步骤102可以包括如下子步骤:
子步骤S41,获取所述可加载内核模块LKM模板支持的内核版本范围;
本发明实施例中,可以查找可加载内核模块LKM模板支持的内核版本范围,以查询到支持当前操作系统的系统内核的可加载内核模块LKM模板。
在本发明实施例的一种可选示例中,子步骤S41可以包括如下子步骤:
子步骤S411,当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的内核版本范围。
在本示例中,若内核版本范围记录在文件名里,则可以从文件名中读取内核版本范围。
若内核版本范围记录在变量名里,则可以从变量名中读取内核版本范围。
子步骤S42,读取当前操作系统的系统内核的版本信息;
在具体实现中,可以通过cat指令等方式读取当前设备的处理器CPU的版本信息。
子步骤S43,检测当前操作系统的系统内核的版本信息是否归属于所述源文件中的内核版本范围;若是,则执行子步骤S44;
子步骤S44,判断所述可加载内核模块LKM模板支持当前操作系统的系统内核。
若当前操作系统的系统内核的版本信息归属于源文件中的内核版本范围,则可以认为可加载内核模块LKM模板支持当前操作系统的系统内核,可以继续适配流程。
若当前操作系统的系统内核的版本信息不归属于源文件中的内核版本范围,则可以认为可加载内核模块LKM模板不支持当前操作系统的系统内核,可以停止适配流程。
步骤103,对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配;
本发明实施例中,可以采用可加载内核模块LKM模板尝试生成目标可加载内核模块LKM,以判断是否与当前操作系统的系统内核适配。
应用程序带到操作系统的代码里保存的是的若干数组及其长度,这些数组是预先编译好的可加载内核模块LKM模板的二进制码。
将二进制数组直接保存为可加载内核模块LKM,得到的是跟预先编译出来的可加载内核模块LKM一模一样的可加载内核模块LKM,一般情况下很难加载到系统内核。
所以,可以根据操作系统的实际情况编辑这个二进制数组,然后再保存为目标可加载内核模块LKM。
具体而言,预先编译的可加载内核模块LKM模板的内核编译选项可能与操作系统不同,modpost生成的一些校验信息也与目标系统不同。
适配的过程可以利用操作系统的一些内核配置,以及操作系统的其他可加载内核模块LKM,通过解析这些文件收集操作系统是否支持insmod内核模块、是否开启内核模块签名校验、是否开启内核模块符号versions校验等编译信息,如果有符号的versions校验,则尝试获取需要的符号在操作系统的校验值,并修改可加载内核模块LKM模板里对应符号段的值,还可以从操作系统获取内核版本并替换可加载内核模块LKM模板的modinfo段的相关值。
参照图3,示出了根据本发明一个实施例的一种可加载内核模块的适配示例的程示意图,在本发明实施例中,步骤103可以包括如下子步骤:
子步骤301,分别读取所述可加载内核模块LKM模板中的配置信息Vermagic和操作系统中的配置信息Vermagic;
子步骤302,判断所述可加载内核模块LKM模板中的配置信息Vermagic与所述操作系统中的配置信息Vermagic是否匹配;当匹配时,则执行子步骤303,当未匹配时,则执行子步骤304;
子步骤303,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
子步骤304,将操作系统中的配置信息Vermagic的值替换对应的可加载内核模块LKM模板中读取配置信息Vermagic的值。
在具体实现中,可以将可加载内核模块LKM模板以elfrelocatable格式进行解析,定位.modinfo section段,获取vermagic(即Version Magic String),在vermagic中可以保存可加载内核模块LKM模板在编译时的内核版本以及SMP等配置信息。
fileprotect_3_10_x86_64.ko中的vermagic的示例可以如下:
#uname–r
2.6.38-10-generic
#modinfo./fileprotect_3_10_x86_64/fileprotect_3_10_x86_64.ko
filename:./hello/hello.ko
license:Dual BSD/GPL
srcversion:31FE72DA6A560C890FF9B3F
depends:
vermagic:2.6.38-9-generic SMP mod_unload modversions
以Linux-3.13 module.c为例,在可加载内核模块LKM加载到系统内核的过程可以如下:
Load_module→layout_and_allocate→check_modinfo;
在check_modinfo函数中,可以解析待加载的加载内核模块LKM的.modinfo section段中的vermagic数据,并与系统内核中的一个字符串(定义在vermagic.h里的VERMAGIC_STRING变量)进行匹配。
如果匹配成功,可加载内核模块LKM将可以加载到系统内核中。
如果匹配失败,insmod会返回失败,可加载内核模块LKM将无法加载到系统内核中。
因此,在匹配失败时,可以从当前设备的drivers目录(该目录的地址可以为/lib/modules/x.x.x./build/drivers)获取其他可加载内核模块LKM,并解析获取vermagic的值替换到可加载内核模块LKM模板中modinfo对应字段的值。
子步骤305,从所述可加载内核模块LKM模板中读取编译所需的第一符号;
子步骤306,读取与操作系统适配的、编译所需的第二符号;
子步骤307,将所述第二符号的值替换所述第一符号的值;
子步骤308,当全部符号的值替换成功时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
在具体实现中,可以将可加载内核模块LKM模板以elfrelocatable格式进行解析,定位.versions section段,解析得到所需符号列表。
以Linux-3.13 module.c为例,在可加载内核模块LKM加载到系统内核的过程可以如下:
Load_module→layout_and_allocate→setup_load_info→check_modstruct_version→check_version;
在check_version函数中,可以对逐个获取待加载可加载内核模块LKM模板的符号的crc值并与系统内核中同名符号的crc值做对比。
如果全部对比成功,可加载内核模块LKM将可以加载到系统内核中。
如果对比失败,insmod会返回失败,可加载内核模块LKM将无法加载到系统内核中。
在编译一个可加载内核模块LKM,如test.c时,可以自动生成test.mod.c文件,里边可以记录有符号的crc列表,该crc列表的示例可以如下:
17 static const struct modversion_info____versions[]
18__used
19__attribute__((section("__versions")))={
20{0x437afd29,__VMLINUX_SYMBOL_STR(module_layout)},
21{0x487d9343,__VMLINUX_SYMBOL_STR(param_ops_ushort)},
22{0xfc10bcf8,__VMLINUX_SYMBOL_STR(pid_task)},
23{0xb8a1c7eb,__VMLINUX_SYMBOL_STR(find_get_pid)},
24{0x27e1a049,__VMLINUX_SYMBOL_STR(printk)},
25{0xe007de41,__VMLINUX_SYMBOL_STR(kallsyms_lookup_name)},
26{0xbdfb6dbb,__VMLINUX_SYMBOL_STR(__fentry__)},
27};
在本发明实施例的一种可选示例中,子步骤306可以包括如下子步骤:
子步骤S561,从操作系统的指定文件中读取编译所需的第二符号;
和/或,
子步骤S562,从操作系统的其他可加载内核模块LKM中读取编译所需的第二符号。
在本示例中,可以检测/lib/modules/x.x.x./build/Modules.symvers文件是否存在。
若存在,则可以用Modules.symvers文件里的符号crc值替换可加载内核模块LKM模板中_versions的符号crc值。
若不存在,则可以遍历当前设备drivers目录里的其他可加载内核模块LKM,解析其versions段获取需要的符号crc值替换可加载内核模块LKM模板中_versions的符号crc值。
需要说明的是,上述加载可加载内核模块LKM的过程(load_module)时的检测过程只是作为示例,并非所有系统内核在加载可加载内核模块LKM的过程(load_module)时的检测过程都一致,本领域技术人员可以根据实际情况进行设定。
其中,加载可加载内核模块LKM的过程(load_module)主要由几个内核编译选项控制,该个内核编译选项控制的示例可以如下:
CONFIG_MODULES=y如果目标内核这个选择关闭,则完全无法insmod模块
CONFIG_MODULE_FORCE_LOAD强制安装,不需要任何校验,一般不开启
CONFIG_MODVERSIONS是否校验vermagic,一般发行版默认开腔
CONFIG_MODULE_SRCVERSION_ALL是否校验符号crc值,一般发行版默认开腔
CONFIG_MODULE_SIG本项及下面几项都是内核模板签名校验的内容,一般发行版都不开腔
CONFIG_MODULE_SIG_FORCE
CONFIG_MODULE_SIG_ALL=y
CONFIG_MODULE_SIG_SHA1
CONFIG_MODULE_SIG_SHA224
步骤104,采用适配的可加载内核模块LKM模板编译目标可加载内核模块LKM。
在具体实现中,若可加载内核模块LKM模板已配当前操作系统,则可以生成目标可加载内核模块LKM。
在本发明实施例的一种可选示例中,步骤104可以提包括如下子步骤:
子步骤S61,当适配的可加载内核模块LKM模板固化在源文件时,从源文件中读取二进制数组形式的可加载内核模块LKM模板;
子步骤S62,采用二进制数组形式的可加载内核模块LKM模板编译目标可加载内核模块LKM。
本发明实施例中,可以按照标准elf文件解析和编辑过程实现收集操作系统编译选项、符号校验值、modinfo值等信息并成功修改了可加载内核模块LKM模板后,可以将数组保存为文件,即得到目标可加载内核模块LKM。
本发明实施例读取被触发组件对应的一个或多个可加载内核模块LKM模板,在支持当前设备的处理器和/或当前操作系统的系统内核的情况下,采用与当前操作系统的系统内核适配的可加载内核模块LKM模板编译目标可加载内核模块LKM,通过可控数量的模板,在操作系统对模板进行必要的编辑最终生成可以转载入操作系统的LKM,大大减少了工作量、降低了成本,便于逐步地让应用程序支持不同的体系架构和内核范围,最终推出可以支持多种处理器体系架构和非常大范围的系统内核的应用程序。
在本发明的一种可选实施例中,所述方法还可以包括如下步骤:
步骤105,将所述目标可加载内核模块LKM加载进当前操作系统的系统内核中。
本发明实施例中,可以用insmod指令等方式将目标可加载内核模块LKM加载进当前操作系统的系统内核中。
当目标可加载内核模块LKM加载进当前操作系统的系统内核中后,则可以实现相应的组件的功能。
例如,若“文件保护”组件的目标可加载内核模块LKM加载进当前操作系统的系统内核中后,应用程序可以实现保护文件功能。
若“目录保护”组件的目标可加载内核模块LKM加载进当前操作系统的系统内核中后,应用程序可以实现保护目录功能。
若“进程免杀”组件的目标可加载内核模块LKM加载进当前操作系统的系统内核中后,应用程序可以实现进程免遭其他程序关闭的功能。
当然,若可加载内核模块LKM模板与操作系统无法适配,对应用程序在应用层的功能没有影响。
对于方法实施例,为了简单描述,故将其都表述为一系列的动作组合,但是本领域技术人员应该知悉,本发明实施例并不受所描述的动作顺序的限制,因为依据本发明实施例,某些步骤可以采用其他顺序或者同时进行。其次,本领域技术人员也应该知悉,说明书中所描述的实施例均属于优选实施例,所涉及的动作并不一定是本发明实施例所必须的。
参照图4,示出了根据本发明一个实施例的一种可加载内核模块的编译装置实施例的结构框图,具体可以包括如下模块:
读取模块401,适于在应用程序的组件被触发时,读取所述组件对应的一个或多个可加载内核模块LKM模板;
检测模块402,适于检测所述一个或多个可加载内核模块LKM模板是否支持当前设备的处理器和/或当前操作系统的系统内核;若是,则调用编适配模块403;
适配模块403,适于对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配;
编译模块404,适于采用适配的可加载内核模块LKM模板编译目标可加载内核模块LKM。
在本发明的一种可选实施例中,所述可加载内核模块LKM模板可以通过以下方式生成:
基于模板操作系统的内核环境编译可加载内核模块LKM模板。
在本发明的一种可选实施例中,所述可加载内核模块LKM模板还可以通过以下方式生成:
将所述可加载内核模块LKM模板编译为二进制数组;
将所述二进制数组与模板标识固化在源文件中;
其中,所述模板标识包括可支持的处理器版本信息、组件标识、可支持的内核版本范围中的至少一个;所述模板操作系统的系统内核的内核版本归属于内核版本范围。
在本发明的一种可选实施例中,所述读取模块401还可以适于:
获取与所述组件匹配的组件标识;
读取所述组件标识对应的一个或多个可加载内核模块LKM模板。
在本发明实施例的一种可选示例中,所述读取模块401还可以适于:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中、与所述组件匹配的组件标识。
在本发明的一种可选实施例中,所述检测模块402还可以适于:
获取所述可加载内核模块LKM模板支持的处理器版本信息;
读取当前设备的处理器的版本信息;
检测当前设备的处理器的版本信息是否与所述源文件中处理器版本信息匹配;
若是,则判断所述可加载内核模块LKM模板支持当前设备的处理器。
在本发明实施例的一种可选示例中,所述检测模块402还可以适于:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的处理器版本信息。
在本发明的一种可选实施例中,所述检测模块402还可以适于:
获取所述可加载内核模块LKM模板支持的内核版本范围;
读取当前操作系统的系统内核的版本信息;
检测当前操作系统的系统内核的版本信息是否归属于所述源文件中的内核版本范围;
若是,则判断所述可加载内核模块LKM模板支持当前操作系统的系统内核。
在本发明实施例的一种可选示例中,所述检测模块402还可以适于:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的内核版本范围。
在本发明的一种可选实施例中,所述适配模块403还可以适于:
分别读取所述可加载内核模块LKM模板中的配置信息Vermagic和操作系统中的配置信息Vermagic;
判断所述可加载内核模块LKM模板中的配置信息Vermagic与所述操作系统中的配置信息Vermagic是否匹配;
当匹配时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
在本发明的一种可选实施例中,所述适配模块403还可以适于:
当未匹配时,将操作系统中的配置信息Vermagic的值替换对应的可加载内核模块LKM模板中读取配置信息Vermagic的值。
在本发明的一种可选实施例中,所述适配模块403还可以适于:
从所述可加载内核模块LKM模板中读取编译所需的第一符号;
读取与操作系统适配的、编译所需的第二符号;
将所述第二符号的值替换所述第一符号的值;
当全部符号的值替换成功时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
在本发明实施例的一种可选示例中,所述适配模块403还可以适于:
从操作系统的指定文件中读取编译所需的第二符号;
和/或,
从操作系统的其他可加载内核模块LKM中读取编译所需的第二符号。
在本发明的一种可选实施例中,所述编译模块404还可以适于:
当适配的可加载内核模块LKM模板固化在源文件时,从源文件中读取二进制数组形式的可加载内核模块LKM模板;
采用二进制数组形式的可加载内核模块LKM模板编译目标可加载内核模块LKM。
在本发明的一种可选实施例中,所述装置还可以包括如下模块:
加载模块,适于将所述目标可加载内核模块LKM加载进当前操作系统的系统内核中。
对于装置实施例而言,由于其与方法实施例基本相似,所以描述的比较简单,相关之处参见方法实施例的部分说明即可。
在此提供的算法和显示不与任何特定计算机、虚拟系统或者其它设备固有相关。各种通用系统也可以与基于在此的示教一起使用。根据上面的描述,构造这类系统所要求的结构是显而易见的。此外,本发明也不针对任何特定编程语言。应当明白,可以利用各种编程语言实现在此描述的本发明的内容,并且上面对特定语言所做的描述是为了披露本发明的最佳实施方式。
在此处所提供的说明书中,说明了大量具体细节。然而,能够理解,本发明的实施例可以在没有这些具体细节的情况下实践。在一些实例中,并未详细示出公知的方法、结构和技术,以便不模糊对本说明书的理解。
类似地,应当理解,为了精简本公开并帮助理解各个发明方面中的一个或多个,在上面对本发明的示例性实施例的描述中,本发明的各个特征有时被一起分组到单个实施例、图、或者对其的描述中。然而,并不应将该公开的方法解释成反映如下意图:即所要求保护的本发明要求比在每个权利要求中所明确记载的特征更多的特征。更确切地说,如下面的权利要求书所反映的那样,发明方面在于少于前面公开的单个实施例的所有特征。因此,遵循具体实施方式的权利要求书由此明确地并入该具体实施方式,其中每个权利要求本身都作为本发明的单独实施例。
本领域那些技术人员可以理解,可以对实施例中的设备中的模块进行自适应性地改变并且把它们设置在与该实施例不同的一个或多个设备中。可以把实施例中的模块或单元或组件组合成一个模块或单元或组件,以及此外可以把它们分成多个子模块或子单元或子组件。除了这样的特征和/或过程或者单元中的至少一些是相互排斥之外,可以采用任何组合对本说明书(包括伴随的权利要求、摘要和附图)中公开的所有特征以及如此公开的任何方法或者设备的所有过程或单元进行组合。除非另外明确陈述,本说明书(包括伴随的权利要求、摘要和附图)中公开的每个特征可以由提供相同、等同或相似目的的替代特征来代替。
此外,本领域的技术人员能够理解,尽管在此所述的一些实施例包括其它实施例中所包括的某些特征而不是其它特征,但是不同实施例的特征的组合意味着处于本发明的范围之内并且形成不同的实施例。例如,在下面的权利要求书中,所要求保护的实施例的任意之一都可以以任意的组合方式来使用。
本发明的各个部件实施例可以以硬件实现,或者以在一个或者多个处理器上运行的软件模块实现,或者以它们的组合实现。本领域的技术人员应当理解,可以在实践中使用微处理器或者数字信号处理器(DSP)来实现根据本发明实施例的可加载内核模块的编译设备中的一些或者全部部件的一些或者全部功能。本发明还可以实现为用于执行这里所描述的方法的一部分或者全部的设备或者装置程序(例如,计算机程序和计算机程序产品)。这样的实现本发明的程序可以存储在计算机可读介质上,或者可以具有一个或者多个信号的形式。这样的信号可以从因特网网站上下载得到,或者在载体信号上提供,或者以任何其他形式提供。
应该注意的是上述实施例对本发明进行说明而不是对本发明进行限制,并且本领域技术人员在不脱离所附权利要求的范围的情况下可设计出替换实施例。在权利要求中,不应将位于括号之间的任何参考符号构造成对权利要求的限制。单词“包含”不排除存在未列在权利要求中的元件或步骤。位于元件之前的单词“一”或“一个”不排除存在多个这样的元件。本发明可以借助于包括有若干不同元件的硬件以及借助于适当编程的计算机来实现。在列举了若干装置的单元权利要求中,这些装置中的若干个可以是通过同一个硬件项来具体体现。单词第一、第二、以及第三等的使用不表示任何顺序。可将这些单词解释为名称。
本发明实施例公开了A1、一种可加载内核模块的编译方法,包括:
当应用程序的组件被触发时,读取所述组件对应的一个或多个可加载内核模块LKM模板;
检测所述一个或多个可加载内核模块LKM模板是否支持当前设备的处理器和/或当前操作系统的系统内核;
若是,则对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配;
采用适配的可加载内核模块LKM模板编译目标可加载内核模块LKM。
A2、如A1所述的方法,所述可加载内核模块LKM模板通过以下方式生成:
基于模板操作系统的内核环境编译可加载内核模块LKM模板。
A3、如A2所述的方法,所述可加载内核模块LKM模板还通过以下方式生成:
将所述可加载内核模块LKM模板编译为二进制数组;
将所述二进制数组与模板标识固化在源文件中;
其中,所述模板标识包括可支持的处理器版本信息、组件标识、可支持的内核版本范围中的至少一个;所述模板操作系统的系统内核的内核版本归属于内核版本范围。
A4、如A1或A2或A3所述的方法,所述读取所述组件对应的一个或多个可加载内核模块LKM模板的步骤包括:
获取与所述组件匹配的组件标识;
读取所述组件标识对应的一个或多个可加载内核模块LKM模板。
A5、如A4所述的方法,所述获取与所述组件匹配的组件标识的步骤包括:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中、与所述组件匹配的组件标识。
A6、如A1或A2或A3所述的方法,所述检测所述一个或多个可加载内核模块LKM模板是否支持当前设备的处理器和/或当前操作系统的系统内核的步骤包括:
获取所述可加载内核模块LKM模板支持的处理器版本信息;
读取当前设备的处理器的版本信息;
检测当前设备的处理器的版本信息是否与所述源文件中处理器版本信息匹配;
若是,则判断所述可加载内核模块LKM模板支持当前设备的处理器。
A7、如A6所述的方法,所述获取所述可加载内核模块LKM模板支持的处理器版本信息的步骤包括:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的处理器版本信息。
A8、如A1或A2或A3所述的方法,所述检测所述一个或多个可加载内核模块LKM模板是否支持当前设备的处理器和/或当前操作系统的系统内核的步骤包括:
获取所述可加载内核模块LKM模板支持的内核版本范围;
读取当前操作系统的系统内核的版本信息;
检测当前操作系统的系统内核的版本信息是否归属于所述源文件中的内核版本范围;
若是,则判断所述可加载内核模块LKM模板支持当前操作系统的系统内核。
A9、如A8所述的方法,所述获取所述可加载内核模块LKM模板支持的内核版本范围的步骤包括:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的内核版本范围。
A10、如A1或A2或A3所述的方法,所述对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配的步骤包括:
分别读取所述可加载内核模块LKM模板中的配置信息Vermagic和操作系统中的配置信息Vermagic;
判断所述可加载内核模块LKM模板中的配置信息Vermagic与所述操作系统中的配置信息Vermagic是否匹配;
当匹配时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
A11、如A10所述的方法,所述对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配的步骤包括:
当未匹配时,将操作系统中的配置信息Vermagic的值替换对应的可加载内核模块LKM模板中读取配置信息Vermagic的值。
A12、如A11所述的方法,所述对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配的步骤包括:
从所述可加载内核模块LKM模板中读取编译所需的第一符号;
读取与操作系统适配的、编译所需的第二符号;
将所述第二符号的值替换所述第一符号的值;
当全部符号的值替换成功时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
A13、如A12所述的方法,所述读取与操作系统适配的、编译所需的符号的步骤包括:
从操作系统的指定文件中读取编译所需的第二符号;
和/或,
从操作系统的其他可加载内核模块LKM中读取编译所需的第二符号。
A14、如A1或A2或A3或A5或A7或A9或A11或A12或A13所述的方法,所述采用适配的可加载内核模块LKM模板编译目标可加载内核模块LKM的步骤包括:
当适配的可加载内核模块LKM模板固化在源文件时,从源文件中读取二进制数组形式的可加载内核模块LKM模板;
采用二进制数组形式的可加载内核模块LKM模板编译目标可加载内核模块LKM。
A15、如A1或A2或A3或A5或A7或A9或A11或A12或A13所述的方法,还包括:
将所述目标可加载内核模块LKM加载进当前操作系统的系统内核中。
本发明实施例还公开了B16、一种可加载内核模块的编译装置,包括:
读取模块,适于在应用程序的组件被触发时,读取所述组件对应的一个或多个可加载内核模块LKM模板;
检测模块,适于检测所述一个或多个可加载内核模块LKM模板是否支持当前设备的处理器和/或当前操作系统的系统内核;若是,则调用适配模块;
适配模块,适于对所述可加载内核模块LKM模板与当前操作系统的系统内核进行适配;
编译模块,适于采用适配的可加载内核模块LKM模板编译目标可加载内核模块LKM。
B17、如B16所述的装置,所述可加载内核模块LKM模板通过以下方式生成:
基于模板操作系统的内核环境编译可加载内核模块LKM模板。
B18、如B17所述的装置,所述可加载内核模块LKM模板还通过以下方式生成:
将所述可加载内核模块LKM模板编译为二进制数组;
将所述二进制数组与模板标识固化在源文件中;
其中,所述模板标识包括可支持的处理器版本信息、组件标识、可支持的内核版本范围中的至少一个;所述模板操作系统的系统内核的内核版本归属于内核版本范围。
B19、如B16或B17或B18所述的装置,所述读取模块还适于:
获取与所述组件匹配的组件标识;
读取所述组件标识对应的一个或多个可加载内核模块LKM模板。
B20、如B19所述的装置,所述读取模块还适于:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中、与所述组件匹配的组件标识。
B21、如B16或B17或B18所述的装置,所述检测模块还适于:
获取所述可加载内核模块LKM模板支持的处理器版本信息;
读取当前设备的处理器的版本信息;
检测当前设备的处理器的版本信息是否与所述源文件中处理器版本信息匹配;
若是,则判断所述可加载内核模块LKM模板支持当前设备的处理器。
B22、如B21所述的装置,所述检测模块还适于:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的处理器版本信息。
B23、如B16或B17或B18所述的装置,所述检测模块还适于:
获取所述可加载内核模块LKM模板支持的内核版本范围;
读取当前操作系统的系统内核的版本信息;
检测当前操作系统的系统内核的版本信息是否归属于所述源文件中的内核版本范围;
若是,则判断所述可加载内核模块LKM模板支持当前操作系统的系统内核。
B24、如B23所述的装置,所述检测模块还适于:
当所述可加载内核模块LKM模板固化在源文件时,读取固化在所述源文件中的内核版本范围。
B25、如B16或B17或B18所述的装置,所述适配模块还适于:
分别读取所述可加载内核模块LKM模板中的配置信息Vermagic和操作系统中的配置信息Vermagic;
判断所述可加载内核模块LKM模板中的配置信息Vermagic与所述操作系统中的配置信息Vermagic是否匹配;
当匹配时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
B26、如B25所述的装置,所述适配模块还适于:
当未匹配时,将操作系统中的配置信息Vermagic的值替换对应的可加载内核模块LKM模板中读取配置信息Vermagic的值。
B27、如B26所述的装置,所述适配模块还适于:
从所述可加载内核模块LKM模板中读取编译所需的第一符号;
读取与操作系统适配的、编译所需的第二符号;
将所述第二符号的值替换所述第一符号的值;
当全部符号的值替换成功时,判断所述可加载内核模块LKM模板与操作系统的系统内核适配。
B28、如B27所述的装置,所述适配模块还适于:
从操作系统的指定文件中读取编译所需的第二符号;
和/或,
从操作系统的其他可加载内核模块LKM中读取编译所需的第二符号。
B29、如B16或B17或B18或B20或B22或B24或B26或B27或B28所述的装置,所述编译模块还适于:
当适配的可加载内核模块LKM模板固化在源文件时,从源文件中读取二进制数组形式的可加载内核模块LKM模板;
采用二进制数组形式的可加载内核模块LKM模板编译目标可加载内核模块LKM。
B30、如B16或B17或B18或B20或B22或B24或B26或B27或B28所述的装置,还包括:
加载模块,适于将所述目标可加载内核模块LKM加载进当前操作系统的系统内核中。