爱爱小说网 > 其他电子书 > windows环境下32位汇编语言程序设计 >

第56章

windows环境下32位汇编语言程序设计-第56章

小说: windows环境下32位汇编语言程序设计 字数: 每页3500字

按键盘上方向键 ← 或 → 可快速上下翻页,按键盘上的 Enter 键可回到本书目录页,按键盘上方向键 ↑ 可回到本页顶部!
————未阅读完?加入书签已便下次继续阅读!




;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

                    end     start

由于在对话框初始化的时候,对话框管理器就要根据对话框资源的内容创建每个子窗口控件,所以在调用DialogBoxParam函数显示对话框之前,“HexEdit”类就必须存在,否则初始化工作会失败。因此,程序在DialogBoxParam函数之前调用_SuperClass子程序进行超类化的工作。

在_SuperClass子程序中,程序通过GetClassInfoEx函数获取Edit控件的类结构,然后将结构中的窗口过程指到自己的_ProcEdit子程序中,接下来将hInstance字段设置为自己的实例句柄,并将类的名称改为“HexEdit”,最后用RegisterClassEx函数注册一个新的“HexEdit”类:

                    nst

szEditClass     db      'Edit';0

szClass         db      'HexEdit';0

                    de

        。。。

        mov         @stWC。cbSize;sizeof @stWC ;@stWC是一个WNDCLASSEX结构

        invoke      GetClassInfoEx;NULL;addr szEditClass;addr @stWC

        push            @stWC。lpfnWndProc

        pop         lpOldProcEdit

    mov         @stWC。lpfnWndProc;offset _ProcEdit

    push            hInstance

    pop         @stWC。hInstance

    mov         @stWC。lpszClassName;offset szClass

        invoke      RegisterClassEx;addr @stWC

新的窗口过程和子类化窗口中的例子是一样的,在这里就不进行分析了,程序的结果就是:用HexEdit类建立的所有窗口的功能和子类化窗口例子中IDC_HEX编辑框的功能是一样的。

本程序演示的是派生类在对话框中的使用情况,在这里基于派生类创建的窗口是由对话框管理器自动调用CreateWindowEx函数创建的,如果将派生类使用在普通窗口中的话,可以通过指定派生类的名称,自己使用CreateWindowEx函数来创建。



 
来源:电子工业出版社 作者:罗云彬 上一页         回书目         下一页          
上一页         回书目         下一页          
  


第10章 内存管理和文件操作


10。1 内 存 管 理(1)

    
10。1。1  内存管理基础

Win32中的内存管理是分层次的,系统提供了几组层次不同的函数来管理内存,它们是标准内存管理函数、堆管理函数、虚拟内存管理函数和内存映射文件函数。所有的这些函数都是为了让用户能在比较高的层次上方便地管理内存,以便将程序和底层的内存分页机制隔离开来。如图10。1所示,这几组函数的层次是各不相同的。


图10。1  Windows的内存分层管理

Windows使用一个以页为基础的虚拟内存系统,与分页有关的概念已经在第1章的1。3。2小节中有所介绍。Windows充分利用了80x86处理器保护模式下的线性寻址机制和分页机制,这些机制是Win32内存管理的基础,Win32提供了一组虚拟内存管理函数来管理虚拟内存,主要用于保留/提交/释放虚拟内存,在虚拟内存页上改变保护方式,锁定虚拟内存页以及查询一个进程的虚拟内存等操作,这是一组位于底层的函数。

堆管理函数相对比较高级一点,堆的主要功能就是有效地管理内存和进程的地址空间。DOS操作系统下的C语言中就已经有了“堆”的概念,这时的“堆”是程序初始化时向操作系统申请并预留的大块内存,程序通过C函数在这块空间中申请和释放内存。

在Win32中,进程可以使用的整个地址空间就是一个堆。并且“堆”的概念又被引伸了一步:Win32中分两种堆,一种是进程的“默认堆”,默认堆只有一个,指的就是可以使用的整个地址空间;另一种是“动态堆”,也称为“私有堆”,私有堆类似于DOS下C语言中使用的那种堆,一个进程可以随意建立多个私有堆,也可以随意将它们释放,私有堆全部位于默认堆中,从概念上看,它和默认堆并没有什么不同,就像一个跨国公司和属下的子公司同样都是按照公司的规程操作一样。使用堆管理函数可以对所有的私有堆和默认堆进行操作。

