一种嵌入式实时操作系统中内存分配的方法

文档序号:6401735阅读:116来源:国知局
专利名称:一种嵌入式实时操作系统中内存分配的方法
技术领域
本发明涉及计算机领域,具体地说,涉及计算机领域中嵌入式实时多任务操作系统中的内存分配。
背景技术
嵌入式实时操作系统中的内存管理是保障应用实时性的重要因素。在通信领域的应用中,内存申请往往呈现各种相同数据结构(即相同大小内存块)的大量申请现象。为了提高实时性能,一般在实时操作系统提供的简单内存分配机制上做如下再“封装”步骤一预先向操作系统申请一块大的内存区。
步骤二将该内存区分为若干子区(本文称为内存池),同一内存池由若干大小相同的内存块组成。各内存池中内存块数量一般根据该领域应用的统计和大量经验估算而得。如通信领域中的一种划分方法(64,1200),(128,1000),(256,800),(512,500),(1024,20),(2048,10),(4096,5),(8192,2),(16384,1),括号中前面数字表示以字节为单位的内存块尺寸,后面数字表示该内存池中内存块总数,相邻内存池中内存块大小关系一般为2倍关系。每种内存池内的内存块可通过静态或动态链表组织成队列,申请时从队列头取一空闲块,归还时归还到队列尾。
为了便于管理,每一种内存池有一控制管理头(本文称为内存池控制头),所包含的信息一般有该池内存块的大小,内存块总量,空闲内存块数,该池中空闲块队列首指针(队列首指针是指队列中第一个元素结点地址),该池中空闲子队列尾指针(队列尾指针是指队列中最后一个元素结点地址),用于互斥操作该内存池结构的信号量(信号量是由操作系统提供的一种互斥访问共享资源的机制)等等。
该现有技术的不足主要有两点1、各内存池中内存块的个数是静态确定的,往往得根据先前积累的统计及经验值而定,不能在应用任务的运行过程中动态调整;2、实时系统通常得想办法尽量保障高优先级任务的实时性,该内存分配方法未予考虑。

