关于VirtualAlloc 函数的PAGE_NOACCESS问题:

jiereliyi 2009-12-28 04:42:18
1. PAGE_NOACCESS参数问题
PAGE_NOACCESS 为任何访问该区域的操作将被拒绝
pVMem = (PUCHAR)VirtualAlloc(0, PAGE_SIZE*3, MEM_RESERVE, PAGE_NOACCESS);
这里如果分配一快虚拟内存不能访问,分配它有什么用。2.我在看驱动的时候看到下面代码
...全文
440 10 打赏 收藏 转发到动态 举报
写回复
用AI写文章
10 条回复
切换为时间正序
请发表友善的回复…
发表回复
jiereliyi 2009-12-30
  • 打赏
  • 举报
回复
谢谢
FLandY1982 2009-12-29
  • 打赏
  • 举报
回复
学习了..
-小仙- 2009-12-29
  • 打赏
  • 举报
回复
很多驱动里面 尤其是在5.0之前 ! 直接用的是
0xB1200000
定义一个该设备控制器相关的结构体,然后将0xB1200000指向这个结构体就可以访问设备寄存器,而不用
VirtualAlloc :

VirtualCopy:
-小仙- 2009-12-29
  • 打赏
  • 举报
回复
VirtualAlloc :
MSDN:
This function reserves or commits a region of pages in the virtual address space of the calling process.


所以 保留一段在calling process. 中的虚拟空间! 这段空间在MEM_RESERVE, PAGE_NOACCESS和参数下不可以被访问,只有通过VirtualCopy才可以直接使用!

-------------------
VirtualCopy:
MSDN:
This function dynamically maps a virtual address to a physical address by creating a new page-table entry.
其实我发现在很多驱动里面!VirtualCopy:是将VirtualAlloc过后的虚拟地址和与设备寄存器关联的地址进行绑定。
我这里用“设备寄存器关联” 是因为这样的例子:
pVMem = (PBYTE)VirtualAlloc(0, PAGE_SIZE*2, MEM_RESERVE, PAGE_NOACCESS);
if (pVMem) {
BOOL fSuccess = VirtualCopy(pVMem, (LPVOID)pContext->dwIOBase,
pContext->dwIOLen, PAGE_READWRITE | PAGE_NOCACHE);
}
dwIOBase, 是从注册表中读到的! 我这里取的是USB的例子 那么dwIOBase,就是0xB1200000
而0xB1200000就是virtual addresses。 0x91200000映射到Uncache field就是了!
DCD 0x91200000, 0x52000000, 1 ; USB device register

jiereliyi 2009-12-29
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 guopeixin 的回复:]
主要用在首先预留内存,后面再进行使用的情况,如下:
    一个比较好的分配512块特殊内存的方法是这样做:
#define PAGESIZE 1024  // Assume we're on a 1-KB page machine.
// Reserve a region first.
pMemBase = VirtualAlloc (NULL, PAGESIZE * 512, MEM_RESERVE,
                        PAGE_NOACCESS);

for (i = 0; i < 512; i++)
    pMem[i] = VirtualAlloc (pMemBase + (i*PAGESIZE), PAGESIZE,
                            MEM_COMMIT, PAGE_READWRITE);
    代码首先保留了一块区域,页面将在以后被提交。因为区域已经被先保留了,提交页就不受64-KB限制(译者注:只有保留页最小值受64KB限制),等等,如果你系统中有512KB的可用内存,分配将会成功。

[/Quote]
上边是预留MEM_RESERVE----只是在虚拟内存分配,下边是提交MEM_COMMIT参数指定----与物理内存关联,这样就可以使用了。
如果要和具体的内存地址关联,就需要调用VirtualCopy函数。
我这样理解对不对?
FrankBIBI 2009-12-29
  • 打赏
  • 举报
回复
学习了~~~~
guopeixin 2009-12-29
  • 打赏
  • 举报
回复
[Quote=引用 4 楼 jiereliyi 的回复:]
引用 2 楼 guopeixin 的回复:
主要用在首先预留内存,后面再进行使用的情况,如下:
    一个比较好的分配512块特殊内存的方法是这样做:
#define PAGESIZE 1024  // Assume we're on a 1-KB page machine.
// Reserve a region first.
pMemBase = VirtualAlloc (NULL, PAGESIZE * 512, MEM_RESERVE,
                        PAGE_NOACCESS);

for (i = 0; i < 512; i++)
    pMem[i] = VirtualAlloc (pMemBase + (i*PAGESIZE), PAGESIZE,
                            MEM_COMMIT, PAGE_READWRITE);
    代码首先保留了一块区域,页面将在以后被提交。因为区域已经被先保留了,提交页就不受64-KB限制(译者注:只有保留页最小值受64KB限制),等等,如果你系统中有512KB的可用内存,分配将会成功。


上边是预留MEM_RESERVE----只是在虚拟内存分配,下边是提交MEM_COMMIT参数指定----与物理内存关联,这样就可以使用了。
如果要和具体的内存地址关联,就需要调用VirtualCopy函数。
我这样理解对不对?

[/Quote]
必须得,呵呵,就是这么回事
FLandY1982 2009-12-28
  • 打赏
  • 举报
回复
MSDN上是这样说的:
If you call VirtualAlloc with dwSize >= 2 MB, flAllocationType set to MEM_RESERVE, and flProtect set to PAGE_NOACCESS, it automatically reserves memory at the shared memory region. This preserves per-process virtual memory.
guopeixin 2009-12-28
  • 打赏
  • 举报
回复
主要用在首先预留内存,后面再进行使用的情况,如下:
一个比较好的分配512块特殊内存的方法是这样做:
#define PAGESIZE 1024 // Assume we're on a 1-KB page machine.
// Reserve a region first.
pMemBase = VirtualAlloc (NULL, PAGESIZE * 512, MEM_RESERVE,
PAGE_NOACCESS);

for (i = 0; i < 512; i++)
pMem[i] = VirtualAlloc (pMemBase + (i*PAGESIZE), PAGESIZE,
MEM_COMMIT, PAGE_READWRITE);
代码首先保留了一块区域,页面将在以后被提交。因为区域已经被先保留了,提交页就不受64-KB限制(译者注:只有保留页最小值受64KB限制),等等,如果你系统中有512KB的可用内存,分配将会成功。
-小仙- 2009-12-28
  • 打赏
  • 举报
回复
留着 下面的函数用!
VirtualCopy(pVMem, (LPVOID)pContext->dwIOBase,
pContext->dwIOLen, PAGE_READWRITE | PAGE_NOCACHE);

19,500

社区成员

发帖
与我相关
我的任务
社区描述
硬件/嵌入开发 嵌入开发(WinCE)
社区管理员
  • 嵌入开发(WinCE)社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