标准内存管理函数总是在默认堆中分配和释放内存,这组函数就是常规意义上的内存管理函数。

内存映射文件函数相对比较独立,它是为了文件操作的方便性而设立的,当对文件进行操作的时候,一般总是先打开文件,然后申请一块内存用做缓冲区,再将文件数据循环读入并处理,当文件长度大于缓冲区长度的时候需要多次读入,每次读入后处理缓冲区边界位置的数据往往是个麻烦的问题。曾经介绍过Windows可以使用磁盘文件当做虚拟内存(参考图1。5,虚拟内存的实现),内存映射文件函数使用同样的办法将一个文件直接映射到进程的地址空间中,这样可以通过内存指针用读写内存的办法直接存取文件内容。

对比这些函数,可以发现它们涉及的系统资源是各不相同的,如表10。1所示。

表10。1  不同内存管理函数的操作对象

内存管理函数
 涉 及 方 面
 
标准内存管理函数
 一个进程的默认堆
 
堆管理函数
 一个进程的虚拟地址空间、系统内存、进程堆资源结构
 
虚拟内存管理函数
 一个进程的虚拟地址空间、系统页文件、系统内存、硬盘空间
 
内存映射文件函数
 一个进程的虚拟地址空间、系统页文件、系统内存、硬盘空间、标准文件I/O
 

10。1。2  内存的当前状态

在第1章中已经介绍过,一个进程可以寻址的地址空间是4 GB,但用户可以直接管理的地址空间是多大呢?实际上,高端的2 GB是供操作系统内核使用的,其中安排了操作系统的代码和数据(Windows 9x中还包括共享内存映射的地址空间),可供应用程序使用的地址空间是低端的2 GB,这2 GB除去应用程序与用户DLL等的代码和静态数据段以后,余下来的才是内存管理函数可以使用的地址空间,应用程序和用户DLL的大小一般只有几兆字节到上百兆字节,所以可以认为能自由使用的地址空间基本上是2 GB。

既然用户可以使用的地址空间大概为2 GB,读者千万不要认为就可以申请2 GB的内存了,因为这2 GB仅是可以使用的“地址”空间,而不是可以使用的“内存”空间,可分配内存的大小还受制于物理内存和磁盘交换文件的大小。因为物理内存和磁盘交换文件是供整个系统和所有用户程序使用的,所有系统内核、当前执行的所有用户程序的代码、数据以及分配的内存总量并不能超过物理内存和磁盘交换文件的总和。

当设计一个可能需要申请大量内存的程序时,如何预先得知系统的配置情况呢?对此可以使用GlobalMemoryStatus函数:

 

    invoke  GlobalMemoryStatus,lpBuffer

lpBuffer指向一个MEMORYSTATUS结构,结构的定义如下:

MEMORYSTATUS STRUCT

  dwLength            DWORD      ?     ;本结构的长度

  dwMemoryLoad      DWORD      ?     ;已用内存的百分比

  dwTotalPhys       DWORD      ?     ;物理内存总量

  dwAvailPhys       DWORD      ?     ;可用物理内存

  dwTotalPageFile   DWORD      ?     ;交换文件总的大小

  dwAvailPageFile   DWORD      ?     ;交换文件中空闲部分大小

  dwTotalVirtual    DWORD      ?     ;用户可用的地址空间

  dwAvailVirtual    DWORD      ?     ;当前空闲的地址空间

MEMORYSTATUS ENDS

在调用之前需要首先将dwLength字段设置为MEMORYSTATUS结构的长度,当调用GlobalMemoryStatus函数后,函数会在结构中返回对应的数值。注意:dwTotalPageFile字段返回的是交换文件的最大值,并不是当前实际建立的交换文件的大小,一般当前的交换文件大小会小于这个数值,但这个数值的大小也不是确定的,如果需要的话,系统会增加它的大小直到不再有空余的磁盘空间放置交换文件为止。