发明内容
本发明要解决的技术问题是,克服现有技术的不足,提出一种新的内存调整分配方法,它能动态调整,保障高优先级任务实时性。
本发明的技术方案,包括1.1预先向操作系统中申请一块大内存区;1.2将所申请的大内存区划分为大小不同的内存池,同一内存池包含若干大小相同的内存块;初始化各内存池控制头;1.3当需要内存块时,根据需要的内存块大小找到对应的内存池,判断该内存池是否有空闲块,若有,从队头取下一块,修改内存池控制头的相关信息,分配结束;若没有,对内存池动态调整;1.4在释放内存的时候,根据要释放的内存大小找到相应的内存池归还到队尾,改写内存池控制头的相关信息。
所述内存池控制头包括的信息有该池中内存块大小(bs),当前内存块总量(cbcnt),空闲内存块数(fbcnt),空闲块队列首指针(pfbhead),空闲块队列尾指针(pfbrear),最近在该池上申请分配失败的次数(failcnt),申请分配失败任务的最高优先级(mprior),该内存池最近是否未访问标识(lrna),最少内存块数阈值(min),该内存池是否从未访问标识(never)。
在本发明中,对分配内存时找到的内存池,将其控制头的最近未访问标识和从未访问标识置为否;对无法从该池分配的,比较申请任务与该池控制结构中的原有的申请分配失败任务最高优级,确保记录下的是所有最近分配失败进程的最高优先级,增加最近分配失败次数。
步骤1.4中的改写内存控制头信息包括将申请分配失败任务最高优级域赋为最低优先级,最近分配失败次数清0,进程最近未访问标识置为真等等。
对内存池进行动态调整,是本发明的核心内容,是指遍历各内存池控制头,查找是否有空闲块数为0且其申请分配失败任务最高优先级域值最大(即内存池控制头的mprior域值最大)的内存池,如不存在这样的内存池,动态调整任务进入睡眠状态(在本发明中,睡眠,睡眠状态,唤醒等术语是专业术语。动态调整任务与许多应用任务一样共同运行在计算机上,调整任务有三种状态睡眠状态、就绪状态及执行状态,当调整任务处于执行态时才能进行动态调整,调整完毕,进入睡眠状态,让其它任务运行。当被唤醒时或睡眠时间到点时,有可能继续运行,进行新一轮的动态调整)。如存在,尝试按下面的步骤对该内存池进行扩容5.1对块尺寸大于待扩容内存池块尺寸的所有内存池依次查找,直到遇到一内存池满足1)内存池从未有进程申请过;2)空闲块数大于其最少内存块数阈值;若存在这样的内存池,从该池空闲块队列头摘下一块,转到5.4;否则,转到5.2;5.2对块尺寸大于待扩容内存池块尺寸的所有内存池依次查找,直到遇到一内存池满足1)该内存池最近无用户任务访问过;2)该池中内存空闲块数大于其内存块总数的一定比例值(该比例值一般的取值范围为3/5至1之间);3)空闲块数大于其最少内存块数阈值;若存在这样的内存池,从该池空闲块队列头摘下一块,转到5.4;否则,转到5.3;5.3对块尺寸大于待扩容内存池块尺寸的所有内存池依次查找,直到遇到一内存池满足1)该池中内存空闲块数大于其内存块总数的一定比例值(该比例值的取值一般大于5.2中的比例值);2)空闲块数大于最少内存块数阈值;若存在这样的内存池,从该池空闲块队列头摘下一块;否则,转到5.7;5.4如果该内存块能满足条件能分拆成待扩容内存池的内存块数量超过某个阈值(通常选取一与最近在该池上申请分配失败次数有关的值),则把该块逐级分拆到多个内存池即第一次等分成两部分,一部分加入该块来源内存池邻接的但块尺寸较小的内存池中,对之进行扩容,并参照步骤5.6修改扩容内存池相关内存控制头信息;对另一部分作同样的判断,如满足条件,又等分成两部分,其中一部分加入与上一次扩容内存池的紧邻内存池中,一直下去,直到得到不满足条件的块。
5.5把5.4中最终得到的内存块扩容到待扩容内存池中;5.6置待扩容内存池最近用户任务访问标识(lma)为无,清最近分配失败次数(failcnt)为0,置该池优先级(mprior)为初始化时设定的最低值,并修改内存池控制头其它相关数据;5.7调整任务进入睡眠状态。
与传统的面向通信领域的内存分配方法相比,该发明方法能在应用系统的运行中动态调整各内存池的容量,同时能尽量保障高优先级任务的实时性,降低了各内存池由于初始容量配置不当引起系统性能的下降或系统崩溃的可能性,具有自适应的特点,大大提高了系统的可靠性和稳定性。


