发明内容
为解决上述问题,本发明的目的在于提供一种能通过软件的方式在32位系统使用4GB以上内存的扩展进程中内存地址控制的方法。
本发明解决其问题所采用的技术方案是:
一种扩展进程中内存地址控制的方法,包括主进程和由主进程创建的一个或以上的扩展进程,所述主进程包括原程序业务组件和第一扩展内存地址空间组件,所述第一扩展内存地址空间组件包括内存-进程映射模块和主分配器模块,所述扩展进程包括第二扩展内存地址空间组件和所扩展的内存地址空间,所述第二扩展内存地址空间组件包括内存-区块映射模块和次分配器模块,所述扩展进程通过扩展进程ID号唯一进行识别,内存地址空间内的内存通过内存ID号进行识别,每一段独立的内存对应一个独立的内存ID号,所述主分配器模块根据内存-进程映射模块维护内存ID与扩展进程ID的关系,所述次分配器模块通过内存-区块映射模块维护内存ID及其对应的内存区块的关系。
进一步,主进程中的内存-进程映射模块中维护了一个内存ID到扩展进程ID的映射表。其输入为内存ID,其输出为扩展进程的ID。
进一步,扩展进程中的内存-区块映射模块中维护了一个内存ID到区块的映射表。其输入为内存ID,其输出为区块信息。一个区块信息由地址、大小这样一个二元组组成,所述区块为内存ID对应的内存在本进程中地址空间的位置。
进一步,主进程中的主分配器模块以管道方式与扩展进程中的次分配器模块通讯,主分配器模块和次分配器模块配合完成内存分配、内存释放、内存读取、内存写入4个不同功能的操作。
具体地,内存分配的步骤为,主分配器模块接受业务逻辑发送过来的内存分配请求,并将请求的内存大小逐一发给各个扩展进程中的次分配器模块,若扩展进程可以分配出内存,则主分配器模块将内存ID,扩展进程ID的对应关系记录到内存-进程映射表中,若所有扩展进程都无法分配出内存,则主分配器模块将启动一个全新的扩展进程,并将分配请求传给这个全新的扩展进程的次分配器;接到主分配器发送过来的内存分配请求后:扩展进程中的次分配器模块如果可以分配出足量的内存,则会给这个内存块分配一个系统中的全局ID值,同时将内存ID、地址、大小记录到本扩展进程的内存-区块映射模块中,最后将内存ID传回给主分配器模块,若扩展进程中的次分配器模块无法分配出足量的内存,则会返回一个分配失败的返回值给主分配器模块。
具体地,内存释放的步骤为:业务逻辑将需要释放的内存ID发给主分配器模块,主分配器模块在内存-进程映射表中查找得到内存ID对应的扩展进程,主分配器模块将内存ID发送给扩展进程ID所对应的次分配器模块,次分配器模块在内存-区块映射模块中查找内存ID所对应的具体区块,即地址、大小这个二元组,删除地址所对应的扩展内存地址空间的内存块,并在内存-区域映射模块中删除内存ID及其所对应的区块信息。
具体地,内存读取的步骤为:业务逻辑将需要读取的内存、偏移值、读取大小发给主分配器模块,主分配器模块在内存-进程映射表中查找得到内存ID对应的扩展进程ID,主分配器模块将内存ID、偏移值、读取大小发送给扩展进程ID所对应的次分配器模块,次分配器模块在内存-区块映射模块中查找内存ID所对应的具体区块,即地址、大小这个二元组,次分配器模块将读取扩展进程中实际地址为 地址+偏移值 大小为读取大小的内存块返回给主分配器模块,主分配器模块将所读取的内存传回给业务逻辑,完成读取。
具体地,内存写入的步骤为:业务逻辑将需要写入的内存ID、偏移值、写入数据发给主分配器模块,主分配器模块在内存-进程映射表中查找得到内存ID对应的扩展进程ID,主分配器模块将内存ID、偏移值、写入数据发送给扩展进程ID所对应的次分配器模块,次分配器模块在内存-区块映射模块中查找内存ID所对应的具体区块,即地址、大小这个二元组,次分配器模块将写入数据写入到扩展进程中实际地址为地址+偏移值的内存,完成写入。
本发明的有益效果是:本发明采用的一种扩展进程中内存地址控制的方法,主进程通过主分配器模块创建多个扩展进程,并由扩展进程中的次分配器模块分配实际的内存。所有内存不通过内存地址标识,而是通过一个全局唯一的内存ID标识。其中内存ID、扩展进程、扩展进程内的内存区块三者之间的关系则通过内存-进程映射模块和内存-区域映射模块来维护。如此一来,虽然32位环境下每个进程仍然只有4GB的地址空间。但是由于可以动态的增长多个进程,且内存ID不像内存地址一样受到4GB地址空间的约束。因此可以不受限制的最大化物理内存的使用。
本发明在无需升级机器硬件和系统的前提下,仅通过改进软件即可充分的利用电脑的物理内存。且本方法通过扩展进程方式实现,使得单个进程所使用的物理内存总量没有上限。即便是在64位系统中,运用此方法的系统仍然可以正常运行。即通过此方法扩展内存不会产生兼容性问题。同时此方法的系统也能扩展64位系统的内存最大使用量。
具体实施方式
参照图1-图3,本发明的一种扩展进程中内存地址控制的方法,包括主进程和由主进程创建的一个或以上的扩展进程,所述主进程包括原程序业务组件和第一扩展内存地址空间组件,所述第一扩展内存地址空间组件包括内存-进程映射模块和主分配器模块,所述扩展进程包括第二扩展内存地址空间组件和所扩展的内存地址空间,所述第二扩展内存地址空间组件包括内存-区块映射模块和次分配器模块,所述扩展进程通过扩展进程ID号唯一进行识别,内存地址空间内的内存通过内存ID号进行识别,每一段独立的内存对应一个独立的内存ID号,所述主分配器模块根据内存-进程映射模块维护内存ID与扩展进程ID的关系,所述次分配器模块通过内存-区块映射模块维护内存ID及其对应的内存区块的关系。
参照图2所示,主进程中的内存-进程映射模块中维护了一个内存ID到扩展进程ID的映射表。其输入为内存ID,其输出为扩展进程的ID。
参照图3所示,扩展进程中的内存-区块映射模块中维护了一个内存ID到区块的映射表。其输入为内存ID,其输出为区块信息。一个区块信息由地址、大小这样一个二元组组成,所述区块为内存ID对应的内存在本进程中地址空间的位置。
具体地,主进程中的主分配器模块以管道方式与扩展进程中的次分配器模块通讯,主分配器模块和次分配器模块配合完成内存分配、内存释放、内存读取、内存写入4个不同功能的操作。
参照图4所示,所述内存分配的过程如下:
A1)业务逻辑将分配的内存大小需求发送给主分配器模块。
B1)主分配器模块将需求发送给第一个扩展进程的次分配器模块
C1)是否有这个扩展进程。如果没有这个扩展进程则主分配器模块创建一个新的扩展进程。并分配一个新的ID给这个扩展进程。
D1)次分配器模块收到分配需求后,在本进程中的扩展的内存地址空间中尝试分配内存。
E1)如果次分配器模块成功分配了内存,则给这个内存一个全局唯一的ID值(即内存ID)。并将内存ID以及分配成功后得到的{地址,大小},记录到内存-区块映射模块中。 如果次分配器模块无法在本进程中分配所需内存,则返回失败。
F1)如果主分配器模块接收到分配失败的返回值,则尝试在下一个扩展进程中进行内存分配。并返回到步骤c)。否则将得到的内存ID扩展进程ID的对应关系记录到内存-进程映射表中。
G1)最后主分配器模块将内存ID返回给业务逻辑。
例如,如业务逻辑需要100MB的内存。这个时候业务逻辑将这个100MB数值发送给主分配器模块,此时主分配器模块将100MB这个请求先发送给扩展进程ID=1的进程的次分配器模块。若此时进程ID=1的次分配器模块可以在此进程中分配出一个100MB的内存,则他会给这个内存分配一个全局唯一的ID值,并将此值返回给主分配器。主分配器最终将这个内存ID返回给业务逻辑。
参照图5所示,内存释放的过程如下:
A2)业务逻辑将需要释放的内存ID发给主分配器模块。
B2)主分配器模块在内存-进程映射表中查找得到内存ID对应的扩展进程ID。
C2)主分配器模块将内存ID发送给扩展进程ID所对应的次分配器模块。
D2)次分配器模块在内存-区块映射模块中查找内存ID所对应的具体区块,即{地址,大小}这个二元组。
E2)删除地址所对应的扩展的内存地址空间中的内存块。
F2)在内存-区域映射模块中删除内存ID及其所对应的区块信息。
G2)主分配器模块删除内存-进程映射模块内存ID对应的信息。
参照图6所示,内存读取的过程如下:
A3)业务逻辑将需要读取的{内存ID,偏移值,读取大小}发给主分配器模块。
B3)主分配器模块在内存-进程映射表中查找得到内存ID对应的扩展进程ID。
C3)主分配器模块将{内存ID,偏移值,读取大小}发送给扩展进程ID所对应的次分配器模块。
D3)次分配器模块在内存-区块映射模块中查找内存ID所对应的具体区块,即{地址,大小}这个二元组。
E3)次分配器模块将读取扩展进程中实际地址为 地址+偏移值 大小为读取大小的内存块返回给主分配器模块。
F3)主分配器模块将所读取的内存传回给业务逻辑,完成读取。
参照图7所示,内存写入的过程如下:
A4)业务逻辑将需要写入的{内存ID,偏移值,写入数据}发给主分配器模块。
B4)主分配器模块在内存-进程映射表中查找得到内存ID对应的扩展进程ID。
C4)主分配器模块将{内存ID,偏移值,写入数据}发送给扩展进程ID所对应的次分配器模块。
D4)次分配器模块在内存-区块映射模块中查找内存ID所对应的具体区块,即{地址,大小}这个二元组。
E4)次分配器模块将写入数据写入到扩展进程中实际地址为 地址+偏移值的内存,完成写入。
以下通过一个实施例对整个过程进行描述,架设一个系统启动后,原程序业务组件会先后做如下几个操作:1.分配一块100K的内存。2.将100K数据写入到内存中。3.读取100K中偏移值为50K,大小为50K的内存。4.释放这块内存。
内存分配的过程如下(可参考图4所示):
1.业务组件中的业务逻辑会向同进程中的主分配器模块申请100K的内存。
2.主分配器模块会将这个请求转发给第一个扩展进程。(即ID=1的扩展进程)
3.由于是第一次请求。系统中并没有任何扩展进程,因此主分配器模块会建立一个新的扩展进程。并将设置此扩展进程的ID=1。
4.ID=1的扩展进程收到这个请求后。在本进程的“扩展内存地址空间”中尝试分配内存。(即用普通方法分配一块内存)
5.由于是第一次分配,且100K是一个比较小的内存,扩展进程肯定可以分配得出来。因此内存会分配成功了。设这时候分配成功后得到的内存地址是500。
6. 次分配器为这个内存设置一个系统中全局唯一的ID值。由于系统中暂时没有其他的内存块,我们假设这次分配的ID值=1。
7.次分配器将{1,500,100k}这么一组数据记录到id=1的扩展进程中的“内存-区块映射表中”。(三元组的意义是{内存ID,地址,大小})
8.次分配器将“内存ID=1”这个信息返回给主分配器。即主分配器拿到了一个内存ID。
9.主分配器将{1,1}这么一组数据记录到“内存-进程映射表”中。(二元组对应{内存ID,扩展进程ID})。
10.最后主分配器将“内存ID”返回给业务逻辑。业务逻辑拿到这个ID后即可在后续过程中对内存中的信息进行读写或释放操作。分配过程完成。
内存写入的过程如下(可参考图7所示):
1.设此时业务逻辑需要将100K的某段数据写入到内存中。
2.业务逻辑将{1, 0, “具体写入的信息..长度是100K”}这个请求发给主分配器模块。(这个三元组中的信息对应{内存ID,偏移值,写入数据})。
3.主分配器模块在“内存-进程映射表”中查找内存ID=1的扩展进程ID。得到扩展进程ID=1.
4.主分配器通过管道将{1, 0, “具体写入的信息..长度是100K”}这个信息发给ID=1的扩展进程的次分配器。
5.次分配器得到这个消息后,在“内存-区块映射表”中查找内存ID=1所对应的区块信息。得到{500,100K}这么一个二元组。(即 地址= 500, 大小= 100K)。
6.次分配器将需要写入的内容“具体写入的信息..长度是100K”,写入到地址为500,大小为100K的内存区块中。
7.写入过程结束。
内存读取的过程如下(可参考图6所示):
1.设此时业务逻辑需要读取刚刚写入的100K中偏移值为50K,大小为50K的内存。
2.业务逻辑将{1,50K,50K}这个读取请求发送给“主分配器模块”。({内存ID,偏移值,读取大小})
3.“主分配器模块”在“内存-进程映射表”中搜索ID=1的内存。得到扩展进程ID=1这样一个结果。
4.“主分配器模块”通过管道将{1,50K,50K}发送给ID=1的扩展进程的次分配器。
5.扩展进程中的“次分配器模块”在“内存区域映射模块”中查找内存ID=1的内存的具体区域信息。得到{500,100K}这么一个信息。(即内存存储在扩展进程中 地址=500 大小=100K 的位置中)
6.将读取扩展进程中以500+50K为地址。50K为大小的这么一个区块。(即读取扩展进程中实际地址为 “地址+偏移值” 大小为“读取大小”的内存块)
7.“次分配器模块”将读取到的内容,通过管道主进程的“主分配器模块”。
8.“主分配器模块”将传回的内容传给业务逻辑。完成读取。
内存释放的过程如下(可参考图5所示):
1.当业务逻辑不再需要使用ID=1的这块内存时,其可以触发内存释放过程。
2.将所需要释放的内存ID=1发送给“主分配器模块”。
3.“主分配器模块”在“内存-进程映射表”中查找ID=1的内存块对应的扩展进程ID。得到扩展进程ID=1。
4.“主分配器模块”将内存ID=1发送给ID=1的扩展进程的“次分配器模块”。
5.扩展进程中的“次分配器模块”在“内存区域映射模块”中查找内存ID=1的内存的具体区域信息。得到{500,100K}这么一个信息。
6.“次分配器模块”释放地址=500, 大小= 100K的这个内存块。
7.“次分配器模块”删除“内存-区域映射模块”内存ID=1对应的信息。
8.“主分配器模块”删除“内存-进程映射模块”内存ID=1对应的信息。
以上所述,只是本发明的较佳实施例而已,本发明并不局限于上述实施方式,只要其以相同的手段达到本发明的技术效果,都应属于本发明的保护范围。