在所附光盘的Chapter10MemInfo目录中的MemInfo。asm文件利用这个功能定时获取并显示当前内存的使用信息,源代码如下:

                    。386

                    。model flat; stdcall

                    option casemap :none

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

; Include 文件定义

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

include         windows。inc

include         user32。inc

includelib      user32。lib

include         kernel32。inc

includelib      kernel32。lib

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

; Equ 等值定义

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

ICO_MAIN            equ     1000

DLG_MAIN            equ     100

IDC_INFO            equ         101

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

; 数据段

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》



 
来源:电子工业出版社 作者:罗云彬 上一页         回书目         下一页          
上一页         回书目         下一页          
  


第10章 内存管理和文件操作


10。1 内 存 管 理(2)

    
                。data?

hInstance       dd      ?

hWinMain         dd     ?

 

                 nst

szInfo           db     '物理内存总数     %lu 字节';0dh;0ah

                 db     '空闲物理内存     %lu 字节';0dh;0ah

                 db     '虚拟内存总数     %lu 字节';0dh;0ah

                 db     '空闲虚拟内存     %lu 字节';0dh;0ah

                 db     '已用内存比例     %d%%';0dh;0ah

                 db     '————————————————';0dh;0ah

                 db     '用户地址空间总数 %lu 字节';0dh;0ah

                 db     '用户可用地址空间 %lu 字节';0dh;0ah;0

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

; 代码段

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

 

                    de

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

_GetMemInfo     proc

                    local   @stMemInfo:MEMORYSTATUS

                    local   @szBuffer'1024':byte

 

                    mov     @stMemInfo。dwLength;sizeof @stMemInfo

                    invoke  GlobalMemoryStatus;addr @stMemInfo

                    invoke  wsprintf;addr @szBuffer;addr szInfo;

                            @stMemInfo。dwTotalPhys;@stMemInfo。dwAvailPhys;

                            @stMemInfo。dwTotalPageFile;

                            @stMemInfo。dwAvailPageFile;

                            @stMemInfo。dwMemoryLoad;

                            @stMemInfo。dwTotalVirtual;@stMemInfo。dwAvailVirtual

                    invoke  SetDlgItemText;hWinMain;IDC_INFO;addr @szBuffer

                    ret

 

_GetMemInfo     endp

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

_ProcDlgMain        proc        uses ebx edi esi hWnd;wMsg;wParam;lParam

 

                    mov     eax;wMsg

                    。if     eax   WM_TIMER

                            call        _GetMemInfo

                    。elseif eax   WM_CLOSE

                            invoke  KillTimer;hWnd;1

                            invoke  EndDialog;hWnd;NULL

;********************************************************************

                。elseif eax   WM_INITDIALOG

                        push        hWnd

                        pop     hWinMain

                        invoke  LoadIcon;hInstance;ICO_MAIN

                        invoke  SendMessage;hWnd;WM_SETICON;ICON_BIG;eax

                        invoke  SetTimer;hWnd;1;1000;NULL

                        call        _GetMemInfo

;********************************************************************

                。else

                        mov     eax;FALSE

                        ret

                。endif

                mov     eax;TRUE

                ret

 

_ProcDlgMain    endp

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

start:

                invoke  GetModuleHandle;NULL

                mov     hInstance;eax

                invoke  DialogBoxParam;hInstance;DLG_MAIN;NULL;

                        offset _ProcDlgMain;NULL

                invoke  ExitProcess;NULL

;》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

                end     start

MemInfo。rc文件如下:

 

//》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

#include            

//》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

#define ICO_MAIN                1000

#define DLG_MAIN                100

#define IDC_INFO                101

//》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

ICO_MAIN        ICON                〃Main。ico〃

//》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》》

DLG_MAIN DIALOG 188; 193; 140; 75

STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU

CAPTION 〃内存状态〃

FONT 9; 〃宋体〃



 LTEXT 〃〃; IDC_INFO; 6; 6; 135; 65

返回目录 上一页 下一页 回到顶部 2 2

你可能喜欢的