图1描述了内存池初始化后的内存映象;图2描述了初始化后的内存池控制头数组;图3是本发明的一个实施例的初始流程图;图4是本发明的一个实施例的内存块分配流程图;
图5是本发明的一个实施例的内存块释放流程图。
具体实施例方式
本发明的技术方案,可以分为初始化、内存分配和内存释放三个阶段。
第一阶 段初始化第一步 预先向操作系统申请一块大的内存区。
第二步 从第一步所分配的大内存区中静态划分出各内存池并初始化各内存池控制头。为了提高检索性能,内存池控制头一般由一数组集中存放,并按各内存池控制头所对应的内存块尺寸有序存放。内存池控制头包括的主要管理信息有该池中内存块大小(bs),当前内存块总量(cbcnt),空闲内存块数(fbcnt),空闲块队列首指针(pfbhead),空闲块队列尾指针(pfbrear),最近在该池上申请分配失败的次数(failcnt),申请分配失败任务的最高优先级(mprior),该内存池最近是否未访问标识(lrna),最少内存块数阈值(min),该内存池是否从未访问标识(never)等等。
第三步 产生内存池动态调整任务,并使之处于睡眠状态。
第二阶 段内存分配第一步 当需要内存块时,由申请的内存块大小找到对应的内存池。
第二步 置该内存池控制头的最近未访问标识为否和从未访问标识为否;第三步 判断该池是否还有空闲块,若没有转做第五步。
第四步 从队头取下一块,修改内存池控制头的其它相关信息域,转做第七步。
第五步 无法从该池分配,比较申请任务与该池控制结构中的原有的申请分配失败任务最高优级,确保记录下的是所有最近分配失败进程的最高优先级,增加最近分配失败次数。
第六步 唤醒内存池动态调整任务。
第七步 内存分配结束。
上述第六步,动态调整任务的功能详细描述如下遍历各内存池控制头,查找是否有空闲块数为0且其申请分配失败任务最高优先级域值最大(即内存池控制头的mprior域值最大)的内存池,如不存在这样的内存池,动态调整任务进入睡眠状态;如存在,尝试按下面的步骤对该内存池进行扩容5.1对块尺寸大于待扩容内存池块尺寸的所有内存池依次查找,直到遇到一内存池满足1)内存池从未有进程申请过;2)空闲块数大于其最少内存块数阈值。若存在这样的内存池,从该池空闲块队列头摘下一块,转到5.2。否则,转到5.7。
5.2对块尺寸大于待扩容内存池块尺寸的所有内存池依次查找,直到遇到一内存池满足1)该内存池最近无用户任务访问过;2)该池中内存空闲块数大于其内存块总数的某个比例值(该比例值一般的取值范围为3/5至1之间);3)空闲块数大于其最少内存块数阈值。若存在这样的内存池,从该池空闲块队列头摘下一块,转到5.3;否则,转到5.7。
5.3对块尺寸大于待扩容内存池块尺寸的所有内存池依次查找,直到遇到一内存池满足1)该池中内存空闲块数大于其内存块总数的某个比例值(该比例值的取值一般大于第二步中的比例值);2)空闲块数大于最少内存块数阈值。若存在这样的内存池,从该池空闲块队列头摘下一块,转到5.4;否则,转到5.7。
5.4如果该内存块能满足条件能分拆成待扩容内存池的内存块数量超过某个阈值(通常选取一与最近在该池上申请分配失败次数有关的值),则把该块逐级分拆到多个内存池即第一次等分成两部分,一部分加入该块来源内存池邻接的但块尺寸较小的内存池中,对之进行扩容,并参照第六步修改扩容内存池相关内存控制头信息;对另一部分作同样的判断,如满足条件,又等分成两部分,其中一部分加入与上一次扩容内存池的紧邻内存池中,一直下去,直到得到不满足条件的块。[之所以采取逐级分拆的方式是因为若前面三步中找到的内存块远远大于待扩容内寸池中的内存块的话,若全部分配给它会为以后的调整带来不便,造成整个内存向低端内存池(内存块尺寸较小的内存池)聚集现象特别严重,因为考虑到时间性能的问题,本发明不调整低端内存池中内存到高端内存池中]。
5.5把5.4中最终得到的内存块扩容到待扩容内存池中。
5.6置待扩容内存池最近用户任务访问标识(lrna)为无,清最近分配失败次数(failcnt)为0,置该池优先级(mprior)为初始化时设定的最低值,并修改内存池控制头其它相关数据。
5.7动态调整任务进入睡眠状态。
第三阶 段内存释放第一步 根据要释放的内寸尺寸找到对应的内存池。
第二步 归还到队尾,把内存控制头中改写相应的内存控制头中的申请分配失败任务最高优级域赋为最低优先级,最近分配失败次数清0,进程最近未访问标识置为真。
本发明对内存池动态调整时,优先级的设置主要从内存分配对系统的可靠性与实时性的影响方面来考虑。如果应用任务因分配不到内存往往会导致整个系统的崩溃的话,可把内存池动态调整任务优先级设置为最高,让其周期性地进行动态调整,使得当有某内存池中的内存块分配完时能得到及时补充扩容,从而在一定程度上提前预防内存分配失败事件的发生。如果内存分配失败只是导致任务阻塞,则可给内存池动态调整任务设置一中间级别的优先级,而且只在分配失败时进行调整,以免其频繁运行导致系统性能下降。
下面就以(64,1200),(128,1000),(256,800),(512,500),(1024,20),(2048,10),(4096,5),(8192,2),(16384,1)传统的统计预估内存池结构为基础,对本发明进行更具体详细的描述如图3所示的步骤,首先向操作系统申请的一块大的内存区(图1中阴影部分所示)并设置了64,128,256,512,1024,2048,4096,8192,16384九种内存块大小的内存池。所有内存池头组成九个元素的数组,整个数组中的元素按内存块大小有序存放,该内存控制头数组的元素的初始化后的内容如图2中的表格内容所示。其中表中第一行即(64,1200)对应的内存池控制头,由于不会被挪用,故该内存池头的当前内存块数(cbcnt)与最少内存块数阈值(min)都设定为初始统计值1200;表中最后一行即(16384,1)对应的内存池,由于应用系统很少去申请,同时考虑到便于内存动态调整,该池初始化时给它多分了一内存块,起到后备内存的作用。其余的内存池最少内存块数阈值(min)初始化值分别简单地设为其初始当前内存块数(cbcnt)的7/8、6/7、5/6、,4/5、3/4、2/3、1/2,当然该值也可根据统计经验而设定,分配失败任务的最高优先级域(mprior)设定为1,是基于假定1表示系统的最低优先级,当然该值最好根据具体的应用系统而设定。
当有任务申请内存时,如图4所示由任务的申请内存块大小找到对应的内存池;置该内存池控制头的最近未访问标识为否和从未访问标识为否,表示已有任务对该内存池进行访问。然后判断该池是否还有空闲块,若有从该池中取下一块,这次分配成功;如过没有,该任务分配内存失败,修改内存控制头相关数据,对内存池动态调整。
图5描述了有任务释放内存块的过程。首先根据要释放的内寸块大小找到对应的内存池,然后把该块挂到该内存池的空闲队列中,并修改内存控制头中相应的控制信息。之所以把内存控制头中的申请分配失败任务最高优级域赋为低优先级1、最近分配失败次数清0,进程最近未访问标识置为真,主要是考虑到现在该内存池已经有可供分配的内存块了。
动态调整的具体实现可描述如下在图1所示的表中,找出空闲块数(fbcnt)为0且申请分配失败任务最高优先级值(mprior)最大的表项,如没有这样的表项存在,表示不需调整,调整任务进入睡眠状态;如存在,不妨假定第i个表项满足条件,需对其代表的内存池进行扩容,其扩容方法的步骤描述为第一步 从表项i+1起到表尾依次查找,直到遇到一表项满足1)never为1(内存池从未有进程申请过);2)fbcnt大于min(空闲块数大于其最少内存块数阈值)。若存在这样的表项,从该表项对应的内存池空闲块队列头摘下一块,转第四步。
第二步 从表项i+1起到表尾依次查找,直到遇到一表项满足1)lrna为1(该内存池最近无用户任务访问过);2)fbcnt大于cbcnt的3/5(该池中内存空闲块数大于其当前内存块总数的3/5;3)fbcnt大于min(空闲块数大于其最少内存块数阈值)。若存在这样的表项,从该表项对应的内存池空闲块队列头摘下一块,转第四步。
第三步 从表项i+1起到表尾依次查找,直到遇到一表项满足1)fbcnt大于cbcnt的4/5(该池中内存空闲块数大于其当前内存块总数的4/5;2)fbcnt大于min(空闲块数大于其最少内存块数阈值)。若存在这样的表项,从该表项对应的内存池空闲块队列头摘下一块,转第四步;若不存在,表示调整失败,转第七步。
第四步 如果从上面三步中得到的内存块能满足条件能分拆成待扩容内存池的内存块数量超过表项i中的failcnt(申请分配失败次数)+2,则把该块逐级分拆到多个内存池即第一次等分成两部分,一部分加入该块来源内存池(假定为表项j,由上面的查找步骤可知j>i)邻接的但块尺寸较小的内存池中(即j-1表项对应的内存池中),对之进行扩容,并参照第六步修改内存控制头相关信息域;对另一部分作同样的判断,如满足条件,又等分成两部分,其中一部分加入与上一次扩容内存池的紧邻内存池中(即j-2表项对应的内存池),一直下去,直到得到不满足条件的块。
第五步 把第四步中最终得到的内存块扩容到表项i所代表的待扩容内存池中。
第六步 置待扩容内存池最近用户任务访问标识(lrna)为0,清最近分配失败次数(failcnt)为0,置该池申请失败最高优先域值(mprior)为1,并修改内存池控制头其它相关控制信息。
第七步 调整任务进入睡眠状态。
权利要求
1.一种嵌入式实时操作系统中内存分配的方法,包括1.1预先向操作系统中申请一块大内存区;1.2将所申请的大内存区划分为大小不同的内存池,同一内存池包含若干大小相同的内存块;初始化各内存池控制头;1.3当需要内存块时,根据需要的内存块大小找到对应的内存池,判断该内存池是否有空闲块,若有,从队头取下一块,修改内存池控制头的相关信息,分配结束;若没有,对内存池动态调整;1.4在释放内存的时候,根据要释放的内存大小找到相应的内存池归还到队尾,改写内存控制头的相关信息。
2.权利要求1所述的嵌入式实时操作系统中内存分配的方法,其特征在于,所述内存块控制头包括的信息有该池中内存块大小,当前内存块总量,空闲内存块数,空闲块队列首指针,空闲块队列尾指针,最近在该池上申请分配失败的次数,申请分配失败任务的最高优先级,该内存池最近是否无用户任务访问标识,最少内存块数阈值,该内存池是否从未有用户任务访问标识。
3.权利要求2所述的嵌入式实时操作系统中内存分配的方法,其特征在于,对分配内存时找到的内存池,将其控制头的最近访问标识和从未访问标识置为否;对无法从该池分配的,比较申请任务与该池控制结构中的原有的申请分配失败任务最高优级,确保记录下的是所有最近分配失败进程的最高优先级,增加最近分配失败次数。
4.权利要求2所述的嵌入式实时操作系统中内存分配的方法,其特征在于,所述步骤1.4中的改写内存控制头信息,是指将申请分配失败任务最高优级域赋为最低优先级,最近分配失败次数清0,进程最近未访问标识置为真。
5.权利要求1至4任一权利要求所述的嵌入式实时操作系统中内存分配的方法,其特征在于,所述对内存池进行动态调整,是指遍历各内存池控制头,查找是否有空闲块数为0且其申请分配失败任务最高优先级域值最大的内存池,如不存在这样的内存池,动态调整任务进入睡眠状态;如存在,尝试按下面的步骤对该内存池进行扩容5.1对块尺寸大于待扩容内存池块尺寸的所有内存池依次查找,直到遇到一内存池满足1)内存池从未有进程申请过;2)空闲块数大于其最少内存块数阈值;若存在这样的内存池,从该池空闲块队列头摘下一块,转到5.4;否则,转到5.2;5.2对块尺寸大于待扩容内存池块尺寸的所有内存池依次查找,直到遇到一内存池满足1)该内存池最近无用户任务访问过;2)该池中内存空闲块数大于其内存块总数的一定比例值;3)空闲块数大于其最少内存块数阈值;若存在这样的内存池,从该池空闲块队列头摘下一块,转到5.4;否则,转到5.3;5.3对块尺寸大于待扩容内存池块尺寸的所有内存池依次查找,直到遇到一内存池满足1)该池中内存空闲块数大于其内存块总数的一定比例值;2)空闲块数大于最少内存块数阈值;若存在这样的内存池,从该池空闲块队列头摘下一块;否则,转到5.7;5.4如果该内存块能满足条件能分拆成待扩容内存池的内存块数量超过某个阈值,则把该块逐级分拆到多个内存池即第一次等分成两部分,一部分加入该块来源内存池邻接的但块尺寸较小的内存池中,对之进行扩容,修改扩容内存池相关内存控制头信息;对另一部分作同样的判断,如满足条件,又等分成两部分,其中一部分加入与上一次扩容内存池的紧邻内存池中,一直下去,直到得到不满足条件的块;5.5把5.4中最终得到的内存块扩容到待扩容内存池中;5.6置待扩容内存池最近用户任务访问标识为无,清最近分配失败次数为0,置该池优先级为初始化时设定的最低值,并修改内存池控制头其它相关数据;5.7调整任务进入睡眠状态。
6.权利要求5所述的嵌入式实时操作系统中内存分配的方法,其特征在于,步骤5.2中比例值一般的取值范围为3/5至1之间,步骤5.3中的比例值大于该值。
全文摘要
一种嵌入式实时操作系统中内存分配的方法,包括预先向操作系统中申请一块大内存区;将大内存区划分为大小不同的内存池,同一内存池包含若干大小相同的内存块;初始化各内存池控制头;当需要内存块时,根据需要的内存块大小找到对应的内存池,判断该内存池是否有空闲块,若有,从队头取下一块,修改内存池控制头的相关信息,分配结束;若没有,对内存池动态调整;在释放内存的时候,根据要释放的内存大小找到相应的内存池归还到队尾,改写内存池控制头的相关信息。本发明能动态调整各内存池的容量,同时保障高优先级任务的实时性,提高了系统的可靠性和稳定性。
文档编号G06F9/46GK1722106SQ200410041459
公开日2006年1月18日 申请日期2004年7月13日 优先权日2004年7月13日
发明者何先波, 张芝萍, 徐立锋 申请人:中兴通讯股份有限公司
网友询问留言 已有0条留言
  • 还没有人留言评论。精彩留言会获得点赞!
1