⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 7.2 效能监视.htm

📁 Windows2000后台服务程序开发手册
💻 HTM
📖 第 1 页 / 共 4 页
字号:
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>在WinLogon的位址空间里载x入一个效能DLL的分派比在应用程序的位址空间里载入DLL更为重要。如果DLL现在呼叫了ExitProcess函数,WinLogon将会终止执行,并会使整个作业系统当机。再次申明,测试效能DLL程序代码是相当重要的一件事。</FONT></P><A 
            style="LINE-HEIGHT: 25px" name=207003>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#3e70d7 
            size=5><B style="LINE-HEIGHT: 25px">收集效能资料<BR 
            style="LINE-HEIGHT: 25px"> </B></FONT></P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>系统监控程序透过建立对登录的呼叫来要求效能资讯。为了收集效能资讯,负责提出要求的应用程序必须先呼叫RegQueryValueEx,如下所示:</FONT></P>
            <DIV style="LINE-HEIGHT: 25px; BACKGROUND-COLOR: #d7d7d7"><FONT 
            style="LINE-HEIGHT: 25px" face=Arial size=3><PRE style="LINE-HEIGHT: 25px">// 用来询问效能资料的特殊登录机码 <BR>HKEY hkeyPerf = HKEY_PERFORMANCE_DATA; <BR>// 取得效能资料之缓冲区大小 <BR>DWORD cb = 10240; <BR>// 配置取得效能资料的缓冲区 <BR>PBYTE pbPerfData = (PBYTE)malloc(cb); <BR>// 要求提供本地机器上的所有(「Global」)效能资料 <BR>while (RegQueryValueEx(hkeyPerf, TEXT("Global"), 0, NULL, <BR> pbPerfData, &amp;cb) == ERROR_MORE_DATA){ <BR> // 缓冲区太小;使它变大并重试 <BR> cb += 1024; <BR> pbPerfData = (PBYTE)realloc(pbPerfData, cb); <BR>} <BR>// 缓冲区够大 <BR>// pbPerfData包含效能计数器资讯</PRE></FONT></DIV>
            <HR style="LINE-HEIGHT: 25px">

            <P><FONT style="LINE-HEIGHT: 25px" face=Arial color=#3e77d7 size=3 
            Black><B style="LINE-HEIGHT: 25px">说明</B></FONT> </P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>为了更清楚的说明,前面所列的程序代码中没有处理任何的错误检查。当您要在自己的应用程序中加入类似的程序代码时,请加入适当的错误检查机制。</FONT></P>
            <HR style="LINE-HEIGHT: 25px">

            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>若要重覆地要求效能资讯,只要再次呼叫RegQueryValueEx即可。RegQueryValueEx呼叫中的「Global」会告诉系统您想要回传系统中所有元件的效能资讯。这会是大量的资讯;如果您想要取得可用资讯的子集合,只要简单地将「Global」以一组物件数字取代即可(以空白分开)。例如,如果您想要取得System和Memory物件的效能资讯,可传递一个「2 
            4」的字串至RegQueryValuEx。您通常会传递物件数字给RegQueryValueEx,并且总是会回传与DLL符合的所有计数器和被指定之物件相关的实例资讯。</FONT></P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>如果有一个应用程序想从一个远端电脑要求效能资讯,它必须做的事情即是在进入先前所列示程序代码之while回圈前,呼叫RegConnectRegistry:</FONT></P>
            <DIV style="LINE-HEIGHT: 25px; BACKGROUND-COLOR: #d7d7d7"><FONT 
            style="LINE-HEIGHT: 25px" face=Arial size=3><PRE style="LINE-HEIGHT: 25px">RegConnectRegistry(TEXT("\\\\RemoteMachineName"),&nbsp;&nbsp;<BR> HKEY_PERFORMANCE_DATA, &amp;hkeyPerf);</PRE></FONT></DIV>
            <HR style="LINE-HEIGHT: 25px">

            <P><FONT style="LINE-HEIGHT: 25px" face=Arial color=#3e77d7 size=3 
            Black><B style="LINE-HEIGHT: 25px">说明</B></FONT> </P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>在预设的情形下,管理者和系统对系统的效能计数器资讯拥有完全的存取权,同时与它互动的使用者只被允许读取权限。被应用在下列登录机码的许可权决定了谁可以存取效能计数器资讯:</FONT></P>
            <DIV style="LINE-HEIGHT: 25px; BACKGROUND-COLOR: #d7d7d7"><FONT 
            style="LINE-HEIGHT: 25px" face=Arial size=3><PRE style="LINE-HEIGHT: 25px">HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Perflib</PRE></FONT></DIV>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>您可以使用RegEdt32.exe工具来改变许可权。</FONT></P>
            <HR style="LINE-HEIGHT: 25px">

            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>如果您不要再建立任何效能资讯的要求时,应该呼叫以下的程序代码关闭登录:</FONT></P>
            <DIV style="LINE-HEIGHT: 25px; BACKGROUND-COLOR: #d7d7d7"><FONT 
            style="LINE-HEIGHT: 25px" face=Arial size=3><PRE style="LINE-HEIGHT: 25px">RegCloseKey(hkeyPerf);</PRE></FONT></DIV>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>注意到即使您从来没有明确地呼叫RegOpenKeyEx来开启此机码,仍然应该建立此呼叫。</FONT></P>
            <HR style="LINE-HEIGHT: 25px">

            <P><FONT style="LINE-HEIGHT: 25px" face=Arial color=#3e77d7 size=3 
            Black><B style="LINE-HEIGHT: 25px">说明</B></FONT> </P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>不要在每次呼叫RegQueryValueEx后关闭机码—这个动作将会严重地损坏您的应用程序之执行效能。当一个例如系统监控程序元件呼叫RegQueryValueEx以要求效能资讯时,系统会查看目的机器的HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services子机码,并且为每一个包含Performance子机码的项目载入特定的DLL。如果这是DLL第一次被载入,DLL的Open函数会被呼叫。当RegCloseKey被呼叫后,系统会呼叫每一个DLL的Close函数并从处理程序的位址空间载出该DLL。只有在您的应用程序终止时呼叫RegCloseKey才能改善执行效能。</FONT></P>
            <HR style="LINE-HEIGHT: 25px">

            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>一旦被载入且初始化后,系统会呼叫每一个DLL的Collect函数。这是为了给DLL一个用它的效能资讯载入这个内存缓冲区的机会。Collect函数看起来应该像这样:</FONT></P>
            <DIV style="LINE-HEIGHT: 25px; BACKGROUND-COLOR: #d7d7d7"><FONT 
            style="LINE-HEIGHT: 25px" face=Arial size=3><PRE style="LINE-HEIGHT: 25px">DWORD __declspec(dllexport)WINAPI Collect(PWSTR pszValueName,&nbsp;&nbsp;<BR> PVOID* ppvData, PDWORD pcbTotalBytes, PDWORD pdwNumObjectTypes){ <BR> // 收集效能资料 <BR> return(ERROR_SUCCESS);&nbsp;&nbsp; // or ERROR_MORE_DATA if buffer too small <BR>}</PRE></FONT></DIV>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>第一个参数pszValueName是一个值与传递到RegQueryValueEx相同的Unicode字串。如果此字串为「Global」,那么Collect函数就必须回传它负责的所有效能资讯。如果该字串包含了一组以空白分开的数字,则DLL必须决定提供哪一个有关被要求之物件资讯,并且只回传与它相关的资讯。</FONT></P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>ppvData参数是一个指向内存位址的指标。在输入至Collect函数中,*ppvData会指向DLL应该写入资讯之内存缓冲区。从Collect回传前,*ppvData应该被更新,以使它指向紧接在被放置至缓冲区之新资料后面的内存位址。下一个效能DLL将会从这个新的位址开始附加它的资料。</FONT></P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>pcbTotalBytes参数是指向一个DWORD的指标,指示缓冲区的大小。在输入至Collect时,*pcbTotalBytes指示为了您的DLL而新增至缓冲区之可用资讯的位元组大小。在DLL附加它的资料至缓冲区后,Collect必须设定*pcbTotalBytes为所有被加至缓冲区之位元组总数。当Collect返回时,系统将会以剩下的缓冲区大小减去此值并传递这个新的数字至下个效能DLL。</FONT></P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>pdwNumObjectTypes参数也是指向一个DWORD的指标,但是这个DWORD表示没有任何值被输入至Collect函数。一个单一的Collect函数可以为许多物件回传效能资讯。在Collect返回前,*pdwNumObjectTypes应该被设定为被加至资料缓冲区之效能资讯物件的数字。</FONT></P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>例如,如果Collect函数被呼叫且pszValueName参数没有指示任何DLL负责的物件,Collect函数应该不要改变*ppvData的内容、设定*pcbTotalBytes和*pdwNumObjectTypes为0,并回传ERROR_SUCCESS。</FONT></P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>如果Collect函数为您需要回传的资料决定了太小的资料缓冲区,那么您应该让*ppvData保持不变、设定*pcbTotalBytes和*pdwNumObjectTypes为0,并且回传ERROR_MORE_DATA。</FONT></P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>如果Collect函数成功地将资讯附加至缓冲区,它会将新增的位元组数字附加至*ppvData、设定*pcbTotalBytes为被附加之位元组数字、*pdwNumObjectTypes则设定为被附加至物件的数字,并且回传ERROR_SUCCESS。</FONT></P></A><A 
            style="LINE-HEIGHT: 25px" name=207004>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#3e70d7 
            size=5><B style="LINE-HEIGHT: 25px">效能资讯之资料结构<BR 
            style="LINE-HEIGHT: 25px"> </B></FONT></P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>在这个重点上,我们没有涵盖到的唯一项目即是Collect函数必须放置在呼叫者的资料区块里之效能资讯的格式。可惜的是,资料区块含有一套不同的资料架构,它的长度是可变的,充其量只是使这个资料缓冲区的内容建构更困难而已。图7-9显示了如何为一个物件安排效能资讯的内容。</FONT></P>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>这个特定的物件没有支援实例,但是支援了二个计数器。这意味着有叁个字串项目为了这个物件而存在登录中:一个确认物件名称且被指定其值为2938的字串;二个确定计数器名称并被指定其值为2940以和2942的其他字串。这叁个项目的Help字串分别为2939、2941以及2943。</FONT></P>
            <P><BR style="LINE-HEIGHT: 25px"> </P>
            <CENTER style="LINE-HEIGHT: 25px">
            <P><INPUT id=9 style="LINE-HEIGHT: 25px" type=image height=525 
            width=738 src="7.2 效能监视.files/7-9.gif" border=0 
            &#111nclick="imgclick"></P></CENTER>
            <CENTER style="LINE-HEIGHT: 25px">
            <TABLE style="LINE-HEIGHT: 25px" border=0>
              <TBODY style="LINE-HEIGHT: 25px">
              <TR style="LINE-HEIGHT: 25px">
                <TD style="LINE-HEIGHT: 25px" align=middle><FONT 
                  style="LINE-HEIGHT: 25px" face=arial color=#000000 
                  size=2><FONT style="LINE-HEIGHT: 25px" face=arial 
                  color=#3e80d7 size=2><B 
                  style="LINE-HEIGHT: 25px">&nbsp;图7-9&nbsp;</B></FONT>描述一个不支援实例之效能物件的资料缓冲区</FONT></TD></TR></TBODY></TABLE></CENTER>
            <P><FONT style="LINE-HEIGHT: 25px" face=arial color=#000000 
            size=2>为了回报此物件的效能资讯,被传递到我们的Collect函数之资料区块首先必须有一个被放置在里面的PERF_OBJECT_TYPE结构。由于《Platform 
            SDK》文件提供了此结构成员的细节部份,我将在表7-1中描述它们。</FONT></P></A><A 
            style="LINE-HEIGHT: 25px" name=320-1>
            <CENTER style="LINE-HEIGHT: 25px">
            <TABLE style="LINE-HEIGHT: 25px" border=0>
              <TBODY style="LINE-HEIGHT: 25px">
              <TR style="LINE-HEIGHT: 25px">
                <TD style="LINE-HEIGHT: 25px" align=middle><FONT 
                  style="LINE-HEIGHT: 25px" face=arial color=#000000 
                  size=2><FONT style="LINE-HEIGHT: 25px" face=arial 
                  color=#3e80d7 size=2><B 
                  style="LINE-HEIGHT: 25px">&nbsp;表7-1&nbsp;</B></FONT>PERF_OBJECT_TYPE结构的成员</FONT></TD></TR></TBODY></TABLE></CENTER>
            <CENTER style="LINE-HEIGHT: 25px">
            <TABLE style="LINE-HEIGHT: 25px" border=1>
              <TBODY style="LINE-HEIGHT: 25px">
              <TR style="LINE-HEIGHT: 25px">
                <TH style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>成员</FONT> </TH>
                <TH style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>说明</FONT></TH></TR>
              <TR style="LINE-HEIGHT: 25px">
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>TotalByteLength DefinitionLength HeaderLength</FONT></TD>
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>指示位元组大小。这些值必须被初始化。以正确地使一个像系统监视器的工具可以适当地在资料结构中流动。</FONT></TD></TR>
              <TR style="LINE-HEIGHT: 25px">
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>ObjectNameTitleIndex ObjectHelpTitleIndex</FONT></TD>
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>指示被指定至物件文字的数字以及当它们被加至登录时的Help内容。</FONT></TD></TR>
              <TR style="LINE-HEIGHT: 25px">
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>ObjectNameTitle ObjectHelpTitle</FONT></TD>
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>应该永远被设定为NULL,因为这些成员只有在应用程序要求资料时才会被使用。</FONT></TD></TR>
              <TR style="LINE-HEIGHT: 25px">
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>DetailLevel</FONT></TD>
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>指示此物件对大部份使用者来说有多「难以理解」。大部份的物件对初学者来说是可理解的。然而您可以指定您的物件可被初学者、进阶使用者、专家或高阶使用者所理解。</FONT></TD></TR>
              <TR style="LINE-HEIGHT: 25px">
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>NumCounters</FONT></TD>
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>指示物件提供了多少计数器。如图7-9所示,物件提供了二个计数器,因此有二个PERF_COUNTER_DEFINITION结构会紧接着此PERF_OBJECT_TYPE结构(我将会尽快讨论PERF_COUNTER_DEFINITION结构的内容)。</FONT></TD></TR>
              <TR style="LINE-HEIGHT: 25px">
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>DefaultCounter</FONT></TD>
                <TD style="LINE-HEIGHT: 25px"><FONT style="LINE-HEIGHT: 25px" 
                  size=2>当一个物件被选择时,此成员会指在预设计数器清单方块中的哪一个计数器应该被选择。系统监视器控制监控程序的新增计数器对话方块使用此成员。</FONT></TD></TR>

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -