CN101226487B - 基于嵌入式Linux操作系统的内核级线程库的实现方法 - Google Patents

基于嵌入式Linux操作系统的内核级线程库的实现方法 Download PDF

Info

Publication number
CN101226487B
CN101226487B CN 200810046848 CN200810046848A CN101226487B CN 101226487 B CN101226487 B CN 101226487B CN 200810046848 CN200810046848 CN 200810046848 CN 200810046848 A CN200810046848 A CN 200810046848A CN 101226487 B CN101226487 B CN 101226487B
Authority
CN
China
Prior art keywords
thread
kernel
task
linux
library
Prior art date
Legal status (The legal status is an assumption and is not a legal conclusion. Google has not performed a legal analysis and makes no representation as to the accuracy of the status listed.)
Expired - Fee Related
Application number
CN 200810046848
Other languages
English (en)
Other versions
CN101226487A (zh
Inventor
蔡斌
邓广宏
刘毅
池志强
黄志华
程雄
Current Assignee (The listed assignees may be inaccurate. Google has not performed a legal analysis and makes no representation or warranty as to the accuracy of the list.)
709th Research Institute of CSIC
Original Assignee
709th Research Institute of CSIC
Priority date (The priority date is an assumption and is not a legal conclusion. Google has not performed a legal analysis and makes no representation as to the accuracy of the date listed.)
Filing date
Publication date
Application filed by 709th Research Institute of CSIC filed Critical 709th Research Institute of CSIC
Priority to CN 200810046848 priority Critical patent/CN101226487B/zh
Publication of CN101226487A publication Critical patent/CN101226487A/zh
Application granted granted Critical
Publication of CN101226487B publication Critical patent/CN101226487B/zh
Expired - Fee Related legal-status Critical Current
Anticipated expiration legal-status Critical

Links

Images

Landscapes

  • Debugging And Monitoring (AREA)

Abstract

本发明一种基于嵌入式Linux操作系统的内核级线程库的实现方法,实现了一个完整的内核线程管理体系,提供了内核线程的管理、信号量的管理、内存的管理和日志的管理等功能,还提供标准C库的功能子集的A-IP函数接口。其优点在于:第一,对内核进行较小的改动就可以支持现有嵌入式Linux操作系统内核中的软实时或者硬实时调度机制,能够保证应用的实时性需求;第二,能够彻底消除应用进程在用户态和内核态之间反复切换带来的开销,显著提高嵌入式Linux应用系统的整体性能;第三,屏蔽了内核模块编程的复杂性,提供了一个供编程人员使用的开发框架以及一套编程接口(API),能够降低应用开发的复杂度,提高开发效率。

Description

基于嵌入式Linux操作系统的内核级线程库的实现方法
技术领域
本发明涉及嵌入式操作系统领域,具体涉及基于嵌入式Linux操作系统的内核级线程库的实现方法。
背景技术
内核是操作系统的内在核心,系统的其他部分必须依靠内核提供的服务,如管理硬件设备、分配系统资源等等。操作系统内核通常由响应中断的中断服务程序、管理多进程的处理器调度程序、管理进程地址空间的内存管理程序和网络、进程间通信等系统服务共同组成。
Linux作为基于GNU规范的操作系统,由于其硬件支持的多样性、内核运行的高效和稳定性、应用程序开发的灵活性、独特的可按需裁剪性以及内核模块的动态可加载性,日益得到嵌入式操作系统领域的重视。随着Li-nux操作系统的不断发展,逐渐由以前的非实时调度内核发展为目前的软实时调度内核(如2.6及以上的内核版本),提供了对事件优先级调度和抢占调度的支持,可以抢占当前正在运行的进程并运行新的优先级更高的可运行进程,能够满足非常严格的实时性要求,极大地扩展了Linux操作系统在嵌入式系统中的使用范围。
软实时调度内核将尽力调度进程,使得在它们的限定时间到来之前运行,但不能够保证总能满足这些进程的时间要求。与此对应的,硬实时调度内核保证在一定条件下,可以满足任何调度的时间要求。为此,出现了一些商用的嵌入式Linux产品,如RT-Linux,大大增强了Linux操作系统的硬实时性。其原理是在Linux的非实时内核上再增加一个小型的实时内核,由该实时内核来控制实时任务,而原来的非实时内核则控制非实时任务,同时将Linux本身的任务以及Linux内核本身作为一个优先级最低的任务,而实时任务作为优先级最高的任务,即在实时任务存在的情况下运行实时任务,否则才运行Linux本身的任务。由于实时内核的实现比较简单,且L-inux本身的非实时内核作为实时内核可抢占的一个任务,因此在任务运行和调度的效率上完全可以达到硬实时的要求。
在Linux操作系统中,内核是独立于普通应用程序的,它一般处于系统态,拥有受保护的内存空间和访问硬件设备的所有权限,这种系统态和被保护起来的内存空间,统称为内核空间。相对的,应用程序在用户空间执行,它们只能够看到允许它们使用的部分系统资源,并且不能够使用某些特定的系统功能,不能够直接访问硬件,此外还有一些使用限制。当内核运行时,系统以内核态进入内核空间,相反,普通用户程序以用户态进入用户空间,应用程序通过系统调用(如访问文件系统、分配系统资源、建立网络连接等)与内核通信,访问内核提供的系统服务。系统调用是应用程序访问系统服务的唯一手段。
由上述分析可知,现有的嵌入式Linux操作系统主要是从内核运行的角度提高了任务调度的效率和实时性。但是从应用程序运行的角度来看,每当进行系统调用时,必须通过一次从用户态到内核态的切换,进入到内核态后才能够访问操作系统的服务。当使用完系统调用后,又必须通过一次从内核态到用户态的切换,返回到用户空间后才能够继续执行应用程序。应用程序每进行一次系统调用,必须进行两次切换。此外,每当系统中有中断发生时,应用程序也要进行两次切换,从用户态进入到内核态处理中断,然后从内核态返回到用户态继续应用程序的执行。因此,嵌入式Linux应用系统的主要瓶颈在于应用程序从用户态进入到内核态以及从内核态返回到用户态的反复切换上。
为了减少反复切换带来的开销,提高应用系统的整体性能,目前存在使用用户级线程库的方式,它是通过在用户空间中增加运行库来实现的。这种实现方式由用户级线程库自身进行用户线程的调度,各用户线程之间是非抢占式,一个用户线程会一直运行,直至它主动放弃CPU(线程退出、等待同步对象或执行阻塞式系统调用)或是整个进程被内核重新调度。用户级线程库的优点在于,用户线程调度时不需要切换到内核态,免去了切换的开销。然而这种实现方式的缺点也是非常明显的,它不能够利用内核中的实时调度机制,因此不适应对实时性要求较高的嵌入式应用。
另一种方式是将应用程序以内核模块的形式动态加载到Linux操作系统内核中,直接在内核空间中以内核线程的方式运行。但是涉及到的内核API接口非常多,内核模块编程非常复杂,需要编程人员对Linux内核非常了解,加重了应用程序的开发和移植难度。
为了解决现有技术的不足,本发明提供了基于嵌入式Linux操作系统的内核级线程库的实现方法,提供了内核线程的管理、信号量同步机制、内存的动态分配和回收和日志管理功能,如内核线程的创建、终止和延时,互斥信号量的申请和释放,按照优先级记录日志信息等,并且还提供标准C库的功能子集,如基本输入输出,字符串操作,文件操作和网络套接字等。本发明提供的方法的优势在于:第一,对内核进行较小的改动就可以支持现有嵌入式Linux操作系统内核中的软实时或者硬实时调度机制,能够保证应用的实时性需求;第二,能够彻底消除应用进程在用户态和内核态之间反复切换带来的开销,显著提高嵌入式Linux应用系统的整体性能;第三,屏蔽了内核模块编程的复杂性,提供了一个供编程人员使用的开发框架以及一套编程接口(API),能够降低应用开发的复杂度,提高开发效率。
发明内容
本发明的目的在于提供基于嵌入式Linux操作系统的内核级线程库的实现方法,提供了内核线程的管理、信号量的管理、内存的管理和日志的管理等功能,内核线程的管理实现了一个比较完整的内核线程管理体系,包括线程的创建、中止和延迟等功能;信号量的管理提供了2种信号量机制,包括互斥信号量(Mutex Semaphore)和计数信号量(Counting Semaphore),在信号量的获取、释放和删除上使用了统一的接口,每种信号量都包括阻塞和非阻塞2种形式;内存的管理提供了灵活高效的内存分配/回收、释放和查看;日志的管理实现了信息记录功能,提供了按照日志优先级的过虑机制方便定位用户关注的信息。此外,还提供标准C库的功能子集,如基本输入输出,字符串操作,文件操作和网络套接字等AIP函数接口。
本发明基于嵌入式Linux操作系统的内核级线程库的实现方法,其步骤包括:
(1)按照下述步骤修改Linux内核源代码,以提供对Linux内核级线程库底层运行环境的支持,完成后进入步骤(4):
(1.1)在代表进程描述符的task_struct数据结构中增加一个新的vo-id类型的指针lktl并且初始化为NULL。
(1.2)在进程的内核堆栈中增加一个int类型的指针lktl_esp_stack并且初始化为NULL,由该指针指向通过Linux内核级线程库而运行在内核空间中的应用程序的堆栈地址,堆栈大小和堆栈地址则以参数的形式通知Li-nux内核级线程库的线程创建函数。通过lktl_esp_stack指针,可以动态扩展进程的内核堆栈的大小,使得在Linux内核级线程库的支持下运行的进程的内核堆栈的大小突破8K字节或者4K字节的限制;
(1.3)根据不同的硬件体系结构,判断是否需要修改内核中原有的获取当前运行进程的task_struct指针的实现。不同的硬件体系结构,内核中原有的获取当前运行进程的task_struct指针的实现也不同。有些硬件体系结构使用一个专门的寄存器来保存指向当前运行进程的task_struct指针,内核原有的实现方式是使用一个定义为current的宏直接读取专门寄存器中的值来获取当前进程的task_struct指针。在这种硬件体系结构下,保留内核中原有的获取当前进程的task_struct指针的实现不变,即通过内核定义的current宏直接读取专门寄存器中的值来获取当前进程的task_struct指针,然后进入步骤(3)。有些硬件体系结构,内核原有的实现方式是通过计算进程的内核堆栈偏移的方法计算出当前运行进程的task_struct指针的值,然后将计算出的task_struct指针的值再保存到内核定义的current宏中,并且计算进程的内核堆栈偏移是在内核堆栈大小固定为8K字节或者4K字节的条件下完成的。在这种硬件体系结构下,进入步骤(2)修改内核中原有的实现;
(2)修改获取当前的通过Linux内核级线程库而运行在内核空间中的应用程序的task_struct指针的实现方式,同时不影响其他的普通应用程序的运行,即普通应用进程的内核堆栈的大小仍然固定为8K字节或者4K字节。按照下述步骤进行,完成后进入步骤(3):
(2.1)修改内核中原有的current宏的定义,首先,去掉内核中原有的current宏的定义,然后,相应地增加一个名称为current的全局变量的定义,类型为task_struct的指针类型,最后将该全局变量的初始值赋为N-ULL ;
(2.2)修改内核中原有的计算进程的内核堆栈偏移的函数,在该函数中增加对全局变量current的值的判断,如果current的值为NULL,则使用内核中原有的计算进程的内核堆栈偏移的方法计算出当前运行进程的tas-k_struct指针的值,然后该函数返回task_struct指针的值;否则该函数直接返回全局变量current的值;
(2.3)修改内核中原有的计算进程的内核堆栈偏移的宏定义,将全局变量current的值直接传送到寄存器中;
(2.4)在内核启动函数的开始处对全局变量current进行赋值,首先使用内核中原有的计算进程的内核堆栈偏移的方法计算出当前运行进程的task_struct指针的值,然后将该task_struct指针的值赋给全局变量curr-ent,即内核中的0号进程仍然按照内核中原有的获取进程的task_struct指针的方式进行获取;
(2.5)在进程调度程序中对进程上下文进行切换之前增加对全局变量current的赋值,使得全局变量current的值为调度程序经过选择并且准备投入运行的进程的task_struct指针的值;
(3)在进程创建函数中将lktl_esp_stack指针赋值为Linux内核级线程库创建的应用程序的堆栈地址,然后进入步骤(4);
(4)编译修改后的Linux内核源代码,生成新的内核映像并且启动新内核映像,然后进入步骤(5);
(5)加载Linux内核级线程库内核模块,按照下述步骤执行Linux内核级线程库各功能模块的初始化,完成后进入步骤(6):
(5.1)加载标准C库的功能子集的功能模块,提供内核级的基本输入输出、字符串操作、文件操作和网络套接字等API函数接口,应用程序在需要时可直接调用这些API函数接口;
(5.2)进行内存管理功能模块的初始化,设定分配的内存块的大小、初始化内存块链表以及注册内存回收的回调函数lktl_kmem_reap();
(5.3)进行信号量管理功能模块的初始化,注册信号量的获取函数、信号量的释放函数以及信号量的删除函数,并且初始化等待信号量的任务队列;
(5.4)进行日志管理功能模块的初始化,设置需要记录的事件类型以及各自的优先级;
(5.5)进行线程管理功能模块的初始化,创建Linux内核级线程库线程的工作队列lktl_thread_workqueue、注册Linux内核级线程库线程退出时的回调函数lktl_thread_exit_callback()、通知Linux内核的后台线程kevent创建一个master_thread主线程、设置master_thread的优先级为最高的实时优先级并且进入睡眠状态,然后设置master_thread主线程的SIG-CHLD信号;
(5.6)当master_thread主线程创建完成之后,设置它的SIGCHLD信号,处理其子线程执行完毕退出时发送的SIGCHLD信号;
(6)将需要创建Linux内核级线程库线程的任务加入到lktl_thread_-workqueue工作队列的尾端,一旦master_thread线程被唤醒时,就由它将工作队列中的任务一个个取出,依次完成创建每个Linux内核级线程库线程的任务,被创建的Linux内核级线程库线程是master_thread主线程的子线程,当lktl_thread_workqueue工作队列中没有需要处理的任务时master_-thread进入睡眠状态;
(7)新创建的Linux内核级线程库线程的优先级设置为较高的实时优先级,使得Linux内核级线程库线程的优先级小于master_thread主线程的实时优先级并且大于Linux的普通内核线程的优先级;
(8)当Linux内核级线程库线程创建完成之后,设置它的SIGKILL信号,处理master_thread主线程发送的强制Linux内核级线程库线程终止的SIG-KILL信号;
(9)master_thread主线程、代表应用程序的Linux内核级线程库线程以及Linux的普通内核线程由Linux内核调度器统一调度执行;
(10)等待应用程序的执行,应用程序以内核模块的方式加载到Linux内核,由代表应用程序的Linux内核级线程库线程来执行;
(11)应用程序执行完毕退出时,由代表应用程序的Linux内核级线程库线程向master_thread主线程发送SIGCHLD信号,master_thread主线程收到信号后等待Linux内核级线程库线程的退出,然后进入睡眠状态;
(12)重复上述步骤(6)-(11),直至Linux内核级线程库内核模块卸载;
(13)按照下述步骤执行Linux内核级线程库内核模块的卸载:
(13.1)终止线程管理功能模块,当master_thread主线程处于睡眠状态时,等待被调度运行,向所有的Linux内核级线程库线程发送强制终止信号SIGKILL,等待这些Linux内核级线程库线程的退出,然后master_thread主线程自身退出;当master_thread主线程处于运行状态时直接向所有的L-inux内核级线程库线程发送强制终止信号SIGKILL,等待这些Linux内核级线程库线程的退出,然后master_thread主线程自身退出;
(13.2)终止日志管理功能模块,注销需要记录的事件类型和各自的优先级;
(13.3)终止信号量管理功能模块,释放等待信号量的任务队列;
(13.4)终止内存管理功能模块,回收分配的内存并且释放内存块链表;
(14)Linux内核级线程库停止运行。
本发明基于嵌入式Linux操作系统的内核级线程库的实现方法的优点是:第一,对内核进行较小的改动就可以支持现有嵌入式Linux操作系统内核中的软实时或者硬实时调度机制,能够保证应用的实时性需求;第二,能够彻底消除应用进程在用户态和内核态之间反复切换带来的开销,显著提高嵌入式Linux应用系统的整体性能;第三,屏蔽了内核模块编程的复杂性,提供了一个供编程人员使用的开发框架以及一套编程接口(API),能够降低应用开发的复杂度,提高开发效率。
附图说明
图1为本发明方法的流程示意图;
图2为修改Linux内核源代码以提供对Linux内核级线程库底层运行环境支持的过程;
图3为执行Linux内核线程库各功能模块的初始化示意图;
图4为master_thread主线程管理Linux内核级线程库线程创建的工作流程示意图;
图5为Linux内核级线程库内核模块卸载的执行流程示意图。
具体实施方式
下面结合附图对本发明作进一步详细的说明。
如图1所示,本发明方法包括以下步骤:
(1)修改Linux内核源代码,以提供对Linux内核级线程库底层运行环境的支持(为了描述简便起见,后续将使用LKTL来简称Linux内核级线程库)。如图2所示,修改Linux内核源代码按照以下步骤进行,完成后进入步骤(4):
(1.1)在代表进程描述符的task_struct数据结构中增加一个新的vo-id类型的指针lktl并且初始化为NULL。如果lktl不为NULL,表明应用程序通过LKTL运行在内核空间中,否则,表明应用程序即为普通的应用程序。通过对lktl的判断,内核可以在提供LKTL运行环境的同时不影响其他的普通应用程序的运行;
(1.2)在进程的内核堆栈中增加一个int类型的指针lktl_esp_stack并且初始化为NULL,由该指针指向通过LKTL运行在内核空间中的应用程序的堆栈地址。内核空间只有进程的内核堆栈,而应用程序的堆栈中存放了应用程序的调用函数、参数、返回值和局部变量等。通过lktl_esp_stack指针,可以动态扩展进程的内核堆栈的大小,突破进程的内核堆栈大小固定为8K字节或者4K字节的限制。应用程序的堆栈大小和堆栈地址则由LKTL在创建进程时以参数的形式通知内核;
(1.3)根据不同的硬件体系结构,判断是否需要修改内核中原有的获取当前运行进程的task_struct指针的实现。在内核中,访问进程通常需要获取指向其task_struct指针,实际上,内核是通过定义一个current宏来获取当前正在运行进程的task_struct指针,不同的硬件体系结构下current宏的实现也不同。有些硬件体系结构使用一个专门的寄存器来保存指向当前运行进程的task_struct指针,内核原有的实现方式是使用current宏直接读取专门寄存器中的值来获取当前进程的task_struct指针,在这种硬件体系结构下,保留内核中原有的获取当前进程的task_struct指针的实现不变,即通过内核定义的current宏直接读取专门寄存器中的值来获取当前进程的task_struct指针,然后进入步骤(3)。有些硬件体系结构,内核原有的实现方式是通过计算进程的内核堆栈偏移的方法计算出当前运行进程的task_struct指针的值,然后将计算出的task_struct指针的值再保存到内核定义的current宏中,在这种硬件体系结构下,进入步骤(2)修改内核中原有的实现;
(2)对于通过计算进程的内核堆栈偏移的方法计算出当前运行进程的task_struct指针的硬件体系结构,如x86,是在进程的内核堆栈大小固定为8K字节或者4K字节的条件下完成的。而通过LKTL运行在内核空间中的应用程序的堆栈需要突破这个限制,因此需要修改获取当前的通过LKTL运行在内核空间中的应用程序的task_struct指针的实现方式,同时不影响其他的普通应用程序的运行,即普通应用进程的内核堆栈大小仍然固定为8K字节或者4K字节。按照下述步骤进行,完成后进入步骤(3):
(2.1)修改内核中原有的current宏的定义,首先,去掉内核中原有的current宏的定义,然后,相应地增加一个名称为current的全局变量的定义,类型为task_struct的指针类型,最后将该全局变量的初始值赋为N-ULL;
(2.2)修改内核中原有的计算进程的内核堆栈偏移的函数(如2.6内核版本中的current_thread_info(void)函数),在该函数中对全局变量cu-rrent的值进行判断,如果current的值为NULL,则使用内核中原有的计算进程的内核堆栈偏移的方法计算出当前运行进程的task_struct指针的值,然后该函数返回task_struct指针的值;否则该函数直接返回全局变量cur-rent的值;
(2.3)修改内核中原有的计算进程的内核堆栈偏移的宏定义,将全局变量current的值直接传送到寄存器中(如2.6内核版本中的GET_THREAD_I-NFO(reg)宏定义,将全局变量current的值直接传送到reg中);
(2.4)在内核启动函数(如2.6内核版本中的start_kernel(void)函数)的开始处对全局变量current进行赋值,首先使用内核中原有的计算进程的内核堆栈偏移的方法计算出当前运行进程的task_struct指针的值,然后将该task_struct指针的值赋给全局变量current,即内核中的0号进程仍然按照内核中原有的获取进程的task_struct指针的方式进行获取;
(2.5)在进程调度程序中对进程上下文进行切换之前(如2.6内核版本中的context_switch()函数),增加对全局变量current的赋值,使得全局变量current的值为调度程序经过选择并且准备投入运行的进程的task-_struct指针的值;
(3)在进程创建函数(如2.6内核版本中的copy_process()函数)中将lktl_esp_stack指针赋值为LKTL指定的应用程序的堆栈地址,然后进入步骤(4);
(4)编译修改后的Linux内核源代码,生成新的内核映像并且启动新内核映像,然后进入步骤(5);
(5)加载LKTL内核模块,执行LKTL各功能模块的初始化。如图3所示,各功能模块的初始化按照以下步骤进行,完成后进入步骤(6):
(5.1)加载标准C库的功能子集的功能模块,提供内核级的基本输入输出、字符串操作、文件操作和网络套接字等API函数接口,应用程序在需要时可直接调用这些API函数接口;
(5.2)进行内存管理功能模块的初始化,设定分配的内存块的大小、初始化内存块链表以及注册内存回收的回调函数lktl_kmem_reap();
(5.3)进行信号量管理功能模块的初始化,注册信号量的获取函数、信号量的释放函数以及信号量的删除函数,并且初始化等待信号量的任务队列;
(5.4)进行日志管理功能模块的初始化,设置需要记录的事件类型以及各自的优先级;
(5.5)进行线程管理功能模块的初始化,创建LKTL线程的工作队列l-ktl_thread_workqueue、注册LKTL线程退出时的回调函数lktl_thread_ex-it_callback()、通知Linux内核的后台线程kevent创建一个master_thread主线程、设置master_thread的优先级为最高的实时优先级并且进入睡眠状态,然后设置master_thread主线程的SIGCHLD信号;
(5.6)当master_thread主线程创建完成之后,设置它的SIGCHLD信号,处理其子线程执行完毕退出时发送的SIGCHLD信号;
(6)由master_thread主线程管理LKTL线程的创建。如图4所示,mas-ter_thread主线程管理LKTL线程的创建按照以下步骤执行:
(6.1)将需要创建LKTL线程的任务加入到lktl_thread_workqueue工作队列的尾端;
(6.2)判断master_thread是否处于运行状态,如果master_thread不是处于运行状态,则继续睡眠;否则进入步骤(6.3);
(6.3)判断lktl_thread_workqueue工作队列是否为空,如果为空,则master_thread由运行状态转入睡眠状态;否则进入步骤(6.4);
(6.4)从lktl_thread_workqueue工作队列中头部取出一个任务并且完成创建LKTL线程的任务,被创建的LKTL线程是master_thread主线程的子线程;
(7)新创建的LKTL线程的优先级设置为较高的实时优先级,使得LKTL线程的优先级小于master_thread主线程的实时优先级并且大于Linux的普通内核线程的优先级;
(8)当LKTL线程创建完成之后,设置它的SIGKILL信号,处理mast-er_thread主线程发送的强制LKTL线程终止的SIGKILL信号;
(9)master_thread主线程、代表应用程序的LKTL线程以及Linux的普通内核线程由Linux内核调度器统一调度执行;
(10)等待应用程序的执行,应用程序以内核模块的方式加载到Linux内核,由代表应用程序的LKTL线程来执行;
(11)应用程序执行完毕退出时,由代表应用程序的LKTL线程向mast-er_thread主线程发送SIGCHLD信号,master_thread主线程收到信号后等待LKTL线程的退出,然后进入睡眠状态;
(12)重复上述步骤(6)-(11),直至LKTL内核模块卸载;
(13)执行LKTL内核模块的卸载。如图5所示,按照下述步骤执行LKTL内核模块的卸载:
(13.1)终止线程管理功能模块,当master_thread主线程处于睡眠状态时,等待被调度运行,向所有的LKTL线程发送强制终止信号SIGKILL,等待这些LKTL线程的退出,然后master_thread主线程自身退出;当mast-er_thread主线程处于运行状态时直接向所有的LKTL线程发送强制终止信号SIGKILL,等待这些LKTL线程的退出,然后master_thread主线程自身退出;
(13.2)终止日志管理功能模块,注销需要记录的事件类型和各自的优先级;
(13.3)终止信号量管理功能模块,释放等待信号量的任务队列;
(13.4)终止内存管理功能模块,回收分配的内存并且释放内存块链表;
(14)Linux内核级线程库LKTL停止运行。
实例:
测试了LKTL线程库对嵌入式Linux系统性能的提升,分别评价在不使用LKTL线程库时和使用LKTL线程库时,嵌入式Linux系统的响应时间。测试环境使用的是虚拟机的模拟环境,进行了如下的3种测试:
(1)分别创建10和100个线程时的创建延时;
(2)文件系统的系统调用open和close循环执行1000时的响应延时;
(3)C/S模式下的典型客户端应用程序的执行延时,客户端和服务器进行简单的信息交互。
通过模拟实验,得出如下的测试结果:
  连续创建10个线程的延时(微秒/线程)  连续创建100个线程(微秒/线程)
  没有采用LKTL线程库   535.3  470.878
  采用LKTL线程库   222.52  221.17
 循环调用open(),close()函数1000次的总延时(微秒)
  没有采用LKTL线程库  31043.2
 循环调用open(),close()函数1000次的总延时(微秒)
  采用LKTL线程库  5627.2
  C/S模式下的典型客户端应用程序的执行延时(微秒)
  没有采用LKTL线程库   112785.2
  采用LKTL线程库   7537
实验结果表明:本方法能够显著提高嵌入式Linux应用系统的性能,在需要创建大量线程和频繁进行系统调用的工作负载的情况下,本方法所带来的性能提升是非常巨大的。

Claims (1)

1.一种基于嵌入式Linux操作系统的内核级线程库的实现方法,其特征在于:
(1)按照下述步骤修改Linux内核源代码,以提供对Linux内核级线程库底层运行环境的支持,完成后进入步骤(4):
(1.1)在代表进程描述符的task_struct数据结构中增加一个新的void类型的指针lktl并且初始化为NULL;
(1.2)在进程的内核堆栈中增加一个int类型的指针lktl_esp_sta-ck并且初始化为NULL,由该指针指向通过Linux内核级线程库而运行在内核空间中的应用程序的堆栈地址,堆栈大小和堆栈地址则以参数的形式通知Linux内核级线程库的线程创建函数;通过lktl_esp_stack指针,可以动态扩展进程的内核堆栈的大小,使得在Linux内核级线程库的支持下运行的进程的内核堆栈的大小突破8K字节或者4K字节的限制;
(1.3)根据不同的硬件体系结构,判断是否需要修改内核中原有的获取当前运行进程的task_struct指针的实现;不同的硬件体系结构下内核中原有的获取当前运行进程的task_struct指针的实现也不同;有些硬件体系结构使用一个专门的寄存器来保存指向当前运行进程的task_struct指针,内核原有的实现方式是使用一个定义为current的宏直接读取专门寄存器中的值来获取当前进程的task_struct指针,在这种硬件体系结构下,保留内核中原有的获取当前进程的task_struct指针的实现不变,即通过内核定义的current宏直接读取专门寄存器中的值来获取当前进程的task_struct指针,然后进入步骤(3);有些硬件体系结构,内核原有的实现方式是通过计算进程的内核堆栈偏移的方法计算出当前运行进程的task_struct指针的值,然后将计算出的task_struct指针的值再保存到内核定义的current宏中,并且计算进程的内核堆栈偏移是在内核堆栈大小固定为8K字节或者4K字节的条件下完成的,在这种硬件体系结构下,进入步骤(2)修改内核中原有的实现;
(2)修改获取当前的通过Linux内核级线程库而运行在内核空间中的应用程序的task_struct指针的实现方式,同时不影响其他的普通应用程序的运行,即普通应用进程的内核堆栈的大小仍然固定为8K字节或者4K字节;按照下述步骤进行,完成后进入步骤(3):
(2.1)修改内核中原有的current宏的定义,首先,去掉内核中原有的current宏的定义,然后,相应地增加一个名称为current的全局变量的定义,类型为task_struct的指针类型,最后将该全局变量的初始值赋为NULL;
(2.2)修改内核中原有的计算进程的内核堆栈偏移的函数,在该函数中增加对全局变量current的值的判断,如果current的值为NULL,则使用内核中原有的计算进程的内核堆栈偏移的方法计算出当前运行进程的t-ask_struct指针的值,然后该函数返回task_struct指针的值;否则该函数直接返回全局变量current的值;
(2.3)修改内核中原有的计算进程的内核堆栈偏移的宏定义,将全局变量current的值直接传送到寄存器中;
(2.4)在内核启动函数的开始处对全局变量current进行赋值,首先使用内核中原有的计算进程的内核堆栈偏移的方法计算出当前运行进程的task_struct指针的值,然后将该task_struct指针的值赋给全局变量cu-rrent,即内核中的0号进程仍然按照内核中原有的获取进程的task_struct指针的方式进行获取;
(2.5)在进程调度程序中对进程上下文进行切换之前增加对全局变量current的赋值,使得全局变量current的值为调度程序经过选择并且准备投入运行的进程的task_struct指针的值;
(3)在进程创建函数中将lktl_esp_stack指针赋值为Linux内核级线程库创建的应用程序的堆栈地址,然后进入步骤(4);
(4)编译修改后的Linux内核源代码,生成新的内核映像并且启动新内核映像,然后进入步骤(5);
(5)加载Linux内核级线程库内核模块,按照下述步骤执行Linux内核级线程库各功能模块的初始化,完成后进入步骤(6):
(5.1)加载标准C库的功能子集的功能模块,提供内核级的基本输入输出、字符串操作、文件操作和网络套接字等API函数接口,应用程序在需要时可直接调用这些API函数接口;
(5.2)进行内存管理功能模块的初始化,设定分配的内存块的大小、初始化内存块链表以及注册内存回收的回调函数lktl_kmem_reap();
(5.3)进行信号量管理功能模块的初始化,注册信号量的获取函数、信号量的释放函数以及信号量的删除函数,并且初始化等待信号量的任务队列;
(5.4)进行日志管理功能模块的初始化,设置需要记录的事件类型以及各自的优先级;
(5.5)进行线程管理功能模块的初始化,创建Linux内核级线程库线程的工作队列lktl_thread_workqueue、注册Linux内核级线程库线程退出时的回调函数lktl_thread_exit_callback()、通知Linux内核的后台线程kevent创建一个master_thread主线程、设置master_thread的优先级为最高的实时优先级并且进入睡眠状态,然后设置master_thread主线程的S-IGCHLD信号;
(5.6)当master_thread主线程创建完成之后,设置它的SIGCHLD信号,处理其子线程执行完毕退出时发送的SIGCHLD信号;
(6)将需要创建Linux内核级线程库线程的任务加入到lktl_thread_-workqueue工作队列的尾端,一旦master_thread线程被唤醒时,就由它将工作队列中的任务一个个取出,依次完成每个创建Linux内核级线程库线程的任务,被创建的Linux内核级线程库线程是master_thread主线程的子线程,当lktl_thread_workqueue工作队列中没有需要处理的任务时master_-thread进入睡眠状态;
(7)新创建的Linux内核级线程库线程的优先级设置为较高的实时优先级,使得Linux内核级线程库线程的优先级小于master_thread主线程的实时优先级并且大于Linux的普通内核线程的优先级;
(8)当Linux内核级线程库线程创建完成之后,设置它的SIGKILL信号,处理master_thread主线程发送的强制Linux内核级线程库线程终止的SIG-KILL信号;
(9)master_thread主线程、代表应用程序的Linux内核级线程库线程以及Linux的普通内核线程由Linux内核调度器统一调度执行;
(10)等待应用程序的执行,应用程序以内核模块的方式加载到Linux内核,由代表应用程序的Linux内核级线程库线程来执行;
(11)应用程序执行完毕退出时,由代表应用程序的Linux内核级线程库线程向master_thread主线程发送SIGCHLD信号,master_thread主线程收到信号后等待Linux内核级线程库线程的退出,然后进入睡眠状态;
(12)重复上述步骤(6)-(11),直至Linux内核级线程库内核模块卸载;
(13)按照下述步骤执行Linux内核级线程库内核模块的卸载:
(13.1)终止线程管理功能模块,当master_thread主线程处于睡眠状态时,等待被调度运行,向所有的Linux内核级线程库线程发送强制终止信号SIGKILL,等待这些Linux内核级线程库线程的退出,然后master_thr-ead主线程自身退出;当master_thread主线程处于运行状态时直接向所有的Linux内核级线程库线程发送强制终止信号SIGKILL,等待这些Linux内核级线程库线程的退出,然后master_thread主线程自身退出;
(13.2)终止日志管理功能模块,注销需要记录的事件类型和各自的优先级;
(13.3)终止信号量管理功能模块,释放等待信号量的任务队列;
(13.4)终止内存管理功能模块,回收分配的内存并且释放内存块链表;
(14)Linux内核级线程库停止运行。
CN 200810046848 2008-01-30 2008-01-30 基于嵌入式Linux操作系统的内核级线程库的实现方法 Expired - Fee Related CN101226487B (zh)

Priority Applications (1)

Application Number Priority Date Filing Date Title
CN 200810046848 CN101226487B (zh) 2008-01-30 2008-01-30 基于嵌入式Linux操作系统的内核级线程库的实现方法

Applications Claiming Priority (1)

Application Number Priority Date Filing Date Title
CN 200810046848 CN101226487B (zh) 2008-01-30 2008-01-30 基于嵌入式Linux操作系统的内核级线程库的实现方法

Publications (2)

Publication Number Publication Date
CN101226487A CN101226487A (zh) 2008-07-23
CN101226487B true CN101226487B (zh) 2010-06-02

Family

ID=39858501

Family Applications (1)

Application Number Title Priority Date Filing Date
CN 200810046848 Expired - Fee Related CN101226487B (zh) 2008-01-30 2008-01-30 基于嵌入式Linux操作系统的内核级线程库的实现方法

Country Status (1)

Country Link
CN (1) CN101226487B (zh)

Cited By (1)

* Cited by examiner, † Cited by third party
Publication number Priority date Publication date Assignee Title
CN102223376A (zh) * 2011-06-23 2011-10-19 中国人民解放军国防科学技术大学 网络协议栈兼容方法及装置

Families Citing this family (32)

* Cited by examiner, † Cited by third party
Publication number Priority date Publication date Assignee Title
CN101989189B (zh) * 2009-07-30 2014-06-11 中兴通讯股份有限公司 间接寄存器的模拟操作方法及装置
CN102073528B (zh) * 2011-01-28 2013-04-03 中国人民解放军国防科学技术大学 一种获得传统操作系统动态更新时间点的方法
CN103246557A (zh) * 2012-02-07 2013-08-14 腾讯科技(深圳)有限公司 一种跨进程调用应用信息的方法及装置
CN102647344B (zh) * 2012-03-30 2014-12-10 迈普通信技术股份有限公司 嵌入式分布式系统中报文发送方法
CN102866917B (zh) * 2012-09-27 2015-08-19 深圳市金宏威技术股份有限公司 一种基于Linux平台的冷火实时处理方法及系统
CN104090747B (zh) * 2014-05-22 2018-08-21 清华大学 利用实时调度优化器对Linux智能终端进行优化的方法
CN107003899B (zh) * 2015-10-28 2020-10-23 皓创科技(镇江)有限公司 一种中断响应方法、装置及基站
DE102016200777A1 (de) * 2016-01-21 2017-07-27 Robert Bosch Gmbh Verfahren und Vorrichtung zum Überwachen und Kontrollieren quasi-paralleler Ausführungsstränge in einem ereignisorientierten Betriebssystem
CN107797848B (zh) * 2016-08-29 2020-10-23 华为数字技术(苏州)有限公司 进程调度方法、装置和主机设备
CN108536609B (zh) * 2017-03-02 2022-02-22 迈普通信技术股份有限公司 内存碎片管理系统及方法
US10430245B2 (en) 2017-03-27 2019-10-01 Hong Kong Applied Science And Technology Research Institute Co., Ltd. Systems and methods for dynamic low latency optimization
CN107220111B (zh) * 2017-04-28 2019-08-09 华中科技大学 一种基于任务窃取的任务调度方法及系统
CN109426556B (zh) * 2017-08-31 2021-06-04 大唐移动通信设备有限公司 一种进程调度方法和装置
CN107967176A (zh) * 2017-11-22 2018-04-27 郑州云海信息技术有限公司 一种Samba多线程架构异常处理方法及相关装置
CN109101313A (zh) * 2018-03-15 2018-12-28 山东超越数控电子股份有限公司 一种实时内核的实现及测试方法
WO2019174010A1 (zh) * 2018-03-15 2019-09-19 深圳前海达闼云端智能科技有限公司 硬件控制方法、装置、电子设备及计算机可读介质
CN110928596B (zh) * 2018-09-04 2024-02-06 三六零科技集团有限公司 一种杀死常驻进程的方法及装置
CN110069326A (zh) * 2018-09-26 2019-07-30 北京技德终端技术有限公司 一种红黑树定时器管理实时操作系统
CN109542719B (zh) * 2018-10-26 2022-05-13 金蝶软件(中国)有限公司 线程状态监控方法、装置、计算机设备和存储介质
CN109614221B (zh) * 2018-10-30 2024-01-09 北京技德系统技术有限公司 一种实时操作系统的应用框架及其方法
CN112540871B (zh) * 2019-09-20 2022-10-04 无锡江南计算技术研究所 通用寄存器保留恢复的实现方法
CN111538580B (zh) * 2020-04-23 2024-01-05 苏州大学 一种嵌入式实时操作系统的线程信号操作方法与系统
CN111580792B (zh) * 2020-04-29 2022-07-01 上海航天计算机技术研究所 一种基于操作系统的高可靠星载软件架构设计方法
CN111966472B (zh) * 2020-07-02 2023-09-26 佛山科学技术学院 一种工业实时操作系统的进程调度方法及系统
CN112083914B (zh) * 2020-08-31 2023-09-12 深圳航天科技创新研究院 实现对象模型嵌入式操作系统软总线的方法及系统
CN112231246A (zh) * 2020-10-31 2021-01-15 王志平 一种处理器缓存结构的实现方法
CN114625061A (zh) * 2020-12-08 2022-06-14 山东新松工业软件研究院股份有限公司 一种导航控制器
CN112883007A (zh) * 2021-02-20 2021-06-01 杭州迪普科技股份有限公司 用于Linux系统的本机协议报文的处理方法及装置
CN113806106B (zh) * 2021-08-13 2023-09-15 中国航空无线电电子研究所 面向VxWorks实时进程的通信系统
CN114491507A (zh) * 2022-01-13 2022-05-13 南京翼辉信息技术有限公司 一种基于嵌入式实时操作系统实现轻量级安全容器的设计方法
CN115729716B (zh) * 2023-01-10 2023-05-09 云和恩墨(北京)信息技术有限公司 多线程内存管理方法及系统、计算机设备、存储介质
CN117251292B (zh) * 2023-11-13 2024-03-29 山东泽赢信息科技服务有限公司 内存管理方法、系统、终端及存储介质

Citations (1)

* Cited by examiner, † Cited by third party
Publication number Priority date Publication date Assignee Title
US5903752A (en) * 1994-10-13 1999-05-11 Intel Corporation Method and apparatus for embedding a real-time multi-tasking kernel in a non-real-time operating system

Patent Citations (1)

* Cited by examiner, † Cited by third party
Publication number Priority date Publication date Assignee Title
US5903752A (en) * 1994-10-13 1999-05-11 Intel Corporation Method and apparatus for embedding a real-time multi-tasking kernel in a non-real-time operating system

Cited By (1)

* Cited by examiner, † Cited by third party
Publication number Priority date Publication date Assignee Title
CN102223376A (zh) * 2011-06-23 2011-10-19 中国人民解放军国防科学技术大学 网络协议栈兼容方法及装置

Also Published As

Publication number Publication date
CN101226487A (zh) 2008-07-23

Similar Documents

Publication Publication Date Title
CN101226487B (zh) 基于嵌入式Linux操作系统的内核级线程库的实现方法
US8276145B2 (en) Protected mode scheduling of operations
US9542231B2 (en) Efficient execution of parallel computer programs
Kato et al. Gdev:{First-Class}{GPU} Resource Management in the Operating System
US6732138B1 (en) Method and system for accessing system resources of a data processing system utilizing a kernel-only thread within a user process
US10620988B2 (en) Distributed computing architecture
CN102375761A (zh) 业务管理方法和装置、以及设备
Tabish et al. A real-time scratchpad-centric os with predictable inter/intra-core communication for multi-core embedded systems
WO2006055864A2 (en) Method and apparatus for implementing task management of computer operations
Mashayekhi et al. Execution templates: Caching control plane decisions for strong scaling of data analytics
WO2005048009A2 (en) Method and system for multithreaded processing using errands
US9612863B2 (en) Hardware device for accelerating the execution of a systemC simulation in a dynamic manner during the simulation
Lannurien et al. Serverless Cloud Computing: State of the Art and Challenges
CN102117224B (zh) 一种面向多核处理器的操作系统噪声控制方法
CN109324881A (zh) 一种前端编程项目的打包方法及电子设备
Zhou et al. Shum-ucos: A rtos using multi-task model to reduce migration cost between sw/hw tasks
Itoh et al. Concurrent object-oriented device driver programming in apertos operating system
Juhász et al. A method for designing and implementing a real-time operating system for industrial devices
Burgio et al. Real-time heterogeneous platforms
Butler et al. Improving application concurrency on GPUs by managing implicit and explicit synchronizations
Schor et al. Reliable and Efficient Execution of Multiple Streaming Applications on Intel’s SCC Processor
Peng et al. EmSBoTScript: A Tiny Virtual Machine-Based Embedded Software Framework
Lopez et al. Prioritized Asynchronous Calls for Parallel Processing on Responsive MultiThreaded Processor
Wang Rhodes: A Next-Generation OS based on Resource Governance Model
CN116991553A (zh) 一种基于api拦截转发的容器云环境下的虚拟gpu分配方法及系统

Legal Events

Date Code Title Description
C06 Publication
PB01 Publication
C10 Entry into substantive examination
SE01 Entry into force of request for substantive examination
C14 Grant of patent or utility model
GR01 Patent grant
C53 Correction of patent for invention or patent application
CB03 Change of inventor or designer information

Inventor after: Cai Bin

Inventor after: Deng Guanghong

Inventor after: Liu Yi

Inventor after: Chi Zhiqiang

Inventor after: Huang Zhihua

Inventor after: Cheng Xiong

Inventor before: Cai Bin

Inventor before: Deng Guanghong

Inventor before: Liu Yi

Inventor before: Chi Zhiqiang

Inventor before: Huang Zhihua

Inventor before: Cheng Xiong

EE01 Entry into force of recordation of patent licensing contract

Assignee: China Shipbuilding Heavy Industries (Wuhan) Long Ling Electronics Co., Ltd.

Assignor: No. 709 Research Institute of China Shipbuilding Industry Corporation

Contract record no.: 2011420000071

Denomination of invention: Method for implementing inner core level thread library based on built-in Linux operating system

Granted publication date: 20100602

License type: Exclusive License

Open date: 20080723

Record date: 20110510

CF01 Termination of patent right due to non-payment of annual fee

Granted publication date: 20100602

Termination date: 20180130

CF01 Termination of patent right due to non-payment of annual fee