当前位置 : 主页 > 编程语言 > java >

GlobalLock的前世今生3: 进入Win32的世界

来源:互联网 收集:自由互联 发布时间:2022-09-29
至此,你应该明白16位Windows的内存管理器是如何处理全局堆了。是时候来进入32位的Windows的世界了。 到了32位之后,GlobalAlloc会继续和之前一样模拟所有内存移动规则,但是GlobalAlloc的返


至此,你应该明白16位Windows的内存管理器是如何处理全局堆了。是时候来进入32位的Windows的世界了。

到了32位之后,GlobalAlloc会继续和之前一样模拟所有内存移动规则,但是GlobalAlloc的返回值不再是一个选择子(Selector),因为在Win32中,处理器是运行在平坦地址模式(Flat Mode)。

这意味着,之前缓存选择子并在底层重新分配内存的技法不再有效。

内存的移动性语义被完整地保留下来。内存块依然会有一个属性叫做锁定计数,即使它并没有什么意义,因为Win32系统从来都不会对内存进行压缩(请回忆一下,锁定计数是用来防止内存在压缩期间进行移动的一个属性)。

如果不是为了照顾GlobalFlags这个函数,可移动内存和锁定计数可以被完全地从系统中移除。GlobalFlags会返回一些奇怪的位信息模式,但现在这些信息都和内存不相关了,唯有锁定计数这一项信息。所以,锁定计数依然保留,以防止有一些应用程序会使用到它,或者一个程序会预期GlbalReAlloc会在一个已锁定的内存块上执行失败。

除此之外,一块可移动内存除了上述的开销之外,并不能给你带来什么其他的东西。

另外一个函数,LocalAlloc也是一样,它依然会带有内存移动性的操作开销,但是因为在Win16上,本地内存不会在DLL之间传递,所以本地堆相关的函数不会像全局堆那样会带有16位兼容性开销的问题。
在Win32上,基于上面的原因,推荐使用LocalAlloc。
(当然了,很多函数在内存分配时,需要指定一个特殊的类型,这个时候,你就不会有太多选择。例如,剪贴板就需要一个可移动的全局句柄,另外,COM需要使用一个任务分配器)

接下来,我们将会关注内存的锁定是如何实现的(虽然它也不会做什么有实际意义的操作)。

总结

拓扑梅尔智慧办公平台(Topomel Box):还是Win32对我们好,API丰富,兼容性也好,文档又全面。
Win11:还没好够…(DOG)

最后

Raymond Chen的《The Old New Thing》是我非常喜欢的博客之一,里面有很多关于Windows的小知识,对于广大Windows平台开发者来说,确实十分有帮助。
本文来自:《A history of GlobalLock, part 3: Transitioning to Win32》

GlobalLock的前世今生3: 进入Win32的世界_开发者

 

网友评论