Nt*与Zw*的区别

        今天在看Undocumented Windows 2000 Secrets的时候, 一段对于Nt*与Zw*的区别,看了很久,看得不是很明白,后来通过网上查阅,现在比较清楚了.

        以下为原文:

        "一组与执行体的系统服务(executive's system services)平行的入口点.从内核模式的代码()中调用一个ZwXxx入口点将获得相应的系统服务,只是在使用Zw*()函数时,不会检查调用者的访问权限和参数的有效性,而且调用不会将先前模式(previous mode)切换到用户模式"

        "尽管任意一组函数都可以从内核模式调用,但如果用Zw*()函数来代替Nt*()函数,则可将先前模式(这里的先前模式指的是发出请求的模式)切换到内核模式"

        借助于LiveKd,我们来看一下Nt*()和Zw*()的区别:

1.在Ntdll.dll中的Nt*()与Zw*()

kd> u Ntdll!NtCreateFile L4
ntdll!NtCreateFile:
7c92d682 b825000000 mov eax,25h
7c92d687 ba0003fe7f mov edx,offset SharedUserData!SystemCallStub (7ffe0
300)
7c92d68c ff12 call dword ptr [edx]
7c92d68e c22c00 ret 2Ch

--------------------------------------------------------------------------------

kd> u Ntdll!ZwCreateFile L4
ntdll!NtCreateFile:
7c92d682 b825000000 mov eax,25h
7c92d687 ba0003fe7f mov edx,offset SharedUserData!SystemCallStub (7ffe0
300)
7c92d68c ff12 call dword ptr [edx]
7c92d68e c22c00 ret 2Ch

通过上面的代码,我们不难发现,实际上在Ntdll中Nt*()与Zw*()是完全一样的.

2.在ntoskrnl.exe中的Nt*()与Zw*()

kd> u nt!ZwCreateFile L14
nt!ZwCreateFile:
808059a0 b825000000 mov eax,25h
808059a5 8d542404 lea edx,[esp+4]
808059a9 9c pushfd
808059aa 6a08 push 8
808059ac e8801c0000 call nt!KiSystemService (80807631)
808059b1 c22c00 ret 2Ch

-------------------------------------------------------------------------------

kd> u nt!NtCreateFile L16
nt!NtCreateFile:
80898bf8 8bff mov edi,edi
80898bfa 55 push ebp
80898bfb 8bec mov ebp,esp
80898bfd 33c0 xor eax,eax
80898bff 50 push eax
80898c00 50 push eax
80898c01 50 push eax
80898c02 ff7530 push dword ptr [ebp+30h]
80898c05 ff752c push dword ptr [ebp+2Ch]
80898c08 ff7528 push dword ptr [ebp+28h]
80898c0b ff7524 push dword ptr [ebp+24h]
80898c0e ff7520 push dword ptr [ebp+20h]
80898c11 ff751c push dword ptr [ebp+1Ch]
80898c14 ff7518 push dword ptr [ebp+18h]
80898c17 ff7514 push dword ptr [ebp+14h]
80898c1a ff7510 push dword ptr [ebp+10h]
80898c1d ff750c push dword ptr [ebp+0Ch]
80898c20 ff7508 push dword ptr [ebp+8]
80898c23 e87bfeffff call nt!IoCreateFile (80898aa3)
80898c28 5d pop ebp
80898c29 c22c00 ret 2Ch

当我们看到上面代码的时候,就会发现在ntoskrnl.exe中Nt*()与Zw*()的区别了

转载于:https://www.cnblogs.com/XiaoHui/archive/2007/05/13/745028.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
generateMatrix函数是一个用于生成n阶方阵的函数。它接受一个整数n作为输入参数,并返回一个n*n的二维整数数组作为方阵。同时,函数还通过指针参数returnSize返回方阵的大小,通过指针参数returnColumnSizes返回每一列的大小。 函数的实现思路如下: 1. 首先,创建一个n*n的二维数组matrix来存储方阵。 2. 定义四个变量top、bottom、left、right来表示当前方阵的上下左右边界。 3. 使用一个循环来遍历方阵的每一个元素,并按照顺时针的顺序依次填入数字。 - 从左到右填充上边界,同时将top加1。 - 从上到下填充右边界,同时将right减1。 - 从右到左填充下边界,同时将bottom减1。 - 从下到上填充左边界,同时将left加1。 - 当top大于bottom或left大于right时,表示已经填充完所有元素,退出循环。 4. 返回生成的方阵matrix,并将方阵的大小赋值给returnSize,每一列的大小赋值给returnColumnSizes。 以下是generateMatrix函数的具体实现代码: ```c int** generateMatrix(int n, int* returnSize, int** returnColumnSizes) { // 创建n*n的二维数组 int** matrix = (int**)malloc(sizeof(int*) * n); for (int i = 0; i < n; i++) { matrix[i] = (int*)malloc(sizeof(int) * n); } // 定义边界和初始值 int top = 0, bottom = n - 1, left = 0, right = n - 1; int num = 1; // 填充方阵 while (top <= bottom && left <= right) { // 填充上边界 for (int i = left; i <= right; i++) { matrix[top][i] = num++; } top++; // 填充右边界 for (int i = top; i <= bottom; i++) { matrix[i][right] = num++; } right--; // 填充下边界 if (top <= bottom) { for (int i = right; i >= left; i--) { matrix[bottom][i] = num++; } bottom--; } // 填充左边界 if (left <= right) { for (int i = bottom; i >= top; i--) { matrix[i][left] = num++; } left++; } } // 设置返回值 *returnSize = n; *returnColumnSizes = (int*)malloc(sizeof(int) * n); for (int i = 0; i < n; i++) { (*returnColumnSizes)[i] = n; } return matrix; } ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值